Title: OSGi Enablement for Tuscany
1OSGi Enablement for Tuscany
2Overview
3Motivations
- Provide modularity for Tuscany to
formalize/enforce the SPI contracts and minimize
the package dependencies across modules - Enable Tuscany to work with OSGi environment such
as JEE application servers, Eclipse RCP or Spring
DM - Provide versioning and isolation so that Tuscany
extensions can depend on different versions of
the same library - Provide lifecycle management for extensions
install/uninstall/start/stop a module
4Objectives
- Tuscany runtime will be able to run in both
non-OSGi and OSGi environment - No OSGi APIs should be used for non-OSGi specific
modules - Build a consistent OSGi story to facilitate
developing, building, launching, running and
testing Tuscany - Makes developers life a bit easier to work with
OSGi
5What problems do we try to solve?
- Turning Tuscany modules into OSGi bundles
- Turning 3rd party dependencies into OSGi bundles
- Developing, building, launching, running and
testing with OSGi - Producing distributions that are compatible with
the OSGi bundle structure in an efficient way (in
one-two minutes)
6Turning Tuscany modules into OSGi bundles
7Creating bundles for Tuscany modules
- Modularize Tuscany after the maven modules
- One OSGi bundle per maven module
- Be consistent for build, packaging and runtime
- Much easier to aggregating than decomposing
- Developers are responsible for authoring and
maintaining MANIFEST.MF (instead of MF generation
tools) - Tooling friendly
- Developers pay more attentions to the dependencies
8Things to consider to create an OSGi bundle for a
module
- Add META-INF/MANIFEST.MF (dont stop here )
- Clean up module dependencies and package
visibilities - Prepare for code changes
- Service Discovery
- ClassLoading
9Rules of thumb
- Identify the absolutely necessary SPI packages
that need to be exported - Don't try to export everything
- For model modules, try to only export the package
that contains the interfaces - Try not to export any package from the
xxx-runtime moudles - Any classes that can be accessed via the
ExtensionPointRegistry using interfaces should
not be exported - Only import other packages when it's needed
- For example, we used to have a lot of modules
pull in assembly for just a constant for the SCA
namespace - Avoid DynamicImport-Package
- Avoid Require-Bundle
- Do not export "private" packages as a workaround
or hack which can fail the "clean SPI". Refactor
things into SPIs if necessary
10Granularity Discussion
- 180 bundles cumbersome
- Multiple bundles required to enable one
capability - Much debate about right level of granularity
(flexibility vs. usability) - Some opinions
- Fine-grained bundles suitable for developer view
- Features/Profiles used to group bundles to
provide a user view - Inspired by Eclipse Features
11Dealing with 3rd party jars
12Handling 3rd party jars
- We have to live with the reality
- Many 3rd party jars are not OSGi bundles. No repo
is available to get all converted bundles - We need to convert them (build time, run time)
- Some of the 3rd party bundles are broken (w/
bogus MF) - We need to fix them (replacing the MF)
- More and more 3rd party jars are upgraded to be
OSGi bundles - We should be able to incrementally consume 3rd
party jars as OSGi bundles
13Converting 3rd party jars to OSGi bundles
- A folder bundle is created to represent a 3rd
party jar - The folder structure looks like
- jaxb-impl-2.1.12
- META-INF
- MANIFEST.MF
- jaxb-impl-2.1.12.jar
- It is non-invasive and flexible
- The original jar is not changed (avoid legal,
signature issues) - Multiple jars can be easily aggregated (control
the bundle granularity) - The MANIFEST.MF can be easily customized
OSGi Framework
MANIFESTBundle-Classpath third-party.jar Dynamic
-Import-Package Export-Package ... ...
third-party-osgi.jar
MANIFESTBundle-Classpath third-party.jar Import-
Package ... Export-Package ... ...
Install
third-party.jar
third-party.jar
third-party.jar
14Sample META-INF/MANIFEST.MF
- Manifest-Version 1.0
- Bundle-ManifestVersion 2
- Bundle-SymbolicName com.sun.xml.bind.jaxb-impl
- Bundle-Name com.sun.xml.bind.jaxb-impl
- Bundle-Version 2.1.12
- DynamicImport-Package javax.transactionversion"
1.1",javax.transacti - on.xaversion"1.1",
- Bundle-ClassPath jaxb-impl-2.1.12.jar
- Export-Package com.sun.xml.bind.v2.schemagenvers
ion2.1.12,com.sun.x - ml.bind.v2.utilversion2.1.12,com.sun.xml.txw2.a
nnotationversion2. - 1.12,com.sun.xml.bind.v2.model.runtimeversion2.
1.12,com.sun.xml.bin - d.v2.runtimeversion2.1.12,com.sun.xml.txw2.outp
utversion2.1.12,co - m.sun.xml.bind.v2version2.1.12,com.sun.istackv
ersion2.1.12,com.su - n.xml.bind.v2.runtime.propertyversion2.1.12,com
.sun.xml.bind.v2.run - time.unmarshallerversion2.1.12,com.sun.xml.bind
.v2.model.navversio - n2.1.12,com.sun.xml.bind.marshallerversion2.1.
12,com.sun.xml.bind. - v2.runtime.reflect.optversion2.1.12,com.sun.xml
.bind.v2.runtime.out - putversion2.1.12,com.sun.xml.txw2version2.1.1
2,com.sun.xml.bind.v - 2.schemagen.xmlschemaversion2.1.12,com.sun.xml.
bind.v2.runtime.refl
15Developing Tuscany with OSGi
16Checking out source code and building with maven
- Check out the Tuscany source code from SVN
- svn co https//svn.apache.org/repos/asf/tuscany/ja
va/sca/ - Run maven build
- mvn clean install -fn
- Generate Eclipse projects
- mvn -Peclipse
17Setting up Eclipse PDE
- Download Eclipse (w/ plugin development)
- http//www.eclipse.org/downloads/download.php?file
/technology/epp/downloads/release/galileo/SR1/ecl
ipse-jee-galileo-SR1-win32.zip - Configure PDE target platform
- File ? Open File
- lttuscanygt\sca\distribution\all\target\features\tus
cany-pde35.target - Click on Set as target platform
- Load Tuscany modules into Eclipse
- File ? Import ? General ? Import Existing
Projects
18Whats happening during the Tuscany build?
- Validating OSGi constraints to report bundle
resolution issues during compilation - Generating PDE project so that Tuscany modules
can be loaded in Eclipse to leverage the nice
OSGi tooling - Generating OSGi bundles for 3rd party jars
- Generating PDE target platform definitions so
that 3rd party bundles can be used in Eclipse as
plugin dependencies - Generating Equinox configuration so that Tuscany
distribution can be directly loaded as an OSGi
framework
19Maven/OSGi Tools provided by Tuscany
- Maven-bundle-plugin
- Generates bundles for 3rd party jars
- Generates OSGi enabled PDE projects
- Version 1.0.4 released at 10/09/2009
- Maven-eclipse-compiler
- Expose OSGi aware Eclipse JDT compiler
- Expose Eclipse OSGi bundle validation
- Version 1.0.1 released on 04/07/2009
- Maven-osgi-junit-plugin
- JUnit tests in a OSGi enabled environment
- Version 1.0 released on 10/28/2009
- https//svn.apache.org/repos/asf/tuscany/maven-plu
gins/trunk/
20Development Time
- Eclipse PDE provides nice OSGi tooling
- Graphical editor for MANIFEST.MF (w/ additional
tools to analyze/calculate dependencies) - Plugin Dependencies Classpath Container
- Compilation errors/warning for OSGi constraint
violations (w/ Quick Fix suggestions) - OSGi test environment to validate and launch OSGi
framework (w/ console)
21Runtime
- Provide a SCA node launcher to start an OSGi
runtime and run SCA application with the
OSGi-enabled Tuscany runtime - We need to use Tuscany's service discovery
mechanism to discover and instantiate the
factories - Change how JDK factories such as XMLInputFactory,
XPathFactory, and DocumentBuilderFactory, are
discovered and instantiated - XMLInputFactory.newInstance() used the JSE
service provider pattern which doesn't work with
OSGi - Adjust the code that assumes there is a flat
thread context classloader that can access all
the classes in the Tuscany runtime - With OSGi, there is a network of classloaders
(one classloader per module) and the class
visibility is constrained by the OSGi headers
such as Import-Package and Export-Package - The classloader for the current class is a good
starting point for Class.forName() with OSGi
22Launching OSGi framework within Eclipse PDE
23Launching OSGi from Tuscany distribution
- Equinox
- java -jar osgi-3.5.0-v20090520.jar -clean
-console -configuration ..\features\configuration - http//cwiki.apache.org/confluence/display/TUSCANY
xDOCx2x/RunningTuscanySCA2.xwithEquinoxandF
elix
24Testing Tuscany with OSGi
25A few options
- Tuscany maven-osgi-junit plugin
- Generate two bundles for the main and test
classes respectively. The test bundle is a
fragment of the main bundle. - For example, the plugin generates the following
bundles for sample-calculator-osgi.jar
sample-calculator-osgi-osgi.jar
sample-calculator-osgi-osgi-tests.jar - Find the EquinoxHost class from
tuscany-node-launcher-equinox and create an
instance - Start the equinox runtime
- Set up the classloader for surefire so that it
uses OSGi classloading for the test cases with
the test bundle. - Delegate to surefire to run the unit tests
- Apache Felix junit4osgi
- http//felix.apache.org/site/apache-felix-ipojo-ju
nit4osgi.html
26Trouble-shooting OSGi related issues
27Common traps
- System packages need to be explicitly imported,
such as javax.xml.namespace - Be careful of TCCL (ThreadContext Classloader)
- No well-defined TCCL in OSGi
- Equinox uses ContextFinder to find the closest
class on the calling stack that is loaded by an
OSGi bundle - JDK and some 3rd party libraries uses service
discover pattern relying on TCCL being able to
load/see everything
28Some tips
- Most common exceptions
- ClassNotFoundException
- NoClassDefFoundError
- Bundle is not resolved
- Missing Import-Package (including system packages
from the JDK) - Split package from Export-Package
- Different versions of the same package are
exported - Chain of bundle resolution (Exported packages
from unresolved bundle cannot be seen.)
29Useful Links
- http//cwiki.apache.org/autoexport-2.2.9/TUSCANYxD
OCx2x/osgi-enablement-for-tuscany-runtime.html - Infoq.com articles
- http//www.infoq.com/articles/modular-java-what-is
-it - http//www.infoq.com/articles/modular-java-static-
modularity - http//www.infoq.com/articles/modular-java-dynamic
-modularity - http//www.dynamicjava.org/