Struts2.1.6 +Spring2.5.6 + Hibernate3.3.2
1. 需要的jar包列表
jar包名称 | 所在位置 | 说明 |
antlr-2.7.6.jar | hibernate/lib/required | 解析HQL |
aspectjrt | spring/lib/aspectj | AOP |
aspectjweaver | .. | AOP |
cglib-nodep-2.1_3.jar | spring/lib/cglib | 代理,二进制增强 |
common-annotations.jar | spring/lib/j2ee | @Resource |
commons-collections-3.1.jar | hibernate/lib/required | 集合框架 |
commons-fileupload-1.2.1.jar | struts/lib | struts |
commons-io-1.3.2 | struts/lib | struts |
commons-logging-1.1.1 | 单独下载,删除1.0.4(struts/lib) | struts spring |
dom4j-1.6.1.jar | hibernate/required | 解析xml |
ejb3-persistence | hibernate-annotation/lib | @Entity |
freemarker-2.3.13 | struts/lib | struts |
hibernate3.jar | hibernate |
|
hibernate-annotations | hibernate-annotation/ |
|
hibernate-common-annotations | hibernate-annotation/lib |
|
javassist-3.9.0.GA.jar | hiberante/lib/required | hibernate |
jta-1.1.jar | .. | hibernate transaction |
junit4.5 |
|
|
mysql- |
|
|
ognl-2.6.11.jar | struts/lib |
|
slf4j-api-1.5.8.jar | hibernate/lib/required | hibernate-log |
slf4j-nop-1.5.8.jar | hibernate/lib/required |
|
spring.jar | spring/dist |
|
struts2-core-2.1.6.jar | struts/lib |
|
xwork-2.1.2.jar | struts/lib | struts2 |
commons-dbcp | spring/lib/jarkata-commons |
|
commons-pool.jar | .. |
|
struts2-spring-plugin-2.1.6.jar | struts/lib |
|
|
|
|
2. BestPractice:
a) 将这些所有的jar包保存到一个位置,使用的时候直接copy
3. 步骤
a) 加入jar包
b) 首先整合Spring + Hibernate
i. 建立对应的package
1. dao / dao.impl / model / service / service.impl/ test
ii. 建立对应的接口与类框架
1. S2SH_01
iii. 建立spring的配置文件(建议自己保留一份经常使用的配置文件,以后用到的时候直接copy改)
iv. 建立数据库
v. 加入Hibernate注解
1. 在实体类上加相应注解@Entity @Id等
2. 在beans配置文件配置对应的实体类,使之受管
vi. 写dao service的实现
vii. 加入Spring注解
1. 在对应Service及DAO实现中加入@Component,让spring对其初始化
2. 在Service上加入@Transactional或者使用xml方式(此处建议后者,因为更简单)
3. 在DAO中注入sessionFactory
4. 在Service中注入DAO
5. 写DAO与Service的实现
viii. 写测试
c) 整合Struts2
i. 结合点:Struts2的Action由Spring产生
ii. 步骤:
1. 修改web.xml加入 struts的filter
2. 再加入spring的listener,这样的话,webapp一旦启动,spring容器就初始化了
3. 规划struts的action和jsp展现
4. 加入struts.xml
a) 修改配置,由spring替代struts产生Action对象
5. 修改action配置
a) 把类名改为bean对象的名称,这个时候就可以使用首字母小写了
b) @Scope(“prototype”)不要忘记
iii. struts的读常量:
1. struts-default.xml
2. struts-plugin.xml
3. struts.xml
4. struts.properties
5. web.xml
iv. 中文问题:
1. Struts2.1.8已经修正,只需要改i18n.encoding = gbk
2. 使用spring的characterencoding
3. 需要严格注意filter的顺序
4. 需要加到Struts2的filter前面
v. LazyInitializationException
1. OpenSessionInViewFilter
2. 需要严格顺序问题
需要加到struts2的filter
_____________________________________________________________________________________________
pageEncoding 改成可以显示中文的GB18030
Spring_2300_Registration_1
以下程序是jsp和数据打交道的一个登陆页面
register.jsp
registerDeal.jsp
registerFail.jsp
registerSuccess.jsp
<!-- register.jsp 登陆页面-->
<%@ page language="java" import="java.util.*" pageEncoding="GB18030"%>
<%
String path = request.getContextPath();
String basePath = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+path+"/";
%>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
<head>
<base href="<%=basePath%>">
<title>用户注册</title>
</head>
<body>
<form action="registerDeal.jsp" method="post">
用户名:<input type="text" name="username"><br/>
密 码:<input type="password" name="password"><br/>
确认密码:<input type="password" name="password2"><br/>
<input type="submit" value="提交">
<input type="reset" value="重置">
</form>
</body>
</html>
<!-- registerDeal.jsp -->
<%@ page language="java" import="java.util.*" pageEncoding="GB18030"%>
<%@ page import="java.sql.*" %>
<%
String path = request.getContextPath();
String basePath = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+path+"/";
String username = request.getParameter("username");
String password = request.getParameter("password");
String password2 = request.getParameter("password2");
Class.forName("com.mysql.jdbc.Driver");
Connection conn = DriverManager.getConnection("jdbc:mysql://localhost:3306/spring","root","root");
//判断用户名是否存在
String sqlQuery = "select count(*) from user where username = ?";
PreparedStatement pstmQuery = conn.prepareStatement(sqlQuery);
pstmQuery.setString(1,username);
ResultSet rs = pstmQuery.executeQuery();
rs.next();
int count = rs.getInt(1);
if(count > 0) {
response.sendRedirect("registerFail.jsp");
pstmQuery.close();
conn.close();
return;
}
//在插入之前要检查用户名是否存在,不存在就插入
String sql = "insert into user values(null,?,?)";
PreparedStatement pstm = conn.prepareStatement(sql);
pstm.setString(1,username);
pstm.setString(2,password);
pstm.executeUpdate();
pstm.close();
conn.close();
response.sendRedirect("registerSuccess.jsp");
%>
用户注册得有个实体类吧 User
把jsp的业务逻辑封装在一个业务逻辑层
jsp直接调用UserManager类里面的业务逻辑即可package com.demo.registration.service; import java.sql.Connection; import java.sql.DriverManager; import java.sql.PreparedStatement; import java.sql.ResultSet; import java.sql.SQLException; import com.demo.registration.model.User; public class UserManager { //判断用户名是否存在 public boolean exists(User user) { Connection conn = null; PreparedStatement pstmQuery = null; String sqlQuery = "select count(*) from user where username = ?"; try { Class.forName("com.mysql.jdbc.Driver"); conn = DriverManager.getConnection("jdbc:mysql://localhost:3306/spring","root","root"); pstmQuery = conn.prepareStatement(sqlQuery); pstmQuery.setString(1,user.getUsername()); ResultSet rs = pstmQuery.executeQuery(); int count = 0; while(rs.next()){ count = rs.getInt(1); if(count > 0) { return true; } return false; } } catch (ClassNotFoundException e) { e.printStackTrace(); } catch (SQLException e) { e.printStackTrace(); } finally { if(pstmQuery != null) { try { pstmQuery.close(); pstmQuery = null; } catch (Exception e2) { e2.printStackTrace(); } } if(conn != null) { try { conn.close(); conn = null; } catch (Exception e2) { e2.printStackTrace(); } } } return false; } //在插入之前要检查用户名是否存在,不存在就插入 public void add(User user) { Connection conn = null; PreparedStatement pstm = null; String sql = "insert into user values(null,?,?)"; try { Class.forName("com.mysql.jdbc.Driver"); conn = DriverManager.getConnection("jdbc:mysql://localhost:3306/spring","root","root"); pstm = conn.prepareStatement(sql); pstm.setString(1,user.getUsername()); pstm.setString(2, user.getPassword()); pstm.executeUpdate(); } catch (ClassNotFoundException e) { e.printStackTrace(); } catch (SQLException e) { e.printStackTrace(); } finally { if(pstm != null) { try { pstm.close(); pstm = null; } catch (Exception e2) { e2.printStackTrace(); } } if(conn != null) { try { conn.close(); conn = null; } catch (Exception e2) { e2.printStackTrace(); } } } } }
<!-- registerDeal.jsp --> <%@ page language="java" import="java.util.*" pageEncoding="GB18030"%> <%@ page import="java.sql.*" %> <%@ page import="com.demo.registration.service.UserManager" %> <%@page import="com.demo.registration.model.User"%> <% String path = request.getContextPath(); String basePath = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+path+"/"; String username = request.getParameter("username"); String password = request.getParameter("password"); String password2 = request.getParameter("password2"); User user = new User(); user.setUsername(username); user.setPassword(password); UserManager userManager = new UserManager(); boolean exists = userManager.exists(user); if(exists) { response.sendRedirect("registerFail.jsp"); return ; } userManager.add(user); response.sendRedirect("registerSuccess.jsp"); %>
项目在tomcat中的加载
加入hibernate 和数据库打交道 引入的准备工作:
1、引入jar包
2、搭建hibernate.cfg.xml , log4j.properties 两个配置文件
3、引入junit 进行测试
package com.demo.registration.service; import java.sql.Connection; import java.sql.DriverManager; import java.sql.PreparedStatement; import java.sql.ResultSet; import java.sql.SQLException; import org.hibernate.Session; import org.hibernate.SessionFactory; import com.demo.registration.model.User; import com.demo.registration.util.HibernateUtil; public class UserManager { //判断用户名是否存在 public boolean exists(User user) { SessionFactory sessionFactory = HibernateUtil.getSessionFactory(); Session session = sessionFactory.getCurrentSession(); session.beginTransaction(); Long count = (Long)session.createQuery("select count(*) from User u where u.username = :username") .setString("username", user.getUsername()) .uniqueResult(); session.getTransaction().commit(); if(count > 0) return true; return false; } //在插入之前要检查用户名是否存在,不存在就插入 public void add(User user) { SessionFactory sessionFactory = HibernateUtil.getSessionFactory(); Session session = sessionFactory.getCurrentSession(); session.beginTransaction(); session.save(user); session.getTransaction().commit(); } }
//Junit测试类 package com.demo.registration.service; import org.junit.Assert; //自动提示 import org.junit.Test; import com.demo.registration.model.User; public class UserManagerTest { @Test public void testExists() { UserManager userManager = new UserManager(); User user = new User(); user.setUsername("a"); boolean exists = userManager.exists(user); Assert.assertEquals(true, exists); } @Test public void testAdd() throws Exception { UserManager userManager = new UserManager(); User user = new User(); user.setUsername("o"); user.setPassword("o"); boolean exists = userManager.exists(user); if(!exists) { userManager.add(user); user.setUsername("o"); Assert.assertEquals(true, userManager.exists(user)); } else { Assert.fail("not added"); } } }
抽象DAO层,咋们考虑另一种客户端,不通过自己的逻辑,就想直接访问数据库里面的内容,所以我们把DAO层抽象出来,不要直接把数据库这张表暴露给它,保证安全。
假如,要跨数据库的实现,要跨各种各样的存储方式来实现,不只是包括Hibernate去访问数据库,还要包括:如把User存在xml文件里,把User存在网络上去。 因此UserManager不要把
User的存储最好不要写死,写死成Hibernate、写成JDBC或者xml。
所以这个时候就需要DAO层(专门用来封装对实体类的数据库的访问,就是增删改查,不加业务逻辑)。
UserDao层
UserDAOImpl实现层
UserManagerImple实现层
根据一个实现类抽取接口的方法
package com.demo.registration.service; import com.demo.registration.model.User; public interface UserManager { public abstract boolean exists(User user) throws Exception; public abstract void add(User user) throws Exception; }
package com.demo.registration.service.impl; import com.demo.registration.dao.UserDao; import com.demo.registration.dao.impl.UserDaoImpl; import com.demo.registration.model.User; import com.demo.registration.service.UserManager; public class UserManagerImpl implements UserManager { UserDao userDao = new UserDaoImpl(); public UserDao getUserDao() { return userDao; } public void setUserDao(UserDao userDao) { this.userDao = userDao; } public boolean exists(User user) { return userDao.checkUserExistsWithName(user.getUsername()); } public void add(User user) { userDao.save(user); } }
struts2 解决了容器Cotroller (控制器)1、把view (V)层和 业务逻辑层(M)分开
2、view也可以进行重复使用,也可以进行替换,也可以进行扩展 (其实只是把view 起了个名,想把实现文件替换掉,只需要该配置文件即可)
3、(M)业务逻辑层 也可以进行重复使用,也可以进行扩展
4、主要解决互相之间耦合性不那么强的依赖于对方
struts 这一层准备工作:
1、引入jar包
2、web.xml 里面进行filter的配置
3、把struts.xml 引入进来
4、建立action
//struts.xml <?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE struts PUBLIC "-//Apache Software Foundation//DTD Struts Configuration 2.0//EN" "http://struts.apache.org/dtds/struts-2.0.dtd"> <struts> <constant name="struts.devMode" value="true"/> <package name="registration" extends="struts-default"> <action name="user" class="com.demo.registration.action.UserAction"> <result name="success">/registerSuccess.jsp</result> <result name="fail">/registerFail.jsp</result> </action> </package> </struts>
web.xml <filter> <filter-name>struts2</filter-name> <filter-class>org.apache.struts2.dispatcher.ng.filter.StrutsPrepareAndExecuteFilter</filter-class> </filter> <filter-mapping> <filter-name>struts2</filter-name> <url-pattern>/*</url-pattern> </filter-mapping>
package com.demo.registration.action; import com.demo.registration.model.User; import com.demo.registration.service.UserManager; import com.demo.registration.service.impl.UserManagerImpl; import com.opensymphony.xwork2.ActionSupport; public class UserAction extends ActionSupport { private String username; private String password; private String password2; UserManager userManager = new UserManagerImpl(); public UserManager getUserManager() { return userManager; } public void setUserManager(UserManager userManager) { this.userManager = userManager; } @Override public String execute() throws Exception { User user = new User(); user.setUsername(username); user.setPassword(password); if(userManager.exists(user)) { return "fail"; } userManager.add(user); return "success"; } public String getUsername() { return username; } public void setUsername(String username) { this.username = username; } public String getPassword() { return password; } public void setPassword(String password) { this.password = password; } public String getPassword2() { return password2; } public void setPassword2(String password2) { this.password2 = password2; } }
spring 加入
需要的配置
1、加入jar包
2、 beans.xml 、 log4j.properties
3、hibernate数据连接的配置已经在beans.xml里面 因此 hibernate.cfg.xml 可以删除了
业务分析
1、当UserManager 去拿UserDao的时候是spring帮你注入的
2、UserManager本身也是由spring来管理的
3、Action要用UserManager的时候也是由spring帮我注入的
4、UserManager里面的方法它都会帮你加上AOP
listener的作用:<listener> <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class> </listener>
就是我们当前的Application启动,它就启动,listener启动之后就去找我们的配置文件,就把我们配置文件里面的对象全部都初始化出来,容器就产生了。
// 对beans.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: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 /> <!-- 扫描所有 com.demo包下面类中所有的组件和注入的资源Component Resource --> <context:component-scan base-package="com.demo"/> <!-- <bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource" destroy-method="close"> <property name="driverClassName" value="com.mysql.jdbc.Driver"/> <property name="url" value="jdbc:mysql://localhost:3306/spring"/> <property name="username" value="root"/> <property name="password" value="root"/> </bean> --> <!-- 连接数据库 --> <bean class="org.springframework.beans.factory.config.PropertyPlaceholderConfigurer"> <property name="locations"> <value>classpath:jdbc.properties</value> </property> </bean> <bean id="dataSource" destroy-method="close" class="org.apache.commons.dbcp.BasicDataSource"> <property name="driverClassName" value="${jdbc.driverClassName}"/> <property name="url" value="${jdbc.url}"/> <property name="username" value="${jdbc.username}"/> <property name="password" value="${jdbc.password}"/> </bean> <!-- 通过数据库配置连接 --> <bean id="sessionFactory" class="org.springframework.orm.hibernate3.annotation.AnnotationSessionFactoryBean"> <property name="dataSource" ref="dataSource"/> <!-- <property name="annotatedClasses"> <list> <value>com.demo.model.User</value> <value>com.demo.model.Log</value> </list> </property> --> <!-- 实体类(用@Entity标注)的自动扫描 --> <property name="packagesToScan"> <list> <value>com.demo.registration.model</value> </list> </property> <property name="hibernateProperties"> <props> <prop key="hibernate.dialect">org.hibernate.dialect.MySQLDialect</prop> <prop key="hibernate.show_sql">true</prop> </props> </property> </bean> <!-- 事物管理 HibernateTransactionManager 管理事务嵌套,开启,关闭,资源线程同步,提交,回滚 --> <bean id="txManager" class="org.springframework.orm.hibernate3.HibernateTransactionManager"> <property name="sessionFactory" ref="sessionFactory"/> </bean> <aop:config> <aop:pointcut id="bussinessService" expression="execution(public * com.demo.registration.service..*.*(..))"/> <aop:advisor advice-ref="txAdvice" pointcut-ref="bussinessService"/> </aop:config> <!-- 在指定方法上面加事物 事物边界是放在service 这里,只有调用才会产生 --> <tx:advice id="txAdvice" transaction-manager="txManager"> <tx:attributes> <tx:method name="exists" read-only="true"/> <tx:method name="add*" propagation="REQUIRED"/> </tx:attributes> </tx:advice> <!-- Hibernate的常规用法,就可完成大多数DAO对象的CRUD操作 也支持分页 --> <bean id="hibernateTemplate" class="org.springframework.orm.hibernate3.HibernateTemplate"> <property name="sessionFactory" ref="sessionFactory"></property> </bean> </beans>
引入jar包 D:\javasoft\ssh\struts-2.1.6\lib\struts2-spring-plugin-2.1.6.jar<listener> <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class> <!-- default: /WEB-INF/applicationContext.xml --> </listener> <!-- Context Configuration locations for Spring XML files --> <context-param> <param-name>contextConfigLocation</param-name> <!--<param-value>/WEB-INF/applicationContext-*.xml,classpath*:applicationContext-*.xml</param-value>--> <param-value>classpath:beans.xml</param-value> </context-param>
转自 http://zhou568xiao.iteye.com/blog/192208下面是struts2+hibernate+spring配置文件的一部分,以前都是仿造已经写好的bean的配置。有一次 scope="prototype"忘记写了结果出了问题 项目中对一个表的增删该操作是用一个action,这个action有add,update,delete,save这些方法,添加和修改是共用一个页面,当页面得到id时代表进行的修改操作,反之是添加操作。因为在配置spring的bean是忘了写scope="prototype"所以每次添加时都显示最后一次访问过的记录 找了很长时间,原来是spring bean出了问题。 scope="prototype" 会在该类型的对象被请求时创建一个新的action对象。如果没有配置scope=prototype则添加的时候不会新建一个action,他任然会保留上次访问的过记录的信息。 <bean id="assetAction" class="com.servicezone.itsd.asset.webapp.action.AssetAction" scope="prototype"> <property name="assetManager" ref="assetManager"/> <property name="itProductManager" ref="itProductManager"/> <property name="vendorManager" ref="vendorManager"/> <property name="deptManager" ref="deptManager"/> <property name="userManager" ref="userManager"/> <property name="assetTypeManager" ref="assetTypeManager"/> </bean>
/** * scope="prototype" 会在该类型的对象被请求时创建一个新的action对象。 * 如果没有配置scope=prototype则添加的时候不会新建一个action, * 他任然会保留上次访问的过记录的信息。 */
//web.xml <?xml version="1.0" encoding="UTF-8"?> <web-app version="2.5" xmlns="http://java.sun.com/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"> <welcome-file-list> <welcome-file>index.jsp</welcome-file> </welcome-file-list> <!-- 监听器 初始化所有的配置文件 --> <listener> <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class> <!-- default: /WEB-INF/applicationContext.xml --> </listener> <!-- Context Configuration locations for Spring XML files --> <context-param> <param-name>contextConfigLocation</param-name> <!--<param-value>/WEB-INF/applicationContext-*.xml,classpath*:applicationContext-*.xml</param-value>--> <param-value>classpath:beans.xml</param-value> </context-param> <!-- struts的配置文件 --> <filter> <filter-name>struts2</filter-name> <filter-class>org.apache.struts2.dispatcher.ng.filter.StrutsPrepareAndExecuteFilter</filter-class> </filter> <filter-mapping> <filter-name>struts2</filter-name> <url-pattern>/*</url-pattern> </filter-mapping> </web-app>
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE struts PUBLIC "-//Apache Software Foundation//DTD Struts Configuration 2.0//EN" "http://struts.apache.org/dtds/struts-2.0.dtd"> <struts> <constant name="struts.devMode" value="true"/> <package name="registration" extends="struts-default"> <action name="user" class="com.demo.registration.action.UserAction"> <result name="success">/registerSuccess.jsp</result> <result name="fail">/registerFail.jsp</result> </action> </package> </struts>
ssh 整合视图
/** * scope="prototype" 会在该类型的对象被请求时创建一个新的action对象。 * 如果没有配置scope=prototype则添加的时候不会新建一个action, * 他任然会保留上次访问的过记录的信息。 */ @Component("user") @Scope("prototype") // 每个请求都会生成一个新的action
再加DTO层
package com.demo.registration.vo; public class UserRegisterInfo { private String username; private String password; private String password2; public String getUsername() { return username; } public void setUsername(String username) { this.username = username; } public String getPassword() { return password; } public void setPassword(String password) { this.password = password; } public String getPassword2() { return password2; } public void setPassword2(String password2) { this.password2 = password2; } }
package com.demo.registration.action; import javax.annotation.Resource; import org.springframework.context.ApplicationContext; import org.springframework.context.annotation.Scope; import org.springframework.context.support.ClassPathXmlApplicationContext; import org.springframework.stereotype.Component; import com.demo.registration.model.User; import com.demo.registration.service.UserManager; import com.demo.registration.vo.UserRegisterInfo; import com.opensymphony.xwork2.ActionSupport; import com.opensymphony.xwork2.ModelDriven; //1、action类中不要写annotation写了没用struts自己产生 // 2、spring可以注入 public class UserAction extends ActionSupport implements ModelDriven { private UserRegisterInfo info = new UserRegisterInfo(); private UserManager userManager; public UserManager getUserManager() { return userManager; } public void setUserManager(UserManager userManager) { this.userManager = userManager; } @Override public String execute() throws Exception { User user = new User(); user.setUsername(info.getUsername()); user.setPassword(info.getPassword()); if(userManager.exists(user)) { return "fail"; } userManager.add(user); return "success"; } public UserRegisterInfo getInfo() { return info; } public void setInfo(UserRegisterInfo info) { this.info = info; } @Override public Object getModel() { return info; } }
以下为MVC架构图形
mvc
因此分析如下:
1、界面原型,帮我们建立分析需求
2、确定实体类,建立数据库表
<s:debug></s:debug> 把开发模式设为 true <constant name="struts.devMode" value="true"/>
获取数据库里面的usernam
<body> <s:iterator value="users"> <!-- UserAction 里面 private List<User> users; users属性 --> <s:property value="username"></s:property> <!-- 封装在这个类里面UserRegisterInfo的username属性 --> </s:iterator> <s:debug></s:debug> </body>
package com.demo.registration.action; import java.util.List; import javax.annotation.Resource; import org.springframework.context.ApplicationContext; import org.springframework.context.annotation.Scope; import org.springframework.context.support.ClassPathXmlApplicationContext; import org.springframework.stereotype.Component; import com.demo.registration.model.User; import com.demo.registration.service.UserManager; import com.demo.registration.vo.UserRegisterInfo; import com.opensymphony.xwork2.ActionSupport; import com.opensymphony.xwork2.ModelDriven; public class UserAction extends ActionSupport implements ModelDriven { private UserRegisterInfo info = new UserRegisterInfo(); private UserManager userManager; private List<User> users; public UserManager getUserManager() { return userManager; } public void setUserManager(UserManager userManager) { this.userManager = userManager; } public String list() { this.users = this.userManager.getUsers(); return "list"; } @Override public String execute() throws Exception { User user = new User(); user.setUsername(info.getUsername()); user.setPassword(info.getPassword()); if(userManager.exists(user)) { return "fail"; } userManager.add(user); return "success"; } public UserRegisterInfo getInfo() { return info; } public void setInfo(UserRegisterInfo info) { this.info = info; } @Override public Object getModel() { return info; } public List<User> getUsers() { return users; } public void setUsers(List<User> users) { this.users = users; } }
/* * 在测试load方法的时候因为是getCurrentSession load 完了就关闭 * 在web.xml里面配置 OpenSessionInViewFilter jsp关闭session才关闭不过要配置的 * StrutsPrepareAndExecuteFilter的前面 */ public String load() { this.user = this.userManager.loadById(info.getId()); return "load"; }
// 以下是jsp获取属性的2中同样的方法 <!-- <s:iterator value="user"> <s:property value="username"/> </s:iterator> --> <s:property value="user.username"/>
//以下配置文件作用是把Session 打开的时间一直延续到jsp这层,完了之后就关闭,不过单个对象可以用get方法(load) 如果没有配事物边界HibernateTransactionManager 那么它
//openSessionInView 认为这个session里面的这个事物是只读的,
<filter><filter-name>openSessionInView</filter-name><filter-class>org.springframework.orm.hibernate3.support.OpenSessionInViewFilter</filter-class></filter><filter-mapping> <filter-name>openSessionInView</filter-name> <url-pattern>/*</url-pattern> </filter-mapping><?xml version="1.0" encoding="UTF-8"?> <web-app version="2.5" xmlns="http://java.sun.com/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"> <welcome-file-list> <welcome-file>index.jsp</welcome-file> </welcome-file-list> <listener> <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class> <!-- default: /WEB-INF/applicationContext.xml --> </listener> <!-- Context Configuration locations for Spring XML files --> <context-param> <param-name>contextConfigLocation</param-name> <!--<param-value>/WEB-INF/applicationContext-*.xml,classpath*:applicationContext-*.xml</param-value>--> <param-value>classpath:beans.xml</param-value> </context-param> <filter> <filter-name>openSessionInView</filter-name> <filter-class>org.springframework.orm.hibernate3.support.OpenSessionInViewFilter</filter-class> </filter> <filter-mapping> <filter-name>openSessionInView</filter-name> <url-pattern>/*</url-pattern> </filter-mapping> <filter> <filter-name>struts2</filter-name> <filter-class>org.apache.struts2.dispatcher.ng.filter.StrutsPrepareAndExecuteFilter</filter-class> </filter> <filter-mapping> <filter-name>struts2</filter-name> <url-pattern>/*</url-pattern> </filter-mapping> </web-app>
//查看mysql数据库表里面的编码 mysql> show create table user; +-------+---------------------------------- -------------------------------+ | Table | Create Table | +-------+---------------------------------- -------------------------------+ | user | CREATE TABLE `user` ( `id` int(11) NOT NULL AUTO_INCREMENT, `username` varchar(100) DEFAULT NULL, `password` varchar(20) DEFAULT NULL, PRIMARY KEY (`id`) ) ENGINE=InnoDB DEFAULT CHARSET=gb2312 | +-------+---------------------------------- -------------------------------+ 1 row in set (0.05 sec)
编码问题 1、如果是在action 往数据库里面插入产生的,那么就需要解决action与数据库之间的编码问题,数据库连接,数据库底层表的实现的编码 2、如果是接收参数产生的就是配置web方面产生的
web.xml配置 filter 乱码乱码问题解决 利用spring
<filter>
<filter-name>encodingFilter</filter-name>
<filter-class>org.springframework.web.filter.CharacterEncodingFilter</filter-class>
<init-param>
<param-name>encoding</param-name>
<param-value>GBK</param-value>
</init-param>
</filter>
<filter-mapping>
<filter-name>encodingFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
package com.demo.registration.action; import java.util.List; import javax.annotation.Resource; import org.springframework.context.ApplicationContext; import org.springframework.context.annotation.Scope; import org.springframework.context.support.ClassPathXmlApplicationContext; import org.springframework.stereotype.Component; import com.demo.registration.model.User; import com.demo.registration.service.UserManager; import com.demo.registration.vo.UserRegisterInfo; import com.opensymphony.xwork2.ActionSupport; import com.opensymphony.xwork2.ModelDriven; /** * scope="prototype" 会在该类型的对象被请求时创建一个新的action对象。 * 如果没有配置scope=prototype则添加的时候不会新建一个action, * 他任然会保留上次访问的过记录的信息。 */ @Component("u") //这个与struts.xml配置里面的 calss一直 @Scope("prototype")// 每个请求都会生成一个新的action public class UserAction extends ActionSupport implements ModelDriven { private UserRegisterInfo info = new UserRegisterInfo(); private UserManager userManager; private List<User> users; private User user; public UserManager getUserManager() { return userManager; } @Resource public void setUserManager(UserManager userManager) { this.userManager = userManager; } public String list() { this.users = this.userManager.getUsers(); return "list"; } /* * 在测试load方法的时候因为是getCurrentSession load 完了就关闭 * 在web.xml里面配置 OpenSessionInViewFilter jsp关闭session才关闭不过要配置的 * StrutsPrepareAndExecuteFilter的前面 */ public String load() { this.user = this.userManager.loadById(info.getId()); return "load"; } @Override public String execute() throws Exception { System.out.println(info.getUsername());//判断乱码问题 User user = new User(); user.setUsername(info.getUsername()); user.setPassword(info.getPassword()); if(userManager.exists(user)) { return "fail"; } userManager.add(user); return "success"; } public UserRegisterInfo getInfo() { return info; } public void setInfo(UserRegisterInfo info) { this.info = info; } @Override public Object getModel() { return info; } public List<User> getUsers() { return users; } public void setUsers(List<User> users) { this.users = users; } public User getUser() { return user; } public void setUser(User user) { this.user = user; } }
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE struts PUBLIC "-//Apache Software Foundation//DTD Struts Configuration 2.0//EN" "http://struts.apache.org/dtds/struts-2.0.dtd"> <struts> <constant name="struts.devMode" value="true"/> <package name="registration" extends="struts-default"> <action name="userAction" class="u"> <result name="success">/registerSuccess.jsp</result> <result name="fail">/registerFail.jsp</result> <result name="list">/userlist.jsp</result> <result name="load">/user.jsp</result> </action> </package> </struts>