结果跳转方式

转发

<!--  转发 --> 
        <action name="Demo1Action" class="cn.itheima.a_result.Demo1Action" method="execute" > 
            <result name="success" type="dispatcher" >/hello.jsp</result> 
        </action>

重定向

<!-- 重定向 --> 
        <action name="Demo2Action" class="cn.itheima.a_result.Demo2Action" method="execute" > 
            <result name="success" type="redirect" >/hello.jsp</result> 
        </action>

转发到Action

<!-- 转发到Action --> 
        <action name="Demo3Action" class="cn.itheima.a_result.Demo3Action" method="execute" > 
             <result name="success" type="chain"> 
                     <!-- action的名字 --> 
                 <param name="actionName">Demo1Action</param> 
                     <!-- action所在的命名空间 --> 
                 <param name="namespace">/</param> 
             </result> 
        </action>

重定向到Action

<!-- 重定向到Action --> 
        <action name="Demo4Action" class="cn.itheima.a_result.Demo4Action" method="execute" > 
            <result  name="success"  type="redirectAction"> 
                 <!-- action的名字 --> 
                 <param name="actionName">Demo1Action</param> 
                 <!-- action所在的命名空间 --> 
                 <param name="namespace">/</param> 
            </result> 
        </action>

Struts2访问servlet的API

在Struts2中,Action并没有直接和Servlet API进行耦合,即在Struts2的Action中不能直接访问Servlet API。这是Struts2中Action的重要改良之一,方便Action进行单元测试。

在Struts2中,访问Servlet API有3中方法,具体如下:

通过ActionContext类访问

ActionContext是Action执行的上下文对象,保存了Action执行所需要的所有对象,包括parameters,request,Session,application等。下面列举ActionContext类访问Servlet API的几个常用方法,具体如表所示。

//如何在action中获得原生ServletAPI 
public class Demo5Action extends ActionSupport { 
 
    public String execute() throws Exception { 
        //request域=> map (struts2并不推荐使用原生request域) 
        //不推荐 
        Map<String, Object> requestScope = (Map<String, Object>) ActionContext.getContext().get("request"); 
        //推荐 
        ActionContext.getContext().put("name", "requestTom"); 
        //session域 => map 
        Map<String, Object> sessionScope = ActionContext.getContext().getSession(); 
        sessionScope.put("name", "sessionTom"); 
        //application域=>map 
        Map<String, Object> applicationScope = ActionContext.getContext().getApplication(); 
        applicationScope.put("name", "applicationTom"); 
         
        return SUCCESS; 
    } 
}

Struts2中,每次提交请求都是不同的线程,每个线程都会绑定一个新的action实例。所以和request的生命周期相同。

通过ServletActionContext访问

 为了直接访问Servlet API,Struts2框架还提供了ServletActionContext类,该类包含了几个常用的静态方法,具体如下:

//如何在action中获得原生ServletAPI 
public class Demo6Action extends ActionSupport { 
    //并不推荐 
    public String execute() throws Exception { 
        //原生request 
        HttpServletRequest request = ServletActionContext.getRequest(); 
        //原生session 
        HttpSession session = request.getSession(); 
        //原生response 
        HttpServletResponse response = ServletActionContext.getResponse(); 
        //原生servletContext 
        ServletContext servletContext = ServletActionContext.getServletContext(); 
        return SUCCESS; 
    } 
}

通过实现接口方式访问

 上面的两种方式都无法直接获得Servlet API实例,为了在Action中直接访问Servlet API,Struts2还提供了一系列接口,具体如下:

//如何在action中获得原生ServletAPI 
public class Demo7Action extends ActionSupport implements ServletRequestAware { 
     
     
    private HttpServletRequest request; 
 
    public String execute() throws Exception {  
         
        System.out.println("原生request:"+request); 
        return SUCCESS; 
    } 
 
    @Override 
    public void setServletRequest(HttpServletRequest request) { 
        this.request = request; 
    } 
}

获取参数

以前的Servlet开发中,获取界面传递的参数,然后封装到javabean中,然后将javabean传递到业务层。需要两步操作。在Struts2中,自动将参数进行了封装。Struts2将数据的封装分成两大类,一类被称为是属性驱动,一类被称为是模型驱动。

每次请求到来时,都会创建一个新的Action实例。Action是线程安全的,可以使用成员变量接收参数。

属性驱动可以细分成两种:

  1. 只需要提供属性的set方法即可
  2. 通过表达式方式直接封装到对象中。

属性驱动

提供属性set方法的方式

package cn.itheima.c_param; 
 
import java.util.Date; 
 
import com.opensymphony.xwork2.ActionSupport; 
 
//struts2如何获得参数 
//每次请求Action时都会创建新的Action实例对象 
public class Demo8Action extends ActionSupport  { 
     
    public Demo8Action() { 
        super(); 
        System.out.println("demo8Action被创建了!"); 
    } 
 
 
    //准备与参数键名称相同的属性 
    private String name; 
    //自动类型转换 只能转换8大基本数据类型以及对应包装类 
    private Integer age; 
    //支持特定类型字符串转换为Date ,例如 yyyy-MM-dd 
    private Date   birthday; 
     
 
    public String execute() throws Exception {  
         
        System.out.println("name参数值:"+name+",age参数值:"+age+",生日:"+birthday); 
         
        return SUCCESS; 
    } 
 
 
    public String getName() { 
        return name; 
    } 
 
 
    public void setName(String name) { 
        this.name = name; 
    } 
 
 
    public Integer getAge() { 
        return age; 
    } 
 
 
    public void setAge(Integer age) { 
        this.age = age; 
    } 
 
 
    public Date getBirthday() { 
        return birthday; 
    } 
 
 
    public void setBirthday(Date birthday) { 
        this.birthday = birthday; 
    } 
 
 
     
}
<form action="${pageContext.request.contextPath}/Demo8Action"> 
        用户名:<input type="text" name="name" /><br> 
        年龄:<input type="text" name="age" /><br> 
        生日:<input type="text" name="birthday" /><br> 
        <input type="submit" value="提交" /> 
    </form>

以上方式不够优雅,在类中存在大段的set/get方法,不利于代码维护。

把属性和相应的getter/setter方法从action中提取出来,单独作为一个值对象,一般以javaBean来实现,所封装的属性和表单的属性一一对应,JavaBean将称为数据传递的载体。

页面提供表达式方式

package cn.itheima.c_param; 
 
import com.opensymphony.xwork2.ActionSupport; 
 
import cn.itheima.domain.User; 
 
//struts2如何获得参数-方式2 
public class Demo9Action extends ActionSupport  { 
    //准备user对象 
    private User user; 
 
    public String execute() throws Exception {  
         
        System.out.println(user); 
         
        return SUCCESS; 
    } 
 
    public User getUser() { 
        return user; 
    } 
 
    public void setUser(User user) { 
        this.user = user; 
    } 
 
     
}
    <form action="${pageContext.request.contextPath}/Demo9Action"> 
        用户名:<input type="text" name="user.name" /><br> 
        年龄:<input type="text" name="user.age" /><br> 
        生日:<input type="text" name="user.birthday" /><br> 
        <input type="submit" value="提交" /> 
    </form>

以上实现方式需要在表单里以user.name的方式,看起来怪怪的。

模型驱动

 通过实现ModelDriven接口来接收请求参数,Action类必须实现ModelDriven接口,并且要重写getModel()方法,这个方法返回的就是Action所使用的数据模型对象。

模型驱动方式通过JavaBean模型进行数据传递。只要是普通的JavaBean,就可以充当模型部分。采用这种方式,JavaBean所封装的属性与表单的属性一一对应,JavaBean将成为数据传递的载体。

大部分我们会优先使用该方式。因为Struts2内部有很多结果围绕模型驱动设计的。但如果页面向多个对象中封装,那么就需要使用属性驱动的方式二了。

//struts2如何获得参数-方式2 
public class Demo10Action extends ActionSupport implements ModelDriven<User> { 
    //准备user 成员变量 
    private User user =new User(); 
 
    public String execute() throws Exception {  
         
        System.out.println(user); 
         
        return SUCCESS; 
    } 
 
    @Override 
    public User getModel() { 
        return user; 
    } 
}
    <form action="${pageContext.request.contextPath}/Demo10Action"> 
        用户名:<input type="text" name="name" /><br> 
        年龄:<input type="text" name="age" /><br> 
        生日:<input type="text" name="birthday" /><br> 
        <input type="submit" value="提交" /> 
    </form>

集合类型的参数封装

在实际开发中,有些时候我们需要批量插入用户或者批量插入其他的对象,在Action中需要接受到这多个Action中封装的对象,然后传递给业务层。这时候就需要将表单中的数据封装到集合中。

package cn.itheima.c_param; 
 
import java.util.List; 
import java.util.Map; 
 
import com.opensymphony.xwork2.ActionSupport; 
 
//struts2 封装集合类型参数 
public class Demo11Action extends ActionSupport  { 
    //list 
    private List<String> list; 
    //Map 
    private Map<String,String> map; 
     
     
    public String execute() throws Exception {  
         
        System.out.println("list:"+list); 
        System.out.println("map:"+map); 
         
        return SUCCESS; 
    } 
 
    public List<String> getList() { 
        return list; 
    } 
 
    public void setList(List<String> list) { 
        this.list = list; 
    } 
 
    public Map<String, String> getMap() { 
        return map; 
    } 
 
    public void setMap(Map<String, String> map) { 
        this.map = map; 
    } 
 
}
<form action="${pageContext.request.contextPath}/Demo11Action" method="post" > 
        list:<input type="text" name="list" /><br> 
        list:<input type="text" name="list[3]" /><br> 
        map:<input type="text" name="map['haha']" /><br> 
        <input type="submit" value="提交" /> 
    </form>

 

发布评论

分享到:

IT虾米网

微信公众号号:IT虾米 (左侧二维码扫一扫)欢迎添加!

Struts2学习笔记四 OGNL详解
你是第一个吃螃蟹的人
发表评论

◎欢迎参与讨论,请在这里发表您的看法、交流您的观点。