1 準備開發工具

a) SpringSource Tool Suite 2.9.2.REALEASE:解壓即可
http://download.springsource.com/release/STS/2.9.2/dist/e3.7/springsource-tool-suite-2.9.2.RELEASE-e3.7.2-win32-x86_64.zip

b) Virgo Tomcat Server 3.5.0.RELEASE:解壓即可
http://eclipse.stu.edu.tw//virgo/release/VTS/3.5.0.RELEASE/virgo-tomcat-server-3.5.0.RELEASE.zip

c) Virgo插件:通過Update site安裝
http://download.eclipse.org/virgo/milestone/tooling

2 運行SpringSource Tool Suite

a)  進入SpringSource安裝目錄/sts-2.9.2.RELEASE,點擊STS.exe

3 創建Virgo Runtime

a) Window->Preferences->Server->Runtime Environment->add

b) 輸入vi過濾,選中EclicpseRT下的Virgo Runtime,勾選Create a new local server,點擊Next

c) 點擊browse,選中Virgo Tomcat Server安裝目錄確定

4 管理Bundle依賴

a) 打開Server視圖
Window->Show View->Server

b) 打開Server編輯器
在Server view中雙擊已創建好的Virgo Server

c) 進入Repository標簽頁
在Server編輯器下方點擊Repository


d) 下載hibernate相關bundle
Repository標簽頁左上側輸入框輸入antlr->點擊search,勾選輸入框下方搜索結果中的bundles:com.springsource.antlr,點擊Repository標簽頁中間下方的download按鈕,依次下載如下bundle
com.springsource.antlr-2.7.6.jar
com.springsource.com.mysql.jdbc-5.1.6.jar
com.springsource.javassist-3.3.0.ga.jar
com.springsource.net.sf.cglib-2.1.3.jar
com.springsource.org.apache.commons.collections-3.2.1.jar
com.springsource.org.apache.commons.dbcp-1.2.2.osgi.jar
com.springsource.org.apache.commons.pool-1.4.0.jar
com.springsource.org.dom4j-1.6.1.jar
com.springsource.org.hibernate.annotations.common-3.3.0.ga.jar
com.springsource.org.hibernate.annotations-3.4.0.GA.jar
com.springsource.org.hibernate-3.3.1.GA.jar
com.springsource.org.jgroups-2.5.1.jar

e) 查看下載完畢的bundle
下載的bundle存放在Virgo服務器安裝目錄/Repository/usr目錄下,如果不可見,嘗試點擊右側Refresh按鈕或右下方Update the bundle and library index鏈接,Virgo服務器安裝目錄/Repository/ext目錄下存放的是服務器自帶的bundle

5 開發Bundle

5.1 com.dw.test.datasource

a) 創建bundle項目
File->new->project,輸入bun過濾,選中Virgo下的bundle項目->next,輸入com.dw.test.datasource->next,勾選Enable Bundle Classpath Container,Target runtime下拉框選擇Virgo Runtime->finish

b) 導入依賴包
雙擊src/META-INF/MANIFEST.MF->點擊下方dependencies標簽頁->在Import Package區域點擊Add按鈕->輸入com.mysql.jdbc,點擊OK。按此步驟依次導入以下依賴包
com.mysql.jdbc,javax.sql,org.apache.commons.dbcp

c) 定義Spring bean
src/META-INF/spring/appContext.xml

 1<?xml version="1.0" encoding="UTF-8"?>
 2<beans xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
 3    xmlns="http://www.springframework.org/schema/beans"
 4    xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd"
 5    xmlns:p="http://www.springframework.org/schema/p">
 6
 7    <bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource"
 8        p:driverClassName="com.mysql.jdbc.Driver"
 9        p:url="jdbc:mysql://localhost:3306/test?autoReconnect=true"
10        p:username="root" p:password="" init-method="createDataSource"
11        destroy-method="close" />
12
13</beans>


d) 定義Spring OSGi bean
src/META-INF/spring/osgiContext.xml

 1<?xml version="1.0" encoding="UTF-8"?>
 2<beans xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
 3    xmlns="http://www.springframework.org/schema/beans" xmlns:osgi="http://www.springframework.org/schema/osgi"
 4    xsi:schemaLocation="http://www.springframework.org/schema/beans
 5        http://www.springframework.org/schema/beans/spring-beans.xsd
 6        http://www.springframework.org/schema/osgi
 7        http://www.springframework.org/schema/osgi/spring-osgi.xsd">
 8
 9    <osgi:service ref="dataSource" interface="javax.sql.DataSource" />
10
11</beans>


5.2 com.dw.test.domain

a) 創建
bundle項目,名為com.dw.test.domain,參考5.1 a

b)
導入依賴包javax.persistence,javassist.util.proxy,org.hibernate.proxy,參考5.1 b

c) 創建并導出共享包
創建包com.dw.test.domain,打開src/META-INF/MANIFEST.MF編輯器->點擊runtime標簽頁->在Exported Packages區域點擊Add按鈕->輸入com.dw.test.domain,點擊OK

d) 創建entity
src/com.dw.test.domain.User.java

 1package com.dw.test.domain;
 2
 3import java.io.Serializable;
 4
 5import javax.persistence.Basic;
 6import javax.persistence.Entity;
 7import javax.persistence.GeneratedValue;
 8import javax.persistence.GenerationType;
 9import javax.persistence.Id;
10import javax.persistence.Table;
11
12@Entity
13@Table(name = "user")
14public class User implements Serializable {
15
16    private static final long serialVersionUID = 1L;
17
18    @Id
19    @GeneratedValue(strategy = GenerationType.AUTO)
20    private Long id;
21    @Basic
22    private String username;
23    @Basic
24    private String password;
25
26    public Long getId() {
27        return id;
28    }

29
30    public void setId(Long id) {
31        this.id = id;
32    }

33
34    public String getUsername() {
35        return username;
36    }

37
38    public void setUsername(String username) {
39        this.username = username;
40    }

41
42    public String getPassword() {
43        return password;
44    }

45
46    public void setPassword(String password) {
47        this.password = password;
48    }

49
50}

51

5.3 com.dw.test.dao

a) 創建bundle項目,名為com.dw.test.dao,參考5.1 a

b) 引入項目com.dw.test.domain
右鍵項目->點擊Properties->選中Project References->勾選com.dw.test.domain->點擊OK

c) 導入依賴包com.dw.test.domain,參考5.1 b

d) 創建并導出共享包com.dw.test.dao,參考5.2 c

e) 創建IBaseDao基類接口
src/com.dw.test.dao.IBaseDao
 1package com.dw.test.dao;
 2
 3import java.io.Serializable;
 4
 5public interface IBaseDao<T> {
 6
 7    void save(T entity);
 8    
 9    void update(T entity);
10    
11    void delete(T entity);
12
13    T findById(Serializable id);
14
15}

f) 創建IUserDao業務接口
src/com.dw.test.dao.IUserDao
1package com.dw.test.dao;
2
3import com.dw.test.domain.User;
4
5
6public interface IUserDao extends IBaseDao<User>{
7
8}

5.4 com.dw.test.dao.impl

a) 創建bundle項目,名為com.dw.test.dao.impl,參考5.1 a

b) 引入項目com.dw.test.domain,com.dw.test.dao,參考5.3 b

c) 導入依賴包com.dw.test.domain,com.dw.test.dao,javax.sql,參考5.1 b

d) 導入Hibernate bundle
雙擊src/META-INF/MANIFEST.MF->點擊下方dependencies標簽頁->在Import Bundle區域點擊Add按鈕->輸入com.springsource.org.hibernate,點擊OK。

e) 導入Spring庫
雙擊src/META-INF/MANIFEST.MF->點擊下方dependencies標簽頁->在Import Library區域點擊Add按鈕->輸入org.springframework.spring,點擊OK。

f) 實現IBaseDao接口
src/com.dw.test.dao.impl.BaseDaoImpl.java
 1package com.dw.test.dao.impl;
 2
 3import java.io.Serializable;
 4import java.lang.reflect.ParameterizedType;
 5import java.lang.reflect.Type;
 6
 7import org.springframework.orm.hibernate3.support.HibernateDaoSupport;
 8
 9import com.dw.test.dao.IBaseDao;
10
11public abstract class BaseDaoImpl<T> extends
12        HibernateDaoSupport implements IBaseDao<T> {
13
14    protected Class<T> entityclass;
15
16    public BaseDaoImpl() {
17        entityclass = getEntityClass();
18    }

19
20    @Override
21    public void save(T entity) {
22        getHibernateTemplate().save(entity);
23    }

24
25    @Override
26    public void update(T entity) {
27        getHibernateTemplate().update(entity);
28    }

29
30    @Override
31    public void delete(T entity) {
32        getHibernateTemplate().delete(entity);
33    }
;
34    
35    @Override
36    public T findById(Serializable id) {
37        T entity = getHibernateTemplate().get(entityclass, id);
38        return entity;
39    }

40
41    @SuppressWarnings("unchecked")
42    protected Class<T> getEntityClass() {
43        Type type = getClass().getGenericSuperclass();
44        Class<T> result = null;
45        if (type instanceof ParameterizedType) {
46            ParameterizedType parameterizedType = (ParameterizedType) type;
47            result = (Class<T>) parameterizedType.getActualTypeArguments()[0];
48        }

49        return result;
50    }

51
52}

g) 實現IUserDao接口
src/com.dw.test.dao.impl.UserDaoImpl.java
1package com.dw.test.dao.impl;
2
3import org.springframework.stereotype.Repository;
4
5import com.dw.test.dao.IUserDao;
6import com.dw.test.domain.User;
7
8
9@Repository("userDao")
10public class UserDaoImpl extends BaseDaoImpl<User> implements IUserDao{
11
12}

h) 定義Spring Bean
src/META-INF/spring/appContext.xml
1<?xml version="1.0" encoding="UTF-8"?>
2<beans xmlns="http://www.springframework.org/schema/beans"
3 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context"
4 xsi:schemaLocation="http://www.springframework.org/schema/beans
5 http://www.springframework.org/schema/beans/spring-beans.xsd
6 http://www.springframework.org/schema/context
7 http://www.springframework.org/schema/context/spring-context.xsd" default-autowire="byName">
8
9 <context:annotation-config />
10
11 <context:component-scan base-package="com.dw.test" />
12
13 <bean id="sessionFactory" class="org.springframework.orm.hibernate3.annotation.AnnotationSessionFactoryBean">
14 <property name="dataSource" ref="dataSource" />
15 <property name="schemaUpdate" value="false" />
16 <property name="hibernateProperties">
17 <props>
18 <prop key="hibernate.dialect">
19 org.hibernate.dialect.MySQLDialect
20 </prop>
21 <prop key="hibernate.show_sql">true</prop>
22 <prop key="cache.provider_class">org.hibernate.cache.NoCacheProvider</prop>
23 </props>
24 </property>
25 <property name="annotatedClasses">
26 <list>
27 <value>com.dw.test.domain.User</value>
28 </list>
29 </property>
30 </bean>
31
32 <bean id="transactionManager" class="org.springframework.orm.hibernate3.HibernateTransactionManager">
33 <property name="sessionFactory" ref="sessionFactory" />
34 </bean>
35</beans>

i) 定義OSGi bean

src/META-INF/spring/osgiContext.xml
 1<?xml version="1.0" encoding="UTF-8"?>
 2<beans xmlns="http://www.springframework.org/schema/beans"
 3    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
 4    xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
 5        http://www.springframework.org/schema/osgi http://www.springframework.org/schema/osgi/spring-osgi.xsd"
 6    xmlns:osgi="http://www.springframework.org/schema/osgi">
 7
 8    <osgi:reference id="dataSource" interface="javax.sql.DataSource" />
 9    
10    <osgi:service ref="sessionFactory" interface="org.hibernate.SessionFactory" />
11
12    <osgi:service ref="transactionManager" interface="org.springframework.transaction.PlatformTransactionManager" context-class-loader="service-provider" />
13
14    <osgi:service ref="userDao" interface="com.dw.test.dao.IUserDao" />
15
16</beans>

5.5 com.dw.test.service

a) 創建bundle項目,名為com.dw.test.service,參考5.1 a

b) 引入項目com.dw.test.domain,com.dw.test.dao,參考5.3 b

c) 導入依賴包com.dw.test.domain,com.dw.test.dao,參考5.1 b

d) 創建并導出共享包com.dw.test.service,參考5.2 c

e) 創建IBaseService類接口
src/com.dw.test.service.IBaseService
 1package com.dw.test.service;
 2
 3import java.io.Serializable;
 4
 5
 6public interface IBaseService<T> {
 7
 8    void create(T entity);
 9
10    void modify(T entity);
11
12    void remove(T entity);
13
14    T getById(Serializable id);
15    
16}

f) 創建IUserService業務接口
src/com.dw.test.service.IUserService
1package com.dw.test.service;
2
3import com.dw.test.domain.User;
4
5public interface IUserService extends IBaseService<User> {
6
7}

5.6 com.dw.test.service.impl
a) 創建bundle項目,名為com.dw.test.service.impl,參考5.1 a

b) 引入項目com.dw.test.domain,com.dw.test.dao,com.dw.test.service參考5.3 b

c) 導入依賴包,com.dw.test.dao,com.dw.test.domain,com.dw.test.service,org.aopalliance.aop,參考5.1 b

d) 導入Hibernate bundle,參考5.4 d

e) 導入Spring庫,參考5.4 e

f) 實現IBaseService接口
src/com.dw.test.service.impl.BaseServiceImpl.java
 1package com.dw.test.service.impl;
 2
 3import java.io.Serializable;
 4
 5import com.dw.test.dao.IBaseDao;
 6import com.dw.test.service.IBaseService;
 7
 8public abstract class BaseServiceImpl<T> implements IBaseService<T>{
 9    
10    @Override
11    public void create(T entity) {
12        System.out.println(getBaseDao() == null);
13        getBaseDao().insert(entity);
14    }

15
16    @Override
17    public void modify(T entity) {
18        getBaseDao().update(entity);
19    }

20
21    @Override
22    public void remove(T entity) {
23        getBaseDao().delete(entity);
24    }

25
26    @Override
27    public T getById(Serializable id) {
28        return getBaseDao().findById(id);
29    }

30
31    protected abstract IBaseDao<T> getBaseDao();
32}

33

f) 實現IUserService接口
src/com.dw.test.service.impl.UserServiceImpl.java

 1
package com.dw.test.service.impl;
 2
 3import org.springframework.beans.factory.annotation.Autowired;
 4import org.springframework.stereotype.Service;
 5import org.springframework.transaction.annotation.Transactional;
 6
 7import com.dw.test.dao.IBaseDao;
 8import com.dw.test.dao.IUserDao;
 9import com.dw.test.domain.User;
10import com.dw.test.service.IUserService;
11
12@Service("userService")
13@Transactional
14public class UserServiceImpl extends BaseServiceImpl<User> implements
15        IUserService {
16
17    @Autowired
18    private IUserDao userDao;
19
20    @Override
21    public IBaseDao<User> getBaseDao() {
22        return userDao;    
23    }

24
25}

26

g) 定義Spring Bean
src/META-INF/spring/appContext.xml
 1<?xml version="1.0" encoding="UTF-8"?>
 2<beans xmlns="http://www.springframework.org/schema/beans"
 3    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:aop="http://www.springframework.org/schema/aop"
 4    xmlns:tx="http://www.springframework.org/schema/tx" xmlns:context="http://www.springframework.org/schema/context"
 5    xsi:schemaLocation="http://www.springframework.org/schema/beans
 6        http://www.springframework.org/schema/beans/spring-beans.xsd
 7        http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd
 8        http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx.xsd
 9        http://www.springframework.org/schema/context
10        http://www.springframework.org/schema/context/spring-context.xsd">
11
12
13    <context:annotation-config />
14    
15    <context:component-scan base-package="com.dw.test" />
16
17    <tx:annotation-driven transaction-manager="transactionManager" />
18
19    <tx:advice id="txAdvice" transaction-manager="transactionManager">
20        <tx:attributes>
21            <tx:method name="search*" read-only="true" />
22            <tx:method name="*" rollback-for="Exception" />
23        </tx:attributes>
24    </tx:advice>
25    
26    <aop:config>
27        <aop:pointcut id="serviceCut" expression="execution(* com.dw.test..service..*.*(..))" />
28        <aop:advisor pointcut-ref="serviceCut" advice-ref="txAdvice" />
29    </aop:config>
30    
31    
32</beans>
33

h) 定義OSGi bean
src/META-INF/spring/osgiContext.xml
<?xml version="1.0" encoding="UTF-8"?>
<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"
    xmlns:context
="http://www.springframework.org/schema/context"
    xsi:schemaLocation
="http://www.springframework.org/schema/beans
        http://www.springframework.org/schema/beans/spring-beans.xsd
        http://www.springframework.org/schema/osgi
        http://www.springframework.org/schema/osgi/spring-osgi.xsd
        http://www.springframework.org/schema/context
        http://www.springframework.org/schema/context/spring-context.xsd">


    
<osgi:reference id="userDao" interface="com.dw.test.dao.IUserDao" />
    
    
<osgi:reference id="transactionManager"    interface="org.springframework.transaction.PlatformTransactionManager" />

    
<osgi:service ref="userService" interface="com.dw.test.service.IUserService" />

</beans>


5.7 com.dw.test.web

a) 創建bundle項目,名為com.dw.test.web,參考5.1 a(創建過程中記得勾選Web Application Bundle,源碼編譯輸出目錄設置為WEB-INF/classes)

b) 引入項目com.dw.test.domain,com.dw.test.service,參考5.3 b

c) 導入依賴包,com.dw.test.domain,com.dw.test.service,org.eclipse.virgo.web.dm,org.slf4j,參考5.1 b

d) 導入Hibernate bundle,參考5.4 d

e) 導入Spring庫,參考5.4

f) 創建控制器
src/com.dw.test.web.controller.UserController.java
 1package com.dw.test.web.controller;
 2
 3import javax.annotation.Resource;
 4
 5import org.slf4j.Logger;
 6import org.slf4j.LoggerFactory;
 7import org.springframework.stereotype.Controller;
 8import org.springframework.web.bind.annotation.RequestMapping;
 9
10import com.dw.test.domain.User;
11import com.dw.test.service.IUserService;
12
13@Controller
14@RequestMapping("/user")
15public class UserController {
16
17    Logger logger = LoggerFactory.getLogger(UserController.class);
18    
19    @Resource
20    private IUserService userService;
21    
22    @RequestMapping(value="/create")
23    public String create(){
24        logger.info("創建用戶:");
25        User user = new User();
26        user.setUsername("osmos");
27        user.setPassword("123456");
28        userService.create(user);
29        return null;
30    }

31}

32

g) 定義web配置
WEB-INF/web.xml
1<?xml version="1.0" encoding="UTF-8"?>
2<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
3 xmlns="http://java.sun.com/xml/ns/javaee" xmlns:web="http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"
4 xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"
5 id="WebApp_ID" version="2.5">
6
7 <display-name>test</display-name>
8
9 <context-param>
10 <param-name>webAppRootKey</param-name>
11 <param-value>test.root</param-value>
12 </context-param>
13
14
15 <context-param>
16 <param-name>contextClass</param-name>
17 <param-value>org.eclipse.virgo.web.dm.ServerOsgiBundleXmlWebApplicationContext</param-value>
18 </context-param>
19 <listener>
20 <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
21 </listener>
22
23
24 <servlet>
25 <servlet-name>app</servlet-name>
26 <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
27 </servlet>
28 <servlet-mapping>
29 <servlet-name>app</servlet-name>
30 <url-pattern>/</url-pattern>
31 </servlet-mapping>
32
33</web-app>

h) 定義Spring MVC配置
WEB-INF/app-servlet.xml
1<?xml version="1.0" encoding="UTF-8"?>
2<beans xmlns="http://www.springframework.org/schema/beans"
3 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:p="http://www.springframework.org/schema/p"
4 xmlns:aop="http://www.springframework.org/schema/aop" xmlns:context="http://www.springframework.org/schema/context"
5 xmlns:util="http://www.springframework.org/schema/util" xmlns:mvc="http://www.springframework.org/schema/mvc"
6 xmlns:tx="http://www.springframework.org/schema/tx"
7 xsi:schemaLocation="
8 http://www.springframework.org/schema/beans
9 http://www.springframework.org/schema/beans/spring-beans.xsd
10 http://www.springframework.org/schema/context
11 http://www.springframework.org/schema/context/spring-context.xsd
12 http://www.springframework.org/schema/aop
13 http://www.springframework.org/schema/aop/spring-aop.xsd
14 http://www.springframework.org/schema/tx
15 http://www.springframework.org/schema/tx/spring-tx.xsd
16 http://www.springframework.org/schema/util
17 http://www.springframework.org/schema/util/spring-util.xsd
18 http://www.springframework.org/schema/mvc
19 http://www.springframework.org/schema/mvc/spring-mvc.xsd">
20
21 <context:component-scan base-package="com.dw.test" />
22
23 <bean class="org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter" />
24
25 <mvc:interceptors>
26 <bean id="openSessionInViewInterceptor"    class="org.springframework.orm.hibernate3.support.OpenSessionInViewInterceptor">
27 <property name="sessionFactory" ref="sessionFactory" />
28 </bean>
29 </mvc:interceptors>
30
31 <bean id="viewResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver">
32 <property name="viewClass" value="org.springframework.web.servlet.view.JstlView" />
33 <property name="prefix" value="/WEB-INF/views/" />
34 <property name="suffix" value=".jsp" />
35 </bean>
36
37</beans>
38

i) 定義服務引用
WEB-INF/applicationContext.xml
1<?xml version="1.0" encoding="UTF-8"?>
2<beans xmlns="http://www.springframework.org/schema/beans"
3 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:osgi="http://www.springframework.org/schema/osgi"
4 xmlns:context="http://www.springframework.org/schema/context"
5 xsi:schemaLocation="http://www.springframework.org/schema/beans
6 http://www.springframework.org/schema/beans/spring-beans.xsd
7 http://www.springframework.org/schema/osgi
8 http://www.springframework.org/schema/osgi/spring-osgi.xsd
9 http://www.springframework.org/schema/context
10 http://www.springframework.org/schema/context/spring-context.xsd">
11
12 <osgi:reference id="sessionFactory" interface="org.hibernate.SessionFactory" />
13
14 <osgi:reference id="userService" interface="com.dw.test.service.IUserService"/>
15
16</beans>
17
18

j) 注意事項
com.dw.test.web項目的MANIFEST.MF文件內容有如下頭信息,否則會有無法訪問以及注解無效等問題
Web-ContextPath: /test
Bundle-ClassPath: WEB-INF/classes