Apache Muse - Add WSRF Service Groups to an Endpoint
WSRF service groups provide a way to create resource directories that clients can easily search to find the resource(s) they need to manipulate. Adding a service group to Muse-based applications is as easy as adding some boilerplate XML to your muse.xml file. The only real thought required is when you want to limit (filter) the resources that can belong to a service group - this requires you to define membership content rules for your service groups. We will discuss membership content rules after we demonstrate basic service group usage.
To add service groups to your application, you must add the XML in this file to your application's muse.xml file. This XML contains the definitions for two resource types: WSRF ServiceGroup and WSRF ServiceGroupEntry. For details on how these two resource types work together, please review the documentation for the the WSRF ServiceGroup capability.
After updating your muse.xml file, you must also add the WSDL and XSD files for the WSRF ServiceGroup specification to your application's WSDL directory (by default, this is /WEB-INF/classes/wsdl). You can find these files here.
At this point you now have the ability to create service groups that will accept any other resource into their directory. If you create one service group resource using the Muse persistence layer, it will add all other resources in your application to its membership as they are created (conversely, it will remove resources from its membership as they are destroyed). You can see what resources are in your service group using the following client code:
import java.net.URI;
import org.apache.muse.ws.addressing.EndpointReference;
import org.apache.muse.ws.resource.sg.remote.ServiceGroupClient;
...
//
// Create a client for our service group resource
//
URI serviceGroupURI = URI.create("http://localhost/my-app/services/service-group");
EndpointReference serviceGroupEPR = new EndpointReference(serviceGroupURI);
//
// Add reference parameters if necessary...
//
// serviceGroupEPR.addParameter(...);
//
ServiceGroupClient serviceGroup = new ServiceGroupClient(serviceGroupEPR);
serviceGroup.setTrace(true);
//
// Get client objects for every resource inside the service group
//
WsResourceClient[] members = serviceGroup.getMembers();
//
// Print the EPRs of the members
//
System.out.println("Here are the members of your service group:\n");
for (int n = 0; n < members.length; ++n)
System.out.println(members[n].getEndpointReference());
If you want to make your service group more exclusive, you can do so by adding membership content rules to it (a service group with no rules allows any resource to be a member). A membership content rule is a list of one or more resource properties that a potential member must have in order to be allowed in the service group; the use of resource properties allows the service group to reason about what capabilities the resource supports and, thus, what kind of resource it is.
You can add membership content rules declaratively or programmatically. The declarative method is easiest, as you don't have to recompile your code each time you want to tweak your service group's criteria. You can add the rules to your service group by adding "static values" to your service group's metadata document (RMD document). Adding the following to a service group's RMD document will load the membership content rules during service group initialization and force the service group to check the resource's eligibility (using WSRP) before adding it.
<Property name="wsrf-sg:MembershipContentRule" mutability="constant" modifiability="read-only">
<InitialValues>
<wsrf-sg:MembershipContentRule ContentElements="muws1:ResourceId muws2:Version myns:SomeProperty"/>
</InitialValues>
</Property>
The XML above adds one rule to the service group. That rule requires each member resource to have a certain three properties in order to be added. If the resource does not have these properties in its WSRP document, it will not be allowed in. You can add as many rules as you like, with as many properties as you like in the ContentElements attribute. Just make sure that the prefixes you use in the property names in ContentElements are defined in the RMD document.
Alternatively, you can create the membership content rules programmatically. You can either use the ServiceGroup.setMembershipContentRule() method to add the rules during initialization or you can sub-class Muse's default service group implementation, org.apache.muse.ws.resource.sg.impl.SimpleServiceGroup, and override the createMembershipContentRules() method. This will allow you to create the rules as part of service group initialization without having to rely on other resources or capabilities. In either case, you will need to create instances of org.apache.muse.ws.resource.sg.MembershipContentRule to represent your rules; you can use the default implementation, named org.apache.muse.ws.resource.sg.impl.SimpleMembershipContentRule. This class will allow you to set the names of the properties at runtime without declaring them during design time.