天天看点

day28_struts2(全天)のPPT学习——05 Action接受请求参数.pptday28_struts2(全天)のPPT学习——05 Action接受请求参数.ppt

day28_struts2(全天)のPPT学习——05 Action接受请求参数.ppt

Action接受请求参数

Struts2 Action接受请求参数

作为MVC框架,必须要负责解析HTTP请求参数,并将其封装到Model对象中

Struts2提供了非常强大的类型转换机制用于请求数据 到 model对象的封装

Struts2 提供三种数据封装的方式

  • Action 本身作为model对象,通过成员setter封装
    例子Action类成员变量setter接收参数

    jsp页面关键代码(name的值要与Action中的变量的值一一对应)

    用户名

    密码

    Action类中的关键代码(只创建setter方法即可(属性修改器))

    public class Form1Action{

    private String username;

    private String password;

    public void setUsername(String usernmae){
        this.username = username;
    }
    public void setPassword(String password){
        this.password = password;
    }
               
    }
  • 创建独立model对象,页面通过ognl表达式封装

例子:创建单独model对象,页面OGNL

1.实体类:User.java

public class User{
    private String username;
    private String password;

    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
    }
}

2.Action类:Form2Action.java

public class Form2Action{
    private User user;

    public void setUser(User user){
        this.user = user;
    }
    public User getUser(){
        return this.user;
    }
}

3.jsp页面关键代码

用户名<input type="text" name="user.username"/><br/>
密码<input type="password" name="user.password"/><br/>
           
  • 使用ModelDriven接口,对请求数据进行封装

    例子:使用ModelDriven接口封装数据

    1.实体类:User.java
        public class User{
        private String username;
        private String password;
    
        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
        }
    }
    
    2.Action类:Form3Action.java
    
    public class Form3Action implements ModeDriven<User>{
        private User user = new User();//这里必须实例化
    
        @Override
        public User getModel(){
            return this.user;
        }
    }
    
    3.jsp页面关键代码
    
    用户名<input type="text" name="username"/><br/>
    密码<input type="password" name="password"/><br/>
               

类型转换与Collection配合使用

Struts2 还允许填充 Collection 里的对象, 这常见于需要快速录入批量数据的场合

(例如上传多个文件,多个图片等)

例子实例

1.实体类:Employee.java

public class Employee{
    private String name;
    private Double salary;

    //setter,getter方法
}

2.Action处理类:UserAction.java

public class UserAction extends ActionSupport{
    private Collection<Employee> emps;

    private Integer id;
    private String userName;
    private java.util.Date createTime;
    private Edu edu;

    //setter,getter方法
}

3.jsp页面关键代码

员工姓名:<input type="text" name="emps[0].name" value=""><br>
薪水:<input type="text" name="emps[0].salary" value=""><br>


员工姓名:<input type="text" name="emps[1].name" value=""><br>
薪水:<input type="text" name="emps[1].salary" value=""><br>
           

类型转换与Map配合使用

Struts2 允许填充Map集合中的对象
1.实体类:User.java

public class User{
    private String username;
    private String password;

    //setter,getter方法
}

2.Action处理类:Form2Action.java

public class Fom2Action{
    private Map<String,User> users;

    public Map<String,User> getUsers(){
        return users;
    }

    public void setUsers(Map<String,User> users){
        this.users = users;
    }
}

3.jsp页面的关键代码

<form method="post" action="${pageContext.request.contextPath}/form2.action">
    第一个用户名<input type="text" name="users['one'].username"/><br>
    第一个密码<input type="password" name="users['one'].password"/><br>

    第二个用户名<input type="text" name="users['two'].username"/><br>
    第二个密码<input type="password" name="users['two'].password"/><br>

    <input type="submit" value="提交"/>
</form>
           

Struts2内建类型转换器

对于大部分常用类型,开发者根本无需创建自己的转换器,Struts2内置了常见数据类型多种转换器
boolean 和 Boolean
char和 Character
int 和 Integer
long 和 Long
float 和 Float
double 和 Double
Date 可以接收 yyyy-MM-dd格式字符串
数组  可以将多个同名参数,转换到数组中
集合  支持将数据保存到 List 或者 Map 集合
           

定制类型转换器

  • Struts2提供常规类型转换器,可以常用数据类型的转换,但如果目标类型是一个特殊类型,则需要自定义转换器
  • Struts2 类型转换器实际上都是基于OGNL实现的,在OGNL项目中,有一个TypeConverter接口
  • 自定义类型转换器必须实现ongl.TypeConverter
    <<interface>>ognl.TypeConverter
            ^
            |
    ognl.DefaultTypeConverter
            ^
            |
    org.apache.struts2.util.StrutsTypeConverter
               

定制类型转换器(Struts2代码)

1. struts2中定义的接口:TypeConverter.java

public interface TypeConverter{
    public Object convertValue(Map context,Object target,Member memeber,String propertyName,Object value,Class toType);
}

2. DefaultTypeConvert.java实现TypeConverter.java

public class DefaultTypeConverter implements TypeConverter{
    public Object convertValue(Map context,Object value, Class toType){//value:原始String[]参数数组,toType:要转换的类型
        return OgnlOps.convertValue(value,toType);
    }

    public Object convertValue(Map context,Object target,Member member,String propertyName,Object value,Class toType){
        return convertValue(context,value,toType);
    }
}

3.StrutsTypeConverter 继承 DefaultTypeConverter

public abstract class StrutsTypeConverter extends DefaultTypeConverter{
    public Object converterValue(Map context,Object o,Class toClass){
        return convertToString(context,0);//将convertValue方法分为convertFromString和convertToString两个方法
    }else if(0 instanceof String[]){
        return convertFromString(context,(String[]) 0,toClass);
    }else if(o instance of String){
        return convertFromString(context,new String[]{(String) 0},toClass);
    }else{
        return performFallbackConversion(context,0,toClass);
    }
}

public abstract Object convertFromString(Map context,String[] values,Class toClass);//转换String类型参数,到Action属性参数类型

public abstract String convertToString(Map context,Objecto);//转换复杂对象到String类型
           

自定义类型转换器

java.util.Date类型的属性可以接收格式为2009-07-20的请求参数值。但如果我们需要接收格式为20091221的请求参数,我们必须定义类型转换器,否则struts2无法自动完成类型转换。
1.自定义的Action类

import java.util.Date;
public class HelloWorldAction {
    private Date createtime;

    public Date getCreatetime() {
        return createtime;
    }

    public void setCreatetime(Date createtime) {
        this.createtime = createtime;
    }
}

2.定义日期类型转换器

public class DateConverter extends DefaultTypeConverter{
    @Override
    public Object convertValue(Map context,Object value,Class toType){
        SimpleDateFormat dateFormat = new SimpleDateFormat(yyyyMMdd");
        try{
            if(toType == Date.class){//当字符串向Date类型转换时
                String[] params = (String[])value;//Request.getParameterValues()
                return dateFormat.parse(params[0]);
            }else if(toType == String.class){//当Date转换成字符串时
                Date date = (Date)value;
                return dateFormat.format(date);
            }
        }catch(ParseException e){
            throw new RuntimeException(e);
        }
        return null;
    }
}

将上面的类型转换器注册为局部类型转换器:
在Action类所在的包下放置ActionClassName-conversion.properties文件,ActionClassName是Action的类名,后面的-conversion.properties是固定写法,对于本例而言,文件的名称应为HelloWorldAction-conversion.properties 。在properties文件中的内容为:
属性名称=类型转换器的全类名
对于本例而言, HelloWorldAction-conversion.properties文件中的内容为:
createtime= cn.itcast.conversion.DateConverter
           

自定义全局类型转换器

将上面的类型转换器注册为全局类型转换器:
  • 在src下放置xwork-conversion.properties文件 。在properties文件中的内容为:

    待转换的类型=类型转换器的全类名

  • 对于本例而言, xwork-conversion.properties文件中的内容为:

    java.util.Date= cn.itcast.conversion.DateConverter

类型转换中的错误处理

  • Struts2提供了一个名为conversionError的拦截器,查看struts-default.xml
    ss="org.apache.struts2.interceptor.StrutsConversionErrorInterceptor"/>
               
  • 如果Struts2的类型转换器执行类型转换时出现错误,该拦截器将负责将对应错误封装成表单域错误(FieldError),并将这些错误信息放入ActionContext中
  • 使用类型转换中的错误处理用户定义Action必须继承ActionSupport
  • 在自定义类型转换器中,异常必须抛出不能捕获,conversionError会处理该异常,然后转入名为input的逻辑视图
  • 在Action所在包中,创建 ActionName.properties,在局部资源文件中配置提示信息 : invalid.fieldvalue.属性名= 错误信息
  • 在input逻辑视图所对应jsp页面中,通过 输出类型转换信息

继续阅读