`
roruby
  • 浏览: 335204 次
  • 来自: ...
社区版块
存档分类
最新评论

Struts原理与实践(2)

阅读更多
下面,我们就从一个最简单的登录例子入手,以对Struts的主要部分有一些直观而清晰的认识。这个例子功能非常简单,假设有一个名为lhb的用户,其密码是awave,程序要完成的任务是,呈现一个登录界面给用户,如果用户输入的名称和密码都正确返回一个欢迎页面给用户,否则,就返回登录页面要求用户重新登录并显示相应的出错信息。这个例子在我们讲述Struts的基础部分时会反复用到。之所以选用这个简单的程序作为例子是因为不想让过于复杂的业务逻辑来冲淡我们的主题。

因为Struts是建立在MVC设计模式上的框架,你可以遵从标准的开发步骤来开发你的Struts Web应用程序,这些步骤大致可以描述如下:
1定义并生成所有代表应用程序的用户接口的Views,同时生成这些Views所用到的所有ActionForms并将它们添加到struts-config.xml文件中。
2在ApplicationResource.properties文件中添加必要的MessageResources项目
3生成应用程序的控制器。
4在struts-config.xml文件中定义Views与 Controller的关系。
5生成应用程序所需要的model组件
6编译、运行你的应用程序.

下面,我们就一步步按照上面所说的步骤来完成我们的应用程序:

第一步,我们的应用程序的Views部分包含两个.jsp页面:一个是登录页面logon.jsp,另一个是用户登录成功后的用户功能页main.jsp,暂时这个页面只是个简单的欢迎页面。

其中,logon.jsp的代码清单如下:

<ccid_nobr>
<ccid_code><%@ page contentType="text/html; charset=UTF-8" %><%@ taglib uri="/WEB-INF/struts-bean.tld" prefix="bean" %><%@ taglib uri="/WEB-INF/struts-html.tld" prefix="html" %><HTML><HEAD><TITLE><bean:message key="logon.jsp.title"/></TITLE><html:base/></HEAD><BODY><h3><bean:message key="logon.jsp.page.heading"/></h3><html:errors/><html:form action="/logonAction.do" focus="username"><TABLE border="0" width="100%"><TR><TH align="right"><bean:message key="logon.jsp.prompt.username"/></TH><TD align="left"><html:text property="username"/></TD></TR><TR><TH align="right"><bean:message key="logon.jsp.prompt.password"/></TH><TD align="left"><html:password property="password"/></TD></TR><TR><TD align="right">  <html:submit><bean:message key="logon.jsp.prompt.submit"/></html:submit></TD><TD align="left">  <html:reset><bean:message key="logon.jsp.prompt.reset"/></html:reset></TD></TR></TABLE></html:form></BODY></HTML></ccid_code>
</ccid_nobr>

main.jsp的代码清单如下:

<ccid_nobr>
<ccid_code><%@ page contentType="text/html; charset=UTF-8" %><%@ taglib uri="/WEB-INF/struts-bean.tld" prefix="bean" %><%@ taglib uri="/WEB-INF/struts-logic.tld" prefix="logic" %><HTML><HEAD><TITLE><bean:message key="main.jsp.title"/></TITLE><html:base/></HEAD><BODY><logic:present name="userInfoForm"><H3>  <bean:message key="main.jsp.welcome"/>   <bean:write name="userInfoForm" property="username"/>!</H3></logic:present></BODY></HTML></ccid_code>
</ccid_nobr>

首先,我们看一下logon.jsp文件,会发现它有这么两个鲜明的特点:一是文件头部有诸如:
<%@ taglib uri="/WEB-INF/struts-bean.tld" prefix="bean" %>
<%@ taglib uri="/WEB-INF/struts-html.tld" prefix="html" %>

这样的指令代码,他们的作用就是指示页面要用到struts的自定义标签,标签库uri是一个逻辑引用,标签库的描述符(tld)的位置在web.xml文件中给出,见上篇文章的配置部分。struts的标签库主要由四组标签组成,它们分别是:
  • bean标签,作用是在jsp中操纵bean
  • logic标签,作用是在jsp中进行流程控制
  • html标签,作用是显示表单等组件
  • template标签,作用是生成动态模板

    关于每类标签的具体作用及语法,因受篇幅限制,不在这里详细讨论,大家可参考struts手册之类的资料。只是心里要明白所谓标签其后面的东西就是一些类,这点与bean有些相似,它们在后端运行,生成标准的html标签返回给浏览器。

    要使用它们显然要把它们的标签库描述文件引入到我们的系统中,这是些以.tld为扩展名的文件,我们要把它们放在<catalina_home>/webapps/mystruts/WEB-INF/目录下。引入struts标签后原来普通的html标签如文本框的标签变成了这样的形式<!----><html:text property="username"></html:text>。

    Jsp文件的第二个特点,就是页面上根本没有直接写用于显示的文字如:username,password等东西,而是用<!----><bean:message key="logon.jsp.prompt.username"></bean:message>这种形式出现。这个特点为国际化编程打下了坚实的基础,关于国际化编程后面的文章还会专门讨论。

    这个简单的应用所用到的ActionForm为UserInfoForm,代码清单如下:

    <ccid_nobr>
    <ccid_code>package entity;import org.apache.struts.action.ActionForm;import org.apache.struts.action.ActionMapping;import javax.servlet.http.HttpServletRequest;public class UserInfoForm extends ActionForm{  private String username;  private String password;  public String getUsername() {    return (this.username);  }  public void setUsername(String username) {    this.username = username;  }  public String getPassword() {    return (this.password);  }  public void setPassword(String password) {    this.password = password;  }}</ccid_code>
    </ccid_nobr>

    在你的应用程序的WEB-INF目录下再建一个classes目录,在新建的这个classes目录下再建如下几个目录entity(用于存放ActionForm类)、action目录(用于存放Action类)、bussness目录(用于存放作为Model的业务对象类)。Classes目录下的子目录就是所谓的包,以后,还会根据需要增加相应的包。

    现在,将UserInfoForm.java保存到entity目录中。

    把如下代码添加到</catalina_home><catalina_home>/webapps/mystruts/WEB-INF/struts-config.xml文件中

    <ccid_nobr>
    <ccid_code><form-beans>    <form-bean name="userInfoForm" type="entity.UserInfoForm" />  </form-beans></ccid_code>
    </ccid_nobr>

    特别要提醒一下的是:关于ActionForm的大小写,一定要按照上面的写,以免造成不必要的麻烦。

    到此,我们完成了第一步工作。

    第二步,我们建一个名为ApplicationResource.properties的文件,并把它放在</catalina_home><catalina_home>/webapps/mystruts/WEB-INF/classes目录下。它在struts-config.xml的配置信息我们已在第一篇文章的末尾说了,就是:
    </catalina_home><message-resources parameter="ApplicationResources">

    目前我们在ApplicationResource.properties文件中加入的内容是:

    <ccid_nobr>
    <ccid_code>#Application Resource for the logon.jsplogon.jsp.title=The logon pagelogon.jsp.page.heading=Welcome World!logon.jsp.prompt.username=Username:logon.jsp.prompt.password=Password:logon.jsp.prompt.submit=Submitlogon.jsp.prompt.reset=Reset#Application Resource for the main.jspmain.jsp.title=The main pagemain.jsp.welcome=Welcome:</ccid_code>
    </ccid_nobr>

    到此,我们已完成了第二个步骤。

    第三步,我们开始生成和配置Controller组件。

    在前面我们已经提到,Struts应用程序的控制器由org.apache.struts.action.ActionServlet和org.apache.struts.action.Action类组成,其中,前者已由Struts准备好了,后者Struts只是为我们提供了个骨架,我们要做的是为实现应用程序的特定功能而扩展Action类,下面是实现我们登录程序的Action类的代码清单:

    <ccid_nobr>
    <ccid_code>package action;import java.io.IOException;import javax.servlet.ServletException;import javax.servlet.http.HttpServletRequest;import javax.servlet.http.HttpSession;import javax.servlet.http.HttpServletResponse;import org.apache.struts.action.Action;import org.apache.struts.action.ActionError;import org.apache.struts.action.ActionErrors;import org.apache.struts.action.ActionForm;import org.apache.struts.action.ActionForward;import org.apache.struts.action.ActionMapping;import org.apache.struts.action.ActionServlet;import bussness.UserInfoBo;import entity.UserInfoForm;public final class LogonAction extends Action {    public ActionForward execute(ActionMapping mapping,         ActionForm form,         HttpServletRequest request,         HttpServletResponse response)         throws IOException, ServletException {    UserInfoForm userInfoForm = (UserInfoForm) form;     	    //从web层获得用户名和口令    String username = userInfoForm.getUsername().trim();    String password = userInfoForm.getPassword().trim();    //声明错误集对象    ActionErrors errors = new ActionErrors();    //校验输入    if(username.equals("")){      ActionError error=new ActionError("error.missing.username");      errors.add(ActionErrors.GLOBAL_ERROR,error);    }    if(password.equals("")){      ActionError error=new ActionError("error.missing.password");      errors.add(ActionErrors.GLOBAL_ERROR,error);    }        //调用业务逻辑    if(errors.size()==0){      String validated = "";      try{        UserInfoBo userInfoBo=new UserInfoBo();        validated =userInfoBo.validatePwd(username,password);        if(validated.equals("match")){          //一切正常就保存用户信息并转向成功的页面	          HttpSession session = request.getSession();          session.setAttribute("userInfoForm", form);                	  return mapping.findForward("success");        }       }            catch(Throwable e){        //处理可能出现的错误        e.printStackTrace();        ActionError error=new ActionError(e.getMessage());        errors.add(ActionErrors.GLOBAL_ERROR,error);      }    }      //如出错就转向输入页面,并显示相应的错误信息    saveErrors(request, errors);        return new ActionForward(mapping.getInput());      } }</ccid_code>
    </ccid_nobr>

    这个action类中有两个错误消息键要加到ApplicationResource.properties文件中,清单如下:

    <ccid_nobr>
    <ccid_code>#Application Resource for the LogonAction.javaerror.missing.username=<li><font color="red">missing username</font></li>error.missing.password=<li><font color="red">missing password</font></li>></ccid_code>
    </ccid_nobr>

    第四步:在struts-config.xml文件中定义Views与 Controller的关系,也就是配置所谓的ActionMapping。它们在struts-config.xml中的位置是排在<form-beans>… </form-beans>标签后,我们的登录程序的配置清单如下:

    <ccid_nobr>
    <ccid_code><action-mappings>    <action input="/logon.jsp" name="userInfoForm" path="/logonAction" scope="session" 	type="action.LogonAction" validate="false">      <forward name="success" path="/main.jsp" />          </action>  </action-mappings></ccid_code>
    </ccid_nobr>

    第五步:生成应用程序所需要的model组件,该组件是完成应用程序业务逻辑的地方,现在我的登录程序的业务逻辑很简单,就是判断用户是不是lhb并且其口令是不是awave如果是就返回一个表示匹配的字符串"match",否则,就抛出出错信息。其代码清单如下:

    <ccid_nobr>
    <ccid_code>package bussness;import entity.UserInfoForm;public class UserInfoBo {  public UserInfoBo(){      }  	  public String validatePwd(String username,String password){    	    String validateResult="";            if(username.equals("lhb")&&password.equals("awave")){      validateResult="match";    }    else{            throw new RuntimeException("error.noMatch");    }    	        return validateResult;         }}</ccid_code>
    </ccid_nobr>

    将其放在bussness包中。

    我们同样要将其表示错误信息的键值设置在ApplicationResource.properties文件中,清单如下:

    <ccid_nobr>
    <ccid_code>#Application Resource for the UserInfoBo.javaerror.noMatch=<li><font color="red">no matched user</font></li></ccid_code>
    </ccid_nobr>

    到此为止,我们已经完成了这个简单登录程序的所有组件。下面就可以享受我们的劳动成果了。

    第六步、编译运行应用程序。

    常规的做法是用Ant来装配和部署Struts应用程序,如果按这个套路,这篇文章就会显得十分冗长乏味,同时也没有太大的必要,因为,用一个IDE一般可以很方便地生成一个应用。因此,我们采用简便的方法,直接编译我们的.java文件。不过这里要注意一点的是:实践证明,要使得编译过程不出错,还必须将struts.jar文件放一份拷贝到</message-resources><catalina_home>/common/lib目录中,并在环境变量中设置CLASSPATH 其值是</catalina_home><catalina_home>/common/lib/struts.jar;配置好后就可以分别编译entity、bussness及action目录下的.java文件了。编译完成后:打开</catalina_home><catalina_home>/conf目录下的server.xml文件,在前加上如下语句为我们的应用程序建一个虚拟目录:

    <ccid_nobr>
    <ccid_code><Context path="/mystruts" docBase="mystruts" debug="0"                 reloadable="true">                 		</Context></ccid_code>
    </ccid_nobr>

    启动,tomcat。在浏览器中输入:http://localhost:8080/mystruts/logon.jsp
    如果前面的步骤没有纰漏的话,一个如图所示的登录画面就会出现在你的眼前。



    如果,不输入任何内容直接点击Submit按钮,就会返回到logon.jsp并显示missing username和missing password错误信息;如果输入其他内容,则会返回no matched user的错误;如果输入的用户名是lhb且口令是awave则会显示表示登录成功的欢迎页面。

    上面虽然是一个功能很简单的应用程序,但麻雀虽小,五脏俱全,基本涉及到了struts的主要组成部分。下面我们就来分析一下程序的特点和基本的工作原理。

    首先,我们在浏览器中输入.jsp文件时,后台将struts的自定义标签"翻译"成普通的html标签返回给浏览器,而一些提示信息如作为输入框label的username、password还有按钮上提示信息还有错误信息等都来自MessageResources即ApplicationResource.properties文件中对应的键值。当我们点击Submit按钮时,从web.xml的配置可以看出,请求将被ActionServlet截获。它通过表单中提供的action参数在struts-config.xml文件中查找对应的</catalina_home><action-mappings>项目,如果有对应的ActionForm,它就用表单中数据填充ActionForm的对应属性,本例中的ActionForm为userInfoForm,相应的属性是username和password,这就是所谓的实例化ActionForm。然后,将控制交给对应的Action,本例中是LogonAction,它做的主要工作是对ActionForm中取出的username和password做了一下校验,这里只是简单检验它们是否为空(这些简单的格式化方面的校验应该放在客户端进行,而且struts也为我们提供了一个很好的模式,后面如果有可能会详细介绍)。如果不为空则调用判断用户及口令是否正确的业务逻辑模块UserInfoBo,同时,它会捕获可能出现的错误,然后根据业务逻辑返回的结果将程序导向不同的页面,本例中如果业务逻辑返回的结果是"match"则依据</action-mappings><action-mappings>中的</action-mappings><forward name="success" path="/main.jsp">返回main.jsp页面给浏览器同时在session对象中保存了用户的登录信息;否则,返回输入页面并显示相应的出错信息,完成了上篇文章所说的它的四个主要职责。

    大家一定注意到了,在本例的业务逻辑模块UserInfoBo中,将用户与密码是写死在程序中的,在一个真实的应用程序中是不会这样做的,那些需要永久保存的信息如,username及口令等都会保存在数据库文件之类的永久介质中,下一篇文章我们将介绍在struts中如何访问数据库。
    </forward>
  • 分享到:
    评论

    相关推荐

      Struts原理与实践.mht

      Struts原理与实践(1) - Java - New - JavaEye论坛.mht

      Struts原理与实践

      ### Struts原理与实践 #### 一、Struts框架概览 **Struts**框架,作为Java Web开发领域内的一款成熟且广泛应用的框架,自问世以来便受到开发者们的青睐。Struts框架的核心设计理念在于实现MVC(Model-View-...

      Struts原理与实践(罗会波)

      罗会波的《Struts原理与实践》这本书深入浅出地解析了Struts的核心概念和技术,帮助开发者全面理解和掌握这一框架。 1. **MVC设计模式**:Struts将Web应用的业务逻辑、数据模型和用户界面分离,使得开发者可以独立...

      Struts原理与实践(五).rar

      在本资料"Struts原理与实践(五)"中,我们将深入探讨Struts的核心概念、工作流程以及实际应用中的关键点。 首先,Struts框架的基础是MVC模式。Model代表业务逻辑,View负责显示,Controller则协调这两者。在Struts...

      Struts原理与实践(一) .rar

      Struts是Java Web开发中的一个开源框架,由Apache软件基金会维护。它主要基于Model-View-Controller(MVC)设计模式,旨在简化企业...通过阅读《Struts原理与实践(一)》PDF文档,可以更深入地了解和掌握Struts框架。

      struts原理与实践(三)

      本文主要讨论Struts中JDBC的工作原理以及在实践中的基本配置。 一、JDBC工作原理 JDBC是Java平台提供的一个标准API,它允许Java应用程序与各种类型的数据库进行通信。JDBC的核心包括两个包:java.sql和javax.sql。...

      初探Struts原理与实践.doc

      6. ActionServlet与RequestDispatcher:Struts的ActionServlet接收请求后,通过RequestDispatcher将请求转发给相应的Action,Action执行完毕后,再通过Dispatcher返回响应到合适的视图。 通过Struts,开发者可以...

      struts原理与实践+指导JAVA学习阶段需研究的开源项目

      提供的文档可能涵盖了这些主题,从"struts原理与实践(1).doc"到"struts原理与实践(7).doc"逐步深入,"Java学习阶段需研究的开源项目.doc"则可能介绍了一些相关的Java学习资源。阅读这些文档将有助于全面理解和掌握...

      Struts原理与实践(二).rar

      在"Struts原理与实践(二)"这个主题中,我们将深入探讨Struts框架的核心概念、工作原理以及实际应用。 **1. Struts框架的核心组件** - **ActionServlet**: Struts框架的核心控制器,负责接收HTTP请求,解析请求...

      struts原理与实践二)

      在本文中,我们将深入理解Struts的基本原理,并通过一个简单的登录示例来演示其工作流程。 首先,我们需要了解MVC模式。在MVC架构中,Model负责处理数据和业务逻辑,View负责展示用户界面,而Controller则作为两者...

      struts原理与实践(一)

      Struts 是一个开源的Java Web应用程序框架,专为构建企业级Web应用而设计。它遵循Model-View-Controller (MVC)设计模式,旨在...通过学习和实践Struts,开发者可以更好地理解和掌握Web应用的架构设计,提升自身技能。

      Struts原理与实践(三).rar

      Struts 2继续发展,提供了与现代开发工具和实践的集成,如RESTful API支持、AJAX集成等。 通过深入理解Struts的工作原理,开发者可以更好地利用其特性,提高开发效率,同时也能为将来学习其他MVC框架打下坚实的基础...

      struts原理与实践(七)

      Struts 是一个基于MVC(Model-View-Controller)设计模式的Java Web应用程序框架,它主要负责处理用户请求,管理业务逻辑,以及与视图层的交互。在本篇文章中,我们将深入探讨如何利用Struts 实现一个文章发布系统,...

      struts2 原理与实践

      在本文中,我们将深入探讨Struts2的原理和实践,以一个简单的登录示例来阐述其关键组件和工作流程。 首先,我们来看一下开发Struts2应用的基本步骤: 1. **定义视图(Views)**:视图通常由JSP页面组成,负责展示...

      struts原理与实践(六)

      2. **.xml配置文件**: 主要有两个XML文件,`validator-rules.xml`和`validation.xml`。前者定义了校验规则,后者则指定需要校验的表单(forms)及其组件。 3. **资源绑定**: 提供本地化的标签和错误消息。这些消息...

      struts原理与实践(四)

      Struts 是一个流行的Java Web开发框架,主要用于...在实践中,开发者需要关注字符集的转换,确保在客户端和服务器之间传输数据时不会丢失或混淆信息。同时,合理地组织和管理资源文件,可以使代码更整洁,更容易维护。

      struts原理与实践(五)

      Struts 是一个经典的Java Web开发框架,主要用于构建MVC(模型-视图-控制器)架构的应用程序。在国际化(i18n)编程方面,Struts 提供了强大的支持,使得应用能够根据用户所在地区和语言环境显示相应的内容。本文将...

      Struts2 工作原理 Struts2框架 有图

      其中,ActionContextCleanUp过滤器是可选的,但它在Struts2与其他框架(如SiteMeshPlugin)的集成中扮演了重要角色,确保了环境的干净与隔离,防止不同请求之间的数据污染。 #### 3. FilterDispatcher调用 接下来...

    Global site tag (gtag.js) - Google Analytics