/*
 *   Licensed to the Apache Software Foundation (ASF) under one
 *   or more contributor license agreements.  See the NOTICE file
 *   distributed with this work for additional information
 *   regarding copyright ownership.  The ASF licenses this file
 *   to you under the Apache License, Version 2.0 (the
 *   "License"); you may not use this file except in compliance
 *   with the License.  You may obtain a copy of the License at
 *
 *     https://www.apache.org/licenses/LICENSE-2.0
 *
 *   Unless required by applicable law or agreed to in writing,
 *   software distributed under the License is distributed on an
 *   "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 *   KIND, either express or implied.  See the License for the
 *   specific language governing permissions and limitations
 *   under the License.
 *
 */
package org.apache.directory.fortress.core.impl;


import java.util.ArrayList;
import java.util.Collection;
import java.util.List;
import java.util.Set;

import junit.framework.Test;
import junit.framework.TestCase;
import junit.framework.TestSuite;

import org.apache.commons.lang3.StringUtils;
import org.apache.directory.fortress.core.model.Permission;
import org.apache.directory.fortress.core.model.SDSet;
import org.apache.directory.fortress.core.model.Session;
import org.apache.directory.fortress.core.model.User;
import org.apache.directory.fortress.core.model.UserRole;
import org.apache.directory.fortress.core.model.RoleConstraint;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import org.apache.directory.fortress.core.AccessMgr;
import org.apache.directory.fortress.core.AccessMgrFactory;
import org.apache.directory.fortress.core.AdminMgr;
import org.apache.directory.fortress.core.AdminMgrFactory;
import org.apache.directory.fortress.core.GlobalErrIds;
import org.apache.directory.fortress.core.PwPolicyMgr;
import org.apache.directory.fortress.core.SecurityException;
import org.apache.directory.fortress.core.util.LogUtil;


/**
 * AccessMgrImpl Tester.
 *
 * @author <a href="mailto:dev@directory.apache.org">Apache Directory Project</a>
 */
public class AccessMgrImplTest extends TestCase
{
    private static final String CLS_NM = AccessMgrImplTest.class.getName();
    private static final Logger LOG = LoggerFactory.getLogger( CLS_NM );


    public static Test suite()
    {
        TestSuite suite = new TestSuite();
        //suite.addTest(new AccessMgrImplTest("testDropActiveRole"));
/*
        suite.addTest( new AdminMgrImplTest( "testResetPassword" ) );
        suite.addTest( new AccessMgrImplTest( "testAuthenticateReset" ) );
        suite.addTest( new AdminMgrImplTest( "testChangePassword" ) );
        suite.addTest( new AccessMgrImplTest( "testAuthenticate" ) );
        suite.addTest( new AdminMgrImplTest( "testLockUserAccount" ) );
        suite.addTest( new AccessMgrImplTest( "testAuthenticateLocked" ) );
        suite.addTest( new AdminMgrImplTest( "testUnlockUserAccount" ) );
        suite.addTest( new AccessMgrImplTest( "testCheckAccess" ) );
*/
        suite.addTest( new AccessMgrImplTest( "testAbacConstraintsRole" ) );

        return suite;
    }


    public AccessMgrImplTest( String name )
    {
        super( name );
    }


    public void setUp() throws Exception
    {
        super.setUp();
    }


    public void tearDown() throws Exception
    {
        super.tearDown();
    }


    public void testGetSession() throws Exception
    {
        //TODO: Test goes here...
        
    }


    public void testGetToken() throws Exception
    {
        //TODO: Test goes here...
    }


    public void testGetUserId()
    {
        // public String getUserId(Session, session)
        getUsers( "GET-USRIDS TU1_UPD", UserTestData.USERS_TU1_UPD );
        getUsers( "GET-USRIDS TU3", UserTestData.USERS_TU3 );
        getUsers( "GET-USRIDS TU4", UserTestData.USERS_TU4 );
    }


    /**
     * @param msg
     * @param uArray
     */
    public static void getUserIds( String msg, String[][] uArray )
    {
        LogUtil.logIt( msg );
        try
        {
            AccessMgr accessMgr = AccessMgrFactory.createInstance( TestUtils.getContext() );
            for ( String[] usr : uArray )
            {
                User user = UserTestData.getUser( usr );
                Session session = accessMgr.authenticate( user.getUserId(), user.getPassword() );
                assertNotNull( session );
                String userId = accessMgr.getUserId( session );
                assertTrue( "getUserIds failed compare found userId [" + userId + "] valid userId ["
                    + UserTestData.getUserId( usr ) + "]", userId.equalsIgnoreCase( UserTestData.getUserId( usr ) ) );
            }
            LOG.debug( "getUserIds successful" );
        }
        catch ( SecurityException ex )
        {
            LOG.error(
                "getUserIds: failed with SecurityException rc=" + ex.getErrorId() + ", msg="
                    + ex.getMessage(), ex );
            fail( ex.getMessage() );
        }
    }


    public void testGetUser()
    {
        // public User getUser(Session, session)
        getUsers( "GET-USRS TU1_UPD", UserTestData.USERS_TU1_UPD );
        getUsers( "GET-USRS TU3", UserTestData.USERS_TU3 );
        getUsers( "GET-USRS TU4", UserTestData.USERS_TU4 );
    }


    /**
     * @param msg
     * @param uArray
     */
    public static void getUsers( String msg, String[][] uArray )
    {
        LogUtil.logIt( msg );
        try
        {
            AccessMgr accessMgr = AccessMgrFactory.createInstance( TestUtils.getContext() );
            for ( String[] usr : uArray )
            {
                User user = UserTestData.getUser( usr );
                Session session = accessMgr.createSession( user, false );
                assertNotNull( session );
                user = accessMgr.getUser( session );
                UserTestData.assertEquals( user, usr );
            }
            LOG.debug( "getUsers successful" );
        }
        catch ( SecurityException ex )
        {
            LOG.error(
                "getUsers: failed with SecurityException rc=" + ex.getErrorId() + ", msg=" + ex.getMessage(),
                ex );
            fail( ex.getMessage() );
        }
    }


    public void testAuthenticate()
    {
        // public Session authenticate(String userId, String password)
        authenticateUsers( "AUTH-USRS TU1_UPD", UserTestData.USERS_TU1_UPD, 1 );
        authenticateUsers( "AUTH-USRS TU2_CHG", UserTestData.USERS_TU2_CHG, 1 );
        authenticateUsers( "AUTH-USRS TU3", UserTestData.USERS_TU3, 1 );
        authenticateUsers( "AUTH-USRS TU4", UserTestData.USERS_TU4, 1 );
    }


    /**
     * @param msg
     * @param uArray
     * @param multiplier
     */
    private static void authenticateUsers( String msg, String[][] uArray, int multiplier )
    {
        LogUtil.logIt( msg );
        try
        {
            AccessMgr accessMgr = AccessMgrFactory.createInstance( TestUtils.getContext() );
            for ( String[] usr : uArray )
            {
                User user = UserTestData.getUser( usr );
                Session session = accessMgr.authenticate( user.getUserId(), user.getPassword() );
                assertNotNull( session );
                // todo: need to test to ensure roles are not added to session.
                // now try negative test case:
                try
                {
                    accessMgr.authenticate( user.getUserId(), "wrongpw" );
                    fail( "authenticateUsers failed negative test" );
                }
                catch ( SecurityException se )
                {
                    assertTrue( "authenticateUsers reset excep id check",
                        se.getErrorId() == GlobalErrIds.USER_PW_INVLD );
                    // pass
                }
            }
            LOG.debug( "authenticateUsers successful" );
        }
        catch ( SecurityException ex )
        {
            LOG.error( "authenticateUsers: failed with SecurityException rc=" + ex.getErrorId() + ", msg="
                + ex.getMessage(), ex );
            fail( ex.getMessage() );
        }
    }


    /**
     *
     */
    public void testAuthenticateLocked()
    {
        // public Session authenticate(String userId, String password)
        authenticateLockedUsers( "AUTH-L-USRS TU1_UPD", UserTestData.USERS_TU1_UPD );
        authenticateLockedUsers( "AUTH-L-USRS TU3", UserTestData.USERS_TU3 );
        authenticateLockedUsers( "AUTH-L-USRS TU4", UserTestData.USERS_TU4 );
    }


    /**
     * @param msg
     * @param uArray
     */
    private static void authenticateLockedUsers( String msg, String[][] uArray )
    {
        LogUtil.logIt( msg );
        try
        {
            AccessMgr accessMgr = AccessMgrFactory.createInstance( TestUtils.getContext() );
            for ( String[] usr : uArray )
            {
                User user = UserTestData.getUser( usr );
                // now try negative test case:
                try
                {
                    accessMgr.authenticate( user.getUserId(), user.getPassword() );
                    fail( CLS_NM + ".authenticateLockedUsers failed test" );
                }
                catch ( SecurityException se )
                {
                    assertTrue( CLS_NM + "authenticateLockedUsers reset excep id check",
                        se.getErrorId() == GlobalErrIds.USER_PW_LOCKED );
                    // pass
                    //LOG.error("locked=" + se.getMsgid() + " msg=" + se.getMessage());
                }
            }
            LOG.debug( "authenticateLockedUsers successful" );
        }
        catch ( SecurityException ex )
        {
            LOG.error( "authenticateLockedUsers: failed with SecurityException rc=" + ex.getErrorId()
                + ", msg=" + ex.getMessage(), ex );
            fail( ex.getMessage() );
        }
    }


    /**
     *
     */
    public void testAuthenticateReset()
    {
        // public Session authenticate(String userId, String password)
        authenticateResetUsers( "AUTH-R-USRS TU2_RST", UserTestData.USERS_TU2_RST, PolicyTestData.POLICIES_TP2[0] );
    }


    /**
     * @param msg
     * @param uArray
     */
    private static void authenticateResetUsers( String msg, String[][] uArray, String[] plcy )
    {
        LogUtil.logIt( msg );
        try
        {
            AccessMgr accessMgr = AccessMgrFactory.createInstance( TestUtils.getContext() );
            PwPolicyMgr policyMgr = PswdPolicyMgrImplTest.getManagedPswdMgr();
            for ( String[] usr : uArray )
            {
                User user = UserTestData.getUser( usr );
                // update this user with pw policy that requires change after reset:
                policyMgr.updateUserPolicy( user.getUserId(), PolicyTestData.getName( plcy ) );
                // now try negative test case:
                try
                {
                    accessMgr.authenticate( user.getUserId(), user.getPassword() );
                    //accessMgr.authenticate( user.getUserId(), user.getPassword() );
                    fail( CLS_NM + ".authenticateResetUsers failed test" );
                }
                catch ( SecurityException se )
                {
                    assertTrue( CLS_NM + "authenticateResetUsers reset excep id check",
                        se.getErrorId() == GlobalErrIds.USER_PW_RESET );
                    // pass
                }
            }
            LOG.debug( "authenticateResetUsers successful" );
        }
        catch ( SecurityException ex )
        {
            LOG.error( "authenticateResetUsers: failed with SecurityException rc=" + ex.getErrorId()
                + ", msg=" + ex.getMessage(), ex );
            fail( ex.getMessage() );
        }
    }


    /**
     *
     */
    public void testCreateSession()
    {
        // public Session createSession(User user, boolean isTrusted)
        try
        {
            // Instantiate the AdminMgr first
            AdminMgr adminMgr = AdminMgrFactory.createInstance();
            
            User myUser = new User( "myUserId", "myPassword", "People" );
            adminMgr.addUser( myUser );
        }
        catch (SecurityException ex)
        {
         // log or throw
        }
        
        
        createSessions( "CREATE-SESS TU1_UPD TR1", UserTestData.USERS_TU1_UPD, RoleTestData.ROLES_TR1 );
        createSessions( "CREATE-SESS TU3 TR3", UserTestData.USERS_TU3, RoleTestData.ROLES_TR3 );
        createSessions( "CREATE-SESS TU4 TR2", UserTestData.USERS_TU4, RoleTestData.ROLES_TR2 );
    }


    /**
     * @param msg
     * @param uArray
     * @param rArray
     */
    public static void createSessions( String msg, String[][] uArray, String[][] rArray )
    {
        LogUtil.logIt( msg );
        try
        {
            AccessMgr accessMgr = AccessMgrFactory.createInstance( TestUtils.getContext() );
            for ( String[] usr : uArray )
            {
                User user = UserTestData.getUser( usr );
                Session session = accessMgr.createSession( user, false );
                assertNotNull( session );
                String userId = accessMgr.getUserId( session );
                assertTrue( CLS_NM + ".createSessions failed compare found userId [" + userId + "] valid userId ["
                    + UserTestData.getUserId( usr ) + "]", userId.equalsIgnoreCase( UserTestData.getUserId( usr ) ) );
                UserTestData.assertEquals( user, usr );
                List<UserRole> uRoles = session.getRoles();
                assertNotNull( uRoles );
                assertEquals( CLS_NM + ".createSessions user role check failed list size user [" + user.getUserId()
                    + "]", rArray.length, uRoles.size() );
                for ( String[] rle : rArray )
                {
                    assertTrue( CLS_NM + ".createSessions failed role search USER [" + user.getUserId() + "] ROLE1 ["
                        + RoleTestData.getName( rle ) + "] should be present",
                        uRoles.contains( RoleTestData.getUserRole( UserTestData.getUserId( usr ), rle ) ) );
                }

                // now try negative test case:
                try
                {
                    User userBad = new User( user.getUserId(), "badpw" );
                    accessMgr.createSession( userBad, false );
                    fail( CLS_NM + ".createSessions failed negative test" );
                }
                catch ( SecurityException se )
                {
                    assertTrue( CLS_NM + "createSessions excep id check", se.getErrorId() == GlobalErrIds.USER_PW_INVLD );
                    // pass
                }
            }
            LOG.debug( "createSessions successful" );
        }
        catch ( SecurityException ex )
        {
            LOG.error(
                "createSessions: failed with SecurityException rc=" + ex.getErrorId() + ", msg="
                    + ex.getMessage(), ex );
            fail( ex.getMessage() );
        }
    }


    /**
     *
     */
    public void testCreateSessionWithRole()
    {
        // public Session createSession(User user, boolean isTrusted)
        createSessionsWithRoles( "CR-SESS-WRLS TU1_UPD TR1", UserTestData.USERS_TU1_UPD, RoleTestData.ROLES_TR1 );
        createSessionsWithRoles( "CR-SESS-WRLS TU3 TR3", UserTestData.USERS_TU3, RoleTestData.ROLES_TR3 );
        createSessionsWithRoles( "CR-SESS-WRLS TU4 TR2", UserTestData.USERS_TU4, RoleTestData.ROLES_TR2 );
    }


    /**
     * @param msg
     * @param uArray
     * @param rArray
     */
    public static void createSessionsWithRoles( String msg, String[][] uArray, String[][] rArray )
    {
        LogUtil.logIt( msg );
        try
        {
            AccessMgr accessMgr = AccessMgrFactory.createInstance( TestUtils.getContext() );
            for ( String[] usr : uArray )
            {
                User user = UserTestData.getUser( usr );
                List<UserRole> rlsRequested = new ArrayList<>();
                int cnt = 0;
                for ( String[] rle : rArray )
                {
                    rlsRequested.add( RoleTestData.getUserRole( user.getUserId(), rle ) );
                    user.setRoles( rlsRequested );
                    Session session = accessMgr.createSession( user, false );
                    assertTrue( CLS_NM + ".createSessionsWithRoles failed role search USER [" + user.getUserId()
                        + "] CNT [" + ++cnt + "] size [" + session.getRoles().size() + "]", cnt == session.getRoles()
                        .size() );
                    String userId = accessMgr.getUserId( session );
                    assertTrue( CLS_NM + ".createSessionsWithRoles failed compare found userId [" + userId
                        + "] valid userId [" + UserTestData.getUserId( usr ) + "]",
                        userId.equalsIgnoreCase( UserTestData.getUserId( usr ) ) );
                    UserTestData.assertEquals( user, usr );
                }
            }
            LOG.debug( "createSessionsWithRoles successful" );
        }
        catch ( SecurityException ex )
        {
            LOG.error( "createSessionsWithRoles: failed with SecurityException rc=" + ex.getErrorId()
                + ", msg=" + ex.getMessage(), ex );
            fail( ex.getMessage() );
        }
    }


    /**
     *
     */
    public void testCreateSessionWithRolesTrusted()
    {
        // public Session createSession(User user, boolean isTrusted)
        createSessionsWithRolesTrusted( "CR-SESS-WRLS-TRST TU1_UPD TR1", UserTestData.USERS_TU1_UPD,
            RoleTestData.ROLES_TR1 );
        createSessionsWithRolesTrusted( "CR-SESS-WRLS-TRST TU3 TR3", UserTestData.USERS_TU3, RoleTestData.ROLES_TR3 );
        createSessionsWithRolesTrusted( "CR-SESS-WRLS-TRST TU4 TR2", UserTestData.USERS_TU4, RoleTestData.ROLES_TR2 );
    }


    /**
     * @param msg
     * @param uArray
     * @param rArray
     */
    public static void createSessionsWithRolesTrusted( String msg, String[][] uArray, String[][] rArray )
    {
        LogUtil.logIt( msg );
        
        try
        {
            AccessMgr accessMgr = AccessMgrFactory.createInstance( TestUtils.getContext() );
            
            for ( String[] usr : uArray )
            {
                User user = UserTestData.getUser( usr );
                List<UserRole> rlsRequested = new ArrayList<>();
                int cnt = 0;
                for ( String[] rle : rArray )
                {
                    rlsRequested.add( RoleTestData.getUserRole( user.getUserId(), rle ) );
                    user.setRoles( rlsRequested );
                    Session session = accessMgr.createSession( user, true );
                    assertTrue( CLS_NM + ".createSessionsWithRolesTrusted failed role search USER [" + user.getUserId()
                        + "] CNT [" + ++cnt + "] size [" + session.getRoles().size() + "]", cnt == session.getRoles()
                        .size() );
                    String userId = accessMgr.getUserId( session );
                    assertTrue( CLS_NM + ".createSessionsWithRolesTrusted failed compare found userId [" + userId
                        + "] valid userId [" + UserTestData.getUserId( usr ) + "]",
                        userId.equalsIgnoreCase( UserTestData.getUserId( usr ) ) );
                    UserTestData.assertEquals( user, usr );
                }
            }
            LOG.debug( "createSessionsWithRolesTrusted successful" );
        }
        catch ( SecurityException ex )
        {
            LOG.error( "createSessionsWithRolesTrusted: failed with SecurityException rc=" + ex.getErrorId()
                + ", msg=" + ex.getMessage(), ex );
            fail( ex.getMessage() );
        }
    }


    /**
     *
     */
    public void testCreateSessionTrusted()
    {
        // public Session createSession(User user, boolean isTrusted)
        createSessionsTrusted( "CR-SESS-TRST TU1_UPD TR1", UserTestData.USERS_TU1_UPD, RoleTestData.ROLES_TR1 );
        createSessionsTrusted( "CR-SESS-TRST TU3 TR3", UserTestData.USERS_TU3, RoleTestData.ROLES_TR3 );
        createSessionsTrusted( "CR-SESS-TRST TU4 TR2", UserTestData.USERS_TU4, RoleTestData.ROLES_TR2 );
    }


    /**
     * @param msg
     * @param uArray
     * @param rArray
     */
    public static void createSessionsTrusted( String msg, String[][] uArray, String[][] rArray )
    {
        LogUtil.logIt( msg );
        try
        {
            AccessMgr accessMgr = AccessMgrFactory.createInstance( TestUtils.getContext() );
            for ( String[] usr : uArray )
            {
                User user = UserTestData.getUser( usr );
                Session session = accessMgr.createSession( user, true );
                assertNotNull( session );
                String userId = accessMgr.getUserId( session );
                assertTrue( CLS_NM + ".createSessionsTrusted failed compare found userId [" + userId
                    + "] valid userId [" + UserTestData.getUserId( usr ) + "]",
                    userId.equalsIgnoreCase( UserTestData.getUserId( usr ) ) );
                UserTestData.assertEquals( user, usr );
                List<UserRole> uRoles = session.getRoles();
                assertNotNull( uRoles );
                assertEquals(
                    CLS_NM + ".createSessionsTrusted user role check failed list size user [" + user.getUserId() + "]",
                    rArray.length, uRoles.size() );
                for ( String[] rle : rArray )
                {
                    assertTrue( CLS_NM + ".createSessionsTrusted failed role search USER [" + user.getUserId()
                        + "] ROLE1 [" + RoleTestData.getName( rle ) + "] should be present",
                        uRoles.contains( RoleTestData.getUserRole( UserTestData.getUserId( usr ), rle ) ) );
                }

                // now try negative test case:
                try
                {
                    User badUser = new User( user.getUserId() + "wrong" );
                    accessMgr.createSession( badUser, true );
                    fail( CLS_NM + ".createSessionsTrusted failed negative test" );
                }
                catch ( SecurityException se )
                {
                    assertTrue( CLS_NM + "createSessionsTrusted excep id check",
                        se.getErrorId() == GlobalErrIds.USER_NOT_FOUND );
                    // pass
                }
            }
            LOG.debug( "createSessionsTrusted successful" );
        }
        catch ( SecurityException ex )
        {
            LOG.error( "createSessionsTrusted: failed with SecurityException rc=" + ex.getErrorId()
                + ", msg=" + ex.getMessage(), ex );
            fail( ex.getMessage() );
        }
    }


    public void createSessionsDSD()
    {
        // public Session createSession(User user, boolean isTrusted)
        createSessionsDSD( "CR-SESS-DSD TU12 DSD_T1", UserTestData.USERS_TU12_DSD, RoleTestData.DSD_T1 );
        createSessionsDSD( "CR-SESS-DSD TU13 DSD_T4_B", UserTestData.USERS_TU13_DSD_HIER, RoleTestData.DSD_T4_B );
        createSessionsDSD( "CR-SESS-DSD TU14 DSD_T5_B", UserTestData.USERS_TU14_DSD_HIER, RoleTestData.DSD_T5_B );
        createSessionsDSD( "CR-SESS-DSD TU15 DSD_T6_C", UserTestData.USERS_TU15_DSD_HIER, RoleTestData.DSD_T6_C );
        createSessionsDSD( "CR-SESS-DSD TU21 DSD_T8_BRUNO", UserTestData.USERS_TU21_DSD_BRUNO,
            RoleTestData.DSD_T8_BRUNO );
    }


    /**
     *
     * @param msg
     * @param uArray
     * @param dsdArray
     */
    public static void createSessionsDSD( String msg, String[][] uArray, String[][] dsdArray )
    {
        LogUtil.logIt( msg );
        try
        {
            AccessMgr accessMgr = AccessMgrFactory.createInstance( TestUtils.getContext() );
            int i = 0;
            for ( String[] usr : uArray )
            {
                SDSet dsd = RoleTestData.getSDSet( dsdArray[i++] );
                User user = UserTestData.getUser( usr );
                Session session = accessMgr.createSession( user, false );
                assertNotNull( session );
                String userId = accessMgr.getUserId( session );
                assertTrue( CLS_NM + ".createSessionsDSD failed compare found userId [" + userId + "] valid userId ["
                    + UserTestData.getUserId( usr ) + "]", userId.equalsIgnoreCase( UserTestData.getUserId( usr ) ) );
                UserTestData.assertEquals( user, usr );
                List<UserRole> uRoles = session.getRoles();
                assertNotNull( uRoles );
                // was the number of members in test DSD greater than the cardinality?
                if ( dsd.getMembers().size() < dsd.getCardinality() )
                {
                    assertEquals(
                        CLS_NM + ".createSessionsDSD role list size check failed user-role user [" + user.getUserId()
                            + "]", dsd.getMembers().size(), uRoles.size() );
                }
                else
                {
                    assertEquals(
                        CLS_NM + ".createSessionsDSD role cardinality check failed user-role list size user ["
                            + user.getUserId() + "] dsd set [" + dsd.getName() + "] card [" + dsd.getCardinality()
                            + "] listsize [" + uRoles.size() + "]", dsd.getCardinality() - 1, uRoles.size() );
                }
            }
            LOG.debug( "createSessionsDSD successful" );
        }
        catch ( SecurityException ex )
        {
            LOG.error( "createSessionsDSD: failed with SecurityException rc=" + ex.getErrorId() + ", msg="
                + ex.getMessage(), ex );
            fail( ex.getMessage() );
        }
    }


    /**
     *
     */
    public void testCreateSessionHier()
    {
        // public Session createSession(User user, boolean isTrusted)
        createSessionsHier( "CREATE-SESS-HIER TU18 TR6 DESC", UserTestData.USERS_TU18U_TR6_DESC );
        createSessionsHier( "CREATE-SESS-HIER TU19U TR7 ASC", UserTestData.USERS_TU19U_TR7_ASC );
    }


    /**
     *
     * @param msg
     * @param uArray
     */
    public static void createSessionsHier( String msg, String[][] uArray )
    {
        LogUtil.logIt( msg );
        try
        {
            AccessMgr accessMgr = AccessMgrFactory.createInstance( TestUtils.getContext() );
            for ( String[] usr : uArray )
            {
                User user = UserTestData.getUser( usr );
                Session session = accessMgr.createSession( user, false );
                assertNotNull( session );
                String userId = accessMgr.getUserId( session );
                assertTrue( CLS_NM + ".createSessionsHier failed compare found userId [" + userId + "] valid userId ["
                    + UserTestData.getUserId( usr ) + "]", userId.equalsIgnoreCase( UserTestData.getUserId( usr ) ) );
                UserTestData.assertEquals( user, usr );

                // Get the authorized roles for this user:
                Collection<String> authZRoles = UserTestData.getAuthorizedRoles( usr );

                // If there are any assigned roles, add them to list of authorized.
                Set<String> asgnRoles = UserTestData.getAssignedRoles( usr );
                assertNotNull( asgnRoles );
                assertTrue( asgnRoles.size() > 0 );

                for ( String asgnRole : asgnRoles )
                {
                    authZRoles.add( asgnRole );
                }

                Set<String> actualRoles = accessMgr.authorizedRoles( session );
                assertNotNull( actualRoles );
                assertEquals(
                    CLS_NM + ".createSessionsHier authorized roles list size test case failed for [" + user.getUserId()
                        + "]", authZRoles.size(), actualRoles.size() );
                for ( String name : authZRoles )
                {
                    assertTrue( CLS_NM + ".createSessionsHier authorized roles compare test case failed for USER ["
                        + user.getUserId() + "] expect role [" + name + "] nout found", actualRoles.contains( name ) );
                }
            }
            LOG.debug( "createSessionsHier successful" );
        }
        catch ( SecurityException ex )
        {
            LOG.error( "createSessionsHier: failed with SecurityException rc=" + ex.getErrorId() + ", msg="
                + ex.getMessage(), ex );
            fail( ex.getMessage() );
        }
    }


    /**
     *
     */
    public void testCheckAccess()
    {
        // public boolean checkAccess(String object, String operation, Session session)
        checkAccess( "CHCK-ACS TU1_UPD TO1 TOP1 ", UserTestData.USERS_TU1_UPD, PermTestData.OBJS_TOB1,
            PermTestData.OPS_TOP1, PermTestData.OBJS_TOB3, PermTestData.OPS_TOP3 );
        checkAccess( "CHCK-ACS TU3 TO3 TOP1 ", UserTestData.USERS_TU3, PermTestData.OBJS_TOB3, PermTestData.OPS_TOP3,
            PermTestData.OBJS_TOB2, PermTestData.OPS_TOP2 );
        checkAccess( "CHCK-ACS TU4 TO4 TOP1 ", UserTestData.USERS_TU4, PermTestData.OBJS_TOB2, PermTestData.OPS_TOP2,
            PermTestData.OBJS_TOB3, PermTestData.OPS_TOP3 );
    }


    public static void checkAccess( String msg, String[][] uArray, String[][] oArray, String[][] opArray,
        String[][] oArrayBad, String[][] opArrayBad )
    {
        LogUtil.logIt( msg );
        
        try
        {
            AccessMgr accessMgr = AccessMgrFactory.createInstance( TestUtils.getContext() );
            
            for ( String[] usr : uArray )
            {
                User user = UserTestData.getUser( usr );
                Session session = accessMgr.createSession( user, false );
                assertNotNull( session );
                int i = 0;
                for ( String[] obj : oArray )
                {
                    int j = 0;
                    for ( String[] op : opArray )
                    {
                        Permission goodPerm;
                        if( StringUtils.isNotEmpty( PermTestData.getObjId( opArray[j] ) ) )
                        {
                            // with an objectId:
                            goodPerm = new Permission(
                                PermTestData.getName( obj ),
                                PermTestData.getName( op ),
                                PermTestData.getObjId( opArray[j] ) );
                        }
                        else
                        {
                            // without an objectId:
                            goodPerm = new Permission(
                                PermTestData.getName( obj ),
                                PermTestData.getName( op ) );
                        }

                        // Positive test case, call checkAccess method, should return 'true':
                        assertTrue( CLS_NM + ".checkAccess failed userId [" + user.getUserId() + "] Perm objName [" +
                                PermTestData.getName( obj ) + "] operationName [" + PermTestData.getName( op ) + "]",
                            accessMgr.checkAccess( session, goodPerm ) );
                        Permission badPerm;
                        if( StringUtils.isNotEmpty( PermTestData.getObjId( opArrayBad[j] ) ) )
                        {
                            // with an objectId:
                            badPerm = new Permission(
                                PermTestData.getName( oArrayBad[i] ),
                                PermTestData.getName( opArrayBad[j] ),
                                PermTestData.getObjId( opArrayBad[j] ) );
                        }
                        else
                        {
                            // without an objectId:
                            badPerm = new Permission(
                                PermTestData.getName( oArrayBad[i] ),
                                PermTestData.getName( opArrayBad[j] ) );
                        }
                        //LOG.warn("Assert False userId [" + user.getUserId() + "], perm: " + badPerm);
                        // Negative test case, call checkAccess method again, should return 'false':
                        assertFalse( CLS_NM + ".checkAccess failed userId [" + user.getUserId() + "] Perm objName [" +
                            PermTestData.getName( oArrayBad[i] ) + "] operationName [" + PermTestData.getName(
                            opArrayBad[j] ) + "]", accessMgr.checkAccess( session, badPerm ) );
                        j++;
                    }
                    i++;
                }
            }
            LOG.debug( "checkAccess successful" );
        }
        catch ( SecurityException ex )
        {
            LOG.error( "checkAccess: failed with SecurityException rc=" + ex.getErrorId() + ", " +
                "msg=" + ex.getMessage(), ex );
            fail( ex.getMessage() );
        }
    }


    /**
     *
     */
    public void testSessionPermission()
    {
        // public List<Permission> sessionPermissions(Session session)
        // public static void sessionPermissions(String msg, String[][] uArray, String[][] oArray, String[][] opArray)
        sessionPermissions( "SESS-PRMS TU1_UPD TO1 TOP1 ", UserTestData.USERS_TU1_UPD, PermTestData.OBJS_TOB1,
            PermTestData.OPS_TOP1 );
        sessionPermissionsH( "SESS-PRMS_H USERS_TU7_HIER OBJS_TOB4 OPS_TOP4 ", UserTestData.USERS_TU7_HIER,
            PermTestData.OBJS_TOB4, PermTestData.OPS_TOP4 );
    }


    /**
     * @param msg
     * @param uArray
     * @param oArray
     * @param opArray
     */
    public static void sessionPermissions( String msg, String[][] uArray, String[][] oArray, String[][] opArray )
    {
        LogUtil.logIt( msg );
        try
        {
            AccessMgr accessMgr = AccessMgrFactory.createInstance( TestUtils.getContext() );
            for ( String[] usr : uArray )
            {
                User user = UserTestData.getUser( usr );
                Session session = accessMgr.createSession( user, false );
                assertNotNull( session );
                List<Permission> pOps = accessMgr.sessionPermissions( session );
                assertNotNull( pOps );
                // There should be objs * ops number of perms in the list returned from sessionPermissions method:
                assertEquals( CLS_NM +
                    ".sessionPermissions failed list size user[" + user.getUserId() + "]",
                    oArray.length * opArray.length, pOps.size() );

                // Iterate over objs x ops, see if every expected valid permission is contained within the returned list:
                for ( String[] obj : oArray )
                {
                    for ( String[] op : opArray )
                    {
                        Permission validPOp = PermTestData.getOp( PermTestData.getName( obj ), op );
                        assertTrue( CLS_NM +
                            ".sessionPermissions failed perm list compare USER [" + user.getUserId() +
                            "] PERM Obj [" + PermTestData.getName( obj ) + "] " +
                            "OPER [" + PermTestData.getName( op ) + "]",
                            pOps.contains( validPOp ) );
                    }
                }
            }
        }
        catch ( SecurityException ex )
        {
            LOG.error( "sessionPermissions: failed with SecurityException rc=" + ex.getErrorId() + ", msg="
                + ex.getMessage(), ex );
            fail( ex.getMessage() );
        }
    }


    /**
     *
     * @param msg
     * @param uArray
     * @param oArray
     * @param opArray
     */
    public static void sessionPermissionsH( String msg, String[][] uArray, String[][] oArray, String[][] opArray )
    {
        LogUtil.logIt( msg );
        try
        {
            AccessMgr accessMgr = AccessMgrFactory.createInstance( TestUtils.getContext() );
            int i = 0;
            for ( String[] usr : uArray )
            {
                i++;
                User user = UserTestData.getUser( usr );
                Session session = accessMgr.createSession( user, false );
                assertNotNull( session );
                List<Permission> pOps = accessMgr.sessionPermissions( session );
                assertNotNull( pOps );
                //LOG.warn("sessionPermissionsH list size user [" + user.getUserId() + "] expected len=" +
                //    (11 - i) * opArray.length + " actual len=" + pOps.size());
                assertEquals( CLS_NM +
                    ".sessionPermissionsH failed list size user[" + user.getUserId() + "]",
                    ( 11 - i ) * opArray.length, pOps.size() );

                // Iterate over objs x ops, see if every expected valid permission is contained within the returned list:
                int j = 0;
                for ( String[] obj : oArray )
                {
                    j++;
                    // role1 inherits 2 - 10, role 2 inherits 3 - 10, role 3 inherits 4 - 10, etc.
                    // obj1.op1 - 10 are granted to role1, obj2.op1 - 10 are granted to role2, etc...
                    // positive tests:
                    if ( i == j || i < j )
                    {
                        int k = 0;
                        for ( String[] op : opArray )
                        {
                            k++;
                            Permission validPOp = PermTestData.getOp( PermTestData.getName( obj ), op );
                            assertTrue( CLS_NM +
                                ".sessionPermissionsH failed perm list compare USER [" + user.getUserId() +
                                "] PERM Obj [" + PermTestData.getName( obj ) + "] " +
                                "OPER [" + PermTestData.getName( op ) + "]",
                                pOps.contains( validPOp ) );

                            boolean result = accessMgr.checkAccess( session, new Permission(
                                PermTestData.getName( obj ), PermTestData.getName( op ) ) );
                            assertTrue( CLS_NM +
                                ".sessionPermissionsH failed checkAccess USER [" + user.getUserId() +
                                "] PERM Obj [" + PermTestData.getName( obj ) + "] " +
                                "OPER [" + PermTestData.getName( op ) + "]",
                                result );
                        }
                    }
                    // negative tests:
                    else
                    {
                        int k = 0;
                        for ( String[] op : opArray )
                        {
                            k++;
                            Permission validPOp = PermTestData.getOp( PermTestData.getName( obj ), op );
                            assertTrue( CLS_NM +
                                ".sessionPermissionsH failed negative perm list compare USER [" + user.getUserId() +
                                "] PERM Obj [" + PermTestData.getName( obj ) + "] " +
                                "OPER [" + PermTestData.getName( op ) + "]",
                                !pOps.contains( validPOp ) );

                            boolean result = accessMgr.checkAccess( session, new Permission(
                                PermTestData.getName( obj ), PermTestData.getName( op ) ) );
                            assertTrue( CLS_NM +
                                ".sessionPermissionsH failed negative checkAccess USER [" + user.getUserId() +
                                "] PERM Obj [" + PermTestData.getName( obj ) + "] " +
                                "OPER [" + PermTestData.getName( op ) + "]",
                                !result );
                        }
                    }
                }
            }
        }
        catch ( SecurityException ex )
        {
            LOG.error( "sessionPermissionsH: failed with SecurityException rc=" + ex.getErrorId() + ", msg="
                + ex.getMessage(), ex );
            fail( ex.getMessage() );
        }
    }


    /**
     *
     */
    public void testSessionRole()
    {
        // public List<UserRole> sessionRoles(Session session)
        sessionRoles( "SESS-RLS TU1_UPD TR1", UserTestData.USERS_TU1_UPD, RoleTestData.ROLES_TR1 );
        sessionRoles( "SESS-RLS TU3 TR3", UserTestData.USERS_TU3, RoleTestData.ROLES_TR3 );
        sessionRoles( "SESS-RLS TU4 TR2", UserTestData.USERS_TU4, RoleTestData.ROLES_TR2 );
    }


    /**
     * @param msg
     * @param uArray
     * @param rArray
     */
    public static void sessionRoles( String msg, String[][] uArray, String[][] rArray )
    {
        LogUtil.logIt( msg );
        try
        {
            AccessMgr accessMgr = AccessMgrFactory.createInstance( TestUtils.getContext() );
            for ( String[] usr : uArray )
            {
                User user = UserTestData.getUser( usr );
                Session session = accessMgr.createSession( user, false );
                assertNotNull( session );
                String userId = accessMgr.getUserId( session );
                assertTrue( CLS_NM + ".sessionRoles failed compare found userId [" + userId + "] valid userId ["
                    + UserTestData.getUserId( usr ) + "]", userId.equalsIgnoreCase( UserTestData.getUserId( usr ) ) );
                UserTestData.assertEquals( user, usr );
                List<UserRole> uRoles = accessMgr.sessionRoles( session );
                assertNotNull( uRoles );
                assertEquals(
                    CLS_NM + ".sessionRoles user role check failed list size user [" + user.getUserId() + "]",
                    rArray.length, uRoles.size() );
                for ( String[] rle : rArray )
                {
                    assertTrue( CLS_NM + ".sessionRoles failed role search USER [" + user.getUserId() + "] ROLE1 ["
                        + RoleTestData.getName( rle ) + "] should be present",
                        uRoles.contains( RoleTestData.getUserRole( UserTestData.getUserId( usr ), rle ) ) );
                }
            }
            LOG.debug( "sessionRoles successful" );
        }
        catch ( SecurityException ex )
        {
            LOG.error(
                "sessionRoles: failed with SecurityException rc=" + ex.getErrorId() + ", msg="
                    + ex.getMessage(), ex );
            fail( ex.getMessage() );
        }
    }


    /**
     *
     */
    public void testAddActiveRole()
    {
        // public void addActiveRole(Session session, String role)
        addActiveRoles( "ADD-ACT-RLS TU1_UPD TR1 bad:TR2", UserTestData.USERS_TU1_UPD, RoleTestData.ROLES_TR1,
            RoleTestData.ROLES_TR2 );
        addActiveRoles( "ADD-ACT-RLS TU3 TR3 bad:TR1:", UserTestData.USERS_TU3, RoleTestData.ROLES_TR3,
            RoleTestData.ROLES_TR1 );
        addActiveRoles( "ADD-ACT-RLS TU4 TR2 bad:TR1", UserTestData.USERS_TU4, RoleTestData.ROLES_TR2,
            RoleTestData.ROLES_TR1 );
        addActiveRolesDSD( "ADD-ACT-RLS-USRS_DSDT1 TU8 DSD_T1", UserTestData.USERS_TU8_SSD, RoleTestData.DSD_T1 );
        addActiveRolesDSD( "ADD-ACT-RLS-USRS_DSDT4B TU9 DSD_T4_B", UserTestData.USERS_TU9_SSD_HIER,
            RoleTestData.DSD_T4_B );
        addActiveRolesDSD( "ADD-ACT-RLS-USRS_DSDT5B TU10 DSD_T5_B", UserTestData.USERS_TU10_SSD_HIER,
            RoleTestData.DSD_T5_B );
        addActiveRolesDSD( "ADD-ACT-RLS-USRS_DSDT6B TU11 DSD_T6_D", UserTestData.USERS_TU11_SSD_HIER,
            RoleTestData.DSD_T6_D );
    }


    /**
     * @param msg
     * @param uArray
     * @param rPosArray
     * @param rNegArray
     */
    public static void addActiveRoles( String msg, String[][] uArray, String[][] rPosArray, String[][] rNegArray )
    {
        LogUtil.logIt( msg );
        try
        {
            AccessMgr accessMgr = AccessMgrFactory.createInstance( TestUtils.getContext() );
            for ( String[] usr : uArray )
            {
                User user = UserTestData.getUser( usr );
                Session session = accessMgr.createSession( user, false );
                assertNotNull( session );
                List<UserRole> uRoles = session.getRoles();
                assertNotNull( uRoles );
                assertEquals( CLS_NM + ".addActiveRoles failed list size user[" + user.getUserId() + "]",
                    rPosArray.length, uRoles.size() );
                for ( String[] rle : rPosArray )
                {
                    assertTrue( CLS_NM + ".addActiveRoles failed role search USER [" + user.getUserId() + "] ROLE ["
                        + RoleTestData.getName( rle ) + "] should be present",
                        uRoles.contains( RoleTestData.getUserRole( UserTestData.getUserId( usr ), rle ) ) );
                }
                // Attempt to activate roles that aren't assigned to user:
                for ( String[] badRle : rNegArray )
                {
                    try
                    {
                        // Add Role (this better fail):
                        accessMgr.addActiveRole( session, new UserRole( RoleTestData.getName( badRle ) ) );
                        String error = "addActiveRoles failed negative test 1 User [" + user.getUserId()
                            + "] Role [" + RoleTestData.getName( badRle ) + "]";
                        LOG.info( error );
                        fail( error );
                    }
                    catch ( SecurityException se )
                    {
                        assertTrue( CLS_NM + "addActiveRoles excep id check",
                            se.getErrorId() == GlobalErrIds.URLE_ACTIVATE_FAILED );
                        // pass
                    }
                }
                // remove all roles from the user's session:
                int ctr = rPosArray.length;
                for ( String[] rle : rPosArray )
                {
                    // Drop Role:
                    accessMgr.dropActiveRole( session, new UserRole( RoleTestData.getName( rle ) ) );
                    assertEquals( CLS_NM + ".addActiveRoles failed list size user[" + user.getUserId() + "]",
                        ( --ctr ), session.getRoles().size() );
                    assertTrue( CLS_NM + ".addActiveRoles failed role search USER [" + user.getUserId() + "] ROLE ["
                        + RoleTestData.getName( rle ) + "] should not contain role",
                        !session.getRoles().contains( RoleTestData.getUserRole( UserTestData.getUserId( usr ), rle ) ) );
                    // Drop Role again: (This better fail because role  has already been deactivated from user's session)
                    try
                    {
                        // Drop Role3 (this better fail):
                        accessMgr.dropActiveRole( session, new UserRole( RoleTestData.getName( rle ) ) );
                        String error = "addActiveRoles failed negative test 2 User [" + user.getUserId()
                            + "] Role [" + RoleTestData.getName( rle ) + "]";
                        LOG.info( error );
                        fail( error );
                    }
                    catch ( SecurityException se )
                    {
                        assertTrue( CLS_NM + "addActiveRoles excep id check",
                            se.getErrorId() == GlobalErrIds.URLE_NOT_ACTIVE );
                    }
                }
                // Now activate the list of assigned roles:
                ctr = 0;
                for ( String[] rle : rPosArray )
                {
                    // Activate Role(s):
                    accessMgr.addActiveRole( session, new UserRole( RoleTestData.getName( rle ) ) );
                    uRoles = session.getRoles();
                    assertEquals( CLS_NM + ".addActiveRoles failed list size user [" + user.getUserId() + "]", ++ctr,
                        uRoles.size() );
                    assertTrue( CLS_NM + ".addActiveRoles failed role search USER [" + user.getUserId() + "] ROLE ["
                        + RoleTestData.getName( rle ) + "] should contain role",
                        uRoles.contains( RoleTestData.getUserRole( UserTestData.getUserId( usr ), rle ) ) );
                    try
                    {
                        // Activate Role again (this should throw SecurityException):
                        accessMgr.addActiveRole( session, new UserRole( RoleTestData.getName( rle ) ) );
                        String error = "addActiveRoles failed test 3 User [" + user.getUserId() + "] Role ["
                            + RoleTestData.getName( rle ) + "]";
                        LOG.info( error );
                        fail( error );
                    }
                    catch ( SecurityException se )
                    {
                        assertTrue( CLS_NM + "addActiveRoles excep id check",
                            se.getErrorId() == GlobalErrIds.URLE_ALREADY_ACTIVE );
                        // this is good
                    }
                }
            }
        }
        catch ( SecurityException ex )
        {
            LOG.error(
                "addActiveRoles: failed with SecurityException rc=" + ex.getErrorId() + ", msg="
                    + ex.getMessage(), ex );
            fail( ex.getMessage() );
        }
    }


    /**
     *
     */
    public void testDropActiveRole()
    {
        // public void dropActiveRole(Session session, String role)
        dropActiveRoles( "DRP-ACT-RLS TU1_UPD TR1 bad:TR2", UserTestData.USERS_TU1_UPD, RoleTestData.ROLES_TR1 );
        dropActiveRoles( "DRP-ACT-RLS TU3 TR3 bad:TR1", UserTestData.USERS_TU3, RoleTestData.ROLES_TR3 );
        dropActiveRoles( "DRP-ACT-RLS TU4 TR2 bad:TR1", UserTestData.USERS_TU4, RoleTestData.ROLES_TR2 );
    }


    /**
     * @param msg
     * @param uArray
     * @param rArray
     */
    public static void dropActiveRoles( String msg, String[][] uArray, String[][] rArray )
    {
        LogUtil.logIt( msg );
        try
        {
            AccessMgr accessMgr = AccessMgrFactory.createInstance( TestUtils.getContext() );
            for ( String[] usr : uArray )
            {
                User user = UserTestData.getUser( usr );
                Session session = accessMgr.createSession( user, false );
                assertNotNull( session );
                List<UserRole> uRoles = session.getRoles();
                assertNotNull( uRoles );
                assertEquals( CLS_NM + ".dropActiveRoles failed list size user[" + user.getUserId() + "]",
                    rArray.length, uRoles.size() );
                for ( String[] rle : rArray )
                {
                    assertTrue( CLS_NM + ".dropActiveRoles failed role search USER [" + user.getUserId() + "] ROLE ["
                        + RoleTestData.getName( rle ) + "] should be present",
                        uRoles.contains( RoleTestData.getUserRole( UserTestData.getUserId( usr ), rle ) ) );
                }
                // remove all roles from the user's session:
                int ctr = rArray.length;
                for ( String[] rle : rArray )
                {
                    // Drop Role:
                    accessMgr.dropActiveRole( session, new UserRole( RoleTestData.getName( rle ) ) );
                    assertEquals( CLS_NM + ".dropActiveRoles failed list size user[" + user.getUserId() + "]",
                        ( --ctr ), session.getRoles().size() );
                    assertTrue( CLS_NM + ".dropActiveRoles failed role search USER [" + user.getUserId() + "] ROLE ["
                        + RoleTestData.getName( rle ) + "] should not contain role",
                        !session.getRoles().contains( RoleTestData.getUserRole( UserTestData.getUserId( usr ), rle ) ) );
                    // Drop Role again: (This better fail because role  has already been deactivated from user's session)
                    try
                    {
                        // Drop Role3 (this better fail):
                        accessMgr.dropActiveRole( session, new UserRole( RoleTestData.getName( rle ) ) );
                        String error = "dropActiveRoles failed negative test 2 User [" + user.getUserId()
                            + "] Role [" + RoleTestData.getName( rle ) + "]";
                        LOG.info( error );
                        fail( error );
                    }
                    catch ( SecurityException se )
                    {
                        assertTrue( "dropActiveRoles excep id check",
                            se.getErrorId() == GlobalErrIds.URLE_NOT_ACTIVE );
                    }
                }
            }
        }
        catch ( SecurityException ex )
        {
            LOG.error(
                "dropActiveRoles: failed with SecurityException rc=" + ex.getErrorId() + ", msg="
                    + ex.getMessage(), ex );
            fail( ex.getMessage() );
        }
    }


    public static void addActiveRolesDSD( String msg, String[][] uArray, String[][] sArray )
    {
        LogUtil.logIt( msg );
        try
        {
            AccessMgr accessMgr = AccessMgrFactory.createInstance( TestUtils.getContext() );
            int i = 0;
            for ( String[] usr : uArray )
            {
                SDSet dsd = RoleTestData.getSDSet( sArray[i++] );
                //Set<String> roles = dsd.getMembers().keySet();
                Set<String> roles = dsd.getMembers();
                User user = UserTestData.getUser( usr );
                Session session = accessMgr.authenticate( user.getUserId(), user.getPassword() );
                int j = 0;
                for ( String role : roles )
                {
                    j++;
                    try
                    {
                        assertNotNull( session );

                        // Activate Role(s):
                        accessMgr.addActiveRole( session, new UserRole( role ) );
                        if ( j >= dsd.getCardinality() )
                        {
                            fail( CLS_NM + ".addActiveRolesDSD user [" + user.getUserId() + "] role [" + role
                                + "] ssd [" + dsd.getName() + "] cardinality [" + dsd.getCardinality() + "] count ["
                                + j + "] failed" );
                        }
                    }
                    catch ( SecurityException ex )
                    {
                        assertTrue( CLS_NM + ".addActiveRolesDSD cardinality test failed user [" + user.getUserId()
                            + "] role [" + role + "] ssd [" + dsd.getName() + "] cardinality [" + dsd.getCardinality()
                            + "] count [" + j + "]", j >= ( dsd.getCardinality() ) );
                        assertTrue(
                            CLS_NM + ".addActiveRolesDSD cardinality test failed [" + UserTestData.getUserId( usr )
                                + "]", ex.getErrorId() == GlobalErrIds.DSD_VALIDATION_FAILED );
                        // still good, break from loop, we're done here
                        break;
                    }
                }
            }
        }
        catch ( SecurityException ex )
        {
            LOG.error(
                "addActiveRolesDSD caught SecurityException rc=" + ex.getErrorId() + ", msg="
                    + ex.getMessage(), ex );
            fail( ex.getMessage() );
        }
    }


    /**
     * Test the Rbac-Abac curly,moe,larry use cases.
     *
     */
    public void testAbacConstraintsRole()
    {

        createSessionsConstraints( "ABAC RBAC", RoleTestData.ROLE_CONSTRAINTS_TR18_ABAC );
    }

    public static void createSessionsConstraints( String msg, String[][] cArray  )
    {
        LogUtil.logIt( msg );
        String TELLERS = "tellers"; // DSD excluded from washer
        String WASHERS = "washers"; // DSD excluded from teller
        String NORTH = "north";
        String SOUTH = "south";
        String EAST = "east";
        String CURLY = "curly"; // Head Teller of the East, Coin Washer in North and South
        String MOE = "moe"; // Head Teller of the North, Coin Washer in East and South
        String LARRY = "larry"; // Head Teller of the South, Coin Washer in North and East

        try
        {
            AccessMgr accessMgr = AccessMgrFactory.createInstance( TestUtils.getContext() );
            for( String[] cons : cArray )
            {
                UserRole uRole = RoleTestData.getUserRoleConstraintAbac( cons );
                User user = new User( uRole.getUserId() );
                RoleConstraint constraint = uRole.getConstraints().get( 0 );
                List<RoleConstraint> constraints = new ArrayList();
                constraints.add( constraint );
                Session session = accessMgr.createSession( user, constraints, true );
                assertNotNull( session );
                if( uRole.getName().equalsIgnoreCase( TELLERS ))
                {
                    List<UserRole> actRoles = session.getRoles();
                    for( UserRole actRole : actRoles )
                    {
                        // Someone with Teller role cannot activate Washer.
                        if( actRole.getName().equalsIgnoreCase( WASHERS ))
                        {
                            fail( CLS_NM + ".createSessionsConstraints " + TELLERS + " cannot contain " + WASHERS +", user: " + uRole.getUserId() + ", constraint value: " + constraint.getValue() );
                        }
                    }
                    if( constraint.getValue().equalsIgnoreCase( EAST ))
                    {
                        // Only Curly is an East Teller
                        if( !uRole.getUserId().equalsIgnoreCase( CURLY ))
                        {
                            fail( CLS_NM + ".createSessionsConstraints " + TELLERS + "," + EAST +" invalid relationship, user: " + uRole.getUserId() + ", role name: " + uRole.getName() + ", constraint value: " + constraint.getValue() );
                        }
                    }
                    else if( constraint.getValue().equalsIgnoreCase( NORTH ))
                    {
                        // Only Moe is North Teller
                        if( !uRole.getUserId().equalsIgnoreCase( MOE ))
                        {
                            fail( CLS_NM + ".createSessionsConstraints " + TELLERS + "," + NORTH + " invalid relationship, user: " + uRole.getUserId() + ", role name: " + uRole.getName() + ", constraint value: " + constraint.getValue() );
                        }
                    }
                    else if( constraint.getValue().equalsIgnoreCase( SOUTH ))
                    {
                        // Only Larry is South Teller
                        if( !uRole.getUserId().equalsIgnoreCase( LARRY ))
                        {
                            fail( CLS_NM + ".createSessionsConstraints " + TELLERS + "," + SOUTH + " invalid relationship, user: " + uRole.getUserId() + ", role name: " + uRole.getName() + ", constraint value: " + constraint.getValue() );
                        }
                    }
                    // Invalid test case
                    else
                    {
                        fail( CLS_NM + ".createSessionsConstraints " + TELLERS + " invalid test role: " + uRole.getName() + ", constraint value: " + constraint.getValue() );
                    }

                    // Verify that the Teller has access to the account operations:
                    for( String[] op : PermTestData.ABAC_ACCOUNT_OPS )
                    {
                        Permission validPOp = PermTestData.getOp( PermTestData.getName( PermTestData.ABAC_ACCOUNT_OBJS[0] ), op );
                        boolean result = accessMgr.checkAccess( session, validPOp );
                        assertTrue( CLS_NM +
                                ".createSessionsConstraints failed checkAccess USER [" + user.getUserId() +
                                "] PERM Obj [" + validPOp.getObjName() + "] " +
                                "OPER [" + validPOp.getOpName() + "]",
                            result );
                    }
                }
                // Verify the Washer has access to currency operations:
                else if( uRole.getName().equalsIgnoreCase( WASHERS ))
                {
                    List<UserRole> actRoles = session.getRoles();
                    for( UserRole actRole : actRoles )
                    {
                        // Someone with Washer role cannot activate Teller.
                        if( actRole.getName().equalsIgnoreCase( TELLERS ))
                        {
                            fail( CLS_NM + ".createSessionsConstraints " + WASHERS + " cannot contain " + TELLERS +", user: " + uRole.getUserId() + ", constraint value: " + constraint.getValue() );
                        }
                    }
                    if( constraint.getValue().equalsIgnoreCase( EAST ))
                    {
                        // Curly cannot be an East Washer
                        if( uRole.getUserId().equalsIgnoreCase( CURLY ))
                        {
                            fail( CLS_NM + ".createSessionsConstraints " + WASHERS + "," + EAST + "  invalid relationship, user: " + uRole.getUserId() + ", role name: " + uRole.getName() + ", constraint value: " + constraint.getValue() );
                        }
                    }
                    else if( constraint.getValue().equalsIgnoreCase( NORTH ))
                    {
                        // Moe cannot be a North Washer
                        if( uRole.getUserId().equalsIgnoreCase( MOE ))
                        {
                            fail( CLS_NM + ".createSessionsConstraints " + WASHERS + ","+ NORTH + " invalid relationship, user: " + uRole.getUserId() + ", role name: " + uRole.getName() + ", constraint value: " + constraint.getValue() );
                        }
                    }
                    else if( constraint.getValue().equalsIgnoreCase( SOUTH ))
                    {
                        // Larry cannot be a South Washer
                        if( uRole.getUserId().equalsIgnoreCase( LARRY ))
                        {
                            fail( CLS_NM + ".createSessionsConstraints " + WASHERS + "," + SOUTH + " invalid relationship, user: " + uRole.getUserId() + ", role name: " + uRole.getName() + ", constraint value: " + constraint.getValue() );
                        }
                    }
                    // Invalid test case
                    else
                    {
                        fail( CLS_NM + ".createSessionsConstraints " + WASHERS + " invalid test role: " + uRole.getName() + ", constraint value: " + constraint.getValue() );
                    }
                    // Verify that the Washer has access to the currency operations:
                    for( String[] op : PermTestData.ABAC_CURRENCY_OPS )
                    {
                        Permission validPOp = PermTestData.getOp( PermTestData.getName( PermTestData.ABAC_CURRENCY_OBJS[0] ), op );
                        boolean result = accessMgr.checkAccess( session, validPOp );
                        assertTrue( CLS_NM +
                                ".createSessionsConstraints failed checkAccess USER [" + user.getUserId() +
                                "] PERM Obj [" + validPOp.getObjName() + "] " +
                                "OPER [" + validPOp.getOpName() + "]",
                            result );
                    }
                }
                // Invalid test case
                else
                {
                    fail( CLS_NM + ".createSessionsConstraints invalid test role: " + uRole.getName() );
                }

            }
            LOG.debug( "createSessionsConstraints successful" );
        }
        catch ( SecurityException ex )
        {
            LOG.error(
                "createSessionsConstraints: failed with SecurityException rc=" + ex.getErrorId() + ", msg="
                    + ex.getMessage(), ex );
            fail( ex.getMessage() );
        }
    }
}
