Struts2 + Spring + Hibernate的集成
我们以综合示例为例子来一步步的完成我们框架的集成
首先建一个web工程, 并将包建好
[img]http://dl.iteye.com/upload/attachment/243956/6130a5dd-1f31-383b-8b14-34fab1dd8d54.bmp[/img]
包名详解:
com.wdpc.ssh.action: 放置Struts2的Action
com.wdpc.ssh.commons: 放置公用组件,工具类
com.wdpc.ssh.dao: 放置dao层的接口
com.wdpc.ssh.dao.impl: 放置dao层的实现类
com.wdpc.ssh.model: 放置实体对象的模型
com.wdpc.ssh.service: 放置业务层的接口
com.wdpc.ssh. service.impl: 放置业务层的实现类
com.wdpc.ssh.test: 放置单元测试类
首先集成Spring + Hibernate
第一步:导入Hiberante的包
[img]http://dl.iteye.com/upload/attachment/243958/2c95dc8d-a7f0-3d7f-8682-e0d352af8297.bmp[/img]
注意我这里的Hibernate包中已经带有c3p0连接池,mysql的驱动包,以及sqljdbc4的包(SQLServer, mysql的驱动包只需要保留一个就可以了, 用什么数据库就保留对应的驱动包.)
将Hibernate中的jar包copy到我们工程的lib目录下
第二步:导入Spring的包
[img]http://dl.iteye.com/upload/attachment/243962/20b165da-e871-38ae-9a48-8aafe7925471.bmp[/img]
注意这里,我的Spring包中有重复的c3p0连接池,mysql的驱动包, 可以删除掉
还需要删除Spring中的asm-2.2.3.jar, commons-logging.jar, log4j-1.2.15.jar这些和Hibernate中重复的包.
第三步,加入配置文件
我们现在开始要将Spring的配置文件进行分离,以免项目大了以后,文件过大,不利于管理.
在src目录下包config, 采用build path将config编译成源目录, 并在此包下建立6个Spring的配置文件
[img]http://dl.iteye.com/upload/attachment/243960/c8f49ead-ea9b-3289-b26f-71337b6bd5f6.bmp[/img]
spring_action.xml : 用于配置Struts2的action
spring_aop.xml : 用于配置AOP
spring_common.xml : 用于配置组件类
spring_dao.xml : 用于配置dao层类
spring_service.xml : 用于配置service类
spring_transation.xml : 用于配置事务
所有Spring文件中的内容模板如下:
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context"
xmlns:aop="http://www.springframework.org/schema/aop" xmlns:tx="http://www.springframework.org/schema/tx"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-2.5.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context-2.5.xsd
http://www.springframework.org/schema/aop
http://www.springframework.org/schema/aop/spring-aop-2.5.xsd
http://www.springframework.org/schema/tx
http://www.springframework.org/schema/tx/spring-tx-2.5.xsd">
</beans>
此头文件加入了IOC,AOP,事务的支持
但是spring_common.xml中的内容需要做一些全局配置:
我们需要做以下一些准备功能
1. 打开IOC注释的功能
2. AOP注释的功能
3. IOC全局扫描的功能
4. 配置事务管理器,并打开事务的注释功能
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context"
xmlns:aop="http://www.springframework.org/schema/aop" xmlns:tx="http://www.springframework.org/schema/tx"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-2.5.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context-2.5.xsd
http://www.springframework.org/schema/aop
http://www.springframework.org/schema/aop/spring-aop-2.5.xsd
http://www.springframework.org/schema/tx
http://www.springframework.org/schema/tx/spring-tx-2.5.xsd">
<context:annotation-config />
<context:component-scan base-package="com.wdpc.ssh" />
<aop:aspectj-autoproxy />
<bean id="sessionFactory"
class="org.springframework.orm.hibernate3.LocalSessionFactoryBean">
<property name="configLocation"
value="classpath:hibernate.cfg.xml">
</property>
</bean>
<bean id="txManager"
class="org.springframework.orm.hibernate3.HibernateTransactionManager">
<property name="sessionFactory" ref="sessionFactory" />
</bean>
<tx:annotation-driven transaction-manager="txManager" />
</beans>
hibernate.cfg.xml
<?xml version='1.0' encoding='utf-8'?>
<!DOCTYPE hibernate-configuration PUBLIC
"-//Hibernate/Hibernate Configuration DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
<session-factory>
<!-- 设置使用数据库的语言 -->
<property name="dialect">org.hibernate.dialect.MySQL5Dialect</property>
<property name="Hibernate.current_session_context_class">thread</property>
<!-- 设置是否显示执行的语言 -->
<property name="show_sql">true</property>
<property name="hbm2ddl.auto">create</property>
<!-- 数据库连接属性设置 -->
<property name="connection.driver_class">com.mysql.jdbc.Driver</property>
<property name="connection.url">jdbc:mysql://localhost:3306/test?useUnicode=true&characterEncoding=utf-8</property>
<property name="connection.username">root</property>
<property name="connection.password">wdpc</property>
<!-- 设置 c3p0连接池的属性-->
<property name="connection.useUnicode">true</property>
<property name="hibernate.c3p0.max_statements">100</property>
<property name="hibernate.c3p0.idle_test_period">3000</property>
<property name="hibernate.c3p0.acquire_increment">2</property>
<property name="hibernate.c3p0.timeout">5000</property>
<property name="hibernate.connection.provider_class">
org.hibernate.connection.C3P0ConnectionProvider
</property>
<property name="hibernate.c3p0.validate">true</property>
<property name="hibernate.c3p0.max_size">3</property>
<property name="hibernate.c3p0.min_size">1</property>
<!-- 加载映射文件-->
<mapping resource="com/wdpc/ssh/model/User.hbm.xml" />
</session-factory>
</hibernate-configuration>
我们以前在单独使用Hibernate的时候,需要一个HibernateUitl工具类,
Spring已经提供了这样一个类给我们(LocalSessionFactoryBean),但是我们需要给这个类的属性值进行配置, 我们需要告诉它,怎么进行连接数据库, Hibernate的Model类的映射文件在哪里, 已经Hibernate的一些常用开关的配置信息.
事务和JDBC事务管理类不一样,可以看到有一个Hibernate专用的HibernateTransactionManager事务管理类,我们同样需要告诉事务管理类数据库的一些信息,但是和JDBC事务管理类不一样, 它需要一个sessionFactory类,而不是一个dataSource.
第四步: 编写Model类,并添加映射文件,并将映射文件路径添加到spring_common.xml文件的sessionFactory类的配置信息中.
public class User {
private String id;
private String name;
public User() {
super();
}
public User(String name) {
super();
this.name = name;
}
public User(String id, String name) {
super();
this.id = id;
this.name = name;
}
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
映射文件:
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
<hibernate-mapping>
<class name="com.wdpc.ssh.model.User" table="users">
<id name="id" type="java.lang.String" column="id" length="32">
<generator class="uuid.hex" />
</id>
<property name="name" type="java.lang.String" column="name"
length="20" />
</class>
</hibernate-mapping>
将映射文件路径加入到Spring_commons.xml的配置文件中
<property name="mappingResources">
<list>
<value>com/wdpc/ssh/model/User.hbm.xml</value>
</list>
</property>
第五步: 编写Dao层接口与实现类,并将其纳入到Spring的管理
接口:
public interface UserDao {
public void create(User user) throws Exception;
public void delete(Integer id) throws Exception;
public void update(User user) throws Exception;
public User findById(Integer id) throws Exception;
public List<User> findAll() throws Exception;
}
实现类:
public class UserDaoImpl implements UserDao {
private SessionFactory sessionFactory;
public void create(User user) throws Exception {
sessionFactory.getCurrentSession().save(user);
}
public void delete(Integer id) throws Exception {
sessionFactory.getCurrentSession().delete(findById(id));
}
public void update(User user) throws Exception {
sessionFactory.getCurrentSession().update(user);
}
public List<User> findAll() throws Exception {
return sessionFactory.getCurrentSession().createQuery("from User")
.list();
}
public User findById(Integer id) throws Exception {
return (User) sessionFactory.getCurrentSession().get(User.class, id);
}
public void setSessionFactory(SessionFactory sessionFactory) {
this.sessionFactory = sessionFactory;
}
}
将UserDao纳入到Spring的管理,我们需要在Spring_dao.xml配置文件中配置
<bean id="userDao" class="com.wdpc.ssh.dao.impl.UserDaoImpl">
<property name="sessionFactory" ref="sessionFactory" />
</bean>
第六步: 编写Service层接口与实现类:
接口:
public interface UserService {
public void create(User user) throws Exception;
public void delete(Integer id) throws Exception;
public void update(User user) throws Exception;
public User findById(Integer id) throws Exception;
public List<User> findAll() throws Exception;
}
实现类:
public class UserServiceImpl implements UserService {
private UserDao userDao;
public void create(User user) throws Exception {
userDao.create(user);
}
public void delete(Integer id) throws Exception {
userDao.delete(id);
}
public List<User> findAll() throws Exception {
return userDao.findAll();
}
public User findById(Integer id) throws Exception {
return userDao.findById(id);
}
public void update(User user) throws Exception {
userDao.update(user);
}
public void setUserDao(UserDao userDao) {
this.userDao = userDao;
}
}
同样的,Service层需要Dao层,需要注入进来.在spring_service.xml中配置
<bean id="userService" class="com.wdpc.ssh.service.impl.UserServiceImpl">
<property name="userDao" ref="userDao" />
</bean>
第七步:给Service层添加事务处理
在spring_transation.xml文件中加入服务层事务的支持
<tx:advice id="txAdvice" transaction-manager="txManager">
<tx:attributes>
<tx:method name="find*" read-only="true" />
<tx:method name="*" rollback-for="Exception" />
</tx:attributes>
</tx:advice>
<aop:config>
<aop:pointcut id="txPointcut"
expression="execution(* com.wdpc.ssh.service..*.*(..))" />
<aop:advisor advice-ref="txAdvice" pointcut-ref="txPointcut" />
</aop:config>
第八步:Test
public class Test {
public static void main(String[] args) {
ApplicationContext ctx = new ClassPathXmlApplicationContext(
new String[] { "spring_action.xml", "spring_aop.xml",
"spring_common.xml", "spring_dao.xml",
"spring_service.xml", "spring_transation.xml" });
UserService userService = (UserService) ctx.getBean("userService");
try {
userService.create(new User("张海当"));
} catch (Exception e) {
e.printStackTrace();
}
}
}
我们以综合示例为例子来一步步的完成我们框架的集成
首先建一个web工程, 并将包建好
[img]http://dl.iteye.com/upload/attachment/243956/6130a5dd-1f31-383b-8b14-34fab1dd8d54.bmp[/img]
包名详解:
com.wdpc.ssh.action: 放置Struts2的Action
com.wdpc.ssh.commons: 放置公用组件,工具类
com.wdpc.ssh.dao: 放置dao层的接口
com.wdpc.ssh.dao.impl: 放置dao层的实现类
com.wdpc.ssh.model: 放置实体对象的模型
com.wdpc.ssh.service: 放置业务层的接口
com.wdpc.ssh. service.impl: 放置业务层的实现类
com.wdpc.ssh.test: 放置单元测试类
首先集成Spring + Hibernate
第一步:导入Hiberante的包
[img]http://dl.iteye.com/upload/attachment/243958/2c95dc8d-a7f0-3d7f-8682-e0d352af8297.bmp[/img]
注意我这里的Hibernate包中已经带有c3p0连接池,mysql的驱动包,以及sqljdbc4的包(SQLServer, mysql的驱动包只需要保留一个就可以了, 用什么数据库就保留对应的驱动包.)
将Hibernate中的jar包copy到我们工程的lib目录下
第二步:导入Spring的包
[img]http://dl.iteye.com/upload/attachment/243962/20b165da-e871-38ae-9a48-8aafe7925471.bmp[/img]
注意这里,我的Spring包中有重复的c3p0连接池,mysql的驱动包, 可以删除掉
还需要删除Spring中的asm-2.2.3.jar, commons-logging.jar, log4j-1.2.15.jar这些和Hibernate中重复的包.
第三步,加入配置文件
我们现在开始要将Spring的配置文件进行分离,以免项目大了以后,文件过大,不利于管理.
在src目录下包config, 采用build path将config编译成源目录, 并在此包下建立6个Spring的配置文件
[img]http://dl.iteye.com/upload/attachment/243960/c8f49ead-ea9b-3289-b26f-71337b6bd5f6.bmp[/img]
spring_action.xml : 用于配置Struts2的action
spring_aop.xml : 用于配置AOP
spring_common.xml : 用于配置组件类
spring_dao.xml : 用于配置dao层类
spring_service.xml : 用于配置service类
spring_transation.xml : 用于配置事务
所有Spring文件中的内容模板如下:
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context"
xmlns:aop="http://www.springframework.org/schema/aop" xmlns:tx="http://www.springframework.org/schema/tx"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-2.5.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context-2.5.xsd
http://www.springframework.org/schema/aop
http://www.springframework.org/schema/aop/spring-aop-2.5.xsd
http://www.springframework.org/schema/tx
http://www.springframework.org/schema/tx/spring-tx-2.5.xsd">
</beans>
此头文件加入了IOC,AOP,事务的支持
但是spring_common.xml中的内容需要做一些全局配置:
我们需要做以下一些准备功能
1. 打开IOC注释的功能
2. AOP注释的功能
3. IOC全局扫描的功能
4. 配置事务管理器,并打开事务的注释功能
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context"
xmlns:aop="http://www.springframework.org/schema/aop" xmlns:tx="http://www.springframework.org/schema/tx"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-2.5.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context-2.5.xsd
http://www.springframework.org/schema/aop
http://www.springframework.org/schema/aop/spring-aop-2.5.xsd
http://www.springframework.org/schema/tx
http://www.springframework.org/schema/tx/spring-tx-2.5.xsd">
<context:annotation-config />
<context:component-scan base-package="com.wdpc.ssh" />
<aop:aspectj-autoproxy />
<bean id="sessionFactory"
class="org.springframework.orm.hibernate3.LocalSessionFactoryBean">
<property name="configLocation"
value="classpath:hibernate.cfg.xml">
</property>
</bean>
<bean id="txManager"
class="org.springframework.orm.hibernate3.HibernateTransactionManager">
<property name="sessionFactory" ref="sessionFactory" />
</bean>
<tx:annotation-driven transaction-manager="txManager" />
</beans>
hibernate.cfg.xml
<?xml version='1.0' encoding='utf-8'?>
<!DOCTYPE hibernate-configuration PUBLIC
"-//Hibernate/Hibernate Configuration DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
<session-factory>
<!-- 设置使用数据库的语言 -->
<property name="dialect">org.hibernate.dialect.MySQL5Dialect</property>
<property name="Hibernate.current_session_context_class">thread</property>
<!-- 设置是否显示执行的语言 -->
<property name="show_sql">true</property>
<property name="hbm2ddl.auto">create</property>
<!-- 数据库连接属性设置 -->
<property name="connection.driver_class">com.mysql.jdbc.Driver</property>
<property name="connection.url">jdbc:mysql://localhost:3306/test?useUnicode=true&characterEncoding=utf-8</property>
<property name="connection.username">root</property>
<property name="connection.password">wdpc</property>
<!-- 设置 c3p0连接池的属性-->
<property name="connection.useUnicode">true</property>
<property name="hibernate.c3p0.max_statements">100</property>
<property name="hibernate.c3p0.idle_test_period">3000</property>
<property name="hibernate.c3p0.acquire_increment">2</property>
<property name="hibernate.c3p0.timeout">5000</property>
<property name="hibernate.connection.provider_class">
org.hibernate.connection.C3P0ConnectionProvider
</property>
<property name="hibernate.c3p0.validate">true</property>
<property name="hibernate.c3p0.max_size">3</property>
<property name="hibernate.c3p0.min_size">1</property>
<!-- 加载映射文件-->
<mapping resource="com/wdpc/ssh/model/User.hbm.xml" />
</session-factory>
</hibernate-configuration>
我们以前在单独使用Hibernate的时候,需要一个HibernateUitl工具类,
Spring已经提供了这样一个类给我们(LocalSessionFactoryBean),但是我们需要给这个类的属性值进行配置, 我们需要告诉它,怎么进行连接数据库, Hibernate的Model类的映射文件在哪里, 已经Hibernate的一些常用开关的配置信息.
事务和JDBC事务管理类不一样,可以看到有一个Hibernate专用的HibernateTransactionManager事务管理类,我们同样需要告诉事务管理类数据库的一些信息,但是和JDBC事务管理类不一样, 它需要一个sessionFactory类,而不是一个dataSource.
第四步: 编写Model类,并添加映射文件,并将映射文件路径添加到spring_common.xml文件的sessionFactory类的配置信息中.
public class User {
private String id;
private String name;
public User() {
super();
}
public User(String name) {
super();
this.name = name;
}
public User(String id, String name) {
super();
this.id = id;
this.name = name;
}
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
映射文件:
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
<hibernate-mapping>
<class name="com.wdpc.ssh.model.User" table="users">
<id name="id" type="java.lang.String" column="id" length="32">
<generator class="uuid.hex" />
</id>
<property name="name" type="java.lang.String" column="name"
length="20" />
</class>
</hibernate-mapping>
将映射文件路径加入到Spring_commons.xml的配置文件中
<property name="mappingResources">
<list>
<value>com/wdpc/ssh/model/User.hbm.xml</value>
</list>
</property>
第五步: 编写Dao层接口与实现类,并将其纳入到Spring的管理
接口:
public interface UserDao {
public void create(User user) throws Exception;
public void delete(Integer id) throws Exception;
public void update(User user) throws Exception;
public User findById(Integer id) throws Exception;
public List<User> findAll() throws Exception;
}
实现类:
public class UserDaoImpl implements UserDao {
private SessionFactory sessionFactory;
public void create(User user) throws Exception {
sessionFactory.getCurrentSession().save(user);
}
public void delete(Integer id) throws Exception {
sessionFactory.getCurrentSession().delete(findById(id));
}
public void update(User user) throws Exception {
sessionFactory.getCurrentSession().update(user);
}
public List<User> findAll() throws Exception {
return sessionFactory.getCurrentSession().createQuery("from User")
.list();
}
public User findById(Integer id) throws Exception {
return (User) sessionFactory.getCurrentSession().get(User.class, id);
}
public void setSessionFactory(SessionFactory sessionFactory) {
this.sessionFactory = sessionFactory;
}
}
将UserDao纳入到Spring的管理,我们需要在Spring_dao.xml配置文件中配置
<bean id="userDao" class="com.wdpc.ssh.dao.impl.UserDaoImpl">
<property name="sessionFactory" ref="sessionFactory" />
</bean>
第六步: 编写Service层接口与实现类:
接口:
public interface UserService {
public void create(User user) throws Exception;
public void delete(Integer id) throws Exception;
public void update(User user) throws Exception;
public User findById(Integer id) throws Exception;
public List<User> findAll() throws Exception;
}
实现类:
public class UserServiceImpl implements UserService {
private UserDao userDao;
public void create(User user) throws Exception {
userDao.create(user);
}
public void delete(Integer id) throws Exception {
userDao.delete(id);
}
public List<User> findAll() throws Exception {
return userDao.findAll();
}
public User findById(Integer id) throws Exception {
return userDao.findById(id);
}
public void update(User user) throws Exception {
userDao.update(user);
}
public void setUserDao(UserDao userDao) {
this.userDao = userDao;
}
}
同样的,Service层需要Dao层,需要注入进来.在spring_service.xml中配置
<bean id="userService" class="com.wdpc.ssh.service.impl.UserServiceImpl">
<property name="userDao" ref="userDao" />
</bean>
第七步:给Service层添加事务处理
在spring_transation.xml文件中加入服务层事务的支持
<tx:advice id="txAdvice" transaction-manager="txManager">
<tx:attributes>
<tx:method name="find*" read-only="true" />
<tx:method name="*" rollback-for="Exception" />
</tx:attributes>
</tx:advice>
<aop:config>
<aop:pointcut id="txPointcut"
expression="execution(* com.wdpc.ssh.service..*.*(..))" />
<aop:advisor advice-ref="txAdvice" pointcut-ref="txPointcut" />
</aop:config>
第八步:Test
public class Test {
public static void main(String[] args) {
ApplicationContext ctx = new ClassPathXmlApplicationContext(
new String[] { "spring_action.xml", "spring_aop.xml",
"spring_common.xml", "spring_dao.xml",
"spring_service.xml", "spring_transation.xml" });
UserService userService = (UserService) ctx.getBean("userService");
try {
userService.create(new User("张海当"));
} catch (Exception e) {
e.printStackTrace();
}
}
}