[jboss-cvs] JBossAS SVN: r85320 - in projects/security/security-jboss-sx/branches/Branch_2_0: acl/src/tests/java/org/jboss/test/security/acl and 1 other directories.

jboss-cvs-commits at lists.jboss.org jboss-cvs-commits at lists.jboss.org
Thu Mar 5 13:57:06 EST 2009


Author: sguilhen at redhat.com
Date: 2009-03-05 13:57:05 -0500 (Thu, 05 Mar 2009)
New Revision: 85320

Added:
   projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/main/java/org/jboss/security/acl/RoleBasedACLProviderImpl.java
   projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/tests/java/org/jboss/test/security/acl/RoleBasedACLProviderUnitTestCase.java
Modified:
   projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/main/java/org/jboss/security/acl/ACLEntryImpl.java
   projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/main/java/org/jboss/security/acl/ACLImpl.java
   projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/main/java/org/jboss/security/acl/ACLProviderImpl.java
   projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/main/java/org/jboss/security/acl/EntitlementEntry.java
   projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/tests/java/org/jboss/test/security/acl/PersistenceTestCase.java
   projects/security/security-jboss-sx/branches/Branch_2_0/parent/pom.xml
Log:
SECURITY-374: Added RoleBasedACLProviderImpl, which uses the identity's roles when checking permissions

Modified: projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/main/java/org/jboss/security/acl/ACLEntryImpl.java
===================================================================
--- projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/main/java/org/jboss/security/acl/ACLEntryImpl.java	2009-03-05 18:55:48 UTC (rev 85319)
+++ projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/main/java/org/jboss/security/acl/ACLEntryImpl.java	2009-03-05 18:57:05 UTC (rev 85320)
@@ -62,8 +62,8 @@
    @Transient
    private Identity identity;
 
-   /* persist the string representation of the identity */
-   private String identityString;
+   /* persist the string representation of the identity or role */
+   private String identityOrRole;
 
    @ManyToOne
    private ACLImpl acl;
@@ -89,10 +89,25 @@
    {
       this.permission = permission;
       this.identity = identity;
+      this.identityOrRole = identity.getName();
    }
 
    /**
     * <p>
+    * Builds an instance of {@code ACLEntryImpl} with the specified permission and identity/role name.
+    * </p>
+    * 
+    * @param permission the {@code ACLPermission} granted to the associated identity.
+    * @param identityOrRole a {@code String} representing the identity or role name.
+    */
+   public ACLEntryImpl(BitMaskPermission permission, String identityOrRole)
+   {
+      this.permission = permission;
+      this.identityOrRole = identityOrRole;
+   }
+
+   /**
+    * <p>
     * Obtains the persistent id of this {@code ACLEntryImpl}.
     * </p>
     * 
@@ -114,7 +129,6 @@
    {
       if (this.permission != null)
          this.bitMask = this.permission.getMaskValue();
-      this.identityString = Util.getIdentityAsString(this.identity);
    }
 
    /**
@@ -129,10 +143,6 @@
       if (this.permission != null)
          throw new IllegalStateException("ACLEntry permission has already been set");
       this.permission = new CompositeACLPermission(this.bitMask);
-
-      if (this.identity != null)
-         throw new IllegalStateException("ACLEntry identity has already been set");
-      this.identity = Util.getIdentityFromString(identityString);
    }
 
    public ACLImpl getAcl()
@@ -148,6 +158,16 @@
    /*
     * (non-Javadoc)
     * 
+    * @see org.jboss.security.acl.ACLEntry#getIdentityOrRole()
+    */
+   public String getIdentityOrRole()
+   {
+      return this.identityOrRole;
+   }
+
+   /*
+    * (non-Javadoc)
+    * 
     * @see org.jboss.security.acl.ACLEntry#getIdentity()
     */
    public Identity getIdentity()
@@ -193,7 +213,7 @@
       if (obj instanceof ACLEntryImpl)
       {
          ACLEntryImpl entry = (ACLEntryImpl) obj;
-         return entry.getIdentity().getName().equals(this.identity.getName());
+         return this.identityOrRole.equals(entry.identityOrRole);
       }
       return false;
    }
@@ -206,6 +226,6 @@
    @Override
    public int hashCode()
    {
-      return this.getIdentity().getName().hashCode();
+      return this.identityOrRole.hashCode();
    }
 }

Modified: projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/main/java/org/jboss/security/acl/ACLImpl.java
===================================================================
--- projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/main/java/org/jboss/security/acl/ACLImpl.java	2009-03-05 18:55:48 UTC (rev 85319)
+++ projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/main/java/org/jboss/security/acl/ACLImpl.java	2009-03-05 18:57:05 UTC (rev 85320)
@@ -67,7 +67,7 @@
    private String resourceAsString;
 
    @Transient
-   private Map<Identity, ACLEntry> entriesMap;
+   private Map<String, ACLEntry> entriesMap;
 
    @OneToMany(mappedBy = "acl", fetch = FetchType.EAGER, cascade =
    {CascadeType.REMOVE, CascadeType.PERSIST})
@@ -149,11 +149,11 @@
          this.initEntriesMap();
 
       // don't add a null entry or an entry that already existSELECT * FROM ACL_ENTRYs.
-      if (entry == null || this.entriesMap.get(entry.getIdentity()) != null)
+      if (entry == null || this.entriesMap.get(entry.getIdentityOrRole()) != null)
          return false;
       this.entries.add((ACLEntryImpl) entry);
       ((ACLEntryImpl) entry).setAcl(this);
-      this.entriesMap.put(entry.getIdentity(), entry);
+      this.entriesMap.put(entry.getIdentityOrRole(), entry);
       return true;
    }
 
@@ -166,7 +166,7 @@
    {
       if (this.entriesMap == null)
          this.initEntriesMap();
-      this.entriesMap.remove(entry.getIdentity());
+      this.entriesMap.remove(entry.getIdentityOrRole());
       return this.entries.remove(entry);
    }
 
@@ -189,12 +189,26 @@
     */
    public ACLEntry getEntry(Identity identity)
    {
-      return this.entriesMap.get(identity);
+      if (this.entriesMap == null)
+         this.initEntriesMap();
+      return this.entriesMap.get(identity.getName());
    }
 
    /*
     * (non-Javadoc)
     * 
+    * @see org.jboss.security.acl.ACL#getEntry(java.lang.String)
+    */
+   public ACLEntry getEntry(String identityOrRole)
+   {
+      if (this.entriesMap == null)
+         this.initEntriesMap();
+      return this.entriesMap.get(identityOrRole);
+   }
+
+   /*
+    * (non-Javadoc)
+    * 
     * @see org.jboss.security.acl.ACL#isGranted(org.jboss.security.acl.ACLPermission,
     *      org.jboss.security.identity.Identity)
     */
@@ -204,7 +218,7 @@
          this.initEntriesMap();
 
       // lookup the entry corresponding to the specified identity.
-      ACLEntry entry = this.entriesMap.get(identity);
+      ACLEntry entry = this.entriesMap.get(identity.getName());
       if (entry != null)
       {
          // check the permission associated with the identity.
@@ -256,9 +270,9 @@
     */
    private void initEntriesMap()
    {
-      this.entriesMap = new HashMap<Identity, ACLEntry>();
+      this.entriesMap = new HashMap<String, ACLEntry>();
       for (ACLEntry entry : this.entries)
-         this.entriesMap.put(entry.getIdentity(), entry);
+         this.entriesMap.put(entry.getIdentityOrRole(), entry);
    }
 
 }

Modified: projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/main/java/org/jboss/security/acl/ACLProviderImpl.java
===================================================================
--- projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/main/java/org/jboss/security/acl/ACLProviderImpl.java	2009-03-05 18:55:48 UTC (rev 85319)
+++ projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/main/java/org/jboss/security/acl/ACLProviderImpl.java	2009-03-05 18:57:05 UTC (rev 85320)
@@ -36,7 +36,9 @@
 
 /**
  * <p>
- * This class is the standard {@code ACLProvider} implementation.
+ * This class is the standard {@code ACLProvider} implementation. The access control decisions are based on the name of
+ * the specified identity (that is, it assumes that entries in an ACL are keyed by the name of the identity and not by
+ * other attributes, like the its roles).
  * </p>
  * 
  * @author <a href="mailto:sguilhen at redhat.com">Stefan Guilhen</a>
@@ -47,7 +49,7 @@
    private static final String PERSISTENCE_STRATEGY_OPTION = "persistenceStrategy";
 
    /** persistence strategy used to retrieve the ACLs */
-   private ACLPersistenceStrategy strategy;
+   protected ACLPersistenceStrategy strategy;
 
    /*
     * (non-Javadoc)
@@ -87,9 +89,9 @@
 
       Set<EntitlementEntry> entitlements = new HashSet<EntitlementEntry>();
       // get the initial permissions - those that apply to the specified resource.
-      ACLPermission permission = this.getInitialPermissions(resource, identity);
+      ACLPermission permission = this.getInitialPermissions(resource, identity.getName());
       if (permission != null)
-         this.fillEntitlements(entitlements, resource, identity, permission);
+         this.fillEntitlements(entitlements, resource, identity.getName(), permission);
       return (Set<T>) entitlements;
    }
 
@@ -120,11 +122,11 @@
     * 
     * @param entitlements a reference for the collection of {@code EntitlementEntry} objects that is being constructed.
     * @param resource the {@code Resource} being visited.
-    * @param identity the {@code Identity} for which the entitlements are being built.
+    * @param identityName a {@code String} representing the identity for which the entitlements are being built.
     * @param permission the {@code ACLPermission} to be used in case no ACL is found for the resource being visited.
     */
    @SuppressWarnings("unchecked")
-   private void fillEntitlements(Set<EntitlementEntry> entitlements, Resource resource, Identity identity,
+   protected void fillEntitlements(Set<EntitlementEntry> entitlements, Resource resource, String identityName,
          ACLPermission permission)
    {
       ACLPermission currentPermission = permission;
@@ -132,17 +134,17 @@
       ACL acl = this.strategy.getACL(resource);
       if (acl != null)
       {
-         ACLEntry entry = acl.getEntry(identity);
+         ACLEntry entry = acl.getEntry(identityName);
          // null entry means the identity has no permissions over the specified resource.
          if (entry == null)
             return;
          currentPermission = entry.getPermission();
-         entitlements.add(new EntitlementEntry(resource, currentPermission));
+         entitlements.add(new EntitlementEntry(resource, currentPermission, identityName));
       }
       else
       {
          // if resource's ACL is null, build an entry using the permission parameter.
-         entitlements.add(new EntitlementEntry(resource, currentPermission));
+         entitlements.add(new EntitlementEntry(resource, currentPermission, identityName));
       }
 
       // iterate through the sub-resources (if any), adding their entries to the entitlements collection.
@@ -150,7 +152,7 @@
       if (childResources != null)
       {
          for (Resource childResource : childResources)
-            fillEntitlements(entitlements, childResource, identity, currentPermission);
+            fillEntitlements(entitlements, childResource, identityName, currentPermission);
       }
    }
 
@@ -170,12 +172,12 @@
     * 
     * @param resource the {@code Resource} for which we want to discover the permissions that have been assigned to the
     *            specified identity.
-    * @param identity the {@code Identity} for which we want to discover the permissions regarding the specified
-    *            resource.
+    * @param identityName a {@code String} representing the identity for which we want to discover the permissions
+    *            regarding the specified resource.
     * @return an {@code ACLPermission} containing the permissions that have been assigned to the identity with respect
     *         to the specified resource, or {@code null} if the identity has no permissions at all.
     */
-   private ACLPermission getInitialPermissions(Resource resource, Identity identity)
+   protected ACLPermission getInitialPermissions(Resource resource, String identityName)
    {
       ACL acl = this.strategy.getACL(resource);
       // if no ACL was found, try to find a parent ACL.
@@ -183,12 +185,12 @@
       {
          Resource parent = (Resource) resource.getMap().get(ResourceKeys.PARENT_RESOURCE);
          if (parent != null)
-            return getInitialPermissions(parent, identity);
+            return getInitialPermissions(parent, identityName);
          // no ACL was found and no parent resource exists - identity has all permissions as resource is not protected.
          return new CompositeACLPermission(BasicACLPermission.values());
       }
       // if an ACL was found, return the permissions associated with the specified identity.
-      ACLEntry entry = acl.getEntry(identity);
+      ACLEntry entry = acl.getEntry(identityName);
       if (entry != null)
          return entry.getPermission();
       // the absence of an entry means that the identity has no permissions over the specified resource.
@@ -230,7 +232,16 @@
       {
          ACL acl = strategy.getACL(resource);
          if (acl != null)
-            return acl.isGranted(permission, identity);
+         {
+            ACLEntry entry = acl.getEntry(identity);
+            if (entry != null)
+            {
+               // check the permission associated with the identity.
+               return entry.checkPermission(permission);
+            }
+            // no entry for identity = deny access
+            return false;
+         }
          else
             throw new AuthorizationException("Unable to locate an ACL for the resource " + resource);
       }
@@ -256,7 +267,7 @@
     * @return a reference to the loaded {@code Class}.
     * @throws PrivilegedActionException if an error occurs while loading the specified class.
     */
-   private Class<?> loadClass(final String name) throws PrivilegedActionException
+   protected Class<?> loadClass(final String name) throws PrivilegedActionException
    {
       return AccessController.doPrivileged(new PrivilegedExceptionAction<Class<?>>()
       {

Modified: projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/main/java/org/jboss/security/acl/EntitlementEntry.java
===================================================================
--- projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/main/java/org/jboss/security/acl/EntitlementEntry.java	2009-03-05 18:55:48 UTC (rev 85319)
+++ projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/main/java/org/jboss/security/acl/EntitlementEntry.java	2009-03-05 18:57:05 UTC (rev 85320)
@@ -26,7 +26,7 @@
 /**
  * <p>
  * This class represents a standard entry in the collection returned by the {@code ACLProvider.getEntitlements} method.
- * It contains the permissions that a particular identity has over an specific resource.
+ * It contains the permissions that a particular identity or role has over an specific resource.
  * </p>
  * 
  * @author <a href="mailto:sguilhen at redhat.com">Stefan Guilhen</a>
@@ -37,6 +37,8 @@
 
    private final ACLPermission permission;
 
+   private final String identityOrRole;
+   
    /**
     * <p>
     * Creates an instance of {@code EntitlementEntry} with the specified resource and permissions.
@@ -44,13 +46,15 @@
     * 
     * @param resource a reference to the {@code Resource} object.
     * @param permission the permissions a particular identity has over the specified resource.
+    * @param identityOrRole a {@code String} containing the name of the identity or the role.
     */
-   public EntitlementEntry(Resource resource, ACLPermission permission)
+   public EntitlementEntry(Resource resource, ACLPermission permission, String identityOrRole)
    {
       if(resource == null || permission == null)
          throw new IllegalArgumentException("Illegal null value for resource or permission");
       this.resource = resource;
       this.permission = permission;
+      this.identityOrRole = identityOrRole;
    }
 
    public Resource getResource()
@@ -62,5 +66,10 @@
    {
       return this.permission;
    }
+   
+   public String getIdentityOrRole()
+   {
+      return this.identityOrRole;
+   }
 
 }

Added: projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/main/java/org/jboss/security/acl/RoleBasedACLProviderImpl.java
===================================================================
--- projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/main/java/org/jboss/security/acl/RoleBasedACLProviderImpl.java	                        (rev 0)
+++ projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/main/java/org/jboss/security/acl/RoleBasedACLProviderImpl.java	2009-03-05 18:57:05 UTC (rev 85320)
@@ -0,0 +1,133 @@
+/*
+ * JBoss, Home of Professional Open Source.
+ * Copyright 2009, Red Hat Middleware LLC, and individual contributors
+ * as indicated by the @author tags. See the copyright.txt file in the
+ * distribution for a full listing of individual contributors. 
+ *
+ * This is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU Lesser General Public License as
+ * published by the Free Software Foundation; either version 2.1 of
+ * the License, or (at your option) any later version.
+ *
+ * This software is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this software; if not, write to the Free
+ * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
+ * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
+ */
+package org.jboss.security.acl;
+
+import java.util.ArrayList;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Set;
+
+import org.jboss.security.authorization.AuthorizationException;
+import org.jboss.security.authorization.Resource;
+import org.jboss.security.identity.Identity;
+import org.jboss.security.identity.Role;
+import org.jboss.security.identity.RoleGroup;
+
+/**
+ * <p>
+ * Implementation of {@code ACLProvider} that uses the identity roles when checking if access to a protected resource
+ * should be granted or not. If no roles are associated with the specified identity, then the default implementation,
+ * which is based on the identity name, is used. Otherwise, {@code #isAccessGranted()} iterates over the roles and if
+ * one of the roles has sufficient permissions, then access is granted.
+ * </p>
+ * 
+ * @author <a href="mailto:sguilhen at redhat.com">Stefan Guilhen</a>
+ */
+public class RoleBasedACLProviderImpl extends ACLProviderImpl
+{
+
+   @Override
+   @SuppressWarnings("unchecked")
+   public <T> Set<T> getEntitlements(Class<T> clazz, Resource resource, Identity identity)
+         throws AuthorizationException
+   {
+      if (identity.getRole() == null)
+         return super.getEntitlements(clazz, resource, identity);
+
+      // currently we only provide sets of EntitlementEntry objects.
+      if (!EntitlementEntry.class.equals(clazz))
+         return null;
+
+      Set<EntitlementEntry> entitlements = new HashSet<EntitlementEntry>();
+      // fill the entitlements for each role.
+      List<Role> roles = new ArrayList<Role>();
+      this.getAllRoles(identity.getRole(), roles);
+
+      for (Role role : roles)
+      {
+         // get the initial permissions - those that apply to the specified resource.
+         ACLPermission permission = super.getInitialPermissions(resource, role.getRoleName());
+         if (permission != null)
+            super.fillEntitlements(entitlements, resource, role.getRoleName(), permission);
+      }
+      return (Set<T>) entitlements;
+   }
+
+   /**
+    * <p>
+    * This method overrides the default implementation to use roles instead of the identity name when checking for
+    * permissions. If the specified identity has one or more roles associated with it, this implementation will use
+    * these roles to check if the identity should be granted access to the resource or not.
+    * </p>
+    */
+   @Override
+   public boolean isAccessGranted(Resource resource, Identity identity, ACLPermission permission)
+         throws AuthorizationException
+   {
+      // if there are no roles associated with the identity, use the default implementation
+      if (identity.getRole() == null)
+         return super.isAccessGranted(resource, identity, permission);
+
+      if (super.strategy != null)
+      {
+         ACL acl = strategy.getACL(resource);
+         if (acl != null)
+         {
+            // check if any of the identity's roles has access to the resource.
+            List<Role> roles = new ArrayList<Role>();
+            this.getAllRoles(identity.getRole(), roles);
+
+            for (Role role : roles)
+            {
+               ACLEntry entry = acl.getEntry(role.getRoleName());
+               if (entry != null && entry.checkPermission(permission))
+                  return true;
+            }
+            return false;
+         }
+         else
+            throw new AuthorizationException("Unable to locate an ACL for the resource " + resource);
+      }
+      throw new AuthorizationException("Unable to retrieve ACL: persistece strategy not set");
+   }
+
+   /**
+    * <p>
+    * This method traverses the role tree that has the specified root role and puts all simple (i.e. not an instance of
+    * RoleGroup) roles into the specified roles list.
+    * </p>
+    * 
+    * @param role the root of the role tree.
+    * @param roles the {@code List<Role>} that contains the simple roles of the tree.
+    */
+   protected void getAllRoles(Role role, List<Role> roles)
+   {
+      if (role instanceof RoleGroup)
+      {
+         RoleGroup group = (RoleGroup) role;
+         for (Role nestedRole : group.getRoles())
+            getAllRoles(nestedRole, roles);
+      }
+      else
+         roles.add(role);
+   }
+}

Modified: projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/tests/java/org/jboss/test/security/acl/PersistenceTestCase.java
===================================================================
--- projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/tests/java/org/jboss/test/security/acl/PersistenceTestCase.java	2009-03-05 18:55:48 UTC (rev 85319)
+++ projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/tests/java/org/jboss/test/security/acl/PersistenceTestCase.java	2009-03-05 18:57:05 UTC (rev 85320)
@@ -42,9 +42,9 @@
 
 /**
  * <p>
- * This {@code TestCase} tests the functionality of the persistence layer added to the {@code ACL} implementation classes.
- * It uses an in-memory hsql test database, so there is no need to perform any special database cleanup in case one of the
- * tests fail. Every time the tests are run a clean new database is used.
+ * This {@code TestCase} tests the functionality of the persistence layer added to the {@code ACL} implementation
+ * classes. It uses an in-memory hsql test database, so there is no need to perform any special database cleanup in case
+ * one of the tests fail. Every time the tests are run a clean new database is used.
  * </p>
  * 
  * @author <a href="mailto:sguilhen at redhat.com">Stefan Guilhen</a>
@@ -61,6 +61,7 @@
 
    /*
     * (non-Javadoc)
+    * 
     * @see junit.framework.TestCase#setUp()
     */
    @Override
@@ -91,6 +92,7 @@
 
    /*
     * (non-Javadoc)
+    * 
     * @see junit.framework.TestCase#tearDown()
     */
    @Override
@@ -156,8 +158,8 @@
       // execute some queries and validate the results.
       ACLEntryImpl entry = this.persistedEntries.get(1);
       ACLEntryImpl queryResult = (ACLEntryImpl) this.entityManager.createQuery(
-            "SELECT e FROM ACLEntryImpl e WHERE e.identityString LIKE '"
-                  + Util.getIdentityAsString(entry.getIdentity()) + "'").getSingleResult();
+            "SELECT e FROM ACLEntryImpl e WHERE e.identityOrRole LIKE '"
+                  + entry.getIdentityOrRole() + "'").getSingleResult();
       assertNotNull("Entry2 could not be retrieved by it's identity", queryResult);
       assertEquals(entry, queryResult);
 
@@ -189,7 +191,7 @@
 
    /**
     * <p>
-    * Tests searching for the persisted {@code ACL} objects. 
+    * Tests searching for the persisted {@code ACL} objects.
     * </p>
     * 
     * @throws Exception if an error occurs when running the test.

Added: projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/tests/java/org/jboss/test/security/acl/RoleBasedACLProviderUnitTestCase.java
===================================================================
--- projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/tests/java/org/jboss/test/security/acl/RoleBasedACLProviderUnitTestCase.java	                        (rev 0)
+++ projects/security/security-jboss-sx/branches/Branch_2_0/acl/src/tests/java/org/jboss/test/security/acl/RoleBasedACLProviderUnitTestCase.java	2009-03-05 18:57:05 UTC (rev 85320)
@@ -0,0 +1,125 @@
+/*
+ * JBoss, Home of Professional Open Source.
+ * Copyright 2009, Red Hat Middleware LLC, and individual contributors
+ * as indicated by the @author tags. See the copyright.txt file in the
+ * distribution for a full listing of individual contributors. 
+ *
+ * This is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU Lesser General Public License as
+ * published by the Free Software Foundation; either version 2.1 of
+ * the License, or (at your option) any later version.
+ *
+ * This software is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this software; if not, write to the Free
+ * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
+ * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
+ */
+package org.jboss.test.security.acl;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import junit.framework.TestCase;
+
+import org.jboss.security.acl.ACLEntry;
+import org.jboss.security.acl.ACLEntryImpl;
+import org.jboss.security.acl.ACLPersistenceStrategy;
+import org.jboss.security.acl.ACLProvider;
+import org.jboss.security.acl.BasicACLPermission;
+import org.jboss.security.acl.CompositeACLPermission;
+import org.jboss.security.acl.JPAPersistenceStrategy;
+import org.jboss.security.acl.RoleBasedACLProviderImpl;
+import org.jboss.security.authorization.Resource;
+import org.jboss.security.identity.Identity;
+import org.jboss.security.identity.Role;
+import org.jboss.security.identity.RoleFactory;
+import org.jboss.security.identity.RoleGroup;
+import org.jboss.security.identity.plugins.IdentityFactory;
+
+/**
+ * <p>
+ * This {@code TestCase} tests the functionality implemented by the {@code RoleBasedACLProviderImpl} class.
+ * </p>
+ * 
+ * @author <a href="mailto:sguilhen at redhat.com">Stefan Guilhen</a>
+ */
+public class RoleBasedACLProviderUnitTestCase extends TestCase
+{
+
+   private Resource[] resources;
+
+   private Identity identity;
+
+   private final ACLPersistenceStrategy strategy = new JPAPersistenceStrategy();
+
+   @Override
+   protected void setUp() throws Exception
+   {
+      super.setUp();
+      // build the test resources.
+      this.resources = new Resource[2];
+      for (int i = 0; i < resources.length; i++)
+         resources[i] = new TestResource(i, "Test Resource " + i);
+
+      // Identity 'john' has two roles (role1 and role2).
+      Role role1 = RoleFactory.createRole("role1");
+      Role role2 = RoleFactory.createRole("role2");
+      RoleGroup roleGroup = RoleFactory.createRoleGroup("RoleGroup");
+      roleGroup.addRole(role1);
+      roleGroup.addRole(role2);
+      this.identity = IdentityFactory.createIdentityWithRole("john", roleGroup);
+
+      // create the ACLs for the resources.
+      ACLEntry entry1 = new ACLEntryImpl(BasicACLPermission.READ, "role1");
+      ACLEntry entry2 = new ACLEntryImpl(
+            new CompositeACLPermission(BasicACLPermission.READ, BasicACLPermission.UPDATE), "role2");
+      ACLEntry entry3 = new ACLEntryImpl(new CompositeACLPermission(BasicACLPermission.values()), "role3");
+      List<ACLEntry> entries = new ArrayList<ACLEntry>();
+      entries.add(entry1);
+      entries.add(entry2);
+      entries.add(entry3);
+      this.strategy.createACL(this.resources[0], entries);
+
+      // the second ACL uses the identity name.
+      entry1 = new ACLEntryImpl(BasicACLPermission.READ, "ritchie");
+      entry2 = new ACLEntryImpl(new CompositeACLPermission(BasicACLPermission.values()), "john");
+      entries = new ArrayList<ACLEntry>();
+      entries.add(entry1);
+      entries.add(entry2);
+      this.strategy.createACL(this.resources[1], entries);
+   }
+
+   /**
+    * <p>
+    * Tests the behavior of the {@code isAccessGranted} method, which uses the identity's roles to check whether
+    * access to the resource should be granted or not.
+    * </p>
+    * 
+    * @throws Exception if an error occurs while running the test.
+    */
+   public void testACLProvider() throws Exception
+   {
+      // create the RoleBasedACLProvider instance.
+      ACLProvider provider = new RoleBasedACLProviderImpl();
+      provider.setPersistenceStrategy(this.strategy);
+
+      // as john has role 2, he should be able to update resource 0.
+      assertTrue(provider.isAccessGranted(this.resources[0], this.identity, BasicACLPermission.UPDATE));
+      // none of john's roles has DELETE permission, so he should not be able to delete resource 0.
+      assertFalse(provider.isAccessGranted(this.resources[0], this.identity, BasicACLPermission.DELETE));
+
+      // now create a new identity for john that has no roles. The role-based provider should now use the
+      // identity name (default impl) when checking for permissions.
+      Identity identity = IdentityFactory.createIdentity("john");
+      assertTrue(provider.isAccessGranted(this.resources[1], identity, new CompositeACLPermission(BasicACLPermission
+            .values())));
+      // access should be denied to resource 0, as that one has an ACL based on the roles.
+      assertFalse(provider.isAccessGranted(this.resources[0], identity, BasicACLPermission.READ));
+   }
+
+}

Modified: projects/security/security-jboss-sx/branches/Branch_2_0/parent/pom.xml
===================================================================
--- projects/security/security-jboss-sx/branches/Branch_2_0/parent/pom.xml	2009-03-05 18:55:48 UTC (rev 85319)
+++ projects/security/security-jboss-sx/branches/Branch_2_0/parent/pom.xml	2009-03-05 18:57:05 UTC (rev 85320)
@@ -133,6 +133,6 @@
 
   <properties>
     <org.jboss.javaee.version>GA</org.jboss.javaee.version>
-    <org.jboss.security.spi.version>2.0.2.SP7</org.jboss.security.spi.version>
+    <org.jboss.security.spi.version>2.0.2-SNAPSHOT</org.jboss.security.spi.version>
   </properties>
 </project>




More information about the jboss-cvs-commits mailing list