Use OSGi applications as SCA component implementations
We can use an OSGi application as a Service Component Architecture (SCA) component.
Identify the OSGi application to use as an SCA component. An OSGi application is a collection of OSGi bundles that use the Blueprint component model to expose or consume services. An OSGi application contains an application manifest that declares the following services:
- Services that the application provides that can be accessed from outside the application
- Services that the application wants to consume from outside the application
We can use SCA to provide service bindings for these services.
To provide service bindings using SCA, do the following:
- Modify an OSGi application to provide or use remote services.
- Write an SCA composite definition that uses an OSGi application as a component implementation, and provide bindings for its remote services.
An OSGi application declares external services in the Application-ImportService and Application-ExportService statements of its application manifest, which is provided in the META-INF/APPLICATION.MF file of the enterprise bundle archive (EBA). The Application-ExportService statement declares remote services provided by the OSGi application. The Application-ImportService statement declares services on which the OSGi application depends. All services specified in the application manifest are remotable.
- Create an implementation.osgiapp component in an SCA composite definition.
Implementation.osgiapp component type and set applicationSymbolicName and applicationVersion to values that match the Application-SymbolicName and Application-Version attributes in the application manifest.
For example, suppose the OSGi application manifest, the META-INF/APPLICATION.MF file, contains the following headers:
Application-SymbolicName: helloworldApp Application-Version: 1.0.0Configure a component that references these headers in an SCA composite definition; for example:
<?xml version="1.0" encoding="UTF-8"?> <composite xmlns="http://www.osoa.org/xmlns/sca/1.0" xmlns:scafp="http://www.ibm.com/xmlns/prod/websphere/sca/1.0/2007/06" targetNamespace="http://www.example.com" name="HelloWorldComposite"> <component name="HelloWorldComponent"> <scafp:implementation.osgiapp applicationSymbolicName="helloworldApp" applicationVersion="1.0.0"/> </component></composite>The implementation.osgiapp element requires the use of an XML namespace prefix that is associated with the "http://www.ibm.com/xmlns/prod/websphere/sca/1.0/2007/06" namespace.
The applicationVersion attribute is optional. We can add it to ensure that a particular version of an OSGi application is used.
- Identify Blueprint services to be made available remotely.
- Edit the Application-ExportService header in the OSGi application manifest so that it identifies one or more service interfaces to be exported.
The following example header specifies that Blueprint services which implement and export the example.HelloWorld interface are to be made available outside the application.
Application-ExportService: example.HelloWorld
An example of a Blueprint component with such a service follows:
<blueprint xmlns="http://www.osgi.org/xmlns/blueprint/v1.0.0"> <bean id="helloWorldComponent" class="example.HelloWorldImpl" <service id="helloWorld" ref="helloWorldComponent" interface="example.HelloWorld"> <service-properties> <entry key="service.exported.interfaces" value="*"/> </service-properties> </service> </blueprint>The Blueprint service must specify the service.exported.interfaces property to identify which of its interfaces are to be exposed remotely. The value can be an asterisk (*) to indicate that all of its interfaces are available remotely, or it can be a particular interface name.
- Configure an SCA service that corresponds to each remotable Blueprint service in the component.
Use the Blueprint service id value for the SCA service name. If a Blueprint service does not have an id value, use the bean id value instead. If more than one interface is defined for the Blueprint service, for the first service interface SCA Service name use the Blueprint id value. For the second and later services, use the Blueprint id_ fully qualified interface name value for the SCA service name in the order of interfaces defined in the blueprint.xml file.
For example, add the helloWorld service that is shown in the Blueprint component from step 2a to the SCA composite definition from step 1:
<?xml version="1.0" encoding="UTF-8"?> <composite xmlns="http://www.osoa.org/xmlns/sca/1.0" xmlns:scafp="http://www.ibm.com/xmlns/prod/websphere/sca/1.0/2007/06" targetNamespace="http://www.example.com" name="HelloWorldComposite"> <component name="HelloWorldComponent"> <scafp:implementation.osgiapp applicationSymbolicName="helloworldApp" applicationVersion="1.0.0"/> <service name="helloWorld"> <binding.sca> </service> </component> </composite>The example uses binding.sca for the service binding. The service can be made available over one or more of the other bindings that SCA supports, except the EJB 2.x service binding.
The SCA service element is not required. If it is not specified, the service is made available over binding.sca by default.
- Identify services to be provided from outside the OSGi application.
- Edit the Application-ImportService header in the OSGi application manifest so that it identifies one or more service interfaces to be imported.
The following example header specifies that the example.Greeting service interface be imported:
Application-ImportService: example.Greeting
A Blueprint reference explicitly requests an imported service by filtering for the service.imported property. Remote services use pass-by-value semantics instead of pass-by-reference semantics for local services within the application. The following example shows a Blueprint component with such a reference:
<blueprint xmlns="http://www.osgi.org/xmlns/blueprint/v1.0.0"> <bean id="helloWorldComponent" class="example.HelloWorldImpl" <property name="greetingList" ref="greetingRef"/> </bean> <service id="helloWorld" ref="helloWorldComponent" interface="example.HelloWorld"> <service-properties> <entry key="service.exported.interfaces" value="*"/> </service-properties> </service> <reference-list id="greetingRef" interface="example.Greeting" filter="(&(service.imported=*))"/> </blueprint>
- Configure an SCA reference that corresponds to each imported service in the component.
Use the fully qualified interface name for the SCA reference name.
For example, add the example.Greeting reference that is shown in the Blueprint component from step 3 to the SCA composite definition from step 2:
<?xml version="1.0" encoding="UTF-8"?> <composite xmlns="http://www.osoa.org/xmlns/sca/1.0" xmlns:scafp="http://www.ibm.com/xmlns/prod/websphere/sca/1.0/2007/06" targetNamespace="http://www.example.com" name="HelloWorldComposite"> <component name="HelloWorldComponent"> <scafp:implementation.osgiapp applicationSymbolicName="helloworldApp" applicationVersion="1.0.0"/> <service name="helloWorld"> <binding.sca> </service> <reference name="example.Greeting"> <binding.sca uri="MyGreetingComponent"> </reference> </component> </composite>The example uses binding.sca for the reference binding. The reference can use one or more of the other bindings that SCA supports.
An SCA reference for an implementation.osgiapp component implicitly has 0-to-many for the multiplicity attribute (multiplicity='0..n'). This means we can wire the reference to 0, 1, or multiple services depending upon the requirements of the application. As to the multiplicity attribute:
- A blueprint reference-list element selects multiple services. The blueprint implementation cannot make any assumptions about the order of the services in the reference list compared to the order of bindings in the composite definition.
- A blueprint reference element selects a single service. If the SCA reference provides more than one binding, the selection of which binding is used is unspecified. If the SCA reference does not provide any bindings, the dependency is unsatisfied. If the reference is mandatory, the bean might not start.
We can override the multiplicity attribute on the SCA reference, setting 1-to-many ('1..n') or 1-to-1 ('1..1'), to ensure that a particular number of bindings is specified.
Results
The OSGi application is defined as an SCA component.
What to do next
Deploy the OSGi application and the SCA composite that uses the application as composition units of the same business-level application. We can use the console or wsadmin commands to create a business-level application, import the EBA file and SCA composite as assets, and then add the EBA and SCA assets as composition units to the business-level application.
Subtopics
- (dist)(zos) SCA programming model support in OSGi applications
Several features of the Service Component Architecture (SCA) programming model can be used with OSGi applications.
Related tasks
Deploy OSGi applications that use SCA Specify bindings in an SCA environment
Related information:
Develop and deploying an OSGi application