From Fedora Project Wiki
(Add List of execution environment that java-1.6.0-openjdk may provide + some minor modifications)
Line 1: Line 1:
= Introduction =
= Introduction =
OSGi bundles contain meta-data just like RPMs do. This meta-data can be used to automatically generate Provides and Requires similar to how it is done for mono packages. This functionality exists in Fedora's rpm-4.7.0-8.fc12 but isn't activate by default at this time (rhbz506471).
OSGi bundles contain meta-data just like RPMs do. This meta-data can be used to automatically generate Provides and Requires similar to how it is done for mono packages. This functionality exists in Fedora's rpm-4.7.0-8.fc12 ([https://bugzilla.redhat.com/506471 bz506471 ]) but isn't activate by default at this time.


BTW, I especially thank Andrew Overolt for reviewing the document and for him nice community spirit - You rocks solid guy!
BTW, I especially thank Andrew Overolt for reviewing the document and for him nice community spirit - You rocks solid guy!
Line 59: Line 59:
We can fix that problem in 3 different ways (maybe more) but I personally prefer the first one because we can stay as close as possible with upstream projects without losing the advantage of not  pulling in unneeded dependencies.
We can fix that problem in 3 different ways (maybe more) but I personally prefer the first one because we can stay as close as possible with upstream projects without losing the advantage of not  pulling in unneeded dependencies.


=== Put entire OSGi meta-data directory ''org.junit%{version}''  into the ''junit''  package as a sub-package that Requires the main package ===
=== 1. Put entire OSGi meta-data directory ''org.junit%{version}''  into the ''junit''  package as a sub-package that Requires the main package ===


<tt>junit-osgi</tt> package can contain <tt>org.junit%{version}</tt> directory and automatically require ''junit'' main package though the Bundle-ClassPath manifest entry.  
<tt>junit-osgi</tt> package can contain <tt>org.junit%{version}</tt> directory and automatically require ''junit'' main package though the Bundle-ClassPath manifest entry.  
Line 72: Line 72:
* Needs more work.
* Needs more work.


=== Create sub package for each bundles that contain OSGi meta-data ===
=== 2. Create sub package for each bundles that contain OSGi meta-data ===


We could create a sub-package that contains the <tt>/usr/lib/eclipse/dropins/jdt/plugins/org.junit%{version}</tt> directory (e.g. <tt>eclipse-jdt-junit</tt> or <tt>eclipse-junit</tt>).
We could create a sub-package that contains the <tt>/usr/lib/eclipse/dropins/jdt/plugins/org.junit%{version}</tt> directory (e.g. <tt>eclipse-jdt-junit</tt> or <tt>eclipse-junit</tt>).
Line 83: Line 83:
* Other OSGi implementations need to create symbolic links to Eclipse-specific paths.
* Other OSGi implementations need to create symbolic links to Eclipse-specific paths.


=== "Inject" OSGi meta-data into ''junit''  package ===
=== 3. "Inject" OSGi meta-data into ''junit''  package ===


This technique is used in existing Fedora packages such as [http://cvs.fedoraproject.org/viewcvs/devel/jakarta-commons-el/ jakarta-commons-el] (''commons-el-eclipse-manifest.patch'' patch).
This technique is used in existing Fedora packages such as [http://cvs.fedoraproject.org/viewcvs/devel/jakarta-commons-el/ jakarta-commons-el] (''commons-el-eclipse-manifest.patch'' patch).
Line 117: Line 117:


===Java Runtimes need to provides appropriate Named Execution Environments (not yet implemented)===
===Java Runtimes need to provides appropriate Named Execution Environments (not yet implemented)===
We can imagine the need to add provides for Execution Environments. OSGi bundles can requires ''osgi(JavaSE-1.6)''  through ''Bundle-RequiredExecutionEnvironment''  and the ''java-1.6.0-openjdk'' package can provide it.  
We can imagine the need to add provides for Execution Environments. OSGi bundles can requires ''osgi(JavaSE-1.6)''  through ''Bundle-RequiredExecutionEnvironment''  and the ''java-1.6.0-openjdk'' package can provide it.


===Why===
====Why====
The OSGi specification say in the Naming Execution Environments paragraph:  
The OSGi specification say in the Naming Execution Environments paragraph:  
''Execution environments require a proper name so that [...] A bundle can require that a Framework provides a certain execution environment before it is installed''
''Execution environments require a proper name so that [...] A bundle can require that a Framework provides a certain execution environment before it is installed''


==== List of Execution Environments that ''java-1.6.0-openjdk'' may provide ====
* OSGi/Minimum-1.1
* J2SE-1.3
* J2SE-1.4
* J2SE-1.5
* JavaSE-1.6
* Foundation-1.0 and Foundation-1.1 can also be provided with the exception that it provides some MicroEdition IO classes. These classes seems to not be used by bundles provided by Eclipse. 
FYI, There is a table containing all bundles that Eclipse 3.5 provides and their needed execution environments available in the [http://www.eclipse.org/eclipse/development/readme_eclipse_3.5.html#Appendix1 3.5 README], maybe it can be useful in the future.
====Table of most common execution environments====
====Table of most common execution environments====
{|- border="1"
{|- border="1"
Line 129: Line 139:
|-
|-
| CDC-1.0/Foundation-1.0
| CDC-1.0/Foundation-1.0
| Equal to J2ME Foundation Profile
| indicates that the bundle can only be run on Foundation 1.0 or greater. Note that with the exception of some MicroEdition IO classes, Foundation 1.0 is a subset of J2SE 1.3.
|-
| CDC-1.1/Foundation-1.1
| indicates that the bundle can only be run on Foundation 1.1 or greater. Note that with the exception of some MicroEdition IO classes, Foundation 1.1 is a subset of J2SE 1.4.
|-
|-
| OSGi/Minimum-1.1
| OSGi/Minimum-1.1
| OSGi EE that is a minimal set that allows the implementation of an OSGi Framework.
| This is a subset of the J2ME Foundation class libraries defined by OSGi to be the base for framework implementations. See the OSGi specification for more details.
|-
| JRE-1.1
| Java 1.1.x
|-
| J2SE-1.2
| Java 2 SE 1.2.x
|-
|-
| J2SE-1.3
| J2SE-1.3
| Java 2 SE 1.3.x
| J2SE 1.3 - indicates that the bundle can only be run on JSE 1.3 or greater.
|-
|-
| J2SE-1.4
| J2SE-1.4
| Java 2 SE 1.4.x
| J2SE 1.4 - indicates that the bundle can only be run on JSE 1.4 or greater.
|-
|-
| J2SE-1.5
| J2SE-1.5
| Java 2 SE 1.5.x
| Java SE 5 - indicates that the bundle can only be run on Java SE 5 or greater.
|-
|-
| JavaSE-1.6
| JavaSE-1.6
| Java SE 1.6.x
| Java SE 6 - indicates that the bundle can only be run on Java SE 6 or greater.
|-
|-
| PersonalJava-1.1
| PersonalJava-1.1

Revision as of 08:12, 25 June 2009

Introduction

OSGi bundles contain meta-data just like RPMs do. This meta-data can be used to automatically generate Provides and Requires similar to how it is done for mono packages. This functionality exists in Fedora's rpm-4.7.0-8.fc12 (bz506471 ) but isn't activate by default at this time.

BTW, I especially thank Andrew Overolt for reviewing the document and for him nice community spirit - You rocks solid guy!

Glossary

OSGi meta-data: information contained in META-INF/MANIFEST.MF file pertaining to a JAR's modularity.

Bundle: a JAR file (that can be expanded) with special OSGi entries in its manifest and containing classes, resources, and other JARs.

OSGi Framework Overview

The Framework forms the core of the OSGi Service Platform Specifications. It provides a general-purpose, secure, and managed Java framework that supports the deployment of extensible and downloadable components known as bundles. OSGi-compliant "devices" can download and install OSGi bundles, and remove them when they are no longer required. The Framework manages the installation and update of bundles in an OSGi environment in a dynamic and scalable fashion. To achieve this, it manages the dependencies between bundles and services in detail. It provides the bundle developer with the resources necessary to take advantage of Java’s platform independence and dynamic code-loading capability in order to easily develop services for small-memory devices that can be deployed on a large scale.

This overview was copied from the OSGi specification version 4.0.1 available for download there: http://www.osgi.org/Specifications/HomePage

OSGi Framework Fedora support (osgideps.pl)

osgideps.pl script is run on each META-INF/MANIFEST.MF and .jar file. It parses OSGi headers and generates RPM Provides and Requires based on this meta-data.

Some rules that the script follows to generate dependencies

  • it doesn't generate Provides for symlinks (these OSGi bundles are not contained in the package as only symlinks are provided).
  • it strictly Requires the file of symlink'd bundles (we ensure that we don't pull-in broken packages due to dead symlinks).
  • it strictly Requires files of symlink'd bundle defined by the Bundle-ClassPath header (an example of this are the symlinks to ant JAR files in the Eclipse packages).
  • it ignores system.bundle (since that's an alias that represents the OSGi framework itself).
  • it doesn't take care of optional dependencies.
  • it always generates the complete OSGi version to be able to match 1.0 and 1.0.0 as equal in RPM.

Options

-provides print provides of OSGi files (META-INF/MANIFEST.MF and .jar)

-requires print requires of OSGi files

-debug print file path (used with -provides or -requires)

-system print system bundle of OSGi .profile files

Example of uses

Print OSGi required bundles of all jar files into the current directory :

ls -1  *.jar | /usr/lib/rpm/osgideps.pl -requires | sort -u

Print OSGi required bundles of all JAR files in /usr/share/java directory with the file path on the same line (useful to debug sub-package errors):

find /usr/share/java -name "*.jar" | /usr/lib/rpm/osgideps.pl -provides -debug

Generate provides of an OSGi .profile file:

ls -1 J2SE-1.6.profile | /usr/lib/rpm/osgideps.pl -s | sed "s/^osgi/Provides\:\tosgi/g"

OSGi Packaging Guidelines

Bundles that only contain symlink'd JAR files

The junit bundle of the eclipse-jdt package is used to explain this problem. Currently if a package Requires the osgi(org.junit) bundle, then the whole eclipse-jdt package is pulled in because it Provides that bundle though meta-data (MANIFEST.MF)

The OSGi specification says The Framework should provide a private persistent storage area for each installed bundle on platforms with some form of file system support.

I conclude that each OSGi implementation that Fedora could support in the future would have they own structure to contain their bundles. So if we will share the same bundle within multiple Framework implementations, we need to play with symbolic links to accomplish this.

We can fix that problem in 3 different ways (maybe more) but I personally prefer the first one because we can stay as close as possible with upstream projects without losing the advantage of not pulling in unneeded dependencies.

1. Put entire OSGi meta-data directory org.junit%{version} into the junit package as a sub-package that Requires the main package

junit-osgi package can contain org.junit%{version} directory and automatically require junit main package though the Bundle-ClassPath manifest entry.

Advantages:

  • Other OSGi implementations don't need to symlink to Eclipse-specific paths.
  • Package name accurately reflects what the content is.
  • No need to patch manifest file or include non-upstream content in the junit package.
  • We stay close to upstream because we can symlink to the same content.

Disadvantages:

  • Needs more work.

2. Create sub package for each bundles that contain OSGi meta-data

We could create a sub-package that contains the /usr/lib/eclipse/dropins/jdt/plugins/org.junit%{version} directory (e.g. eclipse-jdt-junit or eclipse-junit).

Advantages:

  • We stay close to upstream
  • Not many changes are needed

Disadvantages:

  • Other OSGi implementations need to create symbolic links to Eclipse-specific paths.

3. "Inject" OSGi meta-data into junit package

This technique is used in existing Fedora packages such as jakarta-commons-el (commons-el-eclipse-manifest.patch patch).

Advantages:

  • Other OSGi implementations don't need to symlink to Eclipse-specific paths.
  • No need for a sub-package.

Disadvantages:

  • junit package diverges from upstream.
  • In the case of junit bundle, we need to include some other files into the upstream JAR. Not sure if it's a good idea to diverge so much with upstream.

Fedora Java Runtime

Provide appropriate system bundles

Fedora Java Runtime packages need to add appropriate OSGi Provides. These provides can be extracted by osgideps.pl script with the following command.

ls -1 J2SE-1.6.profile | osgideps.pl -s | sed "s/^osgi/Provides\:\tosgi/g"

Why

The OSGi specification says in the Parent Class Loader paragraph: The set of implicitly imported packages are all java.* packages, since these packages are required by the Java runtime, and using multiple versions at the same time is not easy. For example, all objects must extend the same Object class. A bundle must not declare imports or exports for java.* packages; doing so is an error and any such bundle must fail to install. All other packages available through the parent class loader must be hidden from executing bundles.

However, the Framework must explicitly export relevant packages from the parent class loader. The system property

   org.osgi.framework.system.packages

contains the export package descriptions for the system bundle. This property employs the standard Export-Package manifest header syntax:

   org.osgi.framework.system.packages ::= package-description (
   ',' package-description )*

Some classes on the boot classpath assume that they can use any class loader to load other classes on the boot classpath, which is not true for a bundle class loader. Framework implementations should attempt to load these classes from the boot class path. The system bundle (bundle ID zero) is used to export non-java.* packages from the parent class loader. Export definitions from the system bundle are treated like normal exports, meaning that they can have version numbers, and are used to resolve import definitions as part of the normal bundle resolving process. Other bundles may provide alternative implementations of the same packages.

Java Runtimes need to provides appropriate Named Execution Environments (not yet implemented)

We can imagine the need to add provides for Execution Environments. OSGi bundles can requires osgi(JavaSE-1.6) through Bundle-RequiredExecutionEnvironment and the java-1.6.0-openjdk package can provide it.

Why

The OSGi specification say in the Naming Execution Environments paragraph: Execution environments require a proper name so that [...] A bundle can require that a Framework provides a certain execution environment before it is installed

List of Execution Environments that java-1.6.0-openjdk may provide

  • OSGi/Minimum-1.1
  • J2SE-1.3
  • J2SE-1.4
  • J2SE-1.5
  • JavaSE-1.6
  • Foundation-1.0 and Foundation-1.1 can also be provided with the exception that it provides some MicroEdition IO classes. These classes seems to not be used by bundles provided by Eclipse.

FYI, There is a table containing all bundles that Eclipse 3.5 provides and their needed execution environments available in the 3.5 README, maybe it can be useful in the future.

Table of most common execution environments

Name Description
CDC-1.0/Foundation-1.0 indicates that the bundle can only be run on Foundation 1.0 or greater. Note that with the exception of some MicroEdition IO classes, Foundation 1.0 is a subset of J2SE 1.3.
CDC-1.1/Foundation-1.1 indicates that the bundle can only be run on Foundation 1.1 or greater. Note that with the exception of some MicroEdition IO classes, Foundation 1.1 is a subset of J2SE 1.4.
OSGi/Minimum-1.1 This is a subset of the J2ME Foundation class libraries defined by OSGi to be the base for framework implementations. See the OSGi specification for more details.
J2SE-1.3 J2SE 1.3 - indicates that the bundle can only be run on JSE 1.3 or greater.
J2SE-1.4 J2SE 1.4 - indicates that the bundle can only be run on JSE 1.4 or greater.
J2SE-1.5 Java SE 5 - indicates that the bundle can only be run on Java SE 5 or greater.
JavaSE-1.6 Java SE 6 - indicates that the bundle can only be run on Java SE 6 or greater.
PersonalJava-1.1 Personal Java 1.1
PersonalJava-1.2 Personal Java 1.2
CDC-1.0/PersonalBasis-1.0 J2ME Personal Basis Profile
CDC-1.0/PersonalJava-1.0 J2ME Personal Java Profile