Tapestry IoC has two specific areas where it must put some form of contribution into a specific order:
- Ordered Configurations, where different modules may contribute into a service's configuration
- Service Decorators which must be applied to services from a number of modules.
In both these cases, objects (either contributions to a configuration, or decorators) are assigning qualified IDs, simple IDs qualified with the containing/contributing module's ID.
Because the contributions can come from different modules, and there isn't a specific order in which the service contribution methods are invoked, there is no natural ordering of the contributed objects.
To resolve this, constraints are applied to each contribution. These constraints control what other objects must come before a contribution or after it.
The constraints are specified using the @Order annotation (for service decorator methods), or as variable arguments at the end of the add() method for ordered configurations.
Often a single contribution will have more than one constraint.
Each constraint string begins with a prefix, before: or after:, used to identify the type of constraint.
The remainder of the constraint string is a comma-separated list of patterns. The contributed object will be ordered before or after the contributions identified by the patterns.
A constraint match pattern is used to select one or more objects by their ID.
Match patterns support a very simple kind of wildcard matching. A * (asterisk character) may appear at the start and/or end of the pattern, and it will match zero or more characters there. Thus you can have patterns such as Data* or *Logic or even *User*.
Matching is case insensitive.