At EclipseCon 2011, the next release of the core OSGi platform were announced and made available as a public final draft, with the released document happening in the near future. BJ Hargrave gave a presentation on what's new in OSGi 4.3, which sums up the key differences between it and previous releases.
Generics
One of the most anticipated features is the addition of generics to the core OSGi API. This allows type-safe operations to look up (say) services of a specific type, instead of having to do casts. However, since OSGi needs to run on embedded (pre-1.5) VMs, it was not possible to use a 1.5 compiler to build the core APIs. Instead, a largely forgotten option, -target jsr14
allows Java code with generics to be compiled but run on a 1.4 compatible JRE. This option was originally introduced as part of the transition for Generics in JSR 14, but still exists in today's compilers. This permits client code (compiled against either 1.4 with -target jsr14
, or 1.5 and above) to refer to services such as:
// OSGi 4.2 way // ServiceReference ref = context.getServiceReference( // LogService.class.getName()); // LogService log = (LogService)context.getService(ref); // OSGi 4.3 way ServiceReference<LogService> ref = context.getServiceReference( LogService.class); LogService log = context.getService(ref);
However, since the core is not fully Java 1.5 then other features (such as enum
and annotations) have not been used.
Capabilities
The traditional unit of dependency in an OSGi environment is either package or bundle dependencies (through Import-Package
or Require-Bundle
). Although these dependencies work fine for code, they are not very good at representing non-code dependencies. For example, a bundle might need a certain amount of memory or the presence of a webserver, neither of which may be represented as a specific package or bundle.
OSGi 4.3 introduces the notion of generic capabilities, which can be used with Require-Capability
and Provide-Capability
. Non-optional capability requirements must be satisfied before a bundle can be resolved. A typical use-case for this is for the provision of OSGi Declarative Services, which aren't represented as a package dependency but may still be required in order for a bundle to be resolved correctly.
In addition, the minimum required version can be exposed as a capability requirement:
// Old way // Bundle-RequiredExecutionEnvironment: JavaSE-1.6 // New way Require-Capability: osgi.ee;filter:="(&(osgi.ee="JavaSE")(version>=1.6))"
As a result of this generalisation, the Bundle-RequiredExecutionEnvironment
has been deprecated (but still available) in OSGi 4.3.
Remote Services
OSGi Remote Services aren't new (they were chapter 13 in OSGi 4.2 compendium) but they have been promoted to the OSGi 4.3 Core specification. As a result, all OSGi 4.3 runtimes will have support for Remote Services.
Adapting
Some services, like PackageAdmin
, were used to provide meta information about a bundle but without polluting the bundle's interface with type-specific accessors. This typically resulted in boiler-plate code to find out how a bundle was wired up, or what its start level was.
To simplify matters, OSGi 4.3 introduces an adapt(Class)
method on Bundle
. Much like Eclipse's IAdaptable pattern, this allows a Bundle
to be converted into known type. In essence, if the bundle knows how to convert itself into the given type, an instance will be returned; if not (or permissions prevent it) then null
is returned instead. This simplifies PackageAdmin
and StatLevelAdmin
as follows:
BundleWiring wiring = bundle.adapt(BundleWiring.class); // wiring.getRequirements(null) BundleStartLevel bsl = bundle.adapt(BundleStartLevel.class); // bsl.getStartLevel()
The existing services will remain but general users are encouraged to use the new adapt pattern for ease of implementation.
Weaving
Weaving support has also been formalised, which permits extensions to plug into the class loading mechanisms of other bundles. This technique is used by some runtime systems – particularly those implementing JPA or other database backed persistence stores – in order to create code used specifically for that particular class type. The Weaving hook allows a standard mechanism to be in place for OSGi frameworks, which previously used a provider-specific mechanism.
Nested frameworks no more
Although a trial implementation has been available in Equinox for a while, the nested frameworks support (where a framework can launch nested versions) has not been put forward as part of the 4.3 specification.
Instead, a more powerful BundleHook
and ResolverHook
API has been created, which allows an extension to create virtual sets of bundles to hide bundles from one another. This follows the ServiceHook
which has been previously available which allows services to be hidden from others.
It is thus possible to emulate nested frameworks by creating bundle groups who cannot see each other. This has been used to implement the new Virgo region model has been reworked to support this new model.
A side effect means that it's now possible to install multiple versions of the same bundle/version pair in the same framework, provided that these are hidden from each other. Previously, it would be an error to attempt to install the same bundle a second time. This won't be enabled by default, but it will be possible to mark a bundle as being capable of doing this with an attribute org.osgi.framework.bsnversion=multiple
in the properties when launching framework. By default, it is set to org.osgi.framework.bsnversion=single
.
Summary
The new OSGi specification will bring a number of useful features for the framework; for those bundles which don't need to support older frameworks, the use of the new generic API is likely to be a big reason for switching over. The nested frameworks and weaving is unlikely to have a direct effect, but those implementing lower level libraries will switch over to using standardised hooks, which will increase the platform interoperability between different OSGi frameworks.
The specification is not yet officially released, but is expected to be available prior to this year's Eclipse release, since Equinox 3.7 is likely to be declared the reference implementation.