04 maja 2008

Aplikacja webowa jako pakunek OSGi ze Spring Dynamic Modules

Wciąż chodzi mi po głowie sposób tworzenia aplikacji webowej na platformie OSGi, gdzie jej elementy składowe będą faktycznie pakunkami OSGi, które można włączać/wyłączać/uaktualniać dynamicznie bez konieczności jej zatrzymywania, o wielu wersjach tej samej biblioteki w środowisku nie wspominając. Po ostatnim spotkaniu z OSGi skończyło się na skorzystaniu ze Spring Dynamic Modules (Spring-DM). Jednym ze sztandarowych cech najnowszej wersji Spring-DM 1.1.0 M2 jest wsparcie dla uruchamiania aplikacji webowych jako pakunków OSGi. To jest dokładnie to, czego szukałem (chociaż przyznaję, że nie starałem się jakoś specjalnie znaleźć coś innego niż właśnie Spring-DM).

Lekturę dokumentacji Spring-DM rozpocząłem od rozdziału 8. Web Support. Wcześniej czytałem pozostałe rozdziały, więc od razu przeszedłem do sedna. To właśnie lektura rozdziału uzmysłowiła mi, że format dystrybucji aplikacji webowej - plik war - jest faktycznie jarem, a pakunek osgi to właśnie plik jar z odpowiednimi nagłówkami w manifeście (META-INF/MANIFEST.MF). Idąć tym tropem można sobie wyobrazić sytuację, w której umieszczając obowiązkowy nagłówek OSGi - Bundle-SymbolicName - do manifestu w paczce aplikacji webowej nadajemy jej cechy pakunku w środowisku OSGi. Pozostaje jeszcze powiązać oba światy pod względem ich wymagań, np. widoczności klas i pomysł uruchamiania aplikacji webowych jako pakunków OSGi zostanie zmaterializowany. Właśnie taki cel obrał projekt Spring-DM.

Kwintesencją Spring-DM jest następujący zapis w jego dokumentacji:

Spring-DM addresses these problems by bridging the web container and the OSGi space so loading is no longer a concern. Unique in its functionality, the web support in Spring-DM integrates directly with the web container so the WAR processing is literally handled by the server.[...] In short, everything that the target container supports is available to the OSGi WAR through Spring-DM.

Początkowo trudno było mi zrozumieć, co autor miał na myśli, ale teraz po dniu pracy ze Spring-DM sprawa wydaje się być całkowicie oczywista (zakładam, że taka będzie również dla czytelników - rozczarowanych uprasza się o kontakt ;-)). W skrócie, temat sprowadza się do takiego uruchomienia aplikacji webowej, aby jej cechy aplikacji webowej były respektowane w ramach platformy OSGi i odwrotnie, tj. cechy pakunku OSGi (i zasady oraz obowiązki z tego wynikające) będą respektowane przez kontener aplikacji webowej. Nie oznacza to jednak, że samo tworzenie aplikacji webowej powinno zmienić się z punktu widzenia jej twórcy, aczkolwiek uruchomienie na platformie OSGi daje tą zaletę, że jej zależności to zależności pakunku OSGi, więc za pomocą mechanizmów udostępnianych przez platformę OSGi istnieje możliwość zarządzania nimi dynamicznie, w trakcie działania aplilkacji oraz ich automatyczne wersjonowanie. Weźmy na tapetę biblioteki aplikacji webowej umieszczane w katalogu WEB-INF/lib (podobnie będzie z klasami w WEB-INF/classes). Specyfikacja Java Servlet gwarantuje, że oba katalogi WEB-INF/{lib,classes} są dostępne dla zarządcy klas aplikacji webowej. W przypadku pakunku OSGi tak nie jest. Tutaj sprawa jest obwarowana zasadami, które mówią, że pakunek ma dostęp wyłącznie do klas/interfejsów w ramach pakunku oraz tych zależności zewnętrznych zadeklarowanych przez nagłówki Import-Package czy Bundle-Classpath w manifeście. Katalog WEB-INF/lib nie jest niczym specjalnym z punktu widzenia pakunku OSGi, chyba że jest jawnie zadeklarowany we wspomnianym Bundle-Classpath. Podobnie sprawa się tyczy bibliotek zapewnianych przez kontener serwletów, np. javax.servlet. Tylko tyle pakunek OSGi "zobaczy", ile zadeklaruje w Bundle-Classpath i/lub Import-Package. Całe te zawiłości, początkowo mogące być postrzegane jako utrudnienia, dają tę zaletę, że udostępniamy pakunkowi OSGi, który jest aplikacji webową, biblioteki dynamicznie i ich zarządzanie staje się dynamiczne. Jedną z wiodących cech takiego podejścia, jest spowodowanie, że biblioteki, które zazwyczaj znajdowały się w WEB-INF/lib, teraz również instaluje się w środowisku OSGi jako pakunki OSGi, a aplikacje webowe, które jej wymagają deklarują odpowiednią zależność w manifeście (dla już przestraszonych skomplikowaniem sprawy tworzenia aplikacji webowej jako pakunku OSGi, a jeszcze nie dostrzegających zalet takiego podejścia, nadmienię tylko, że Spring-DM poprzez mechanizm wtyczek mavenowych wykrywa zależności i samodzielnie tworzy odpowiedni plik manifestu w trakcie budowania aplikacji). Podsumowując zarządzanie klasami zlecone jest platformie OSGi, więc prawa rządzące aplikacją webową, w kontekście widoczności klas z pakietu javax.servlet i podobnych oraz WEB-INF/{classes,lib} muszą być zadeklarowane w pakunku OSGi explicite (opisane jest to w części 8.3.2. Servlets). Obowiązkowo należy dodać Import-Package: javax.servlet,javax.servlet.http,javax.servlet.resources, które zgodnie ze specyfikacją Java Servlet są automatycznie udostępniane przez kontener serwletów, a w przypadku OSGi muszą być jawnie zadeklarowane (bo nie są niczym szczególnym z punktu widzenia środowiska OSGi).

Podkreślając znaczenie uwspólniania zależności aplikacji webowych przytoczę wycinek dokumentacji Spring-DM - rozdział 8.3.2 Servlets:

Before creating entries for embedded libraries, consider whether the library cannot be installed as an OSGi bundle - doing so will allow it to be shared with other WARs if needed and since OSGi allows versioning, it is perfectly okay to have multiple versions of the library inside the same VM.

Dzięki uaktywnieniu bibliotek wykorzystywanych przez pojedyńczą aplikację webową jako pakunków OSGi (jedynie dodanie odpowiednich nagłówków do manifestu aplikacji) oraz ich instalacja poza tą jedną aplikacją webową mamy możliwość udostępnienia jej dla innych pakunków OSGi, niekoniecznie będących aplikacjami webowymi, oraz najistotniejsze, mamy możliwość dynamicznego uaktualniania jej w trakcie pracy systemu zrzucając na barki platformy OSGi zarządzanie zależnościami - dostępnością klas, niszczeniem dostawców klas czy utrzymaniem wielu wersji w trakcie korzystania z klasy w pakunku, który właśnie jest uaktualniany. Za pomocą Spring-DM mamy możliwość połączenia dwóch światów OSGi oraz aplikacji webowych w jeden, co wymaga od nas postrzegania tworzenia aplikacji webowych, a zmiana wpływa na większą modularyzację aplikacji. Tym razem widzę same zalety stosowania Springa (niejednokrotnie podkreślałem, że Spring nie jest lekarstwem na wszystko i mogłobyć to odebrane jako niechęć w jego wykorzystaniu, co już w przypadku Spring-DM można odczuć nie jest prawdą). O takim podejściu do tworzenia aplikacji webowych pisał chociażby Daniel w komentarzu do wpisu Nawigacja w Wicket:

Jak widać po Twoich wpisach OSGi nie jest Ci obce, dlatego zdziwiło mnie zdanie: "to nie wiem jaki miałby zysk wdrożenie OSGi mając na pokładzie Spring + Wicket." :) Przecież korzyści jakie płyną z wykorzystania OSGi są w miarę jasne, chociażby podstawowa: dobre wsparcie dla modularyzacji aplikacji.

Naczytałem się o Spring DM i jego zaletach aktywacji aplikacji webowych jako pakunków OSGi, albo raczej ich uruchomienia na platformie OSGi z Jetty (domyślnie jest już pakunkiem OSGi i Spring-DM dodaje jedynie aktywator pakunku) lub Tomcat (Spring-DM tworzy z niego pakunek OSGi - wpisy w manifeście - oraz dodaje aktywator), ale nie znalazłem chociażby przykładu jakby to ugryźć. Niestety, ale o jakości dokumentacji również nie mogę napisać w samych superlatywach i liczba błędów w dokumentacji Spring DM oraz oraz brak potrzebnych zależności w dystrybucji Spring-DM świadczą o zbytnim pośpiechu (co ma tą zaletę, że wypuszcza się na rynek produkt do ewaluacji i daje możliwość zrozumienia problemu, który rozwiązuje, a błędy poprawia się w kolejnych iteracjach).

Popróbuję się więc z tymi atrakcjami Spring-DM w kontekście uruchamiania aplikacji webowych jako pakunków OSGi. Zacznę od stworzenia projektu. I tu pytanie numer 1. - jak stworzyć projekt, aby skorzystać z spring-osgi-bundle-archetype tworząc projekt aplikacji webowej? Na stronie Spring Dynamic Modules Demos znajdują się dwie prezentacje tworzenia przykładowych aplikacji z użyciem Spring-DM i do utworzenia projektu wystarczył jedynie domyślny archetyp. Tyle tylko, że tam nie było aplikacji webowej (!) Nie zakładałem, że będzie łatwo, ale już na początku takie problemy?! Nie wygląda to zachęcająco.

Rozpocznę od archetypu maven-archetype-webapp, gdyż chcę uniknąć zawiłości związanych z bardziej zaawansowanymi szkieletami webowymi, np. korzystających z JSF, kiedy przyjdzie mi je uruchamiać na OSGi po raz pierwszy z pomocą Spring-DM, a bez dostępnych bibliotek jako pakunków OSGi (parametr -U dodałem wyłącznie dla celów ochronnych opisanych w Niuanse Apache Maven 2 - opcja -U).
 jlaskowski@work /cygdrive/c/projs/osgi
$ mvn -U archetype:create -DarchetypeArtifactId=maven-archetype-webapp -DgroupId=pl.jaceklaskowski.osgi -DartifactId=spring-osgi-webapp
...
[INFO] ----------------------------------------------------------------------------
[INFO] Using following parameters for creating OldArchetype: maven-archetype-webapp:RELEASE
[INFO] ----------------------------------------------------------------------------
[INFO] Parameter: groupId, Value: pl.jaceklaskowski.osgi
[INFO] Parameter: packageName, Value: pl.jaceklaskowski.osgi
[INFO] Parameter: basedir, Value: c:\projs\osgi
[INFO] Parameter: package, Value: pl.jaceklaskowski.osgi
[INFO] Parameter: version, Value: 1.0-SNAPSHOT
[INFO] Parameter: artifactId, Value: spring-osgi-webapp
[INFO] ********************* End of debug info from resources from generated POM ***********************
[INFO] OldArchetype created in dir: c:\projs\osgi\spring-osgi-webapp
[INFO] ------------------------------------------------------------------------
[INFO] BUILD SUCCESSFUL
[INFO] ------------------------------------------------------------------------
Temat obsługi manifestu sprowadzę do konfiguracji wtyczki maven-war-plugin. Dodaję odpowiednią sekcję do pom.xml i konfiguruję obowiązkowy nagłówek Bundle-SymbolicName (korzystam z pomocy Eclipse i jego wtyczki Maven Integration for Eclipse - m2eclipse).
 <plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-war-plugin</artifactId>
<version>2.0.2</version>
<configuration>
<archive>
<manifestEntries>
<Bundle-SymbolicName>${groupId}.${artifactId}</Bundle-SymbolicName>
</manifestEntries>
</archive>
</configuration>
</plugin>
Uruchomienie aplikacji webowej jako pakunku OSGi spróbuję z Apache Felix 1.0.4 jako platformie OSGi. W 5.3. Required Spring Framework and Spring Dynamic Modules Bundles opisano wszystkie niezbędne pakunki, które należy uruchomić dla poprawnego uruchomienia pakunku dowolnej aplikacji webowej. Nie trwało długo, zanim okazało się, że Spring-DM 1.1.0 M2 dostarcza jedynie część z wymaganych bibliotek, a w tym brakuje najważniejszej - spring-osgi-web-extender (!)

Buduję aplikację webową i podchodzę do jej instalacji na Apache Felix 1.0.4 z Spring-DM.
 jlaskowski@work /cygdrive/c/projs/osgi/spring-osgi-webapp
$ mvn package
[INFO] Scanning for projects...
[INFO] ------------------------------------------------------------------------
[INFO] Building spring-osgi-webapp Maven Webapp
[INFO] task-segment: [package]
[INFO] ------------------------------------------------------------------------
[INFO] [resources:resources]
[INFO] Using default encoding to copy filtered resources.
[INFO] [compiler:compile]
[INFO] No sources to compile
[INFO] [resources:testResources]
[INFO] Using default encoding to copy filtered resources.
[INFO] [compiler:testCompile]
[INFO] No sources to compile
[INFO] [surefire:test]
[INFO] No tests to run.
[INFO] [war:war]
[INFO] Exploding webapp...
[INFO] Assembling webapp spring-osgi-webapp in c:\projs\osgi\spring-osgi-webapp\target\spring-osgi-webapp
[INFO] Copy webapp webResources to c:\projs\osgi\spring-osgi-webapp\target\spring-osgi-webapp
[INFO] Generating war c:\projs\osgi\spring-osgi-webapp\target\spring-osgi-webapp.war
[INFO] Building war: c:\projs\osgi\spring-osgi-webapp\target\spring-osgi-webapp.war
[INFO] ------------------------------------------------------------------------
[INFO] BUILD SUCCESSFUL
[INFO] ------------------------------------------------------------------------
Sposób w jaki działa Spring-DM to dostarczenie pakunku spring-osgi-web-extender, który monitoruje zainstalowane pakunki i rozpoznaje, które są aplikacjami webowymi. Jeśli trafi się jedna, to następuje zainstalowanie jej na kontenerze servletów (Tomcat lub Jetty), który jest również pakunkiem OSGi dostarczanym przez Spring-DM.

Rozpoczynam instalację pakunków OSGi dostarczanych przez Spring-DM - dostępne w katalogach dist oraz lib. Instaluję:
  • dist/spring-osgi-web-1.1.0-m2.jar
  • lib/servlet-api.osgi-2.5-SNAPSHOT.jar
  • lib/slf4j-log4j12-1.4.3.jar
  • lib/jcl104-over-slf4j-1.4.3.jar
  • lib/slf4j-api-1.4.3.jar
  • lib/log4j.osgi-1.2.15-SNAPSHOT.jar
Do rozpoznania pozostaje sposób instalacji wielu pakunków automatycznie bez konieczności ich ręcznej instalacji (gdzieś o tym czytałem, ale teraz nie pamiętam - może ktoś się zlituje i napisze koledze Jackowi?!).

Na zakończenie przychodzi mi instalować moją aplikację webową i wierzyć, że zostanie rozpoznana i poprawnie zainstalowana w kontenerze servletów przez Spring-DM.

W trakcie uaktualniania pakunku na Felix 1.0.4 natrafiłem na błąd, gdzie pakunek musiał koniecznie mieć rozszerzenie pliku jar, aby został zaakceptowany przez polecenie update - zgłosiłem jako FELIX-544 update command should accept other file extensions than jar only.
 -> update 10 file:/C:/projs/osgi/spring-osgi-webapp/target/spring-osgi-webapp.war
Unable to open input stream: java.io.FileNotFoundException:
C:\projs\osgi\spring-osgi-webapp\target\spring-osgi-webapp.war.jar (The system cannot find the file specified)
-> uninstall 10
-> install file:/C:/projs/osgi/spring-osgi-webapp/target/spring-osgi-webapp.war
Bundle ID: 11
-> start 11
-> ps
START LEVEL 1
ID State Level Name
[ 0] [Active ] [ 0] System Bundle (1.0.4)
[ 1] [Active ] [ 1] Apache Felix Shell Service (1.0.1)
[ 2] [Active ] [ 1] Apache Felix Shell TUI (1.0.1)
[ 3] [Active ] [ 1] Apache Felix Bundle Repository (1.0.3)
[ 4] [Active ] [ 1] spring-osgi-web (1.1.0.m2)
[ 5] [Active ] [ 1] servlet-api.osgi (2.5.0.SNAPSHOT)
[ 6] [Active ] [ 1] slf4j-log4j12 (1.4.3)
[ 7] [Active ] [ 1] jcl104-over-slf4j (1.4.3)
[ 8] [Active ] [ 1] slf4j-api (1.4.3)
[ 9] [Active ] [ 1] log4j.osgi (1.2.15.SNAPSHOT)
[ 11] [Active ] [ 1] pl.jaceklaskowski.osgi.spring-osgi-webapp
-> headers 11

Bundle 11
---------
Built-By = jlaskowski
Archiver-Version = Plexus Archiver
Created-By = Apache Maven
Build-Jdk = 1.5.0_14
Manifest-Version = 1.0
Bundle-SymbolicName = pl.jaceklaskowski.osgi.spring-osgi-webapp
Niestety żadnych komunikatów, aby jakakolwiek akcja została wykonana po instalacji aplikacji webowej. Coś nie gra. Pytanie jak to sprawdzić? Jeszcze raz zaglądam do dokumentacji, gdzie znalazłem, że aplikacja webowa zostanie rozpoznana przez Spring DM jedynie, jeśli spełnia jeden z poniższych warunków: zawiera katalog META-INF/spring bądź nagłówek Spring-Context (więcej w 5.1. Bundle format and Manifest headers).

Dodaję do pom.xml:
 <Spring-Context>*;publish-context:=true</Spring-Context>
buduję aplikację i ponownie podchodzę do instalacji (jak można zauważyć zainstalowałem w międzyczasie inne pakunki OSGi dostarczane przez Spring-DM - nazwy pakunków odpowiadają nazwom plików z katalogów dist lub lib).
 -> install file:/C:/projs/osgi/spring-osgi-webapp/target/spring-osgi-webapp.war
Bundle ID: 21
-> ps
START LEVEL 1
ID State Level Name
[ 0] [Active ] [ 0] System Bundle (1.0.4)
[ 1] [Active ] [ 1] Apache Felix Shell Service (1.0.1)
[ 2] [Active ] [ 1] Apache Felix Shell TUI (1.0.1)
[ 3] [Active ] [ 1] Apache Felix Bundle Repository (1.0.3)
[ 4] [Active ] [ 1] spring-osgi-web (1.1.0.m2)
[ 5] [Active ] [ 1] servlet-api.osgi (2.5.0.SNAPSHOT)
[ 6] [Active ] [ 1] slf4j-log4j12 (1.4.3)
[ 7] [Active ] [ 1] jcl104-over-slf4j (1.4.3)
[ 8] [Active ] [ 1] slf4j-api (1.4.3)
[ 9] [Active ] [ 1] log4j.osgi (1.2.15.SNAPSHOT)
[ 12] [Active ] [ 1] spring-osgi-extender (1.1.0.m2)
[ 13] [Active ] [ 1] spring-context (2.5.4)
[ 14] [Active ] [ 1] spring-beans (2.5.4)
[ 15] [Active ] [ 1] spring-osgi-core (1.1.0.m2)
[ 16] [Active ] [ 1] spring-core (2.5.4)
[ 17] [Active ] [ 1] aopalliance.osgi (1.0.0.SNAPSHOT)
[ 18] [Active ] [ 1] spring-osgi-io (1.1.0.m2)
[ 19] [Active ] [ 1] spring-aop (2.5.4)
[ 21] [Installed ] [ 1] pl.jaceklaskowski.osgi.spring-osgi-webapp
-> start 21
-> WARNING: *** Class 'org.springframework.beans.factory.xml.NamespaceHandlerResolver' was not found
because bundle 21 does not import 'org.springframework.beans.factory.xml' even though bundle 14 does export it.
To resolve this issue, add an import for 'org.springframework.beans.factory.xml' to bundle 21.
*** (java.lang.ClassNotFoundException: *** Class 'org.springframework.beans.factory.xml.NamespaceHandlerResolver'
was not found because bundle 21 does not import 'org.springframework.beans.factory.xml' even though bundle 14 does export it.
To resolve this issue, add an import for 'org.springframework.beans.factory.xml' to bundle 21. ***)
...i jeszcze kilka innych WARNINGów. Rozwiązanie w samym komunikacie i zgodnie z 8.3.2. Servlets dodaję odpowiednie zależności w pom.xml w sekcji konfiguracji wtyczki maven-war-plugin:
 <Import-Package>javax.servlet,javax.servlet.http,javax.servlet.resources</Import-Package>
<Bundle-Classpath>.,WEB-INF/classes</Bundle-Classpath>
Ponownie buduję aplikację i podchodzę do jej instalacji.
 -> install file:/C:/projs/osgi/spring-osgi-webapp/target/spring-osgi-webapp.war
INFO: Class path entry not found: WEB-INF/classes
Bundle ID: 23
-> start 23
DEBUG: WIRE: 23.0 -> javax.servlet.http -> 5.0
DEBUG: WIRE: 23.0 -> javax.servlet -> 5.0
DEBUG: WIRE: 23.0 -> javax.servlet.resources -> 5.0
-> WARNING: *** Class 'org.springframework.beans.factory.xml.NamespaceHandlerResolver' was not found
because bundle 23 does not import 'org.springframework.beans.factory.xml' even though bundle 14 does export it.
To resolve this issue, add an import for 'org.springframework.beans.factory.xml' to bundle 23. ***
(java.lang.ClassNotFoundException: *** Class 'org.springframework.beans.factory.xml.NamespaceHandlerResolver'
was not found because bundle 23 does not import 'org.springframework.beans.factory.xml' even though bundle 14 does export it.
To resolve this issue, add an import for 'org.springframework.beans.factory.xml' to bundle 23. ***)
...i ponownie WARNINGi, czyli dokumentacja Spring-DM nie opisuje dokładnie wymaganych importów (!) Dodaję do pom.xml kolejne:
 <Import-Package>javax.servlet,javax.servlet.http,javax.servlet.resources,
org.springframework.beans.factory.xml,org.springframework.aop,
org.springframework.aop.framework,org.aopalliance.aop,org.xml.sax,
org.apache.jasper.servlet,org.apache.commons.el,org.apache.catalina.servlets</Import-Package>
I znowu budowanie aplikacji i jej instalacja (z nadzieją, że to może już).
 -> uninstall 23
-> install file:/C:/projs/osgi/spring-osgi-webapp/target/spring-osgi-webapp.war
INFO: Class path entry not found: WEB-INF/classes
Bundle ID: 24
-> start 24
DEBUG: WIRE: 24.0 -> javax.servlet.http -> 5.0
DEBUG: WIRE: 24.0 -> javax.servlet -> 5.0
DEBUG: WIRE: 24.0 -> org.xml.sax -> 0
DEBUG: WIRE: 24.0 -> org.springframework.beans.factory.xml -> 14.0
DEBUG: WIRE: 24.0 -> javax.servlet.resources -> 5.0
DEBUG: WIRE: 24.0 -> org.springframework.aop.framework -> 19.0
DEBUG: WIRE: 24.0 -> org.aopalliance.aop -> 17.0
DEBUG: WIRE: 24.0 -> org.springframework.aop -> 19.0
Niestety, jeszcze nie koniec zmagań, ale tym razem już czysto. Wciąż żadnych komunikatów związanych z uruchomieniem aplikacji. Dokumentacja wspomina o cglib-nodep jako bibliotece do tworzenia proxy, ale niestety nie ma jej w dystrybucji (!) Dodatkowo informacja o konieczności instalacji pakunku cglib-nodep znajduje się w readme.txt w katalogu lib w dystrybucji Spring DM.

I dalej, rozdział 2. Requirements opisuje wymaganie Bundles deployed for use with Spring Dynamic Modules should specify "Bundle-ManifestVersion: 2" in their manifest (OSGi R4). Koniecznie należy jawnie określić wersję pakunku, gdyż domyślna wartość to 1, która najwyraźniej nie jest rozpoznawana przez Spring-DM.

Za specyfikacją OSGi 4.1 strona 27:

3.2.1.10 Bundle-ManifestVersion: 2
The Bundle-ManifestVersion header defines that the bundle follows the rules of this specification. The Bundle-ManifestVersion header determines whether the bundle follows the rules of this specification. It is 1 (the default) for Release 3 Bundles, 2 for Release 4 and later. Future version of the OSGi Service Platform can define higher numbers for this header.


Dodaję
 <Bundle-ManifestVersion>2</Bundle-ManifestVersion>
do pom.xml.

W 8.2. Web support usage napisano:

To use Spring-DM Web, install:
* spring-osgi-web.jar - Spring-DM web support
* spring-osgi-web-extender.jar - Spring-DM web extender

Niestety, ale już na starcie trudno spełnić to wymaganie, bo nie istnieje spring-osgi-web-extender.jar w katalogu lib lub dist w dystrybucji Spring-DM 1.1.0 M2, a jedynie spring-osgi-extender.jar (!) Nie obejdzie się bez pobrania jej z repozytorium S3 jako spring-osgi-web-extender-1.1.0-m2-20080425.012916-2.jar.

W końcu trochę zniecierpliwiony tymi niespodziankami zabrałem się za przeglądanie kodów źródłowych z repozytorium Spring-DM. Niestety próba zbudowania ich za pomocą polecenia mvn -P equinox,it clean install zakończyła się komunikatem błędu o niedostępności biblioteki do obsługi repozytorium S3 - net.java.dev.jets3t:jets3t:jar:0.5.1-20080115. Ech, jakby nie chciano, abym skosztował tych wszystkich nowości, którymi szczyci się Spring-DM 1.1.0-m2.
 Downloading: http://repo1.maven.org/eclipse//net/java/dev/jets3t/jets3t/0.5.1-20080115/jets3t-0.5.1-20080115.pom
Downloading: http://springframework.svn.sourceforge.net/svnroot/springframework/repos/repo-ext//net/java/dev/jets3t/jets3t/0.5.1-20080115/jets3t-0.5.1-20080115.pom
Downloading: http://maven.springframework.org/release/net/java/dev/jets3t/jets3t/0.5.1-20080115/jets3t-0.5.1-20080115.pom
Downloading: http://maven.springframework.org/external/net/java/dev/jets3t/jets3t/0.5.1-20080115/jets3t-0.5.1-20080115.pom
Downloading: http://maven.springframework.org/milestone/net/java/dev/jets3t/jets3t/0.5.1-20080115/jets3t-0.5.1-20080115.pom
Downloading: http://m2.safehaus.org/net/java/dev/jets3t/jets3t/0.5.1-20080115/jets3t-0.5.1-20080115.pom
Downloading: http://maven.springframework.org/osgi/net/java/dev/jets3t/jets3t/0.5.1-20080115/jets3t-0.5.1-20080115.pom
Downloading: http://jets3t.s3.amazonaws.com/maven2/net/java/dev/jets3t/jets3t/0.5.1-20080115/jets3t-0.5.1-20080115.pom
Downloading: http://repo1.maven.org/maven2/net/java/dev/jets3t/jets3t/0.5.1-20080115/jets3t-0.5.1-20080115.pom
Downloading: http://repo1.maven.org/eclipse//net/java/dev/jets3t/jets3t/0.5.1-20080115/jets3t-0.5.1-20080115.jar
Downloading: http://springframework.svn.sourceforge.net/svnroot/springframework/repos/repo-ext//net/java/dev/jets3t/jets3t/0.5.1-20080115/jets3t-0.5.1-20080115.jar
Downloading: http://maven.springframework.org/release/net/java/dev/jets3t/jets3t/0.5.1-20080115/jets3t-0.5.1-20080115.jar
Downloading: http://maven.springframework.org/external/net/java/dev/jets3t/jets3t/0.5.1-20080115/jets3t-0.5.1-20080115.jar
Downloading: http://maven.springframework.org/milestone/net/java/dev/jets3t/jets3t/0.5.1-20080115/jets3t-0.5.1-20080115.jar
Downloading: http://m2.safehaus.org/net/java/dev/jets3t/jets3t/0.5.1-20080115/jets3t-0.5.1-20080115.jar
Downloading: http://maven.springframework.org/osgi/net/java/dev/jets3t/jets3t/0.5.1-20080115/jets3t-0.5.1-20080115.jar
Downloading: http://jets3t.s3.amazonaws.com/maven2/net/java/dev/jets3t/jets3t/0.5.1-20080115/jets3t-0.5.1-20080115.jar
Downloading: http://repo1.maven.org/maven2/net/java/dev/jets3t/jets3t/0.5.1-20080115/jets3t-0.5.1-20080115.jar
[INFO] ------------------------------------------------------------------------
[ERROR] BUILD ERROR
[INFO] ------------------------------------------------------------------------
[INFO] Failed to resolve artifact.

Missing:
----------
1) net.java.dev.jets3t:jets3t:jar:0.5.1-20080115

Try downloading the file manually from the project website.

Then, install it using the command:
mvn install:install-file -DgroupId=net.java.dev.jets3t -DartifactId=jets3t
-Dversion=0.5.1-20080115 -Dpackaging=jar -Dfile=/path/to/file

Alternatively, if you host your own repository you can deploy the file there:
mvn deploy:deploy-file -DgroupId=net.java.dev.jets3t -DartifactId=jets3t -Dversion=0.5.1-20080115
-Dpackaging=jar -Dfile=/path/to/file -Durl=[url] -DrepositoryId=[id]

Path to dependency:
1) org.springframework.osgi:spring-osgi:pom:1.1.0-rc1-SNAPSHOT
2) net.java.dev.jets3t:jets3t:jar:0.5.1-20080115

----------
1 required artifact is missing.

for artifact:
org.springframework.osgi:spring-osgi:pom:1.1.0-rc1-SNAPSHOT

from the specified remote repositories:
ibiblio.org (http://repo1.maven.org/maven2),
spring-release (http://maven.springframework.org/release),
spring-ext (http://springframework.svn.sourceforge.net/svnroot/springframework/repos/repo-ext/),
safehaus-repository (http://m2.safehaus.org),
spring-external (http://maven.springframework.org/external),
spring-milestone (http://maven.springframework.org/milestone),
springsource-s3-osgi-repo (http://maven.springframework.org/osgi),
jets3t (http://jets3t.s3.amazonaws.com/maven2),
eclipse-repository (http://repo1.maven.org/eclipse/)


[INFO] ------------------------------------------------------------------------
[INFO] For more information, run Maven with the -e switch
[INFO] ------------------------------------------------------------------------
W przykładowej aplikacji dostępnej w katalogu samples/simple-web-app znalazłem klasę testu jednostkowego - integration-test/src/test/java/org/springframework/osgi/samples/simplewebapp/OsgiHttpIntegrationTest.java, gdzie wymieniono wszystkie konieczne zależności do poprawnego jej uruchomienia. Kolejny raz pojawiła się wzmianka o spring-osgi-web-extender.
 col.add(SPRING_OSGI_GROUP + ", servlet-api.osgi, 2.5-SNAPSHOT");
col.add(SPRING_OSGI_GROUP + ", jsp-api.osgi, 2.0-SNAPSHOT");

// JSP compiler
col.add(SPRING_OSGI_GROUP + ", jasper.osgi, 5.5.23-SNAPSHOT");
col.add(SPRING_OSGI_GROUP + ", commons-el.osgi, 1.0-SNAPSHOT");

// standard tag library
col.add("org.springframework.osgi, jstl.osgi, 1.1.2-SNAPSHOT");

// add MX4J for 1.4
// if < jdk 1.5, add an JMX implementation
if (!JdkVersion.isAtLeastJava15())
col.add(SPRING_OSGI_GROUP + ", mx4j.osgi, 3.0.2-SNAPSHOT");

col.add(SPRING_OSGI_GROUP + ", catalina.osgi, 5.5.23-SNAPSHOT");
col.add(SPRING_OSGI_GROUP + ", catalina.start.osgi, 1.0-SNAPSHOT");

// Spring DM web extender
col.add(SPRING_OSGI_GROUP + ", spring-osgi-web," + getSpringDMVersion());
col.add(SPRING_OSGI_GROUP + ", spring-osgi-web-extender," + getSpringDMVersion());
col.add(SPRING_OSGI_GROUP + ", cglib-nodep.osgi, 2.1.3-SNAPSHOT");
Pobieram brakujące pakunki z repozytorium http://jets3t.s3.amazonaws.com/maven2:
Podsumowując zainstalowałem następujące pakunki dostarczane z dystrybucją Spring-DM 1.1.0 M2:
  • install file:/C:/apps/spring-osgi/dist/spring-osgi-web-1.1.0-m2.jar
  • install file:/C:/apps/spring-osgi/lib/servlet-api.osgi-2.5-SNAPSHOT.jar
  • install file:/C:/apps/spring-osgi/lib/jcl104-over-slf4j-1.4.3.jar
  • install file:/C:/apps/spring-osgi/lib/slf4j-api-1.4.3.jar
  • install file:/C:/apps/spring-osgi/lib/slf4j-log4j12-1.4.3.jar
  • install file:/C:/apps/spring-osgi/lib/log4j.osgi-1.2.15-SNAPSHOT.jar
  • install file:/C:/apps/spring-osgi/dist/spring-osgi-extender-1.1.0-m2.jar
  • install file:/C:/apps/spring-osgi/lib/spring-context-2.5.4.jar
  • install file:/C:/apps/spring-osgi/lib/spring-beans-2.5.4.jar
  • install file:/C:/apps/spring-osgi/lib/spring-core-2.5.4.jar
  • install file:/C:/apps/spring-osgi/lib/aopalliance.osgi-1.0-SNAPSHOT.jar
  • install file:/C:/apps/spring-osgi/dist/spring-osgi-io-1.1.0-m2.jar
  • install file:/C:/apps/spring-osgi/lib/spring-aop-2.5.4.jar
oraz pobrane z repozytorium S3:
  • install file:/C:/spring-dm-libs/jsp-api.osgi-2.0-20080103.183925-4.jar
  • install file:/C:/spring-dm-libs/jasper.osgi-5.5.23-20080305.122359-4.jar
  • install file:/C:/spring-dm-libs/commons-el.osgi-1.0-20080303.111409-4.jar
  • install file:/C:/spring-dm-libs/jstl.osgi-1.1.2-20080103.183925-4.jar
  • install file:/C:/spring-dm-libs/catalina.osgi-5.5.23-20080425.154256-4.jar
  • install file:/C:/spring-dm-libs/catalina.start.osgi-1.0-20080425.161832-4.jar
  • install file:/C:/spring-dm-libs/cglib-nodep.osgi-2.1.3-20080103.183925-4.jar
  • install file:/C:/spring-dm-libs/spring-osgi-web-extender-1.1.0-m2-SNAPSHOT.jar
Po instalacji pakunków oraz samej aplikacji webowej pozostało dowiedzieć się jaki jest kontekst aplikacji - adres, pod którym dostępna jest aplikacja. Po przeczytaniu całej dostępnej dokumentacji Spring DM na stronie http://www.springframework.org/osgi w poszukiwaniu odpowiedzi przeniosłem się na forum, gdzie po kolei przeglądałem kolejne pytania dotyczące wsparcia aplikacji webowych w Spring DM. Szczęśliwie natrafiłem na wątek WAR deploy in 1.1.0-m1 vs. 1.1.0-m2?, gdzie zauważyłem nagłówek Bundle-Name, który pasował do nazwy kontekstu (adresu aplikacji).

Dodałem do pom.xml następujący wpis:
 <Bundle-Name>${artifactId}</Bundle-Name>
ponownie zbudowałem aplikację - mvn clean package - i zaktualizowałem pakunek.
 -> uninstall 26
-> install file:/C:/projs/osgi/spring-osgi-webapp/target/spring-osgi-webapp.war
Bundle ID: 27
-> start 27
DEBUG: WIRE: 27.0 -> javax.servlet.http -> 5.0
DEBUG: WIRE: 27.0 -> javax.servlet -> 5.0
DEBUG: WIRE: 27.0 -> org.xml.sax -> 0
DEBUG: WIRE: 27.0 -> org.springframework.beans.factory.xml -> 14.0
DEBUG: WIRE: 27.0 -> javax.servlet.resources -> 5.0
DEBUG: WIRE: 27.0 -> org.springframework.aop.framework -> 19.0
DEBUG: WIRE: 27.0 -> org.aopalliance.aop -> 17.0
DEBUG: WIRE: 27.0 -> org.springframework.aop -> 19.0
-> headers 27

spring-osgi-webapp (27)
-----------------------
Built-By = jlaskowski
Created-By = Apache Maven
Build-Jdk = 1.5.0_14
Manifest-Version = 1.0
Bundle-ManifestVersion = 2
Spring-Context = *;publish-context:=true
Archiver-Version = Plexus Archiver
Import-Package = javax.servlet,javax.servlet.http,javax.servlet.resources,
org.springframework.beans.factory.xml,org.springframework.aop,org.springframework.aop.framework,
org.aopalliance.aop,org.xml.sax
Bundle-Name = spring-osgi-webapp
Bundle-Classpath = .,WEB-INF/classes
Bundle-SymbolicName = pl.jaceklaskowski.osgi.spring-osgi-webapp
W końcu upragnione uruchomienie aplikacji webowej spring-osgi-webapp jako pakunku OSGi, jednakże adres http://localhost:8080/spring-osgi-webapp/ kończył się pustą stroną lub wyjątkiem o niedostępności klas (niestety komunikat nie wskazywał jakiej). Coś zaczęło działać, ale niepoprawnie. Wykluczam mój błąd ;-) Po zmianie strony JSP na statyczną stronę HTML pojawia się wreszcie strona aplikacji!


Wciąż jednak strony JSP nie są poprawnie kompilowane. Stan platformy OSGi (Felix 1.0.4) prezentuje się następująco:
 -> ps
START LEVEL 1
ID State Level Name
[ 0] [Active ] [ 0] System Bundle (1.0.4)
[ 1] [Active ] [ 1] Apache Felix Shell Service (1.0.1)
[ 2] [Active ] [ 1] Apache Felix Shell TUI (1.0.1)
[ 3] [Active ] [ 1] Apache Felix Bundle Repository (1.0.3)
[ 5] [Active ] [ 1] servlet-api.osgi (2.5.0.SNAPSHOT)
[ 6] [Active ] [ 1] slf4j-log4j12 (1.4.3)
[ 7] [Active ] [ 1] jcl104-over-slf4j (1.4.3)
[ 8] [Active ] [ 1] slf4j-api (1.4.3)
[ 9] [Active ] [ 1] log4j.osgi (1.2.15.SNAPSHOT)
[ 13] [Active ] [ 1] spring-context (2.5.4)
[ 14] [Active ] [ 1] spring-beans (2.5.4)
[ 15] [Active ] [ 1] spring-osgi-core (1.1.0.m2)
[ 16] [Active ] [ 1] spring-core (2.5.4)
[ 17] [Active ] [ 1] aopalliance.osgi (1.0.0.SNAPSHOT)
[ 18] [Active ] [ 1] spring-osgi-io (1.1.0.m2)
[ 19] [Active ] [ 1] spring-aop (2.5.4)
[ 32] [Active ] [ 1] spring-webmvc (2.5.4)
[ 33] [Active ] [ 1] spring-web (2.5.4)
[ 37] [Active ] [ 1] spring-osgi-web (1.1.0.m2)
[ 38] [Active ] [ 1] spring-osgi-extender (1.1.0.m2)
[ 50] [Active ] [ 1] jsp-api.osgi (2.0.0.SNAPSHOT)
[ 51] [Active ] [ 1] jasper.osgi (5.5.23.SNAPSHOT)
[ 52] [Active ] [ 1] commons-el.osgi (1.0.0.SNAPSHOT)
[ 56] [Active ] [ 1] cglib-nodep.osgi (2.1.3.SNAPSHOT)
[ 61] [Active ] [ 1] spring-osgi-web-extender (1.1.0.m2-SNAPSHOT)
[ 64] [Active ] [ 1] catalina.start.osgi (1.0.0.SNAPSHOT)
[ 65] [Active ] [ 1] catalina.osgi (5.5.23.SNAPSHOT)
[ 68] [Active ] [ 1] spring-osgi-webapp Maven Webapp (1.0)
[ 69] [Installed ] [ 1] jstl.osgi (1.1.2.SNAPSHOT)
Zauważyłem jednak, że wiele (wszystkie?) z dyskusji na forum Spring-DM dotyczyły uruchomienia aplikacji webowej na Equinox. Equinox jest projektem platformy OSGi rozwijanym w organizacji Eclipse, która jest podstawą technologiczną dla Eclipse IDE i mechanizmu wtyczek, które de facto są pakunkami OSGi. Zniechęcony wynikami moich doświadczeń z Apache Felix, postanowiłem na koniec sprawdzić uruchomienie aplikacji z Spring-DM na Equinoksie.
 jlaskowski@work ~
$ java -jar c:/apps/eclipse/plugins/org.eclipse.osgi_3.4.0.v20080326.jar -console

osgi> ss

Framework is launched.

id State Bundle
0 ACTIVE org.eclipse.osgi_3.4.0.v20080326
Instaluje wszystkie pakunki Spring-DM konieczne do uruchomienia mojej aplikacji webowej, jak to miało miejsce wcześniej z Apache Felix.
 osgi> ss

Framework is launched.

id State Bundle
0 ACTIVE org.eclipse.osgi_3.4.0.v20080326
1 ACTIVE org.springframework.bundle.osgi.web_1.1.0.m2
2 ACTIVE org.springframework.osgi.servlet-api.osgi_2.5.0.SNAPSHOT
3 ACTIVE jcl104.over.slf4j_1.4.3
4 ACTIVE slf4j.api_1.4.3
5 ACTIVE slf4j.log4j12_1.4.3
6 ACTIVE org.springframework.osgi.log4j.osgi_1.2.15.SNAPSHOT
7 ACTIVE org.springframework.bundle.osgi.extender_1.1.0.m2
8 ACTIVE org.springframework.bundle.spring.context_2.5.4
9 ACTIVE org.springframework.bundle.spring.beans_2.5.4
10 ACTIVE org.springframework.bundle.spring.core_2.5.4
11 ACTIVE org.springframework.osgi.aopalliance.osgi_1.0.0.SNAPSHOT
12 ACTIVE org.springframework.bundle.osgi.io_1.1.0.m2
13 ACTIVE org.springframework.bundle.spring.aop_2.5.4
14 ACTIVE org.springframework.osgi.jsp-api.osgi_2.0.0.SNAPSHOT
15 ACTIVE org.springframework.osgi.jasper.osgi_5.5.23.SNAPSHOT
16 ACTIVE org.springframework.osgi.commons-el.osgi_1.0.0.SNAPSHOT
17 INSTALLED org.springframework.osgi.jstl.osgi_1.1.2.SNAPSHOT
18 RESOLVED org.springframework.osgi.catalina.osgi_6.0.16.SNAPSHOT
19 RESOLVED org.springframework.osgi.catalina.start.osgi_6.0.16.SNAPSHOT
20 RESOLVED org.springframework.osgi.cglib-nodep.osgi_2.1.3.SNAPSHOT
21 RESOLVED org.springframework.bundle.osgi.web.extender_1.1.0.m2-SNAPSHOT
22 RESOLVED org.springframework.osgi.catalina.start.osgi_1.0.0.SNAPSHOT
23 RESOLVED org.springframework.osgi.catalina.osgi_5.5.23.SNAPSHOT
24 ACTIVE pl.jaceklaskowski.osgi.spring-osgi-webapp_1.0.0
25 ACTIVE org.springframework.bundle.osgi.core_1.1.0.m2
a następnie próbuję je wszystkie uruchomić poleceniem start 1 2 ... 25 (zamień ... na odpowiednie liczby - identyfikatory pakunków). Niestety pakunek o identyfikatorze 17 odmawia współpracy wyjątkiem:
 org.osgi.framework.BundleException: The bundle could not be resolved. Reason: Missing Constraint: 
Import-Package: org.apache.taglibs.standard.tag.common.fmt; version="0.0.0"
at org.eclipse.osgi.framework.internal.core.BundleHost.startWorker(BundleHost.java:305)
at org.eclipse.osgi.framework.internal.core.AbstractBundle.start(AbstractBundle.java:265)
at org.eclipse.osgi.framework.internal.core.AbstractBundle.start(AbstractBundle.java:257)
at org.eclipse.osgi.framework.internal.core.FrameworkCommandProvider._start(FrameworkCommandProvider.java:257)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:585)
at org.eclipse.osgi.framework.internal.core.FrameworkCommandInterpreter.execute(FrameworkCommandInterpreter.java:150)
at org.eclipse.osgi.framework.internal.core.FrameworkConsole.docommand(FrameworkConsole.java:303)
at org.eclipse.osgi.framework.internal.core.FrameworkConsole.console(FrameworkConsole.java:288)
at org.eclipse.osgi.framework.internal.core.FrameworkConsole.run(FrameworkConsole.java:224)
at java.lang.Thread.run(Thread.java:595)
Nie wygląda to dobrze. Spróbowałem odszukać biblioteki znaczników standard JSTL jako pakunek OSGi, ale niestety nic nie znalazłem w repozytorium Spring-DM na S3. Skoro nie było, to znaczy, że najprawdopodobniej nie jest potrzebne. Podchodzę jeszcze raz do tematu, tyle że postanawiam uruchomić jedynie moją aplikację webową bez uruchamiania pozostałych pakunków (platforma OSGi zmieni ich stan na RESOLVED, ale nie na ACTIVE, w którym otrzymywałem wyjątek brakującego pakietu. Zawiłości platformy OSGi, w które nie ma co na razie wchodzić). Zmieniam również wersję Equinoksa na starszą - 3.3.2.R33x_v20080105.
 jlaskowski@work ~
$ java -jar c:/.m2/eclipse/eclipse/plugins/org.eclipse.osgi_3.3.2.R33x_v20080105.jar -console

osgi> ss

Framework is launched.

id State Bundle
0 ACTIVE org.eclipse.osgi_3.3.2.R33x_v20080105
Skąd ja wziąłem akurat tą wersję Equinoksa jest poza moją wiedzą - jakoś się kiedyś przy czymś ściągnęło. Najlepiej pobrać aktualną produkcyjną wersję ze strony domowej projektu Equinox. Wersja 3.3.2 powinna spełniać nasze wymagania.
 jlaskowski@work ~
$ java -jar c:/.m2/eclipse/eclipse/plugins/org.eclipse.osgi_3.3.2.R33x_v20080105.jar -console

osgi> ss

Framework is launched.

id State Bundle
0 ACTIVE org.eclipse.osgi_3.3.2.R33x_v20080105

osgi> install file:/C:/apps/spring-osgi/dist/spring-osgi-core-1.1.0-m2.jar
Bundle id is 1

osgi> install file:/C:/apps/spring-osgi/dist/spring-osgi-web-1.1.0-m2.jar
Bundle id is 2

osgi> install file:/C:/apps/spring-osgi/dist/spring-osgi-io-1.1.0-m2.jar
Bundle id is 3

osgi> install file:/C:/apps/spring-osgi/lib/servlet-api.osgi-2.5-SNAPSHOT.jar
Bundle id is 4

osgi> install file:/C:/apps/spring-osgi/lib/jcl104-over-slf4j-1.4.3.jar
Bundle id is 5

osgi> install file:/C:/apps/spring-osgi/lib/slf4j-api-1.4.3.jar
Bundle id is 6

osgi> install file:/C:/apps/spring-osgi/lib/slf4j-log4j12-1.4.3.jar
Bundle id is 7

osgi> install file:/C:/apps/spring-osgi/lib/log4j.osgi-1.2.15-SNAPSHOT.jar
Bundle id is 8

osgi> install file:/C:/apps/spring-osgi/dist/spring-osgi-extender-1.1.0-m2.jar
Bundle id is 9

osgi> install file:/C:/apps/spring-osgi/lib/spring-context-2.5.4.jar
Bundle id is 10

osgi> install file:/C:/apps/spring-osgi/lib/spring-beans-2.5.4.jar
Bundle id is 11

osgi> install file:/C:/apps/spring-osgi/lib/spring-core-2.5.4.jar
Bundle id is 12

osgi> install file:/C:/apps/spring-osgi/lib/aopalliance.osgi-1.0-SNAPSHOT.jar
Bundle id is 13

osgi> install file:/C:/apps/spring-osgi/lib/spring-aop-2.5.4.jar
Bundle id is 14

osgi> install file:/C:/spring-dm-libs/jsp-api.osgi-2.0-SNAPSHOT.jar
Bundle id is 15

osgi> install file:/C:/spring-dm-libs/jasper.osgi-5.5.23-SNAPSHOT.jar
Bundle id is 16

osgi> install file:/C:/spring-dm-libs/commons-el.osgi-1.0-SNAPSHOT.jar
Bundle id is 17

osgi> install file:/C:/spring-dm-libs/jstl.osgi-1.1.2-SNAPSHOT.jar
Bundle id is 18

osgi> install file:/C:/spring-dm-libs/catalina.osgi-6.0.16-SNAPSHOT.jar
Bundle id is 19

osgi> install file:/C:/spring-dm-libs/catalina.start.osgi-6.0.16-SNAPSHOT.jar
Bundle id is 20

osgi> install file:/C:/spring-dm-libs/cglib-nodep.osgi-2.1.3-SNAPSHOT.jar
Bundle id is 21

osgi> install file:/C:/spring-dm-libs/spring-osgi-web-extender-1.1.0-m2-SNAPSHOT.jar
Bundle id is 22

osgi> install file:/C:/spring-dm-libs/catalina.start.osgi-1.0-20080425.161832-4.jar
Bundle id is 23

osgi> install file:/C:/spring-dm-libs/catalina.osgi-5.5.23-20080425.154256-4.jar
Bundle id is 24

osgi> install file:/C:/projs/osgi/spring-osgi-webapp/target/spring-osgi-webapp.war
Bundle id is 25

osgi> ss

Framework is launched.

id State Bundle
0 ACTIVE org.eclipse.osgi_3.3.2.R33x_v20080105
1 INSTALLED org.springframework.bundle.osgi.core_1.1.0.m2
2 INSTALLED org.springframework.bundle.osgi.web_1.1.0.m2
3 INSTALLED org.springframework.bundle.osgi.io_1.1.0.m2
4 INSTALLED org.springframework.osgi.servlet-api.osgi_2.5.0.SNAPSHOT
5 INSTALLED jcl104.over.slf4j_1.4.3
6 INSTALLED slf4j.api_1.4.3
7 INSTALLED slf4j.log4j12_1.4.3
8 INSTALLED org.springframework.osgi.log4j.osgi_1.2.15.SNAPSHOT
9 INSTALLED org.springframework.bundle.osgi.extender_1.1.0.m2
10 INSTALLED org.springframework.bundle.spring.context_2.5.4
11 INSTALLED org.springframework.bundle.spring.beans_2.5.4
12 INSTALLED org.springframework.bundle.spring.core_2.5.4
13 INSTALLED org.springframework.osgi.aopalliance.osgi_1.0.0.SNAPSHOT
14 INSTALLED org.springframework.bundle.spring.aop_2.5.4
15 INSTALLED org.springframework.osgi.jsp-api.osgi_2.0.0.SNAPSHOT
16 INSTALLED org.springframework.osgi.jasper.osgi_5.5.23.SNAPSHOT
17 INSTALLED org.springframework.osgi.commons-el.osgi_1.0.0.SNAPSHOT
18 INSTALLED org.springframework.osgi.jstl.osgi_1.1.2.SNAPSHOT
19 INSTALLED org.springframework.osgi.catalina.osgi_6.0.16.SNAPSHOT
20 INSTALLED org.springframework.osgi.catalina.start.osgi_6.0.16.SNAPSHOT
21 INSTALLED org.springframework.osgi.cglib-nodep.osgi_2.1.3.SNAPSHOT
22 INSTALLED org.springframework.bundle.osgi.web.extender_1.1.0.m2-SNAPSHOT
23 INSTALLED org.springframework.osgi.catalina.start.osgi_1.0.0.SNAPSHOT
24 INSTALLED org.springframework.osgi.catalina.osgi_5.5.23.SNAPSHOT
25 INSTALLED pl.jaceklaskowski.osgi.spring-osgi-webapp_1.0.0

osgi> start 24

osgi> ss

Framework is launched.

id State Bundle
0 ACTIVE org.eclipse.osgi_3.3.2.R33x_v20080105
1 RESOLVED org.springframework.bundle.osgi.core_1.1.0.m2
2 RESOLVED org.springframework.bundle.osgi.web_1.1.0.m2
3 RESOLVED org.springframework.bundle.osgi.io_1.1.0.m2
4 RESOLVED org.springframework.osgi.servlet-api.osgi_2.5.0.SNAPSHOT
5 RESOLVED jcl104.over.slf4j_1.4.3
6 RESOLVED slf4j.api_1.4.3
7 RESOLVED slf4j.log4j12_1.4.3
8 RESOLVED org.springframework.osgi.log4j.osgi_1.2.15.SNAPSHOT
9 RESOLVED org.springframework.bundle.osgi.extender_1.1.0.m2
10 RESOLVED org.springframework.bundle.spring.context_2.5.4
11 RESOLVED org.springframework.bundle.spring.beans_2.5.4
12 RESOLVED org.springframework.bundle.spring.core_2.5.4
13 RESOLVED org.springframework.osgi.aopalliance.osgi_1.0.0.SNAPSHOT
14 RESOLVED org.springframework.bundle.spring.aop_2.5.4
15 RESOLVED org.springframework.osgi.jsp-api.osgi_2.0.0.SNAPSHOT
16 RESOLVED org.springframework.osgi.jasper.osgi_5.5.23.SNAPSHOT
17 RESOLVED org.springframework.osgi.commons-el.osgi_1.0.0.SNAPSHOT
18 INSTALLED org.springframework.osgi.jstl.osgi_1.1.2.SNAPSHOT
19 RESOLVED org.springframework.osgi.catalina.osgi_6.0.16.SNAPSHOT
20 RESOLVED org.springframework.osgi.catalina.start.osgi_6.0.16.SNAPSHOT
21 RESOLVED org.springframework.osgi.cglib-nodep.osgi_2.1.3.SNAPSHOT
22 RESOLVED org.springframework.bundle.osgi.web.extender_1.1.0.m2-SNAPSHOT
23 RESOLVED org.springframework.osgi.catalina.start.osgi_1.0.0.SNAPSHOT
24 ACTIVE org.springframework.osgi.catalina.osgi_5.5.23.SNAPSHOT
25 RESOLVED pl.jaceklaskowski.osgi.spring-osgi-webapp_1.0.0

osgi> start 1

osgi> ss

Framework is launched.

id State Bundle
0 ACTIVE org.eclipse.osgi_3.3.2.R33x_v20080105
1 ACTIVE org.springframework.bundle.osgi.core_1.1.0.m2
2 RESOLVED org.springframework.bundle.osgi.web_1.1.0.m2
3 RESOLVED org.springframework.bundle.osgi.io_1.1.0.m2
4 RESOLVED org.springframework.osgi.servlet-api.osgi_2.5.0.SNAPSHOT
5 RESOLVED jcl104.over.slf4j_1.4.3
6 RESOLVED slf4j.api_1.4.3
7 RESOLVED slf4j.log4j12_1.4.3
8 RESOLVED org.springframework.osgi.log4j.osgi_1.2.15.SNAPSHOT
9 RESOLVED org.springframework.bundle.osgi.extender_1.1.0.m2
10 RESOLVED org.springframework.bundle.spring.context_2.5.4
11 RESOLVED org.springframework.bundle.spring.beans_2.5.4
12 RESOLVED org.springframework.bundle.spring.core_2.5.4
13 RESOLVED org.springframework.osgi.aopalliance.osgi_1.0.0.SNAPSHOT
14 RESOLVED org.springframework.bundle.spring.aop_2.5.4
15 RESOLVED org.springframework.osgi.jsp-api.osgi_2.0.0.SNAPSHOT
16 RESOLVED org.springframework.osgi.jasper.osgi_5.5.23.SNAPSHOT
17 RESOLVED org.springframework.osgi.commons-el.osgi_1.0.0.SNAPSHOT
18 INSTALLED org.springframework.osgi.jstl.osgi_1.1.2.SNAPSHOT
19 RESOLVED org.springframework.osgi.catalina.osgi_6.0.16.SNAPSHOT
20 RESOLVED org.springframework.osgi.catalina.start.osgi_6.0.16.SNAPSHOT
21 RESOLVED org.springframework.osgi.cglib-nodep.osgi_2.1.3.SNAPSHOT
22 RESOLVED org.springframework.bundle.osgi.web.extender_1.1.0.m2-SNAPSHOT
23 RESOLVED org.springframework.osgi.catalina.start.osgi_1.0.0.SNAPSHOT
24 ACTIVE org.springframework.osgi.catalina.osgi_5.5.23.SNAPSHOT
25 RESOLVED pl.jaceklaskowski.osgi.spring-osgi-webapp_1.0.0

osgi> start 22
log4j:WARN No appenders could be found for logger (org.springframework.util.ClassUtils).
log4j:WARN Please initialize the log4j system properly.
org.osgi.framework.BundleException: Exception in org.springframework.osgi.web.extender.internal.activator.WarLoaderListener.start()
of bundle org.springframe...
at org.eclipse.osgi.framework.internal.core.BundleContextImpl.startActivator(BundleContextImpl.java:1018)
at org.eclipse.osgi.framework.internal.core.BundleContextImpl.start(BundleContextImpl.java:974)
at org.eclipse.osgi.framework.internal.core.BundleHost.startWorker(BundleHost.java:346)
at org.eclipse.osgi.framework.internal.core.AbstractBundle.start(AbstractBundle.java:260)
at org.eclipse.osgi.framework.internal.core.AbstractBundle.start(AbstractBundle.java:252)
at org.eclipse.osgi.framework.internal.core.FrameworkCommandProvider._start(FrameworkCommandProvider.java:260)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:585)
at org.eclipse.osgi.framework.internal.core.FrameworkCommandInterpreter.execute(FrameworkCommandInterpreter.java:150)
at org.eclipse.osgi.framework.internal.core.FrameworkConsole.docommand(FrameworkConsole.java:300)
at org.eclipse.osgi.framework.internal.core.FrameworkConsole.console(FrameworkConsole.java:285)
at org.eclipse.osgi.framework.internal.core.FrameworkConsole.run(FrameworkConsole.java:221)
at java.lang.Thread.run(Thread.java:595)
Caused by: org.springframework.osgi.OsgiException: Cannot create Tomcat deployer
at org.springframework.osgi.web.extender.internal.activator.WarListenerConfiguration.createDefaultWarDeployer(WarListenerConfiguration.java:156)
at org.springframework.osgi.web.extender.internal.activator.WarListenerConfiguration.<init>(WarListenerConfiguration.java:84)
at org.springframework.osgi.web.extender.internal.activator.WarLoaderListener.start(WarLoaderListener.java:243)
at org.eclipse.osgi.framework.internal.core.BundleContextImpl$2.run(BundleContextImpl.java:999)
at java.security.AccessController.doPrivileged(Native Method)
at org.eclipse.osgi.framework.internal.core.BundleContextImpl.startActivator(BundleContextImpl.java:993)
... 14 more
Caused by: org.springframework.osgi.service.ServiceUnavailableException: service matching filter=[(objectClass=org.apache.catalina.Service)] unavailable
at org.springframework.osgi.service.importer.internal.aop.ServiceDynamicInterceptor.getTarget(ServiceDynamicInterceptor.java:330)
at org.springframework.osgi.service.importer.internal.aop.ServiceDynamicInterceptor.afterPropertiesSet(ServiceDynamicInterceptor.java:366)
at org.springframework.osgi.service.importer.support.OsgiServiceProxyFactoryBean.createProxy(OsgiServiceProxyFactoryBean.java:118)
at org.springframework.osgi.service.importer.support.AbstractOsgiServiceImportFactoryBean.getObject(AbstractOsgiServiceImportFactoryBean.java:94)
at org.springframework.osgi.web.deployer.internal.util.Utils.createServerServiceProxy(Utils.java:117)
at org.springframework.osgi.web.deployer.tomcat.TomcatWarDeployer.afterPropertiesSet(TomcatWarDeployer.java:90)
at org.springframework.osgi.web.extender.internal.activator.WarListenerConfiguration.createDefaultWarDeployer(WarListenerConfiguration.java:152)
... 19 more
Nested Exception:
org.springframework.osgi.OsgiException: Cannot create Tomcat deployer
at org.springframework.osgi.web.extender.internal.activator.WarListenerConfiguration.createDefaultWarDeployer(WarListenerConfiguration.java:156)
at org.springframework.osgi.web.extender.internal.activator.WarListenerConfiguration.<init>(WarListenerConfiguration.java:84)
at org.springframework.osgi.web.extender.internal.activator.WarLoaderListener.start(WarLoaderListener.java:243)
at org.eclipse.osgi.framework.internal.core.BundleContextImpl$2.run(BundleContextImpl.java:999)
at java.security.AccessController.doPrivileged(Native Method)
at org.eclipse.osgi.framework.internal.core.BundleContextImpl.startActivator(BundleContextImpl.java:993)
at org.eclipse.osgi.framework.internal.core.BundleContextImpl.start(BundleContextImpl.java:974)
at org.eclipse.osgi.framework.internal.core.BundleHost.startWorker(BundleHost.java:346)
at org.eclipse.osgi.framework.internal.core.AbstractBundle.start(AbstractBundle.java:260)
at org.eclipse.osgi.framework.internal.core.AbstractBundle.start(AbstractBundle.java:252)
at org.eclipse.osgi.framework.internal.core.FrameworkCommandProvider._start(FrameworkCommandProvider.java:260)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:585)
at org.eclipse.osgi.framework.internal.core.FrameworkCommandInterpreter.execute(FrameworkCommandInterpreter.java:150)
at org.eclipse.osgi.framework.internal.core.FrameworkConsole.docommand(FrameworkConsole.java:300)
at org.eclipse.osgi.framework.internal.core.FrameworkConsole.console(FrameworkConsole.java:285)
at org.eclipse.osgi.framework.internal.core.FrameworkConsole.run(FrameworkConsole.java:221)
at java.lang.Thread.run(Thread.java:595)
Caused by: org.springframework.osgi.service.ServiceUnavailableException: service matching filter=[(objectClass=org.apache.catalina.Service)] unavailable
at org.springframework.osgi.service.importer.internal.aop.ServiceDynamicInterceptor.getTarget(ServiceDynamicInterceptor.java:330)
at org.springframework.osgi.service.importer.internal.aop.ServiceDynamicInterceptor.afterPropertiesSet(ServiceDynamicInterceptor.java:366)
at org.springframework.osgi.service.importer.support.OsgiServiceProxyFactoryBean.createProxy(OsgiServiceProxyFactoryBean.java:118)
at org.springframework.osgi.service.importer.support.AbstractOsgiServiceImportFactoryBean.getObject(AbstractOsgiServiceImportFactoryBean.java:94)
at org.springframework.osgi.web.deployer.internal.util.Utils.createServerServiceProxy(Utils.java:117)
at org.springframework.osgi.web.deployer.tomcat.TomcatWarDeployer.afterPropertiesSet(TomcatWarDeployer.java:90)
at org.springframework.osgi.web.extender.internal.activator.WarListenerConfiguration.createDefaultWarDeployer(WarListenerConfiguration.java:152)
... 19 more
Nested Exception:
org.springframework.osgi.service.ServiceUnavailableException: service matching filter=[(objectClass=org.apache.catalina.Service)] unavailable
at org.springframework.osgi.service.importer.internal.aop.ServiceDynamicInterceptor.getTarget(ServiceDynamicInterceptor.java:330)
at org.springframework.osgi.service.importer.internal.aop.ServiceDynamicInterceptor.afterPropertiesSet(ServiceDynamicInterceptor.java:366)
at org.springframework.osgi.service.importer.support.OsgiServiceProxyFactoryBean.createProxy(OsgiServiceProxyFactoryBean.java:118)
at org.springframework.osgi.service.importer.support.AbstractOsgiServiceImportFactoryBean.getObject(AbstractOsgiServiceImportFactoryBean.java:94)
at org.springframework.osgi.web.deployer.internal.util.Utils.createServerServiceProxy(Utils.java:117)
at org.springframework.osgi.web.deployer.tomcat.TomcatWarDeployer.afterPropertiesSet(TomcatWarDeployer.java:90)
at org.springframework.osgi.web.extender.internal.activator.WarListenerConfiguration.createDefaultWarDeployer(WarListenerConfiguration.java:152)
at org.springframework.osgi.web.extender.internal.activator.WarListenerConfiguration.<init>(WarListenerConfiguration.java:84)
at org.springframework.osgi.web.extender.internal.activator.WarLoaderListener.start(WarLoaderListener.java:243)
at org.eclipse.osgi.framework.internal.core.BundleContextImpl$2.run(BundleContextImpl.java:999)
at java.security.AccessController.doPrivileged(Native Method)
at org.eclipse.osgi.framework.internal.core.BundleContextImpl.startActivator(BundleContextImpl.java:993)
at org.eclipse.osgi.framework.internal.core.BundleContextImpl.start(BundleContextImpl.java:974)
at org.eclipse.osgi.framework.internal.core.BundleHost.startWorker(BundleHost.java:346)
at org.eclipse.osgi.framework.internal.core.AbstractBundle.start(AbstractBundle.java:260)
at org.eclipse.osgi.framework.internal.core.AbstractBundle.start(AbstractBundle.java:252)
at org.eclipse.osgi.framework.internal.core.FrameworkCommandProvider._start(FrameworkCommandProvider.java:260)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:585)
at org.eclipse.osgi.framework.internal.core.FrameworkCommandInterpreter.execute(FrameworkCommandInterpreter.java:150)
at org.eclipse.osgi.framework.internal.core.FrameworkConsole.docommand(FrameworkConsole.java:300)
at org.eclipse.osgi.framework.internal.core.FrameworkConsole.console(FrameworkConsole.java:285)
at org.eclipse.osgi.framework.internal.core.FrameworkConsole.run(FrameworkConsole.java:221)
at java.lang.Thread.run(Thread.java:595)
Nested Exception:
org.springframework.osgi.OsgiException: Cannot create Tomcat deployer
at org.springframework.osgi.web.extender.internal.activator.WarListenerConfiguration.createDefaultWarDeployer(WarListenerConfiguration.java:156)
at org.springframework.osgi.web.extender.internal.activator.WarListenerConfiguration.<init>(WarListenerConfiguration.java:84)
at org.springframework.osgi.web.extender.internal.activator.WarLoaderListener.start(WarLoaderListener.java:243)
at org.eclipse.osgi.framework.internal.core.BundleContextImpl$2.run(BundleContextImpl.java:999)
at java.security.AccessController.doPrivileged(Native Method)
at org.eclipse.osgi.framework.internal.core.BundleContextImpl.startActivator(BundleContextImpl.java:993)
at org.eclipse.osgi.framework.internal.core.BundleContextImpl.start(BundleContextImpl.java:974)
at org.eclipse.osgi.framework.internal.core.BundleHost.startWorker(BundleHost.java:346)
at org.eclipse.osgi.framework.internal.core.AbstractBundle.start(AbstractBundle.java:260)
at org.eclipse.osgi.framework.internal.core.AbstractBundle.start(AbstractBundle.java:252)
at org.eclipse.osgi.framework.internal.core.FrameworkCommandProvider._start(FrameworkCommandProvider.java:260)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:585)
at org.eclipse.osgi.framework.internal.core.FrameworkCommandInterpreter.execute(FrameworkCommandInterpreter.java:150)
at org.eclipse.osgi.framework.internal.core.FrameworkConsole.docommand(FrameworkConsole.java:300)
at org.eclipse.osgi.framework.internal.core.FrameworkConsole.console(FrameworkConsole.java:285)
at org.eclipse.osgi.framework.internal.core.FrameworkConsole.run(FrameworkConsole.java:221)
at java.lang.Thread.run(Thread.java:595)
Caused by: org.springframework.osgi.service.ServiceUnavailableException: service matching filter=[(objectClass=org.apache.catalina.Service)] unavailable
at org.springframework.osgi.service.importer.internal.aop.ServiceDynamicInterceptor.getTarget(ServiceDynamicInterceptor.java:330)
at org.springframework.osgi.service.importer.internal.aop.ServiceDynamicInterceptor.afterPropertiesSet(ServiceDynamicInterceptor.java:366)
at org.springframework.osgi.service.importer.support.OsgiServiceProxyFactoryBean.createProxy(OsgiServiceProxyFactoryBean.java:118)
at org.springframework.osgi.service.importer.support.AbstractOsgiServiceImportFactoryBean.getObject(AbstractOsgiServiceImportFactoryBean.java:94)
at org.springframework.osgi.web.deployer.internal.util.Utils.createServerServiceProxy(Utils.java:117)
at org.springframework.osgi.web.deployer.tomcat.TomcatWarDeployer.afterPropertiesSet(TomcatWarDeployer.java:90)
at org.springframework.osgi.web.extender.internal.activator.WarListenerConfiguration.createDefaultWarDeployer(WarListenerConfiguration.java:152)
... 19 more
Nested Exception:
org.springframework.osgi.service.ServiceUnavailableException: service matching filter=[(objectClass=org.apache.catalina.Service)] unavailable
at org.springframework.osgi.service.importer.internal.aop.ServiceDynamicInterceptor.getTarget(ServiceDynamicInterceptor.java:330)
at org.springframework.osgi.service.importer.internal.aop.ServiceDynamicInterceptor.afterPropertiesSet(ServiceDynamicInterceptor.java:366)
at org.springframework.osgi.service.importer.support.OsgiServiceProxyFactoryBean.createProxy(OsgiServiceProxyFactoryBean.java:118)
at org.springframework.osgi.service.importer.support.AbstractOsgiServiceImportFactoryBean.getObject(AbstractOsgiServiceImportFactoryBean.java:94)
at org.springframework.osgi.web.deployer.internal.util.Utils.createServerServiceProxy(Utils.java:117)
at org.springframework.osgi.web.deployer.tomcat.TomcatWarDeployer.afterPropertiesSet(TomcatWarDeployer.java:90)
at org.springframework.osgi.web.extender.internal.activator.WarListenerConfiguration.createDefaultWarDeployer(WarListenerConfiguration.java:152)
at org.springframework.osgi.web.extender.internal.activator.WarListenerConfiguration.<init>(WarListenerConfiguration.java:84)
at org.springframework.osgi.web.extender.internal.activator.WarLoaderListener.start(WarLoaderListener.java:243)
at org.eclipse.osgi.framework.internal.core.BundleContextImpl$2.run(BundleContextImpl.java:999)
at java.security.AccessController.doPrivileged(Native Method)
at org.eclipse.osgi.framework.internal.core.BundleContextImpl.startActivator(BundleContextImpl.java:993)
at org.eclipse.osgi.framework.internal.core.BundleContextImpl.start(BundleContextImpl.java:974)
at org.eclipse.osgi.framework.internal.core.BundleHost.startWorker(BundleHost.java:346)
at org.eclipse.osgi.framework.internal.core.AbstractBundle.start(AbstractBundle.java:260)
at org.eclipse.osgi.framework.internal.core.AbstractBundle.start(AbstractBundle.java:252)
at org.eclipse.osgi.framework.internal.core.FrameworkCommandProvider._start(FrameworkCommandProvider.java:260)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:585)
at org.eclipse.osgi.framework.internal.core.FrameworkCommandInterpreter.execute(FrameworkCommandInterpreter.java:150)
at org.eclipse.osgi.framework.internal.core.FrameworkConsole.docommand(FrameworkConsole.java:300)
at org.eclipse.osgi.framework.internal.core.FrameworkConsole.console(FrameworkConsole.java:285)
at org.eclipse.osgi.framework.internal.core.FrameworkConsole.run(FrameworkConsole.java:221)
at java.lang.Thread.run(Thread.java:595)

osgi>

osgi> ss

Framework is launched.

id State Bundle
0 ACTIVE org.eclipse.osgi_3.3.2.R33x_v20080105
1 ACTIVE org.springframework.bundle.osgi.core_1.1.0.m2
2 RESOLVED org.springframework.bundle.osgi.web_1.1.0.m2
3 RESOLVED org.springframework.bundle.osgi.io_1.1.0.m2
4 RESOLVED org.springframework.osgi.servlet-api.osgi_2.5.0.SNAPSHOT
5 RESOLVED jcl104.over.slf4j_1.4.3
6 RESOLVED slf4j.api_1.4.3
7 RESOLVED slf4j.log4j12_1.4.3
8 RESOLVED org.springframework.osgi.log4j.osgi_1.2.15.SNAPSHOT
9 RESOLVED org.springframework.bundle.osgi.extender_1.1.0.m2
10 RESOLVED org.springframework.bundle.spring.context_2.5.4
11 RESOLVED org.springframework.bundle.spring.beans_2.5.4
12 RESOLVED org.springframework.bundle.spring.core_2.5.4
13 RESOLVED org.springframework.osgi.aopalliance.osgi_1.0.0.SNAPSHOT
14 RESOLVED org.springframework.bundle.spring.aop_2.5.4
15 RESOLVED org.springframework.osgi.jsp-api.osgi_2.0.0.SNAPSHOT
16 RESOLVED org.springframework.osgi.jasper.osgi_5.5.23.SNAPSHOT
17 RESOLVED org.springframework.osgi.commons-el.osgi_1.0.0.SNAPSHOT
18 INSTALLED org.springframework.osgi.jstl.osgi_1.1.2.SNAPSHOT
19 RESOLVED org.springframework.osgi.catalina.osgi_6.0.16.SNAPSHOT
20 RESOLVED org.springframework.osgi.catalina.start.osgi_6.0.16.SNAPSHOT
21 RESOLVED org.springframework.osgi.cglib-nodep.osgi_2.1.3.SNAPSHOT
22 RESOLVED org.springframework.bundle.osgi.web.extender_1.1.0.m2-SNAPSHOT
23 RESOLVED org.springframework.osgi.catalina.start.osgi_1.0.0.SNAPSHOT
24 ACTIVE org.springframework.osgi.catalina.osgi_5.5.23.SNAPSHOT
25 RESOLVED pl.jaceklaskowski.osgi.spring-osgi-webapp_1.0.0

osgi> start 23

osgi> 2008-04-30 23:43:48 org.apache.catalina.startup.ClusterRuleSetFactory getClusterRuleSet
INFO: Unable to find a cluster rule set in the classpath. Will load the default rule set.
2008-04-30 23:43:48 org.apache.catalina.startup.ClusterRuleSetFactory getClusterRuleSet
INFO: Unable to find a cluster rule set in the classpath. Will load the default rule set.
2008-04-30 23:43:48 org.apache.coyote.http11.Http11Protocol init
INFO: Initializing Coyote HTTP/1.1 on http-8080
2008-04-30 23:43:48 org.apache.catalina.startup.Catalina load
INFO: Initialization processed in 262 ms
2008-04-30 23:43:48 org.apache.catalina.core.StandardService start
INFO: Starting service Catalina
2008-04-30 23:43:48 org.apache.catalina.core.StandardEngine start
INFO: Starting Servlet Engine: Apache Tomcat/6.0.16
2008-04-30 23:43:48 org.apache.coyote.http11.Http11Protocol start
INFO: Starting Coyote HTTP/1.1 on http-8080

osgi> ss

Framework is launched.

id State Bundle
0 ACTIVE org.eclipse.osgi_3.3.2.R33x_v20080105
1 ACTIVE org.springframework.bundle.osgi.core_1.1.0.m2
2 RESOLVED org.springframework.bundle.osgi.web_1.1.0.m2
3 RESOLVED org.springframework.bundle.osgi.io_1.1.0.m2
4 RESOLVED org.springframework.osgi.servlet-api.osgi_2.5.0.SNAPSHOT
5 RESOLVED jcl104.over.slf4j_1.4.3
6 RESOLVED slf4j.api_1.4.3
7 RESOLVED slf4j.log4j12_1.4.3
8 RESOLVED org.springframework.osgi.log4j.osgi_1.2.15.SNAPSHOT
9 RESOLVED org.springframework.bundle.osgi.extender_1.1.0.m2
10 RESOLVED org.springframework.bundle.spring.context_2.5.4
11 RESOLVED org.springframework.bundle.spring.beans_2.5.4
12 RESOLVED org.springframework.bundle.spring.core_2.5.4
13 RESOLVED org.springframework.osgi.aopalliance.osgi_1.0.0.SNAPSHOT
14 RESOLVED org.springframework.bundle.spring.aop_2.5.4
15 RESOLVED org.springframework.osgi.jsp-api.osgi_2.0.0.SNAPSHOT
16 RESOLVED org.springframework.osgi.jasper.osgi_5.5.23.SNAPSHOT
17 RESOLVED org.springframework.osgi.commons-el.osgi_1.0.0.SNAPSHOT
18 INSTALLED org.springframework.osgi.jstl.osgi_1.1.2.SNAPSHOT
19 RESOLVED org.springframework.osgi.catalina.osgi_6.0.16.SNAPSHOT
20 RESOLVED org.springframework.osgi.catalina.start.osgi_6.0.16.SNAPSHOT
21 RESOLVED org.springframework.osgi.cglib-nodep.osgi_2.1.3.SNAPSHOT
22 RESOLVED org.springframework.bundle.osgi.web.extender_1.1.0.m2-SNAPSHOT
23 ACTIVE org.springframework.osgi.catalina.start.osgi_1.0.0.SNAPSHOT
24 ACTIVE org.springframework.osgi.catalina.osgi_5.5.23.SNAPSHOT
25 RESOLVED pl.jaceklaskowski.osgi.spring-osgi-webapp_1.0.0

osgi> start 22

osgi> ss

Framework is launched.

id State Bundle
0 ACTIVE org.eclipse.osgi_3.3.2.R33x_v20080105
1 ACTIVE org.springframework.bundle.osgi.core_1.1.0.m2
2 RESOLVED org.springframework.bundle.osgi.web_1.1.0.m2
3 RESOLVED org.springframework.bundle.osgi.io_1.1.0.m2
4 RESOLVED org.springframework.osgi.servlet-api.osgi_2.5.0.SNAPSHOT
5 RESOLVED jcl104.over.slf4j_1.4.3
6 RESOLVED slf4j.api_1.4.3
7 RESOLVED slf4j.log4j12_1.4.3
8 RESOLVED org.springframework.osgi.log4j.osgi_1.2.15.SNAPSHOT
9 RESOLVED org.springframework.bundle.osgi.extender_1.1.0.m2
10 RESOLVED org.springframework.bundle.spring.context_2.5.4
11 RESOLVED org.springframework.bundle.spring.beans_2.5.4
12 RESOLVED org.springframework.bundle.spring.core_2.5.4
13 RESOLVED org.springframework.osgi.aopalliance.osgi_1.0.0.SNAPSHOT
14 RESOLVED org.springframework.bundle.spring.aop_2.5.4
15 RESOLVED org.springframework.osgi.jsp-api.osgi_2.0.0.SNAPSHOT
16 RESOLVED org.springframework.osgi.jasper.osgi_5.5.23.SNAPSHOT
17 RESOLVED org.springframework.osgi.commons-el.osgi_1.0.0.SNAPSHOT
18 INSTALLED org.springframework.osgi.jstl.osgi_1.1.2.SNAPSHOT
19 RESOLVED org.springframework.osgi.catalina.osgi_6.0.16.SNAPSHOT
20 RESOLVED org.springframework.osgi.catalina.start.osgi_6.0.16.SNAPSHOT
21 RESOLVED org.springframework.osgi.cglib-nodep.osgi_2.1.3.SNAPSHOT
22 ACTIVE org.springframework.bundle.osgi.web.extender_1.1.0.m2-SNAPSHOT
23 ACTIVE org.springframework.osgi.catalina.start.osgi_1.0.0.SNAPSHOT
24 ACTIVE org.springframework.osgi.catalina.osgi_5.5.23.SNAPSHOT
25 RESOLVED pl.jaceklaskowski.osgi.spring-osgi-webapp_1.0.0

osgi> start 25

osgi> 2008-04-30 23:44:21 org.apache.catalina.startup.DigesterFactory register
WARNING: Could not get url for /javax/servlet/jsp/resources/jsp_2_1.xsd
2008-04-30 23:44:21 org.apache.catalina.startup.DigesterFactory register
WARNING: Could not get url for /javax/servlet/jsp/resources/web-jsptaglibrary_2_1.xsd
2008-04-30 23:44:21 org.apache.catalina.startup.DigesterFactory register
WARNING: Could not get url for /javax/servlet/resources/j2ee_web_services_1_1.xsd


osgi> ss

Framework is launched.

id State Bundle
0 ACTIVE org.eclipse.osgi_3.3.2.R33x_v20080105
1 ACTIVE org.springframework.bundle.osgi.core_1.1.0.m2
2 RESOLVED org.springframework.bundle.osgi.web_1.1.0.m2
3 RESOLVED org.springframework.bundle.osgi.io_1.1.0.m2
4 RESOLVED org.springframework.osgi.servlet-api.osgi_2.5.0.SNAPSHOT
5 RESOLVED jcl104.over.slf4j_1.4.3
6 RESOLVED slf4j.api_1.4.3
7 RESOLVED slf4j.log4j12_1.4.3
8 RESOLVED org.springframework.osgi.log4j.osgi_1.2.15.SNAPSHOT
9 RESOLVED org.springframework.bundle.osgi.extender_1.1.0.m2
10 RESOLVED org.springframework.bundle.spring.context_2.5.4
11 RESOLVED org.springframework.bundle.spring.beans_2.5.4
12 RESOLVED org.springframework.bundle.spring.core_2.5.4
13 RESOLVED org.springframework.osgi.aopalliance.osgi_1.0.0.SNAPSHOT
14 RESOLVED org.springframework.bundle.spring.aop_2.5.4
15 RESOLVED org.springframework.osgi.jsp-api.osgi_2.0.0.SNAPSHOT
16 RESOLVED org.springframework.osgi.jasper.osgi_5.5.23.SNAPSHOT
17 RESOLVED org.springframework.osgi.commons-el.osgi_1.0.0.SNAPSHOT
18 INSTALLED org.springframework.osgi.jstl.osgi_1.1.2.SNAPSHOT
19 RESOLVED org.springframework.osgi.catalina.osgi_6.0.16.SNAPSHOT
20 RESOLVED org.springframework.osgi.catalina.start.osgi_6.0.16.SNAPSHOT
21 RESOLVED org.springframework.osgi.cglib-nodep.osgi_2.1.3.SNAPSHOT
22 ACTIVE org.springframework.bundle.osgi.web.extender_1.1.0.m2-SNAPSHOT
23 ACTIVE org.springframework.osgi.catalina.start.osgi_1.0.0.SNAPSHOT
24 ACTIVE org.springframework.osgi.catalina.osgi_5.5.23.SNAPSHOT
25 ACTIVE pl.jaceklaskowski.osgi.spring-osgi-webapp_1.0.0

osgi> uninstall 25

osgi> ss

Framework is launched.

id State Bundle
0 ACTIVE org.eclipse.osgi_3.3.2.R33x_v20080105
1 ACTIVE org.springframework.bundle.osgi.core_1.1.0.m2
2 RESOLVED org.springframework.bundle.osgi.web_1.1.0.m2
3 RESOLVED org.springframework.bundle.osgi.io_1.1.0.m2
4 RESOLVED org.springframework.osgi.servlet-api.osgi_2.5.0.SNAPSHOT
5 RESOLVED jcl104.over.slf4j_1.4.3
6 RESOLVED slf4j.api_1.4.3
7 RESOLVED slf4j.log4j12_1.4.3
8 RESOLVED org.springframework.osgi.log4j.osgi_1.2.15.SNAPSHOT
9 RESOLVED org.springframework.bundle.osgi.extender_1.1.0.m2
10 RESOLVED org.springframework.bundle.spring.context_2.5.4
11 RESOLVED org.springframework.bundle.spring.beans_2.5.4
12 RESOLVED org.springframework.bundle.spring.core_2.5.4
13 RESOLVED org.springframework.osgi.aopalliance.osgi_1.0.0.SNAPSHOT
14 RESOLVED org.springframework.bundle.spring.aop_2.5.4
15 RESOLVED org.springframework.osgi.jsp-api.osgi_2.0.0.SNAPSHOT
16 RESOLVED org.springframework.osgi.jasper.osgi_5.5.23.SNAPSHOT
17 RESOLVED org.springframework.osgi.commons-el.osgi_1.0.0.SNAPSHOT
18 INSTALLED org.springframework.osgi.jstl.osgi_1.1.2.SNAPSHOT
19 RESOLVED org.springframework.osgi.catalina.osgi_6.0.16.SNAPSHOT
20 RESOLVED org.springframework.osgi.catalina.start.osgi_6.0.16.SNAPSHOT
21 RESOLVED org.springframework.osgi.cglib-nodep.osgi_2.1.3.SNAPSHOT
22 ACTIVE org.springframework.bundle.osgi.web.extender_1.1.0.m2-SNAPSHOT
23 ACTIVE org.springframework.osgi.catalina.start.osgi_1.0.0.SNAPSHOT
24 ACTIVE org.springframework.osgi.catalina.osgi_5.5.23.SNAPSHOT

osgi> install file:/C:/projs/osgi/spring-osgi-webapp/target/spring-osgi-webapp.war
Bundle id is 26

osgi> start 26

osgi> ss

Framework is launched.

id State Bundle
0 ACTIVE org.eclipse.osgi_3.3.2.R33x_v20080105
1 ACTIVE org.springframework.bundle.osgi.core_1.1.0.m2
2 RESOLVED org.springframework.bundle.osgi.web_1.1.0.m2
3 RESOLVED org.springframework.bundle.osgi.io_1.1.0.m2
4 RESOLVED org.springframework.osgi.servlet-api.osgi_2.5.0.SNAPSHOT
5 RESOLVED jcl104.over.slf4j_1.4.3
6 RESOLVED slf4j.api_1.4.3
7 RESOLVED slf4j.log4j12_1.4.3
8 RESOLVED org.springframework.osgi.log4j.osgi_1.2.15.SNAPSHOT
9 RESOLVED org.springframework.bundle.osgi.extender_1.1.0.m2
10 RESOLVED org.springframework.bundle.spring.context_2.5.4
11 RESOLVED org.springframework.bundle.spring.beans_2.5.4
12 RESOLVED org.springframework.bundle.spring.core_2.5.4
13 RESOLVED org.springframework.osgi.aopalliance.osgi_1.0.0.SNAPSHOT
14 RESOLVED org.springframework.bundle.spring.aop_2.5.4
15 RESOLVED org.springframework.osgi.jsp-api.osgi_2.0.0.SNAPSHOT
16 RESOLVED org.springframework.osgi.jasper.osgi_5.5.23.SNAPSHOT
17 RESOLVED org.springframework.osgi.commons-el.osgi_1.0.0.SNAPSHOT
18 INSTALLED org.springframework.osgi.jstl.osgi_1.1.2.SNAPSHOT
19 RESOLVED org.springframework.osgi.catalina.osgi_6.0.16.SNAPSHOT
20 RESOLVED org.springframework.osgi.catalina.start.osgi_6.0.16.SNAPSHOT
21 RESOLVED org.springframework.osgi.cglib-nodep.osgi_2.1.3.SNAPSHOT
22 ACTIVE org.springframework.bundle.osgi.web.extender_1.1.0.m2-SNAPSHOT
23 ACTIVE org.springframework.osgi.catalina.start.osgi_1.0.0.SNAPSHOT
24 ACTIVE org.springframework.osgi.catalina.osgi_5.5.23.SNAPSHOT
26 ACTIVE pl.jaceklaskowski.osgi.spring-osgi-webapp_1.0.0
Na razie czysto, a aplikacja jako pakunek 26 wydaje się być uruchomiona (stan ACTIVE) wraz z pakunkami Tomcata (pakunki 22, 23 i 24). Uruchomienie przeglądarki i skierowanie na adres http://localhost:8080/spring-osgi-webapp/index.jsp kończy się....


Aplikacja webowa spring-osgi-webapp działa!

Na koniec jeszcze raz próba z z Apache Felix 1.0.4 (coś mnie tknęło, że to jednak moja wcześniejsza niewiedza niż niedoskonałości Feliksa były przyczyną niepowodzenia).
 jlaskowski@work /cygdrive/c/apps/felix
$ rm -rf c\:/Documents\ and\ Settings/jlaskowski/.felix

jlaskowski@work /cygdrive/c/apps/felix
$ java -Dfelix.cache.profile=spring-osgi-webapp -jar bin/felix.jar

Welcome to Felix.
=================

DEBUG: WIRE: 1.0 -> org.osgi.service.packageadmin -> 0
DEBUG: WIRE: 1.0 -> org.osgi.service.startlevel -> 0
DEBUG: WIRE: 1.0 -> org.ungoverned.osgi.service.shell -> 1.0
DEBUG: WIRE: 1.0 -> org.osgi.framework -> 0
DEBUG: WIRE: 1.0 -> org.apache.felix.shell -> 1.0
DEBUG: WIRE: 2.0 -> org.osgi.framework -> 0
DEBUG: WIRE: 2.0 -> org.apache.felix.shell -> 1.0
DEBUG: WIRE: 3.0 -> org.osgi.service.obr -> 3.0
DEBUG: WIRE: 3.0 -> org.osgi.framework -> 0
-> DEBUG: WIRE: 3.0 -> org.apache.felix.shell -> 1.0

...tutaj instaluję pakunki i niektóre uruchamiam (w stanie ACTIVE)

-> ps
START LEVEL 1
ID State Level Name
[ 0] [Active ] [ 0] System Bundle (1.0.4)
[ 1] [Active ] [ 1] Apache Felix Shell Service (1.0.1)
[ 2] [Active ] [ 1] Apache Felix Shell TUI (1.0.1)
[ 3] [Active ] [ 1] Apache Felix Bundle Repository (1.0.3)
[ 4] [Active ] [ 1] spring-osgi-core (1.1.0.m2)
[ 5] [Resolved ] [ 1] spring-osgi-web (1.1.0.m2)
[ 6] [Resolved ] [ 1] spring-osgi-io (1.1.0.m2)
[ 7] [Resolved ] [ 1] servlet-api.osgi (2.5.0.SNAPSHOT)
[ 8] [Resolved ] [ 1] jcl104-over-slf4j (1.4.3)
[ 9] [Resolved ] [ 1] slf4j-api (1.4.3)
[ 10] [Resolved ] [ 1] slf4j-log4j12 (1.4.3)
[ 11] [Resolved ] [ 1] log4j.osgi (1.2.15.SNAPSHOT)
[ 12] [Installed ] [ 1] spring-osgi-extender (1.1.0.m2)
[ 13] [Resolved ] [ 1] spring-context (2.5.4)
[ 14] [Resolved ] [ 1] spring-beans (2.5.4)
[ 15] [Resolved ] [ 1] spring-core (2.5.4)
[ 16] [Resolved ] [ 1] aopalliance.osgi (1.0.0.SNAPSHOT)
[ 17] [Resolved ] [ 1] spring-aop (2.5.4)
[ 18] [Resolved ] [ 1] jsp-api.osgi (2.0.0.SNAPSHOT)
[ 19] [Resolved ] [ 1] jasper.osgi (5.5.23.SNAPSHOT)
[ 20] [Resolved ] [ 1] commons-el.osgi (1.0.0.SNAPSHOT)
[ 21] [Installed ] [ 1] jstl.osgi (1.1.2.SNAPSHOT)
[ 22] [Resolved ] [ 1] cglib-nodep.osgi (2.1.3.SNAPSHOT)
[ 23] [Active ] [ 1] spring-osgi-web-extender (1.1.0.m2-SNAPSHOT)
[ 24] [Active ] [ 1] catalina.start.osgi (1.0.0.SNAPSHOT)
[ 25] [Active ] [ 1] catalina.osgi (5.5.23.SNAPSHOT)
[ 26] [Active ] [ 1] spring-osgi-webapp Maven Webapp (1.0)
Kieruję przeglądarkę na adres aplikacji i okazuje się, że z Felix też działa! Wersje pakunków i ich stan (uruchomiony - ACTIVE bądź jedynie rozpoznany - RESOLVED) ma najwyraźniej znacznie.

A na koniec ciekawa lektura SpringSource Launches New Application Server without Java EE. I co?! Kto już o tym wspominał rok temu, że aspiracjami i21 czy teraz SpringSource to właśnie rynek serwerów aplikacyjnych, gdzie możnaby potraktować Spring Framework z dodatkami jako właśnie serwer aplikacyjny?! Ciekawe, co teraz oponenci takiego spojrzenia mają do powiedzenia?! Zamieniam się w słuch...

Pytanie konkursowe: Jaki nagłówek manifestu służy Spring-DM do rozpoznania pakunku aplikacji webowej do uruchomienia? Nagród nie przewiduje się.