AZN Concepts
The authorization engine allows administrators to specify which resources may be accessed by a given user. This access is conditional. The condition is defined by means of one or more rules that are associated with the resources. If no rule exists for a particular resource, then access is automatically denied.
The authorization engine supports attribute-based authorization. This means that the engine takes a resource as input, as well as a list of attributes with relevant information about the user, and applies the rules to the resource and the attributes. The user attributes may not only contain attributes identifying the user, but they may also include additional data, such as contextual information. The attributes are represented as a JSON-like object.
The authorization engine is available as a service within TrustBuilder. When the rules have been defined, they may be exported to the TrustBuilder server hosting the authorization service.
The authorization administration tool supports the administrator in this process. First, the user interface allows administrators to declare a list of relevant resources. Then rules may be linked to these resources. Finally, the rules may be exported to the appropriate TrustBuilder servers.
Resources
Each resource has the following attributes:
a non-empty domain, which provides a scope for one or more resources;
a non-empty name, which must be unique within the domain;
a flag specifying if the domain-resource combination will be matched literally.
When the auhorization service starts up, it registers the resources with rules (technically a rule suite). If multiple resources with the same domain-name-flag combination exist, only the last registered resource will be retained.
Resource matching
When the authorization engine attempts to validate access to an input resource, it first tries to locate the rules linked to an 'exact match' resource equal to the input resource. If no such matching resource is found, the engine searches for rules linked to a 'non-exact-match' resource with longest matching prefix.
Example
Registered resources:
A - exact
AB - not exact.
Resources to validate:
A matches resource 1. Access is decided by the rules.
AB matches resource 2. Access is decided by the rules.
ABC matches resource 2. Access is decided by the rules.
AD matches no resource. Access is denied.
Rule suites
Rules linked to a resource are grouped into a rule suite. Rule suites support more sophisticated use cases, but in the context of the current authorization tool, we equate a rule suite with an ordered list of rules. Resources are thus actually linked to rule suites, not to individual rules.
Multiple resources may be linked to the same rule suite, but a resource may only be linked to one rule suite at a time. This implies that rules within a rule suite can be applied to multiple resources, allowing us to share business logic across resources.
The rule suite may also define optional policy information points (PIP's). PIP's allow the rules to use additional data retrieved from external services, based on the input data.
Rules
Each rule has the following structure:
an optional condition (a null condition is considered to be true);
an assertion that must be true if the condition holds;
an optional list of hints, which return extra information (e.g. the client should step up to another authentication level).
Semantics of rules
The first two elements of a rule translate into the following logical statement.
if the condition is true then the assertion must be true
In other words, the rule only fails if the condition is true while the assertion is false.
Note A rule may also fail in case of errors, e.g. when trying to perform operations on data of the wrong type.
Semantics of rule suites
From the semantics of rules, we derive the semantics of rule suites.
A rule suite succeeds if:
all the rules succeed;
at least one rule has a true condition.
The second requirement states that access to a resource must always be granted explicitly: it is not enough that no rule fails. As a corollary, rule suites with an empty rule list always fail.
When the rule suite succeeds, a score of 1 is returned. Otherwise the score is 0.
Lazy evaluation
The execution of a rule or of a rule suite stops as soon as the score can be determined with certainty. For instance, when a rule fails, we know that the rule suite will fail as well.
Conditions and assertions
A rule condition and assertion have the same structure. They both consist of a sequence of tests. These tests are combined in four ways: AND, OR, NOT AND, NOT OR.
Each test consists of a function with zero or more parameters. Each parameter is a constant (like a string or a number), a reference to a variable, or a JSON-like document containing a reference to a variable as one of its values.
Functions
The following functions are currently supported.
One-parameter functions
Function | Description |
---|---|
isBoolean | Tests if the value is a Boolean |
isDocument | Tests if the value a document (JSON-like object) |
isEmpty | Tests if the value is an empty list or string |
isError | Tests if the value is an error (document) |
isNil | Tests if the value is nil |
isNotEmpty | Tests if the value is a not an empty list or string |
isNotNil | Tests if the value is not nil |
isNumber | Tests if the value is a number |
isSequence | Tests if the value is a list (JSON-like array) |
isString | Tests if the value is a string |
Two-parameter functions
Function | Description |
---|---|
= | Tests if the first number equals the second number |
< | Tests if the first number is less than the second number |
Tests if the first number is less than or equal to the second number | |
Tests if the first number is greater than or equal to the second number | |
Tests if the first number is greater than the second number | |
contains: | Tests if the left (interval specified by a list of two numbers) contains the right value |
containsAll: | Tests if the left (interval specified by a list of two numbers) contains the right interval |
ContainsAny: | Tests if the left (interval specified by a list of two numbers) overlaps the right interval |
ContainsNone: | Tests if the left (interval specified by a list of two numbers) does not intersect the right interval |
ContainsNot: | Tests if the left (interval specified by a list of two numbers) does not contain the right value |
ContainsNotString: | Tests if the left (interval specified by a list of two strings) does not contain the right value |
containsString: | Tests if the first string contains the second string |
endsWith: | Tests if the first string ends with the second string |
endsNotWith: | Tests if the first string does not end with the second string |
equals: | Tests if the first string equals the second string |
equalsIgnoreCase: | Tests if the first string equals the second string, ignoring case |
equalsNot: | Tests if the first string does not equal the second string |
equalsNotIgnoreCase: | Tests if the first string does not equal the second string, ignoring case |
includes: | Tests if the left (list) includes the right value |
includesAll: | Tests if the left (list) includes all the right values (list) |
includesAny: | Tests if the left (list) includes any of the right values (list) |
includesNone: | Tests if the left (list) includes none of the right values (list) |
includesNot: | Tests if the left (list) does not include the right value |
matches: | Tests if the left (string) matches the right (regular expression) |
matchesIgnoreCase: | Tests if the left (string) matches the right (regular expression), ignoring case |
startsWith: | Tests if the first string starts with the second string |
startsNotWith: | Tests if the first string does not start with the second string |
Three-parameter functions
Function | Description |
---|---|
isNear:range: | Tests if the first value (a geo-point of the form {'lat': xyz, 'lon' : xyz}) is within *range* meters of the second geo-point |
Rule hints
In addition to the score, a rule may also return a list of hints. By default, the hints are only generated when the rule fails, unless a flag instructs the rule to generate the hint regardless of the rule score.
Variables
Pre-defined variables
Each rule has access to two pre-defined variables.
Variable | Description |
---|---|
resource | This variable contains the qualified resource (domain/resource name) that the client wishes to access. |
in | This value contains a JSON-like document containing attributes that may provide (contextual) information about a user. |
User-defined variables
In addition to the pre-defined variables, user-defined variables may be added in two ways:
to capture the result of a Policy Information Point (aka PIP) request (the variable name is the name of the PIP);
to memoize the score of a rule (variable defined by the optional result attribute of the rule).
Accessing variables
Rules can access a variable by using the following syntax:
$A.x.y.z
where A refers to a variable, and the optional path x.y.z describes a path in a document if the variable holds a document.
Example 1
Suppose to test that the resource variable contains the a path starting with prod/users/, then we can use the following function.
$resource startsWith: prod/users/
Example 2
Suppose that the input variable in contains the following document.
{
"user-id" : "John Doe",
"department" : "HR"
}
Then we can test if the user works in the HR department with the following function.
$in.department equals: HR
PIPs
Policy information points allow the rules to retrieve additional information related to the input data. PIP's have the following attributes:
a non-empty (variable) name;
a TrustBuilder workflow or component id;
a JSON-like document providing the input to the workflow.
The name acts like a variable and may not overlap with other pre-defined or user-defined variables. The variable will hold the result of the workflow call. In this workflow, external services may be accessed to compute the proper response, which is also a JSON-like document.
The value of the PIP variable is computed at most once within the execution of a rule suite, according to the following rules: * if the variable is not needed to calculate the score, the external call will not be performed, i.e. computation is strictly on demand; * once the value has been computed, it is cached for the duration of the rule suite execution.