Download presentation
Presentation is loading. Please wait.
Published byMyles Smith Modified over 8 years ago
1
From “Hello World” to Real World : Building web apps with Spring OSGi Craig Walls The Spring Experience 2007 December 12, 2007
2
Who are you? By show of hands... By show of hands... – Java 6? Java 5? 1.4? 1.3? 1.2 or earlier? – Spring 2.5? Spring 2.0? 1.2 or earlier? – Other languages? C#? Groovy? Ruby? Erlang? Scala? Favorite sessions this week? Favorite sessions this week? What do you hope to get from this session? What do you hope to get from this session?
3
Who am I? Software developer for over 13 years Software developer for over 13 years Worked in telecom, finance, retail, education, and software Worked in telecom, finance, retail, education, and software Developed in Java, C#, Groovy, Ruby, C, C++, C#,...(and more) Developed in Java, C#, Groovy, Ruby, C, C++, C#,...(and more) Spring fanatic Spring fanatic Author of Spring in Action and XDoclet in Action Author of Spring in Action and XDoclet in Action
4
Agenda A brief intro to OSGi A brief intro to OSGi Springifying OSGi Springifying OSGi The end of the WAR The end of the WAR
5
Have you ever used OSGi? Good chance that you have! Good chance that you have! – Eclipse – WebSphere 6.1 – BMW
6
The Spring piece of the puzzle Loose coupling through dependency injection and AOP Loose coupling through dependency injection and AOP Promotes POJO-based development Promotes POJO-based development Rich framework of services and abstractions Rich framework of services and abstractions
7
What about OSGi? Coarse-grained component model Coarse-grained component model Bundle-level deployment Bundle-level deployment May expose services May expose services Not entirely POJO-friendly Not entirely POJO-friendly
8
Spring and OSGi together Even more loosely-coupled components Even more loosely-coupled components Dynamic Dependency Injection Dynamic Dependency Injection
9
Getting started: Where to get it Spring Dynamic Modules for OSGi (aka, Spring-OSGi or Spring-DM) Spring Dynamic Modules for OSGi (aka, Spring-OSGi or Spring-DM) – http://www.springframework.org/osgi Containers Containers – Equinox, Knopflerfish, Felix, Concierge Meta-container Meta-container – PaxRunner http://wiki.ops4j.org/confluence/display/ops4j/Pax+Runner
10
Spring-DM: Key elements OSGi extender bundle OSGi extender bundle – Automatically creates Spring context for Spring-enabled bundles Transparent publishing of POJOs as services Transparent publishing of POJOs as services Transparent consumption of services in Spring context Transparent consumption of services in Spring context
11
Getting started: Simple example The obligatory “Hello World” bundle The obligatory “Hello World” bundle Without Spring Without Spring With Spring With Spring As service/consumer bundles As service/consumer bundles
12
Simple Hello World: No Spring Bundle activator Bundle activator – Effectively the “main” class package com.habuma.hello; import org.osgi.framework.BundleActivator; import org.osgi.framework.BundleContext; public class HelloWorld implements BundleActivator { public void start(BundleContext ctx) throws Exception { System.out.println("Hello World!"); } public void stop(BundleContext ctx) throws Exception { System.out.println("Goodbye World!"); } package com.habuma.hello; import org.osgi.framework.BundleActivator; import org.osgi.framework.BundleContext; public class HelloWorld implements BundleActivator { public void start(BundleContext ctx) throws Exception { System.out.println("Hello World!"); } public void stop(BundleContext ctx) throws Exception { System.out.println("Goodbye World!"); }
13
Simple Hello World: Manifest In META-INF/MANIFEST.MF In META-INF/MANIFEST.MF Manifest-Version: 1.0 Bundle-Name: HelloWorld Bundle-Activator: com.habuma.hello.HelloWorld Bundle-SymbolicName: HelloWorld Bundle-Version: 1.0.0 Import-Package: org.osgi.framework Manifest-Version: 1.0 Bundle-Name: HelloWorld Bundle-Activator: com.habuma.hello.HelloWorld Bundle-SymbolicName: HelloWorld Bundle-Version: 1.0.0 Import-Package: org.osgi.framework
14
Hello World with Spring-DM Main class can be a POJO: Main class can be a POJO: package com.habuma.hello; public class HelloWorld { public void start() throws Exception { System.out.println("Hello World!"); } public void stop() throws Exception { System.out.println("Goodbye World!"); } package com.habuma.hello; public class HelloWorld { public void start() throws Exception { System.out.println("Hello World!"); } public void stop() throws Exception { System.out.println("Goodbye World!"); }
15
Hello World with Spring-DM (2) Declared in Spring Declared in Spring – Configured in META-INF/spring/helloworld.xml – Triggered by init-method/destroy-method <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.5.xsd"> <bean id="helloWorld" class="com.habuma.hello.HelloWorld" init-method="start" destroy-method="stop" /> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.5.xsd"> <bean id="helloWorld" class="com.habuma.hello.HelloWorld" init-method="start" destroy-method="stop" />
16
Hello World with Spring-DM (3) Nothing special in the manifest... Nothing special in the manifest... But, MANIFEST.MF could specify Spring config location: But, MANIFEST.MF could specify Spring config location: Manifest-Version: 1.0 Bundle-Name: HelloSpringWorld Bundle-SymbolicName: HelloSpringWorld Bundle-Version: 1.0.0 Import-Package: org.osgi.framework Manifest-Version: 1.0 Bundle-Name: HelloSpringWorld Bundle-SymbolicName: HelloSpringWorld Bundle-Version: 1.0.0 Import-Package: org.osgi.framework Spring-Context: config/HelloWorld.xml
17
Hello World Service Still implemented as a POJO: Still implemented as a POJO: package com.habuma.hello.service; public class HelloServiceImpl implements HelloService { public String sayHello() { return "Hello World! I'm a service!"; } public String sayGoodbye() { return "I gotta go. See ya later!"; } package com.habuma.hello.service; public class HelloServiceImpl implements HelloService { public String sayHello() { return "Hello World! I'm a service!"; } public String sayGoodbye() { return "I gotta go. See ya later!"; }
18
Hello World Service (2) Wired in Spring Wired in Spring – As a bean – Exposed as service using – Exposed as service using <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:osgi="http://www.springframework.org/schema/osgi" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.5.xsd http://www.springframework.org/schema/osgi http://www.springframework.org/schema/osgi/spring-osgi.xsd"> <bean id="helloService" class="com.habuma.hello.service.HelloServiceImpl" /> <osgi:service ref="helloService" interface="com.habuma.hello.service.HelloService" /> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:osgi="http://www.springframework.org/schema/osgi" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.5.xsd http://www.springframework.org/schema/osgi http://www.springframework.org/schema/osgi/spring-osgi.xsd"> <bean id="helloService" class="com.habuma.hello.service.HelloServiceImpl" /> <osgi:service ref="helloService" interface="com.habuma.hello.service.HelloService" />
19
Hello World Service (3) Still nothing special in the manifest... Still nothing special in the manifest... – Except that it exports the service's package Manifest-Version: 1.0 Bundle-Name: HelloSpringService Bundle-SymbolicName: HelloSpringService Bundle-Version: 1.0.0 Export-Package: com.habuma.hello.service Import-Package: org.osgi.framework Manifest-Version: 1.0 Bundle-Name: HelloSpringService Bundle-SymbolicName: HelloSpringService Bundle-Version: 1.0.0 Export-Package: com.habuma.hello.service Import-Package: org.osgi.framework
20
Hello World Consumer Implemented as a POJO Implemented as a POJO package com.habuma.hello; import com.habuma.hello.service.HelloService; public class HelloWorld { public void start() throws Exception { System.out.println(helloService.sayHello()); } public void stop() throws Exception { System.out.println(helloService.sayGoodbye()); } // injected private HelloService helloService; public void setHelloService(HelloService helloService) { this.helloService = helloService; } package com.habuma.hello; import com.habuma.hello.service.HelloService; public class HelloWorld { public void start() throws Exception { System.out.println(helloService.sayHello()); } public void stop() throws Exception { System.out.println(helloService.sayGoodbye()); } // injected private HelloService helloService; public void setHelloService(HelloService helloService) { this.helloService = helloService; }
21
Hello World Consumer (2) Wired in Spring Wired in Spring <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:osgi="http://www.springframework.org/schema/osgi" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.5.xsd http://www.springframework.org/schema/osgi http://www.springframework.org/schema/osgi/spring-osgi.xsd"> <bean id="helloWorld" class="com.habuma.hello.HelloWorld" init-method="start" destroy-method="stop">... <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:osgi="http://www.springframework.org/schema/osgi" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.5.xsd http://www.springframework.org/schema/osgi http://www.springframework.org/schema/osgi/spring-osgi.xsd"> <bean id="helloWorld" class="com.habuma.hello.HelloWorld" init-method="start" destroy-method="stop">...
22
Hello World Consumer (3) Hello service is wired in through Hello service is wired in through – Notice that only an interface is specified <osgi:reference id="helloService" interface="com.habuma.hello.service.HelloService" /> <osgi:reference id="helloService" interface="com.habuma.hello.service.HelloService" />
23
Hello World Consumer (4) Still not much special in the manifest Still not much special in the manifest – Except import of the service package Manifest-Version: 1.0 Bundle-Name: HelloSpringConsumer Bundle-SymbolicName: HelloSpringConsumer Bundle-Version: 1.0.0 Import-Package: org.osgi.framework,com.habuma.hello.service Manifest-Version: 1.0 Bundle-Name: HelloSpringConsumer Bundle-SymbolicName: HelloSpringConsumer Bundle-Version: 1.0.0 Import-Package: org.osgi.framework,com.habuma.hello.service
24
What Spring-DM needs Spring-DM itself Spring-DM itself – Extender bundle – Core bundle – I/O support bundle Spring Framework Spring Framework – spring-core.jar – spring-beans.jar – spring-aop.jar Supporting libraries Supporting libraries – AOP Alliance – cglib-nodep (for proxying classes) – commons-logging (SLF4J recommended) – Log4J (or some logging implementation) – backport-util (when running on JDK 1.4)
25
Embedded Jetty HTTP service Equinox Jetty bundle Equinox Jetty bundle Equinox HTTP service servlet bundle Equinox HTTP service servlet bundle javax.servlet 2.4.0 bundle javax.servlet 2.4.0 bundle Jetty 5.1.11 Jetty 5.1.11 Commons Logging Commons Logging Eclipse OSGi services Eclipse OSGi services
26
PaxRunner Starts OSGi container of your choice Starts OSGi container of your choice – Felix by default – Also supports Knopflerfish, Concierge, and Equinox Can automatically load bundles Can automatically load bundles – From file or HTTP URLs – Or from Maven repository
27
A typical Java web app
28
A typical OSGi application
29
OSGi app with Spring-DM
30
Domain bundle Basic domain POJOs Basic domain POJOs No services, no imports, no Spring-DM required No services, no imports, no Spring-DM required Manifest exports domain package Manifest exports domain package Manifest-Version: 1.0 Bundle-ManifestVersion: 2 Bundle-Name: SpitterDomain Bundle-SymbolicName: com.habuma.SpitterDomain Bundle-Version: 1.0.0 Export-Package: com.habuma.spitter.domain Manifest-Version: 1.0 Bundle-ManifestVersion: 2 Bundle-Name: SpitterDomain Bundle-SymbolicName: com.habuma.SpitterDomain Bundle-Version: 1.0.0 Export-Package: com.habuma.spitter.domain
31
Persistence layer bundle Manifest exports DAO package Manifest exports DAO package – So that consumers can see interfaces Imports Domain package Imports Domain package Manifest-Version: 1.0 Bundle-ManifestVersion: 2 Bundle-Name: SpitterMemoryPersistence Bundle-SymbolicName: com.habuma.SpitterMemoryPersistence Bundle-Version: 1.0.0 Import-Package: com.habuma.spitter.domain Export-Package: com.habuma.spitter.persistence Manifest-Version: 1.0 Bundle-ManifestVersion: 2 Bundle-Name: SpitterMemoryPersistence Bundle-SymbolicName: com.habuma.SpitterMemoryPersistence Bundle-Version: 1.0.0 Import-Package: com.habuma.spitter.domain Export-Package: com.habuma.spitter.persistence
32
Persistence layer bundle (2) Spring-DM exports DAO beans as OSGi services Spring-DM exports DAO beans as OSGi services <beans xmlns:osgi="http://www.springframework.org/schema/osgi" xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.springframework.org/schema/osgi http://www.springframework.org/schema/osgi/spring-osgi.xsd http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.5.xsd"> <bean id="spittleDao" class="com.habuma.spitter.persistence.InMemorySpittleDao" /> <osgi:service id="spittleDaoService" ref="spittleDao" interface="com.habuma.spitter.persistence.SpittleDao" /> <beans xmlns:osgi="http://www.springframework.org/schema/osgi" xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.springframework.org/schema/osgi http://www.springframework.org/schema/osgi/spring-osgi.xsd http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.5.xsd"> <bean id="spittleDao" class="com.habuma.spitter.persistence.InMemorySpittleDao" /> <osgi:service id="spittleDaoService" ref="spittleDao" interface="com.habuma.spitter.persistence.SpittleDao" />
33
Service layer bundle Manifest imports DAO and Domain packages Manifest imports DAO and Domain packages Exports Service package Exports Service package Manifest-Version: 1.0 Bundle-ManifestVersion: 2 Bundle-Name: SpitterService Bundle-SymbolicName: com.habuma.SpitterService Bundle-Version: 1.0.0 Import-Package: com.habuma.spitter.domain, com.habuma.spitter.persistence Export-Package: com.habuma.spitter.service Manifest-Version: 1.0 Bundle-ManifestVersion: 2 Bundle-Name: SpitterService Bundle-SymbolicName: com.habuma.SpitterService Bundle-Version: 1.0.0 Import-Package: com.habuma.spitter.domain, com.habuma.spitter.persistence Export-Package: com.habuma.spitter.service
34
Service layer bundle (2) References DAO service References DAO service Exports service POJO as OSGi service Exports service POJO as OSGi service <beans xmlns:osgi="http://www.springframework.org/schema/osgi" xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.springframework.org/schema/osgi http://www.springframework.org/schema/osgi/spring-osgi.xsd http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.5.xsd"> <osgi:reference id="spittleDao" interface="com.habuma.spitter.persistence.SpittleDao" /> <osgi:service id="spitterServiceService" ref="spitterService" interface="com.habuma.spitter.service.SpitterService" /> <beans xmlns:osgi="http://www.springframework.org/schema/osgi" xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.springframework.org/schema/osgi http://www.springframework.org/schema/osgi/spring-osgi.xsd http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.5.xsd"> <osgi:reference id="spittleDao" interface="com.habuma.spitter.persistence.SpittleDao" /> <osgi:service id="spitterServiceService" ref="spitterService" interface="com.habuma.spitter.service.SpitterService" />
35
Presentation layer options Deploy presentation layer as another OSGi bundle Deploy presentation layer as another OSGi bundle – No application server required – Servlet/JSP support embedded in OSGi as a service Deploy presentation layer as a WAR file in a web container Deploy presentation layer as a WAR file in a web container – OSGi container embedded in web application – All other layer bundles deployed in embedded OSGi container
36
Presentation layer bundle Now here's the tricky part... Now here's the tricky part... – No WAR file – No WEB-INF/web.xml How do you register the servlet(s)? How do you register the servlet(s)? – With a ServiceTracker
37
Service tracker Register servlets programmatically Register servlets programmatically TODO: INSERT SERVICE TRACKER CODE HERE
Similar presentations
© 2025 SlidePlayer.com. Inc.
All rights reserved.