Overview of Grouper Permission Limits
Grouper permission limits are used to set up runtime constraints on permissions. You can limit a permission to a condition in the environment or data passed to Grouper. Note, limits can only apply to permissions which are allowed, not disallowed.
A limit is an attribute of type limit assigned on the permission assignment, or assigned to the role membership, or assigned to the role.
At runtime, Grouper, or custom logic, or the caller of the API or WS could set environment variables for the request that the limit logic can use.
You may want to review the permission limit built-in implementations to see if any of them apply to your use case.
See also the Access Management Features Overview page for guidelines of when to use rules, roles, permission limits, and enabled / disabled dates.
For instance, a built-in limit expression language could be (note, you set the Root folder where Grouper creates built in things, in this case it is school:etc):
When it is assigned, the value could be:
Those limits would take the environment variables available to the limit, and put them as EL variables.
There could be helper variables or classes to do common things (in this case no arguments are required, though the caller could override)...
Or here the caller passes the user's ip address (ipv4 still :) )
In the grouper.properties you could configure other helper classes that are in scope in the expression language
In the grouper.properties you could associate custom limits with subclass of a limit base clase (or an implementation of a Java interface) to take the environment variables, the value of the limit attribute, and other data about the calculation, and give an answer.
The UI for limits has type checking for values, and validates the inputs.
If there are errors, the exception will be thrown so the caller can see what is going on without looking in the server logs.
The UI can set environment variables to simulate a real query and see the red/green results
For each limit, you need to associate a logic class. You can do this with Java. The Grouper administrator needs to register the implementation, though in the future we could do this with JSON/EL (Expression Language) where the admin does not need to help.
Generally you should extend the edu.internet2.middleware.grouper.permissions.limits.PermissionLimitBase class. If you really want to implement an interface, you can implement edu.internet2.middleware.grouper.permissions.limits.PermissionLimitInterface, though if more methods are added with default implementations, you will have to change your code when you upgrade Grouper. Here are the methods:
Register the limit attribute definition name with the logic class in the grouper.properties:
If the attribute definitions of the limits are not set correctly (e.g. so the same subjects who can READ the permissions can READ the limits), then if limit security worked like Grouper security, then the limits would not be seen and a wider set of ALLOWs would potentially occur than should. So... if you are reading permissions, and processing limits, or reading limits, you will see them if you can see the permissions. Note, the limit execution context is not as GrouperSystem, so if there is something in there that doesnt work, it should throw an exception or return false.
The Logic implementation can cache the result per the limit, limit values, and env variables. Note that if there are other data used in the logic (e.g. based on the subject the permission is for), that you shouldnt cache with this strategy, you should use your own caching or dont cache. Also, note if you want a configurable cache, just return a number from GrouperConfig.getPropertyInt(). Normally this is just a boolean, cache for a few minutes, or dont cache at all.
Limit assignment types
The obvious place to assign limits would be on permissions assignments. You can do this in Grouper, but you can also assign limits to other objects to make more general limits. For instance, here is a limit assigned to a permission assignment
If you want to assign a limit to a role, then all permissions assignments to that role, or permissions assignments to individuals in the context of that role will inherit that limit. This way you do not have to assign the limit to all permissions assignments for that role. Note, there is no way to change this limit further down the inheritance chain, all subjects in this role will have this limit. However, if you have custom logic, and you want to have an algorithm to do this, it is possible.
If you want to assign a limit to all the permissions for a user in a role, you can assign it to the AnyMembership (immediate or effective) of a subject and role.