一、 rusult标签结果集配置
全局结果
<!-- 全局result设置-->
<global-results>
<!-- 不写name属性,默认success -->
<result>/a_result/result.jsp</result>
</global-results>
作用是为package中配置的所有action提供全局的返回结果页面
局部结果
<action name="result_*" class="com.itdream.struts2.test.Struts2_Result" method="{1}">
<!-- 默认是SUCESS -->
<result>/a_result/result.jsp</result>
</action>
写在action标签内,作用是为当前action配置结果页面
结果类型【掌握前四种】
1. dispatcher 转发页面
dispathcer转发到页面。不写type默认值就是dispatcher转发
<result name="resultTypejsp" type="dispatcher">/b_resultType/resultType.jsp</result>
2. chain 转发Action
chain是转发到Action动作类,result标签内填写要转发到的action的name属性,不能加.action的后缀
可以这样理解,转发相当于在当前struts.xml中找action的name,所以不需要加.action后缀
<result name="resultTypejsp" type="chain">resultType2</result>
3. redirect 重定向到页面
重定向到页面。
<result name="resultTypejsp" type="redirect">/b_resultType/resultType.jsp</result>
4. redirectAction 转发Action
重定向到Action动作类中的action的内容可以加.ation后缀名也可以不加
<result name="resultTypejsp" type="redirectAction">resultType2.action</result>
5. stream: 结果为文件流。文件下载
<result name="success" type="stream">
<param name="contentType">image/jpeg</param>
<param name="inputName">imageStream</param>
<param name="contentDisposition">attachment;filename="document.pdf"</param>
<param name="bufferSize">1024</param>
</result>
contentType:下载文件类型
inputName:对应要输出到客户端流声明的名称
contentDisposition:下载到客户端时,客户端文件名称
bufferSize:读文件的缓存大小
6. json:转发。
<package name="xxx" namespace="/xxx" extends="json-default">
<action name="json" method="xxx"
class="org.itheima.struts.action.JsonAction">
<result name="success" type="json">
<param name="encoding">utf-8</param>
<param name="root">jsonObject</param>
</result>
</action>
</package>
由action转发到json结果
encoding:配置编码格式
root:配置对象。action类中必须提供一个和root值相同的属性名称,且需要提供getter方法。
7. jsonActionRedirect:重定向
<action name="xxx" method="xxx"
class="org.itheima.struts.action.JsonAction">
<result name="success" type="jsonActionRedirect">
xxx.action
</result>
</action>
由action重定向到json结果。
8. 小结
dispatcher与chain属于转发,redirect与redirectAction是重定向
这里的转发和重定向的理解与Servlet中一样。
填写的内容.action也与Servlet中的理解差不多。
重定向相当于页面重新发送请求,因此后缀有.action(也可以没有)
转发不能有后缀.action
二、 Struts与Servlet交互对接的三种方式
客户端与服务端交互时,通常会带参数过来,服务器也会回写数据给客户端。在此过程中,参与着请求,和响应,以及会话。servlet在此过程中提供了HttpServletRequest作为获取请求数据的方案,HttpServletResponse作为响应的方案,HttpSession负责了会话方案。Struts其实是基于servlet实现的web框架,他需要遵循规则提供请求,响应和会话的API供开发人员使用,因此Struts针对这一问题提供了自己的一套API封装,提供了多种方式的访问。
1. 使用ActionContext对象间接使用Servlet的API
1.1 ActionContext对象实例获取
ActionContext context = ActionContext.getContext();
ActionContext是绑定在当前线程中的。框架在请求线程开启时,
将ActionContext实例对象就绑定上来了,因此我们可以通过静态方法直接获取。
1.2 请求参数的获得
Map<String, Object> parameters = context.getParamters();
相当于Servlet中的request.getParamters()方法
1.3 存储数据到域中
context.put(key, value); 相当于存储数据到request域中
context.getSession().put(key,value); 相当于存储数据到Session域中
context.getApplication().put(key, value); 相当于存储数据到ServletContext作用域
1.4 表单提交测试
表单form.jsp :
<form action="${pageContext.request.contextPath }/servlet1.action" method="post">
用户名<input type="text" name="username" /><br/>
密码<input type="password" name="password" /><br/>
<input type="submit" value="提交" /><br/>
</form>
----------------------------------------------------------------------------
struts.xml中action的配置 :
<action name="servlet1" class="com.itdream.struts2.test.Struts2_Servlet" method="servlet1">
<result>/c_servlet/result.jsp</result>
</action>
----------------------------------------------------------------------------
Action动作类:
ActionContext context = ActionContext.getContext();
//获取到传递过来的所有参数
Map<String, Object> parameters = context.getParameters();
for(String key : parameters.keySet()) {
//通过获取的key获取到每一个对应的String[]的值
String[] values = (String[]) parameters.get(key);
//存入request作用域
context.put(key, values[0]);
}
//转发到页面显示
return SUCCESS;
---------------------------------------------------------------------------
回显页面 :
用户名:${username }<br/>
密码:${password }
2. 实现Struts2提供的相应接口获取相应的实例
实现以下接口 ,提供声明以及setter方法:
ServletContextAware
ServletRequestAware
ServletResponseAware
ParameterAware
SessionAware
ApplicationAware
PrincipalAware
例如:下面例子实现ServletRequestAware接口,成员位置声明request,并提供setter方法。
public class Struts2_Servlet2 extends ActionSupport implements ServletRequestAware {
//声明request引用
private HttpServletRequest request;
@Override
//提供setter方法,Struts2框架检测到我们实现了ServletRequestAware接口,会将与request对象作为参数传递进来
public void setServletRequest(HttpServletRequest request) {
this.request = request;
}
// 间接方式使用Servlet的API
public String servlet2() {
//获取参数
String username = request.getParameter("username");
String password = request.getParameter("password");
System.out.println(username);
System.out.println(password);
//存入作用域
request.setAttribute("username", username);
request.setAttribute("password", password);
//页面跳转
return SUCCESS;
}
}
3. 使用ServletActionContext直接获取实例
Struts2
还提供了ServletActionContext
类提供了多个静态方法。
1. 获得请求
HttpServletRequest request = ServletActionContext.getRequest();
2. 获得响应
HttpServletResponse response = ServletActionContext.getResponse();
-----------------------------------------------------------------------------
3. 获得ServletContext对象
ServletContext servletContext = ServletActionContext.getServletContext();
4. 获得PageContext对象
PageContext pageContext = ServletActionContext.getPageContext();
============================================================================
例如:
public String servlet2() {
// 获得request对象
HttpServletRequest request = ServletActionContext.getRequest();
// 获取参数
String username = request.getParameter("username");
String password = request.getParameter("password");
// 存入作用域
request.setAttribute("username", username);
request.setAttribute("password", password);
// 页面跳转
return SUCCESS;
}
三、 Struts封装参数的三种方式
1. 属性驱动(有两种)
1.1 将Action作为javaBean类,提供属性的setter方法
将Action动作类作为一个JavaBean的类,提供与表单name属性对应的成员变量的声明,Struts2在执行到
param拦截器时,会根据提供的setter方法将获取到的参数一一封装到对应的字段中去。
-----------------------------------------------------------------------------
例子:
form.jsp :
<form action="${pageContext.request.contextPath }/model1.action" method="post">
用户名<input type="text" name="username" /><br/>
密码<input type="password" name="password" /><br/>
年龄<input type="text" name="age" /><br/>
生日<input type="text" name="birthday" /><br/>
<input type="submit" value="提交" /><br/>
</form>
struts.xml :
<action name="model1" class="com.itdream.model.test.Model1"></action>
Action动作类:
/**
* 属性驱动:将Action动作类作为一个javaBean类,提供属性的setter方法,Struts2使用setter来封装参数
*/
public class Model1 extends ActionSupport {
private String username;
private String password;
private int age;
private Date birthday;
public void setAge(int age) {
this.age = age;
}
public void setBirthday(Date birthday) {
this.birthday = birthday;
}
public void setUsername(String username) {
this.username = username;
}
public void setPassword(String password) {
this.password = password;
}
@Override
public String execute() throws Exception {
// 我们提供了与参数name属性相同的字段,Struts2在调用拦截器时就帮我们对数据进行了封装,但是必须提供setter方法
// 因此我们直接使用封装好了的参数了
System.out.println(username);
System.out.println(password);
System.out.println(age);
System.out.println(birthday);
return NONE;
}
}
这种驱动方式的缺陷是如果传入的数据很多的话,那么Action动作类中需要定义的字段也会很多,同样setter方法也会变的很多。
这使得Action中的代码变得很臃肿。
1.2 属性驱动 : 对象驱动
- 在Action类中声明一个JavaBean的实例对象,通过这个实例对象封装传递过来的参数
- 这种对象驱动的前提是:创建这样一个JavaBean并提供setter/getter方法
- 在页面传值的时候使用ognl表达式,即
对象名.字段名
例子:
form.jsp : 表单提交的参数的name属性必须使用 对象名.字段名的方式
<form action="${pageContext.request.contextPath }/model2.action" method="post">
用户名<input type="text" name="user.username" /><br/>
密码<input type="password" name="user.password" /><br/>
年龄<input type="text" name="user.age" /><br/>
生日<input type="text" name="user.birthday" /><br/>
<input type="submit" value="提交" /><br/>
</form>
struts.xml :
<action name="model2" class="com.itdream.model.test.Model2Action"></action>
Action动作类 :
public class Model2Action extends ActionSupport {
//声明JavaBean对象用于封装
private User user;
//必须提供对象的getter方法,Struts2框架通过getter方法获取到这个javaBean对象,
//这个对象如果为null,Struts2会new一个对象通过setter方法放进来,以便下一次参数的封装
public User getUser() {
return user;
}
public void setUser(User user) {
this.user = user;
}
@Override
public String execute() throws Exception {
System.out.println(user);
return NONE;
}
}
这种 属性驱动_对象驱动 必须提供getter方法,如果没有提供getter方法,Struts2框架底层就无法获得该对象进行封装。
2. 模型驱动
Struts2
中封装参数还有一种方式:模型驱动。
- 实现
ModelDriven
接口封装参数 - 提供一个JavaBean的类,用于封装
- 必须在成员位置创建要封装成的JavaBean的对象
- 必须实现getModel方法,Struts2底层获得该对象
接收到请求,Struts2发现要跳转的Action实现了ModelDriven接口,就会在modelDriven拦截器时执行,
在这个拦截器会获取到提供的Model对象,进行参数的封装。这里要注意,我们必须手动创建对象,Struts2
的底层不会帮我们创建对象。
另外,如果modelDriven拦截器封装了的参数,在该拦截器后的params拦截器就不会再进行封装了,它只会
封装modelDriven未进行封装的参数。
因此,模型驱动优先于属性驱动。
----------------------------------------------------------------------------------
例子:
form.jsp :
<form action="${pageContext.request.contextPath }/model3.action" method="post">
用户名<input type="text" name="username" /><br/>
密码<input type="password" name="password" /><br/>
年龄<input type="text" name="age" /><br/>
生日<input type="text" name="birthday" /><br/>
<input type="submit" value="提交" /><br/>
</form>
-------------------------------------------------------------------------------
struts.xml :
<action name="model3" class="com.itdream.model.test.Model3Action"></action>
-------------------------------------------------------------------------------
Action动作类:
/**
* 模型驱动 : 前提: 提供一个JavaBean的模型类,以供封装
*/
public class Model3Action extends ActionSupport implements ModelDriven<User> {
// 模型驱动:手动构建对象
private User user = new User();
@Override
// Struts2获取到这个对象模型,用于封装
public User getModel() {
return user;
}
@Override
public String execute() throws Exception {
System.out.println(user);
return NONE;
}
}
模型封装,对于封装单个对象是非常方便的,但是如果要封装多个对象,还是需要使用属性驱动中的对象驱动
3. 属性驱动-对象驱动封装对象到List
集合中
与上面属性驱动的对象驱动一样。
1. 必须提供JavaBean的实体类用于封装对象。
2. 页面jsp传参到Action动作类使用OGNL表达式。
3. Action动作类中声明该对象,和模型驱动不同,属性驱动的对象驱动可以不创建对象,框架会帮我们创建对象。
4. 必须提供get和set方法,以便Struts2的底层进行封装
form.jsp
页面OGNL表达式传参:
<form action="${pageContext.request.contextPath }/model4.action" method="post">
用户名<input type="text" name="list[0].username" /><br/>
密码<input type="password" name="list[0].password" /><br/>
年龄<input type="text" name="list[0].age" /><br/>
生日<input type="text" name="list[0].birthday" /><br/>
用户名<input type="text" name="list[1].username" /><br/>
密码<input type="password" name="list[1].password" /><br/>
年龄<input type="text" name="list[1].age" /><br/>
生日<input type="text" name="list[1].birthday" /><br/>
用户名<input type="text" name="list[2].username" /><br/>
密码<input type="password" name="list[2].password" /><br/>
年龄<input type="text" name="list[2].age" /><br/>
生日<input type="text" name="list[2].birthday" /><br/>
<input type="submit" value="提交" /><br/>
</form>
这里name属性使用,list[0]...代表放入List集合中的某一个对象,用list[n].字段名 代表传递单个对象的单个字段的参数。
struts.xml : 请求对应Action配置
<action name="model4" class="com.itdream.model.test.Model4Action"></action>
Action动作类
/**
* 封装多个对象到List集合中 前提: 提供JavaBean类用于封装每一个对象,页面使用OGNL表达式
*/
public class Model4Action extends ActionSupport {
// 提供List集合的声明,用于封装对象
private List<User> list = new ArrayList<>();
//必须提供List集合的get方法,让Struts2框架能够拿到该对象
public List<User> getList() {
return list;
}
//如果拿到的对象为空,Struts2会利用set方法声明的引用设置一个新的对象。即框架底层会帮我new一个对象,并传递进来,以便进行封装
public void setList(List<User> list) {
this.list = list;
}
@Override
public String execute() throws Exception {
System.out.println(list);
return NONE;
}
}
4. 属性驱动-对象驱动封装对象到Map
集合中
与上面属性驱动的对象驱动一样。
1. 必须提供JavaBean的实体类用于封装对象。
2. 页面jsp传参到Action动作类使用OGNL表达式。
3. Action动作类中声明该对象,和模型驱动不同,属性驱动的对象驱动可以不创建对象,框架会帮我们创建对象。
4. 必须提供get和set方法,以便Struts2的底层进行封装
form.jsp
页面OGNL表达式传参:
<form action="${pageContext.request.contextPath }/model5.action" method="post">
用户名<input type="text" name="map['one'].username" /><br/>
密码<input type="password" name="map['one'].password" /><br/>
年龄<input type="text" name="map['one'].age" /><br/>
生日<input type="text" name="map['one'].birthday" /><br/>
用户名<input type="text" name="map['two'].username" /><br/>
密码<input type="password" name="map['two'].password" /><br/>
年龄<input type="text" name="map['two'].age" /><br/>
生日<input type="text" name="map['two'].birthday" /><br/>
用户名<input type="text" name="map['three'].username" /><br/>
密码<input type="password" name="map['three'].password" /><br/>
年龄<input type="text" name="map['three'].age" /><br/>
生日<input type="text" name="map['three'].birthday" /><br/>
<input type="submit" value="提交" /><br/>
</form>
这里name属性使用,map['one']...来代表放入map集合的第几个对象,传递的单个对象的字段的参数,使用map['one'].字段名来表示
struts.xml : 请求对应Action配置
<action name="model5" class="com.itdream.model.test.Model5Action"></action>
Action动作类
/**
* 属性驱动: 对象驱动封装多个对象的参数 前提: 有一个JavaBean的实体类用于封装每个对象 jsp页面使用OGNL表达式表示每一个字段属性进行传参
* 提供get和set方法
*/
public class Model5Action extends ActionSupport {
// 声明/创建一个Map集合用于封装参数
private Map<String, User> map = new HashMap<>();
//提供get方法,Struts2框架可以获得该map集合用于封装
public Map<String, User> getMap() {
return map;
}
//提供set方法,Struts2如果获得的map集合为null,会自动创建一个然后传递Map集合的引用到当前声明
public void setMap(Map<String, User> map) {
this.map = map;
}
@Override
public String execute() throws Exception {
for(String key : map.keySet()) { //遍历获取每一个key
System.out.println(key+">>>"+map.get(key));
System.out.println("==============================");
}
return NONE;
}
}
四、 Struts2的参数类型转换器【了解】
解决的问题:
客户端传输过程中传输特定类型的字符串时,到action类中需要转换为对应的对象时,中间的转换的问题。
主要解决的是对象类型的转换。
一般来说,Struts2提供的类型转换器已经很强大了,一般不需要再自己自定义类型转换器了。
-----------------------------------------------------------------------------
如果类型转换错误,会提示需要跳转到result标签name为input对应的页面去 :
解决方案 : 配置input结果集视图,跳转回输入页面:
<result name="input">/error.jsp</result>
又发现如果只是这么处理让其跳回输入页面没有友好提示 :
解决方案:
页面需要回显错误提示。使用<s:fielderror/>自动回显错误信息。
要使用该标签,必须先引入标签库:
<%@ taglib prefix="s" uri="/struts-tags" %>
<s:fielderror>填写错误</s:fielderror>
-----------------------------------------------------------------------------
为什么参数转换错误会跳转到input逻辑视图页面?
1. 在接收请求参数时, 必然要进行类型转换。如果Struts2的类型转换器执行类型转换时出现错误,那么,Struts2 内部提供了一个名为conversionError的拦截器来处理错误,该拦截器将负责将对应错误封装成表单域错误(FieldError),并将这些错误信息放入ActionContext中的一个集合中;
2. 当执行到WorkFlow拦截器的时候,该拦截器会判断ActionContext的集合中是否存在错误信息,如果存在,则,自动跳转到input逻辑视图。(一般我们还配置到原来的页面,让用户更正输入的数据)。
自定义转换器的配置方案
1. 新建一个类继承StrutsTypeConverter,实现内部方法
public class DateConversion extends StrutsTypeConverter {
private SimpleDateFormat sdf = new SimpleDateFormat("yyyy/MM/dd");
@Override
public Object convertFromString(Map context, String[] values, Class toClass) {
if (values != null && values.length > 0) {
String dateString = values[0];
try {
return sdf.parse(dateString);
} catch (ParseException e) {
e.printStackTrace();
return null;
}
}
return null;
}
@Override
public String convertToString(Map context, Object o) {
if (o != null && o instanceof Date) {
return sdf.format(o);
}
return null;
}
}
2. 在项目的src下新建xwork-conversion.properties,在其中配置要转换的类型(注册全局转换器)
java.util.Date=org.itdream.struts.action.DateConversion
五、 异常Exception捕获
解决的问题:当action代码执行中出现异常时,错误信息会反馈到客户页面,用户体验不好
局部异常捕获:
在action标签中配置exception-mapping标签:
<result name="xxx" type="redirect">/xxx.jsp</result>
<exception-mapping result="xxx" exception="java.lang.Throwable" />
* exception-mapping标签中的result属性指向捕获异常后出错的页面结果。
* exception-mapping标签中的exception属性指的是要捕获那种异常。
全局异常捕获:
在package标签中配置global-exception-mapping标签 :
<global-results>
<result name="xxx">xxx.jsp</result>
</global-results>
<global-exception-mappings>
<exception-mapping result="xxx"
exception="java.lang.Throwable">
</exception-mapping>
</global-exception-mappings>
* global-exception-mapping标签中的result属性指向捕获异常后出错的页面结果。
* global-exception-mapping标签中的exception属性指的是要捕获那种异常。
异常显示 :
异常捕获的作用是为了提示用户界面的显示结果,但如果出错了,开发人员是要知道错误日志的。
如果要开启错误日志,在action标签中配置如下:
<interceptor-ref name="defaultStack">
<param name="exception.logEnabled">true</param>
<param name="exception.logLevel">error</param>
</interceptor-ref>
六、 CRM案例:使用Hibernate与Struts2添加客户
1. 分析
- 创建
Web
工程,Struts
环境搭建- 导入
Struts2
的jar包(与Hibernate的jar包不冲突) -
web.xml
配置Struts2的前端控制器 - 配置
struts.xml
,确定请求与Action动作类,以及响应与result页面的对应关系 - Struts2搭建完成
- 导入
-
Hibernate
环境搭建- 导入
Hibernate
所需的jar包:required,c3p0,log4j - 创建
Hibernate
所需的ORM关系- R : 关系型数据库,创建所需数据库的表
sys_customer
- O : 持久化类,编写持久化类,
Customer
- M : 配置文件,配置文件间的映射关系,
Customer.hbm.xml
- R : 关系型数据库,创建所需数据库的表
-
Hibernate
的核心配置文件hibernate.cfg.xml
- 连接数据库的基本配置
- 配置与线程绑定的
Session
- 普通配置
Hibernate的方言配置,实现了跨数据库
- 显示sql语句
- 格式化sql语句
-
Hibernate
的自动建表hbm2ddl
-
Hibernate
的事务隔离级别配置 -
c3p0
连接池配置
- 加载映射文件
- 编写
Hibernate
工具类HibernateUtils
- 测试
Hibernate
是否搭建成功
- 导入
- 实现客户添加功能
- 这里我为了使用以下
result标签的redirectAction
的功能,修改menu.jsp
点击添加客户时跳转到CustomerAction
,最后跳转到add.jsp
-
add.jsp
填写完成点击提交,将数据提交到CustomerAction动作类
中,在Action
动作类实现将客户保存到数据库中 - 添加完成访问
CustomerAction
的查询所有客户的list
方法 - 功能完成
- 这里我为了使用以下
2. 环境搭建【省略】
3. 代码体现
3.1 修改menu.jsp
点击添加客户跳转到Action
<TD class=menuSmall><A class=style2 href="${pageContext.request.contextPath}/customer_add.action" target="main">- 新增客户</A></TD>
3.2 struts.xml配置根据访问路径跳转对应Action
为了方便,我直接将struts.xml中所有配置直接粘贴过来,看的时候根据逻辑看
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE struts PUBLIC
"-//Apache Software Foundation//DTD Struts Configuration 2.3//EN"
"http://struts.apache.org/dtds/struts-2.3.dtd">
<struts>
<!-- 开发者模式开启 -->
<constant name="struts.devMode" value="true" />
<package name="default" namespace="/" extends="struts-default">
<!-- 与customer有关的Action -->
<action name="customer_*" class="com.itdream.struts2.crm.web.action.CutomerAction" method="{1}">
<result name="addJsp">/jsp/customer/add.jsp</result>
<result name="saveSucess" type="redirectAction">customer_list</result>
<!-- 默认转发 -->
<result name="listCustomer">/jsp/customer/list.jsp</result>
</action>
</package>
</struts>
3.3 Action动作类
/**
* 处理有关Cutomer的Action动作类
*/
public class CutomerAction extends ActionSupport implements ModelDriven<Customer>{
//手动创建model对象,如果不创建只是声明的话,Struts2底层不会帮我们创建
private Customer customer = new Customer();
@Override
//必须提供getModel方法,Struts2才能获得我们创建的model对象,进行封装
public Customer getModel() {
return customer;
}
//用户点击添加客户其实可以直接让他跳转add.jsp,这里为了实现以下result标签的redirect重定向跳转
public String add() {
return "addJsp";
}
//用户添加客户
public String save() {
System.out.println("=======================");
//获取表单提交参数,这里使用模型驱动Struts2框架帮我们进行封装
//实现ModelDriven的接口,泛型是Customer的实体类,成员变量创建Model对象,添加getModel方法让Struts2能够获得声明的对象
//--------------------------------------
//调用Service业务层保存客户
CustomerService service = new CustomerServiceImpl();
service.saveCustomer(customer);
return "saveSucess";
}
//查看所有客户列表
public String list() {
//调用Service业务层
CustomerService service = new CustomerServiceImpl();
List<Customer> listCustomer = service.findAllCustomer();
//存入request作用域
ServletActionContext.getRequest().setAttribute("list", listCustomer);
//跳转页面
return "listCustomer";
}
}
3.4 Service业务层
public class CustomerServiceImpl implements CustomerService {
@Override
// 添加客户
public void saveCustomer(Customer customer) {
// 获取Session对象
Session session = HibernateUtils.getCurrentSession();
// 开启事务
Transaction transaction = session.beginTransaction();
try {
// 调用dao层
CustomerDAO dao = new CustomerDAOImpl();
dao.saveCustomer(customer);
} catch (Exception e) {
// 异常回滚,Hibernate默认异常回滚
// transaction.rollback();
e.printStackTrace();
} finally {
// 提交事务
transaction.commit();
}
}
@Override
//查看所有客户
public List<Customer> findAllCustomer() {
//获取与线程绑定的Session对象
Session session = HibernateUtils.getCurrentSession();
//开启事务
Transaction transaction = session.beginTransaction();
List<Customer> listCustomer = null;
try {
//调用dao层
CustomerDAO dao = new CustomerDAOImpl();
listCustomer = dao.findAllCustomer();
} catch (Exception e) {
transaction.rollback();
e.printStackTrace();
}finally {
//提交事务
transaction.commit();
}
return listCustomer;
}
}
3.5 dao持久层
public class CustomerDAOImpl implements CustomerDAO {
@Override
//添加客户
public void saveCustomer(Customer customer) {
//获取Session对象
Session session = HibernateUtils.getCurrentSession();
//保存对象到Session缓冲区,事务提交自动更新到数据库
session.save(customer);
}
@Override
//查询所有客户
public List<Customer> findAllCustomer() {
//获得Session
Session session = HibernateUtils.getCurrentSession();
return session.createCriteria(Customer.class).list();
}
}
网友评论