struts2-类型转换
2013-05-16 19:13
267 查看
概述
从一个 HTML 表单到一个 Action 对象, 类型转换是从字符串到非字符串.
•HTTP 没有 “类型” 的概念. 每一项表单输入只可能是一个字符串或一个字符串数组. 在服务器端, 必须把 String 转换为特定的数据类型
在 struts2 中, 把请求参数映射到 action 属性的工作由 Parameters 拦截器负责, 它是默认的 defaultStack 拦截器中的一员. Parameters 拦截器可以自动完成字符串和基本数据类型之间转换.
接收请求参数
a) 利用之前学过的知识,接收请求参数
b) 采用基本类型接收请求参数
在Action类中定义与请求参数同名的属性,struts2便能通过反射技术自动接收请求参数并赋予给同名属性。
c) java.util.Date类型的属性可以接收格式为2009-07-20的请求参数值。但如果我们需要接收格式为20091221的请求参数,我们必须定义类型转换器,否则struts2无法自动完成类型转换。
转化失败时,应该转向错误页面
转向错误页面,应该在struts配置文件中,增加如下代码:
定制类型转换器说明
自定义类型转化器必须实现 TypeConverter 接口或对这个接口的某种具体实现做扩展
定制类型转换器说明—底层代码:
定制类型转换器
* context:
* value:要转换的值,是一个数组,因为struts2底层接
收值都用request.getParameterValues("createTime")--String[]
* toType:要转换的数据类型
配置自定义的类型转换器
在应用程序里使用一个自定义的类型转换器之前, 必须先对它进行配置.
这种配置既可以基于字段, 也可以基于类
a) 基于字段配置(局部): 可以为某个动作的各个属性分别制定一个自定义的转换器.
1.创建一个属性文件: ActionClassName-conversion.properties, 该文件需和相对应的动作类(Action)放在同一个目录下,ActionClassName是Action的类名,
后面的-conversion.properties是固定写法.在properties文件中的内容为:
属性名称=类型转换器的全类名
对于本例而言,文件的名称应为UserAction- conversion.properties
2. 编辑属性文件:
createTime=cn.itcast.converter.DateConverter
为什么这样配置自定义的类型转换器
DateConverter.java
b) 基于类配置(全局):
在 WEB-INF/classes/ 目录下创建 xwork-conversion.properties 文件."
在properties文件中的内容为:
待转换的类型=类型转换器的全类名
对于本例而言, xwork-conversion.properties文件中的内容为:java.util.Date= cn.itcast.converter.DateConverter
该拦截器负责对错误信息进行拦截器<interceptor name="conversionError "class="org.apache.struts2.interceptor.StrutsConversionErrorInterceptor"/>
定制类型转换器—抛出异常
如果输入一个错误的格式,应该转向错误页面。但实际上为什么还是转向成功页面?
如果转换器中出现异常,该异常必须抛出,不能捕获
* 只有抛出了异常,struts2拦截器收到异常,才认为转换器出现了异常,才能转到<result name="input">所指向的页面
* struts2拦截器没有收到异常,struts2拦截器认为转换成功
定制类型转换器—处理异常1
•在error.jsp页面中引入
在error.jsp页面中使用<s:fielderror fieldName=“ ”/>打印所有转化的异常错误信息
•name:指定Action属性的名称
• 打印某个属性转化的异常错误信息
定制类型转换器—处理异常2
为什么显示出的错误信息是英文的呢?
在xwork-core-2.3.3.jar包下com\opensymphony\xwork2的xwork-conversion.properties
代码:xwork.default.invalid.fieldvalue=Invalid field value for field "{0}".
如何修改可以让显示出的错误信息是中文的呢?
定制类型转换器—处理异常3
修改让显示出的错误信息是中文!
•在与当前Action同级目录中,新建converter.properties(文件名称自定义)资源文件,在该文件中增加如下内容
xwork.default.invalid.fieldvalue=无效的字段值 "{0}".
•在struts.xml文件加载该资源文件
加载国际化资源文件,如果有多个文件,用","隔开,资源文件的后缀名不用写,加载cn.itcast.converter包下的converter.properties
这个配置是针对所有字段给出提示。
定制类型转换器—处理异常4
针对每个字段给出提示信息!-针对每个字段的提示信息要覆盖针对所有字段的提示信息。
在converter.properties资源文件中增加如下内容
•格式:invalid.fieldvalue.xx=提示信息
•内容:invalid.fieldvalue.createTime=出生时间转化异常
类型转换与复杂对象配合使用
很多时候, 需要把表单字段映射到多个对象的不同属性上form 标签可以被映射到一个属性的属性.
类型转换与Collection配合使用
[b] [/b]Struts 还允许填充 Collection 里的对象, 这常见于需要快速录入批量数据的场合
样例代码:
1、jsp
userform.jsp
success.jsp
error.jsp
2、java
UserAction.java
DateConverter.java
Employee.java
Edu.java
3、xml
struts_converter.xml
struts.xml
4、properties
UserAction-conversion.properties
converter.properties
xwork-conversion.properties
从一个 HTML 表单到一个 Action 对象, 类型转换是从字符串到非字符串.
•HTTP 没有 “类型” 的概念. 每一项表单输入只可能是一个字符串或一个字符串数组. 在服务器端, 必须把 String 转换为特定的数据类型
在 struts2 中, 把请求参数映射到 action 属性的工作由 Parameters 拦截器负责, 它是默认的 defaultStack 拦截器中的一员. Parameters 拦截器可以自动完成字符串和基本数据类型之间转换.
接收请求参数
a) 利用之前学过的知识,接收请求参数
1 HttpServletRequest req = ServletActionContext.getRequest(); String userName = req.getParameter("userName");
b) 采用基本类型接收请求参数
在Action类中定义与请求参数同名的属性,struts2便能通过反射技术自动接收请求参数并赋予给同名属性。
public class UserAction extends ActionSupport { private Integer id; private String userName //struts2通过反射技术调用与请求参数同名的属性的setter方法来获取请求参数值 public void setId(Integer id) { this.id = id; } public Integer getId() {return id;} }
c) java.util.Date类型的属性可以接收格式为2009-07-20的请求参数值。但如果我们需要接收格式为20091221的请求参数,我们必须定义类型转换器,否则struts2无法自动完成类型转换。
public class UserAction extends ActionSupport { private Integer id; private String userName; private java.util.Date createTime; public java.util.Date getCreateTime() { return createTime; } 9 public void setCreateTime(java.util.Date createTime) { this.createTime = createTime; } 12 public String save(){ System.out.println("id "+id); System.out.println("userName "+userName); System.out.println("createTime "+createTime); return "save"; } }
转化失败时,应该转向错误页面
转向错误页面,应该在struts配置文件中,增加如下代码:
<action name="userAction_*" class="cn.itcast.converter.UserAction" method="(1)"> <result name="success">/converter/success.jsp</result> <!-- input:当类型转化失败时,要转到input所指向的页面 --> <result name="input">/converter/error.jsp</result> </action>
定制类型转换器说明
自定义类型转化器必须实现 TypeConverter 接口或对这个接口的某种具体实现做扩展
定制类型转换器说明—底层代码:
定制类型转换器
public class DateConverter extends DefaultTypeConverter { public Object convertValue(Map<String, Object> context, Object value, Class toType) { System.out.println("value = "+value); System.out.println("toType = "+toType); return new Date(); } }
* context:
* value:要转换的值,是一个数组,因为struts2底层接
收值都用request.getParameterValues("createTime")--String[]
* toType:要转换的数据类型
配置自定义的类型转换器
在应用程序里使用一个自定义的类型转换器之前, 必须先对它进行配置.
这种配置既可以基于字段, 也可以基于类
a) 基于字段配置(局部): 可以为某个动作的各个属性分别制定一个自定义的转换器.
1.创建一个属性文件: ActionClassName-conversion.properties, 该文件需和相对应的动作类(Action)放在同一个目录下,ActionClassName是Action的类名,
后面的-conversion.properties是固定写法.在properties文件中的内容为:
属性名称=类型转换器的全类名
对于本例而言,文件的名称应为UserAction- conversion.properties
2. 编辑属性文件:
createTime=cn.itcast.converter.DateConverter
为什么这样配置自定义的类型转换器
DateConverter.java
import java.text.ParseException; import java.text.SimpleDateFormat; import java.util.Date; import sun.misc.JavaAWTAccess; import com.opensymphony.xwork2.conversion.impl.DefaultTypeConverter; /* * 自定义转换器: * * 作用:就是把页面中createTime元素的字符串内容转换成java.util.Date */ public class DateConverter extends DefaultTypeConverter { @Override public Object convertValue(Object value, Class toType) { //要转换的值:[Ljava.lang.String;@3da850 System.out.println("value = "+value); //要转换的类型:class java.util.Date System.out.println("toType = "+toType); if(value==null){ return false; } if(toType==null){ return false; } if(toType!=java.util.Date.class){ return false; } if(value instanceof java.lang.String[]){ String [] str = (String[])value; if(str[0]!=null&&str[0].length()>0){ try { SimpleDateFormat sdf = new SimpleDateFormat("yyyy/MM/dd"); return sdf.parse(str[0]); } catch (ParseException e) { /* * 在struts2框架里,自定义的类型转换器, * 如果我们不手动抛出异常,struts2框架只捕获异常,但是并不抛出。 * 所以框架就会认为类型转换器转换成功,转向成功页面。 */ throw new RuntimeException(e); } } } return new Date(); } }
b) 基于类配置(全局):
在 WEB-INF/classes/ 目录下创建 xwork-conversion.properties 文件."
在properties文件中的内容为:
待转换的类型=类型转换器的全类名
对于本例而言, xwork-conversion.properties文件中的内容为:java.util.Date= cn.itcast.converter.DateConverter
该拦截器负责对错误信息进行拦截器<interceptor name="conversionError "class="org.apache.struts2.interceptor.StrutsConversionErrorInterceptor"/>
定制类型转换器—抛出异常
如果输入一个错误的格式,应该转向错误页面。但实际上为什么还是转向成功页面?
try { … … } catch (ParseException e) { e.printStackTrace();... throw new RuntimeException(e); }
如果转换器中出现异常,该异常必须抛出,不能捕获
* 只有抛出了异常,struts2拦截器收到异常,才认为转换器出现了异常,才能转到<result name="input">所指向的页面
* struts2拦截器没有收到异常,struts2拦截器认为转换成功
定制类型转换器—处理异常1
•在error.jsp页面中引入
<%@ taglib uri="/struts-tags" prefix="s"%>
在error.jsp页面中使用<s:fielderror fieldName=“ ”/>打印所有转化的异常错误信息
•name:指定Action属性的名称
• 打印某个属性转化的异常错误信息
定制类型转换器—处理异常2
为什么显示出的错误信息是英文的呢?
在xwork-core-2.3.3.jar包下com\opensymphony\xwork2的xwork-conversion.properties
代码:xwork.default.invalid.fieldvalue=Invalid field value for field "{0}".
如何修改可以让显示出的错误信息是中文的呢?
定制类型转换器—处理异常3
修改让显示出的错误信息是中文!
•在与当前Action同级目录中,新建converter.properties(文件名称自定义)资源文件,在该文件中增加如下内容
xwork.default.invalid.fieldvalue=无效的字段值 "{0}".
•在struts.xml文件加载该资源文件
加载国际化资源文件,如果有多个文件,用","隔开,资源文件的后缀名不用写,加载cn.itcast.converter包下的converter.properties
<constant name="struts.custom.i18n.resources" value="cn.itcast.converter.converter"></constant>
这个配置是针对所有字段给出提示。
定制类型转换器—处理异常4
针对每个字段给出提示信息!-针对每个字段的提示信息要覆盖针对所有字段的提示信息。
在converter.properties资源文件中增加如下内容
•格式:invalid.fieldvalue.xx=提示信息
•内容:invalid.fieldvalue.createTime=出生时间转化异常
类型转换与复杂对象配合使用
很多时候, 需要把表单字段映射到多个对象的不同属性上form 标签可以被映射到一个属性的属性.
类型转换与Collection配合使用
[b] [/b]Struts 还允许填充 Collection 里的对象, 这常见于需要快速录入批量数据的场合
样例代码:
1、jsp
userform.jsp
<%@ page language="java" pageEncoding="utf-8" contentType="text/html; charset=utf-8"%> <%@ taglib uri="/struts-tags" prefix="s"%> <html> <head> <title>My JSP 'index.jsp' starting page</title> </head> <body> <form action="${pageContext.request.contextPath}/converter/userAction_save.action" name="form1" method="post"> 编号:<input type="text" name="id"><br> 姓名:<input type="text" name="userName"><br> 出生日期:<input type="text" name="createTime"><br> 学历编号:<input type="text" name="edu.eduid"><br> 学历名称:<input type="text" name="edu.eduname"><br> 员工姓名:<input type="text" name="emps[0].name"><br> 员工薪水:<input type="text" name="emps[0].salary"><br> 员工姓名:<input type="text" name="emps[1].name"><br> 员工薪水:<input type="text" name="emps[1].salary"><br> <input type="submit" value="提交"><br> </form> </body> </html>
success.jsp
<%@ page language="java" pageEncoding="utf-8" contentType="text/html; charset=utf-8"%> <%@ taglib uri="/struts-tags" prefix="s"%> <html> <head> <title>My JSP 'index.jsp' starting page</title> </head> <body> 成功!!!!<br> </body> </html>
error.jsp
<%@ page language="java" pageEncoding="utf-8" contentType="text/html; charset=utf-8"%> <%@ taglib uri="/struts-tags" prefix="s"%> <html> <head> <title>My JSP 'index.jsp' starting page</title> </head> <body> 失败!!!! <br> <s:fielderror fieldName="createTime"/> </body> </html>
2、java
UserAction.java
import java.util.Collection; import java.util.Date; import javax.servlet.http.HttpServletRequest; import org.apache.struts2.ServletActionContext; import com.opensymphony.xwork2.ActionSupport; @SuppressWarnings("serial") public class UserAction extends ActionSupport { /* * 在struts2框架中,在对应动作类action中, * 声明与页面中表单元素同名的属性,给出对应的set和get方法。 * struts2框架就会根据反射机制,获取页面中表单元素的值 */ //编号:<input type="text" name="id"><br> private Integer id; //姓名:<input type="text" name="userName"><br> private String userName; //出生日期:<input type="text" name="createTime"><br> private Date createTime; /* * 学历编号:<input type="text" name="edu.eduid"><br> 学历名称:<input type="text" name="edu.eduname"><br> */ private Edu edu; /* * 员工姓名:<input type="text" name="name"><br> 员工薪水:<input type="text" name="salary"><br> */ Collection<Employee> emps; public Collection<Employee> getEmps() { return emps; } public void setEmps(Collection<Employee> emps) { this.emps = emps; } public Edu getEdu() { return edu; } public void setEdu(Edu edu) { this.edu = edu; } public Date getCreateTime() { return createTime; } public void setCreateTime(Date createTime) { this.createTime = createTime; } public Integer getId() { return id; } public void setId(Integer id) { this.id = id; } public String getUserName() { return userName; } public void setUserName(String userName) { this.userName = userName; } @Override public String execute() throws Exception { System.out.println("UserAction ************ execute()"); return "success"; } public String save(){ System.out.println("UserAction ************ save()"); /*HttpServletRequest request = ServletActionContext.getRequest(); String username = request.getParameter("userName"); System.out.println("username = "+username);*/ System.out.println("id = "+id); System.out.println("username = "+userName); System.out.println("createTime = "+createTime); System.out.println(edu.getEduid()+" "+edu.getEduname()); return "success"; } }
DateConverter.java
import java.text.ParseException; import java.text.SimpleDateFormat; import java.util.Date; import sun.misc.JavaAWTAccess; import com.opensymphony.xwork2.conversion.impl.DefaultTypeConverter; /* * 自定义转换器: * * 作用:就是把页面中createTime元素的字符串内容转换成java.util.Date */ public class DateConverter extends DefaultTypeConverter { @Override public Object convertValue(Object value, Class toType) { //要转换的值:[Ljava.lang.String;@3da850 System.out.println("value = "+value); //要转换的类型:class java.util.Date System.out.println("toType = "+toType); if(value==null){ return false; } if(toType==null){ return false; } if(toType!=java.util.Date.class){ return false; } if(value instanceof java.lang.String[]){ String [] str = (String[])value; if(str[0]!=null&&str[0].length()>0){ try { SimpleDateFormat sdf = new SimpleDateFormat("yyyy/MM/dd"); return sdf.parse(str[0]); } catch (ParseException e) { /* * 在struts2框架里,自定义的类型转换器, * 如果我们不手动抛出异常,struts2框架只捕获异常,但是并不抛出。 * 所以框架就会认为类型转换器转换成功,转向成功页面。 */ throw new RuntimeException(e); } } } return new Date(); } }
Employee.java
public class Employee { /* * 员工姓名:<input type="text" name="name"><br> 员工薪水:<input type="text" name="salary"><br> */ private String name; private Double salary; public String getName() { return name; } public void setName(String name) { this.name = name; } public Double getSalary() { return salary; } public void setSalary(Double salary) { this.salary = salary; } }
Edu.java
public class Edu { //学历编号:<input type="text" name="eduid"><br> private Integer eduid; //学历名称:<input type="text" name="eduname"><br> private String eduname; public Integer getEduid() { return eduid; } public void setEduid(Integer eduid) { this.eduid = eduid; } public String getEduname() { return eduname; } public void setEduname(String eduname) { this.eduname = eduname; } }
3、xml
struts_converter.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> <package name="converter" namespace="/converter" extends="struts-default"> <action name="userAction_save" class="cn.itcast.converter.UserAction" method="save"> <result name="success">/converter/success.jsp</result> <!-- * 错误提示:No result defined for action cn.itcast.converter.UserAction and result input * 配置如果出错的时候,自动转向到错误页面 --> <result name="input">/converter/error.jsp</result> </action> </package> </struts>
struts.xml
<constant name="struts.custom.i18n.resources" value="cn.zengfansheng.struts.i18n.resources"></constant> <include file="cn/zengfansheng/struts/converter/struts_converter.xml"></include>
4、properties
UserAction-conversion.properties
createTime=cn.zengfansheng.struts.converter.DateConverter
converter.properties
xwork.default.invalid.fieldvalue=\u7C7B\u578B\u8F6C\u6362\u5931\u8D25 "{0}". invalid.fieldvalue.createTime=\u51FA\u751F\u65E5\u671F\u8F6C\u6362\u5931\u8D25
xwork-conversion.properties
java.util.Date=cn.zengfansheng.struts.converter.DateConverter
相关文章推荐
- Struts2类型转换
- struts2教程(4)--类型转换
- Struts2的类型转换
- struts2中的类型转换,从web页面传来的离散的值在后台封装成一个user对象
- struts2学习(二)--转换器StrutsTypeConverter和全局类型转换
- struts2自定义类型转换(2)基于StrutsTypeConverter
- 2、struts2类型转换
- 关于Struts2的类型转换详解
- Struts2类型转换的作用
- Struts2的类型转换器
- 浪曦_Struts2应用开发系列_第2讲.Struts2的类型转换-学习笔记
- struts2日期类型转换
- 4.1.6: Struts2的类型转换---基于Struts2的自定义类型转换器
- Struts2数据类型转换(页面数据库数据类型转换)
- 【Java EE 学习 35 上】【strus2】【类型转换器】【struts2和Servlet API解耦】【国际化问题】【资源文件乱码问题已经解决】
- Struts2类型转换
- struts2-OGNL和类型转换(structs 自动数据表单获取)
- Struts2总结---数据类型转换详解 (4)
- Struts2自定义类型转换器分为局部类型转换器和全局类型转换器
- Struts2的类型转换--内建转换器