通过前面几篇博客,不知道大家有没有发现这个问题,虽然现在可以灵活控制跳转了,但是Action的数量还是比较多,如何既能保证跳转灵活,还能减少Action的数量?这就是我们这篇博客所说的DispatchAction,如其名,可以理解为“分发式Action”,使用它可以避免为每个Action创建一个类。

我们先来看一下实例。

UserAction

DispatchAction继承的是Action,它的特点就是把以前的多个Action合并为一个,当多个Action关联较大时,可以像这样放在一起,减少Action类的同时,也降低了维护的难度。

package com.tgb.drp.web.actions;

import java.util.Date;
import java.util.List; import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse; import org.apache.commons.beanutils.BeanUtils;
import org.apache.struts.action.ActionForm;
import org.apache.struts.action.ActionForward;
import org.apache.struts.action.ActionMapping;
import org.apache.struts.actions.DispatchAction; import com.tgb.drp.manager.UserManager;
import com.tgb.drp.model.User;
import com.tgb.drp.web.forms.UserActionForm; public class UserAction extends DispatchAction { @Override
protected ActionForward unspecified(ActionMapping mapping, ActionForm form,
HttpServletRequest request, HttpServletResponse response)
throws Exception {
//调用业务逻辑操作
List userList = UserManager.getInstance().findAllUserList();
request.setAttribute("userlist", userList); return mapping.findForward("list_success");
} /**
* 用户删除
* @param mapping
* @param form
* @param request
* @param response
* @return
* @throws Exception
*/
public ActionForward del(ActionMapping mapping, ActionForm form,
HttpServletRequest request, HttpServletResponse response)
throws Exception {
//获取从页面表单中提交过来的值
UserActionForm uaf = (UserActionForm)form; //取得需要删除的userId的集合
String[] userIdList = uaf.getSelectFlag(); //调用业务逻辑操作
UserManager.getInstance().deleteUsers(userIdList);
return mapping.findForward("del_success");
} /**
* 用户添加
* @param mapping
* @param form
* @param request
* @param response
* @return
* @throws Exception
*/
public ActionForward add(ActionMapping mapping, ActionForm form,
HttpServletRequest request, HttpServletResponse response)
throws Exception { //获取从页面表单中提交过来的值
UserActionForm uaf = (UserActionForm)form;
User user = new User();
BeanUtils.copyProperties(user, uaf);
user.setCreateDate(new Date()); //调用业务逻辑操作
UserManager.getInstance().addUser(user);
return mapping.findForward("add_success"); } /**
* 修改用户
* @param mapping
* @param form
* @param request
* @param response
* @return
* @throws Exception
*/
public ActionForward modify(ActionMapping mapping, ActionForm form,
HttpServletRequest request, HttpServletResponse response)
throws Exception {
//获取从页面表单中提交过来的值
UserActionForm uaf = (UserActionForm)form;
User user = new User();
BeanUtils.copyProperties(user, uaf); //调用业务逻辑操作
UserManager.getInstance().modifyUser(user);
return mapping.findForward("modify_success");
} /**
* 根据ID查询用户
*
* @param mapping
* @param form
* @param request
* @param response
* @return
* @throws Exception
*/
public ActionForward find(ActionMapping mapping, ActionForm form,
HttpServletRequest request, HttpServletResponse response)
throws Exception {
//获取从页面表单中提交过来的值
UserActionForm uaf = (UserActionForm)form; String userId = uaf.getUserId(); //调用业务逻辑操作
User user = UserManager.getInstance().findUserById(userId); //将user对象从Action传递到JSP页面
request.setAttribute("user", user); return mapping.findForward("find_success");
} }

UserActionForm

封装表单中的数据,需要注意的是,不用为每个表单 建立一个ActionForm,多个表单可以使用一个进行封装。

package com.tgb.drp.web.forms;

import java.util.Date;

import org.apache.struts.action.ActionForm;

/**
* 用户管理ActionForm
*
*/
public class UserActionForm extends ActionForm { //用户代码
private String userId; //用户名称
private String userName; //密码
private String password; //联系电话
private String contactTel; //email
private String email; //创建日期
private Date createDate; //接收界面中的选中标记的集合
private String[] selectFlag; public String getContactTel() {
return contactTel;
} public void setContactTel(String contactTel) {
this.contactTel = contactTel;
} public Date getCreateDate() {
return createDate;
} public void setCreateDate(Date createDate) {
this.createDate = createDate;
} public String getEmail() {
return email;
} public void setEmail(String email) {
this.email = email;
} public String getPassword() {
return password;
} public void setPassword(String password) {
this.password = password;
} public String getUserId() {
return userId;
} public void setUserId(String userId) {
this.userId = userId;
} public String getUserName() {
return userName;
} public void setUserName(String userName) {
this.userName = userName;
} public String[] getSelectFlag() {
return selectFlag;
} public void setSelectFlag(String[] selectFlag) {
this.selectFlag = selectFlag;
}
}

struts-config

配置Action和ActionForm,区别于以前的是需要添加parameter属性。

    <form-beans>
<form-bean name="userForm" type="com.tgb.drp.web.forms.UserActionForm"/>
</form-beans> <action-mappings>
<action path="/user/user_maint"
type="com.tgb.drp.web.actions.UserAction"
name="userForm"
scope="request"
parameter="command"
>
<forward name="list_success" path="/user/user_list.jsp"/>
<forward name="del_success" path="/user/user_maint.do" redirect="true"/>
<forward name="add_success" path="/user/user_maint.do" redirect="true"/>
<forward name="modify_success" path="/user/user_maint.do" redirect="true"/>
<forward name="find_success" path="/user/user_modify.jsp"/> </action>
<action path="/user/show_add"
forward="/user/user_input.jsp"
></action> </action-mappings>

访问接口

<body>
<a href="user/user_maint.do" title="请点击访问用户管理系统">用户管理系统</a>
</body>

如上所示,它是根据command属性的值确定的。

执行流程

把断点主要设置在DispatchAction中,可以看到,执行流程如下:

代码分析

在DispatchAction的execute函数中,有如下代码:

	// Prevent recursive calls
if ("execute".equals(name) || "perform".equals(name)){
String message =
messages.getMessage("dispatch.recursive", mapping.getPath()); log.error(message);
throw new ServletException(message);
}

所以在给parameter设置值时,不能为execute或perform。

在DispatchAction的dispatchMethod中,有如下代码:

        if (name == null) {
return this.unspecified(mapping, form, request, response);
}

即如果parameter值为空,则执行unspecified函数,可以在子类中实现这个函数,作为无参数值的跳转。

总结

总而言之,DispatchAction的出现减少了Action的数量,将多个Action融合到一起,虽然有显而易见的好处,但是同样会有问题,这样的耦合性的提高,必然伴随着扩展性的降低,所以用还是不用,还要根据具体情况而定。

更多相关博客,请至《层层递进Struts1(八)之总结》

层层递进Struts1(七)详解DispatchAction的更多相关文章

  1. 层层递进Struts1(八)之总结

    先来看一下Struts1学习总结的思维导图,画的主要是Struts1中的重点和博客分布,如下所示: 系列博客的侧重点是: Struts1是什么? 为什么要使用它? 如何使用Struts1? Strut ...

  2. 层层递进Struts1(三)之Struts组成

    这篇博客我们来说一下Struts的主要组成我们,通过前几篇博客,我们知道这个框架最重要的几个步骤:获取路径.封装表单.获取转向列表.转向逻辑处理.转向,与此对应的是:ActionServlet.Act ...

  3. 层层递进Struts1(六)自定义转换器

    Struts提供的类型转换有限,如果我们强行使用没有的类型转换,则会出现错误,以Date类型为例: org.apache.catalina.core.StandardWrapperValve invo ...

  4. 层层递进Struts1(五)之处理流程

    这篇博客我们深入Struts框架执行部分源码,从ActionServlet的process函数开始,看一下其内在的执行过程. 流程图 以下流程图展示的是ActionServlet和RequestPro ...

  5. J2EE学习篇之--Struts1详解

    今天来看一下Struts1的相关知识,其实Struts现在是出名的,每个Web开发者都会知道的,也是现在比较流行的框架,下面就来看一下我们为什么要用Struts框架呢? 摘要 1.建立在mvc这种好的 ...

  6. 七牛云存储Python SDK使用教程 - 上传策略详解

    文 七牛云存储Python SDK使用教程 - 上传策略详解 七牛云存储 python-sdk 七牛云存储教程 jemygraw 2015年01月04日发布 推荐 1 推荐 收藏 2 收藏,2.7k  ...

  7. Iptables详解七层过滤

    <Iptables详解七层过滤> 一.防火墙简介 防火墙其实就是一个加固主机或网络安全的一个设备或者软件而已,通过防火墙可以隔离风险区域与安全区域的连接,同时不会妨碍风险区域的访问.当然需 ...

  8. .Net使用Redis详解之ServiceStack.Redis(七) 转载https://www.cnblogs.com/knowledgesea/p/5032101.html

    .Net使用Redis详解之ServiceStack.Redis(七)   序言 本篇从.Net如何接入Reis开始,直至.Net对Redis的各种操作,为了方便学习与做为文档的查看,我做一遍注释展现 ...

  9. git命令详解( 七 )

    此为git命令详解的第七篇 这章我们可以来逐渐揭开 git push.fetch 和 pull 的神秘面纱了.我们会逐个介绍这几个命令,它们在理念上是非常相似的.   git push的参数 git ...

随机推荐

  1. Java stackoverflow error

    本文想记录一下尝试产生stackoverflow的程序 1 -Xss=1k, 设置stack大小1024个字节,产生515个long,想把stack撑爆. 2 嵌套调用 3 创建大量线程 1 -Xss ...

  2. 2、Python djang 框架下的word Excel TXT Image 等文件的下载

    2.python实现文件下载 (1)方法一.直接用a标签的href+数据库中文件地址,即可下载.缺点:word excel是直接弹框下载,对于image txt 等文件的下载方式是直接在新页面打开. ...

  3. Linux平台上搭建apache+tomcat负载均衡集群

    传统的Java Web项目是通过tomcat来运行和发布的.但在实际的企业应用环境中,采用单一的tomcat来维持项目的运行是不现实的.tomcat 处理能力低,效率低,承受并发小(1000左右).当 ...

  4. ThinkPHP HTML标签代码和UBB互相转换

    1.UBB 转为 HTML TP的扩展里面自带一个ubb方法,用这个方法就能把用户输入的ubb格式代码转换为HTML标签的代码.这里用到的基本知识就是正则表达式啦,今天先不讲正则表达式. 来看一下TP ...

  5. apache 网址重定向

    参考了以下网站,终于基本搞定b2c网站伪静态.剩下的就是体力活了. 回家后整理下. http://yp.oss.org.cn/software/show_resource.php?resource_i ...

  6. Makefile的简单例子

    1.生成test可执行文件,源文件有prog.c prog.h cord.h test:prog.o code.o gcc -o test prog.o code.o prog.o:prog.c pr ...

  7. spm使用之六安装别人写好的spm文档主题模板

    上回说到有个nico-one的文档主题模板, https://github.com/lepture/nico-one 把他可以下载了, 放到 C:\Documents and Settings\Adm ...

  8. websocket nodejs实例

    http://blog.sina.com.cn/s/blog_49cc837a0101aljs.html http://blog.sina.com.cn/s/blog_49cc837a0101a2q3 ...

  9. 重载VerifyRenderingInServerForm

    重载VerifyRenderingInServerForm 今天在做一个AjaxPro的应用时,VerifyRenderingInServerForm给我带来了麻烦,在网上找了找,发现大多数人的解决方 ...

  10. MEMS Gyroscope Technology

    InvenSense®Technology Overview Our technology is comprised of five coreelements: our patented Nasiri ...