10.3.2. Configuring resources for ACL usage
Every resource class for which you wish to support ACL permissions is required to have a corresponding
PermissionHandler
. This interface is primarily responsible for the generation of resource identifier values, plus a couple of other utility methods (please refer to the API documentation for more details):
public interface PermissionHandler { boolean canHandle(Class<?> resourceClass); Serializable getIdentifier(Object resource); Class<?> unwrapResourceClass(Object resource); Set<String> listClassOperations(Class<?> resourceClass); Set<String> listInstanceOperations(Class<?> resourceClass); }
There are two ways that a resource class can be associated with a
PermissionHandler
- the first way is by providing a @PermissionsHandledBy
annotation on the resource class itself:
import org.picketlink.idm.permission.annotations.PermissionsHandledBy; @PermissionsHandledBy(CustomPermissionHandler.class) public class MyResourceClass { }
For the circumstances where it is not possible to annotate the resource class directly, the second way is to register a custom
PermissionHandler
instance for which the canHandle()
method returns true
for the resource class:
public boolean canHandle(Class<?> resourceClass) { return MyResourceClass.class.equals(resourceClass); }
Registering a custom
PermissionHandler
is very easy - simply include it in your application deployment as an @ApplicationScoped
bean, and it will be registered automatically. Here's a complete example of a PermissionHandler
that allows permissions to be assigned to arbitrary string values (this handler is actually provided by PicketLink):
@ApplicationScoped public class StringPermissionHandler implements PermissionHandler { @Override public boolean canHandle(Class<?> resourceClass) { return String.class.equals(resourceClass); } @Override public Serializable getIdentifier(Object resource) { checkResourceValid(resource); return (String) resource; } @Override public Class<?> unwrapResourceClass(Object resource) { checkResourceValid(resource); return String.class; } private void checkResourceValid(Object resource) { if (!(resource instanceof String)) { throw new IllegalArgumentException("Resource [" + resource + "] must be instance of String"); } } @Override public Set<String> listAvailableOperations(Class<?> resourceClass) { return Collections.emptySet(); } }