struts2学习笔记(一)

来源:互联网 发布:mac合盖屏幕亮 编辑:程序博客网 时间:2024/06/12 23:10

 struts2学习笔记

1.用户登录案例

1.      新建web项目

2.      2.导入struts2的jar包

3.      配置web.xml配置struts2的核心过滤器

  <filter>

  <filter-name>struts2</filter-name>

   <filter-class>org.apache.struts2.dispatcher.ng.filter.StrutsPrepareAndExecuteFilter</filter-class>

  </filter>

  <filter-mapping>

  <filter-name>struts2</filter-name>

  <url-pattern>*.action</url-pattern>

  </filter-mapping>

 

4.      在src编写struts.xml

Jar包struts2-core-2.3.4.jar中Struts-default.xml复制前段即可

5.      编辑login.jsp

  <formaction="login.action"method="post">

  用户名:<inputtype="text"name="username"/><br>

  密  码:<inputtype="password"name="password"/><br>

   <inputtype="submit"value="登录"/>

  </form>

   注:action的提交地址.action是扩展名,默认为.action;action的扩展名和web.xml中配置的struts2的核心过滤器匹配;也就是如果表单中提交的地址以.aciton结尾,那么在配置filter的url-pattern时一定是:

6.      编写loginAction类

package com.struts2Test.pj;

 

public class loginAction {

 

    public Stringusername;

    public Stringpassword;

   

    public String execute(){

       if("lipeng".equals(username)||"123".equals(password)){

           return"success";

       }else{

           return"failed";

       }

    }

    public String getUsername() {

       returnusername;

    }

    public void setUsername(String username) {

       this.username = username;

    }

    public String getPassword() {

       returnpassword;

    }

    public void setPassword(String password) {

       this.password = password;

    }     

}

 

 

 

注:action表单中的属性名要和action中的一致(username/password  jsp和action中要一致)

Struts2中会自动将表单中提交的数据设置到loginAction的对应属性上,并且可在jsp中直接获取,不用手动像request设置。

 

 

7.      在Struts.xml中配置loginAction

      <actionname="login"class="com.struts2Test.pj.loginAction">

          <resultname="success">/success.jsp</result>

          <resultname="failed">/login.jsp</result>

      </action>

 

8.      访问测试:

 

 

 

  执行流程

 

 

 

 

 

 

2.线程安全

 

1.      线程安全:在一个进程中有多个线程并发执行,每个线程执行过程中变量值是相同的,执行结果也是相同的。

2.      Struts线程安全吗?(线程安全好吗?好,并发的时候不会出问题,就是效率低)

每次请求都会重新创建新的Action对象,所以线程安全

由于action对象是struts2 反射生成的,所以要求action类要有一个公共的无参数的构造方法。

 

 

3.Struts.xml配置详解

 

常量配置方式一:

1.      解决乱码

<constant name="struts.i18n.encoding" value="UTF-8"/>

   注:和constant和package同级别

2.      自定义扩展名

      <!--extends必须写,直接或者间接继承struts-default name自定义 -->

      <!-- 一个pagckage下面可有多个action -->

<packagename="login"namespace="/"extends="struts-default">

  注:namespace可为空,加上之后访问时候需带上namespace属性值(namespace/action)

3.      友好的提示信息

<constantname="struts.devMode"value="true"></constant><!--友好的提示信息 -->

 

 

常量配置方式二:在src下添加struts.properties,在里面设置值

 

 

4 .团队协作配置

<!-- 团队协作配置 -->

   <includefile="config/struts2Test/strutsxml/login.xml"></include>

 

 

5.struts.xml 的加载顺序

struts-default.xml  ——struts-plugin.xml  ——  struts.xml

 

6.Package的配置

 

 

7.Action的配置

      <!--

        nameaction请求不需要加.action

        class 处理action请求对应的java类,class要求包名+类名,并且该类是有公共的无参构造方法的。

        method:配置处理请求的方法,默认为execute;方法要满足公共的,返回值类型是String无参

        action中的methodaction中的name无关

       -->

8.Result的配置

             result指结果集;

             name:请求的处理方法的返回值,默认是success

<result name="success">/success.jsp</result>

             type:结果的处理类型(请求,转发);默认是dispather转发

<result name="success" type="dispather">/success.jsp</result>

                  chain:action链,链接下一个action

<result name="success" type="chain">logout</result>

                  dispather:转发,如果有数据需要带到前台渲染只能用转发

                  redirect:重定向,也可以重定向一个action;

                                     如果是重定向到jsp页面可以直接重定向;

                                     如果是重定向到另一个action,需注意是否配置了action的后缀名,如果有要求有后缀名那么重定向的action一定要加上后缀名称

                  redirectAction:重定向到另一个action,不用加action的后缀名

 

 

 

 

                                                                                                                                           

9.   全局配置

      <!-- 配置全局结果集 -->

      <global-results>

         <resultname="failed">/login.jsp</result>

      </global-results>

在action的配置中,如果不去配置class属性,将会由默认的action来执行,默认的action是ActionSupport类

 

 

10.Action的实现方式

1.定义一个pojo类:好处自定义一个普通的java类,不具有侵入型

 

public class HelloAction {

    public String execute(){

       System.out.println("hello struts2");

       return"success";

    }

}

2.      实现一个Action接口,使得编写的代码更加规范

public class interfaceAction implements Action{

    @Override

    public String execute()throws Exception {

        System.out.println("implements Action ...");

//     return "success";

        return Action.SUCCESS;

    }

}

 

3.      继承 ActionSupport类

    好处:可以集成一些ActionSupport实现功能,如:验证;官方推荐使用

public class extendAction extends ActionSupport{

    @Override

    public String execute()throws Exception {

        System.out.println("extends ActionSupport...");

        return super.execute();

    }

}

 

11.以对象的方式处理数据(属性驱动)

Jsp

  <formaction="register.action"method="post">

  用户名:<inputtype="text"name="user.username"/><br>

  密  码:<inputtype="password"name="user.password"/><br>

  age:<inputtype="text"name="user.age"/><br>

  email:<inputtype="text"name="user.email"/><br>

   <inputtype="submit"value="提交"/>

  </form>

 

Xml

 <actionname="register"class="com.struts2Test.pj.registerAction">

            <resultname="success">/show.jsp</result>

  </action>

 

Action

 

public class registerAction extends ActionSupport{

    public Useruser;

    public User getUser() {

       returnuser;

    }

    public void setUser(User user) {

       this.user = user;

    }

 

    @Override

    public String execute()throws Exception {

       System.out.println("registerAction...");

       System.out.println(user);

       return Action.SUCCESS;

    }

}

注:前端可直接获取对象 ${user} 跟对象名称一致即可

 

 

 

 

12.模型驱动(ModelDriver)

建议在实体属性比较多时,采用模型驱动

Jsp

  <formaction="regmodel.action"method="post">

  用户名:<inputtype="text"name="username"/><br>

  密  码:<inputtype="password"name="password"/><br>

  age:  <inputtype="text"name="age"/><br>

  email:<inputtype="text"name="email"/><br>

   <inputtype="submit"value="提交"/>

  </form>

 

Struts.xml

<actionname="regmodel"class="com.struts2Test.pj.modelDriverAction"method="register"><!—注意这里指定了方法-->

         <resultname="success">/show.jsp</result>

</action>

 

modelDeiverAction

 

public class modelDriverAction implements ModelDriven<User>{

    private Useruser = new User();//这里必须要new一个对象

   

    /**这里必须get set对象才可在前端拿到值**/

    public User getUser() {                           

       returnuser;

    }      

    public void setUser(User user) {

       this.user = user;

    }

 

    public String register(){

       System.out.println(user);

       return Action.SUCCESS;

    }

   

    @Override

    public User getModel() {

       // TODO Auto-generated method stub

       returnuser;

    }

}

 

 

 

 

 

 

 

 

 

 

 

13.获取serletAPI

1.struts2有2种方式获取servletAPI:一种是解耦,一种是耦合;解耦使得struts2来进行测试的时候不需要启动服务器。在一定程序上是提高了开发效率

2.使用解耦的方式来获取servletAPI通过ActionContext对象获取。

ActionContext.getContext().getSession().put("User",username);

 

3.通过ActionContext对象直接获取ServletHttpRequest

 

14.ActionContext

 

Struts1的Action必须依赖于web容器,他的execute方法自动获得HttpServletRequest、HttpServletResponse对象,从而可以跟web容器进行交互

Struts2的Action不用依赖于web容器,本身就是一个普通的java类而已。但是,在web开发中我们往往需要获得request、session、application等对象。这个时候可以通过ActionContext来处理。

 ActionContext正如其名,是Action执行的上下文,他内部有个map属性,存放了Action执行时需要用到的对象。

 在每次执行Action之前都会创建新的ActionContext对象,所以ActionContext是线程安全的。新New的ActionContext是保存在一个ThreadLocal变量中,即采用ThreadLocal模式。ThreadLocal变量为每个线程提供独立的变量值的副本,是每个线程都可以采用独立的使用自己的副本,而不会和其他线程发生冲突。

 通过ActionContext获取到Session、request、application并不是真正的HttpServletRequest、

HttpServletResponse、ServletContext对象,而是将这三个对象里面的值重新包装成了map对象。这样的封装,我们及获取了我们需要的值,同时避免了跟web容器直接打交道,实现了完全的解耦。

 

1.What is ActionContext?

  ActionContext是map结构的容器。ActionContext是Action的上下文,存放Action执行过程中数据信息。ActionContext存放Action的数据,ActionInvocation.request的数据,session的数据,application的数据,local的数据等。每次请求时会为当前线程创建一个新的ActionContext。而ActionContext采用了ThreadLocal的方式来存放ActionContext所以ActionContext是线程安全的。

 

2..获取ActionContext

 ActionContext.getContext()获取。由于ActionContext是线程安全的,并且是通过静态方法获取的,所以在本线程中的非Action类中,也可以直接访问。

   注意点:ActionContext是基于请求创建的,所以在非请求的线程中是不能使用ActionContext对象的。如:filter的init()方法。

 

4.      ActionContext的简图

 

15.OGNL

 

1.使用ognl

        Map<String, Object> map = new HashMap<String ,Object>();

       map.put("name", "李四");

       map.put("age", "22");

       student stu = new student();

       stu.setName("li");

       Object obj = Ognl.getValue("#name",map, stu);

       System.out.println(obj);

Struts2中使用ognl表达式是通过struts2的标签来取值的,

在jsp中导入struts2标签库                                             

    <%@ taglib prefix="s"uri="/struts-tags"%>

 

注意:要使用struts2的标签,那么要通过struts2过滤器来启用,如果过滤器的配置为*.action结尾时,不能直接访问jsp页面的,需要通过action跳转。如果过滤器配置为*时,可以直接访问jsp页面。

 Struts2推荐不直接访问jsp页面,推荐使用action来控制

 

 

16.类型转换

1.在servlet中,如果表单提交非字符串的时候,需要进行类型转换:如,年龄…

String strAge = req.getParameter(“age”);

Int age = 0;

If(strAge!=null){

      Age = Integer.parseInt(strAge);

}

 

2.在struts2中,常见的数据类型struts2已经自动的进行了类型转换。无需手动转换。

 

3.在某些情况下,有自定义的类型时,struts2不能完成类型转换,那么需要手动转换,如果该自定义类型使用的频率较高时,手动转换重复代码将会增多——使用struts2提供的类型转换器来进行类型转换。

 

4.      案例:比如坐标点

 

5.      使用类型转换步骤:

 

a)      编写类型转换器——继承strutsTypeConverter类

b)      编写xwork-conversion.propertites的配置文件,放于src下;内容为要转换的类型=类型转换器

6.       

 

17. validate()服务端验证

 

 

1.  <action name="register" class="com.struts2Test.pj.registerAction">  

2.    <result name="success">/show.jsp</result>  

3.     <result name="input">/register.jsp</result>  

4.    <!-- INPUTAction的执行,需要从前端界面获取参数,INPUT就是代表这个参数输入的界面,一般在应用中,会对这些参数进行验证,如果验证没有通过,将自动返回到该视图。 -->  

5.  </action>  

 

 

1.  package com.struts2Test.pj;  

2.   

3.  import com.opensymphony.xwork2.Action;  

4. import com.opensymphony.xwork2.ActionSupport;  

5.  import com.struts2Test.beans.User;  

6.   

7.  public class registerAction extends ActionSupport{  

8.   

9.      public User user;  

10.      

11.     public User getUser() {  

12.        return user;  

13.     }  

14.  

15.     public void setUser(User user) {  

16.        this.user = user;  

17.     }  

18.  

19.     @Override  

20.    public String execute() throws Exception {  

21.         System.out.println("registerAction...");  

22.        System.out.println(user);  

23.         return Action.SUCCESS;  

24.    }  

25.       

26.    /** 

27.      * 服务端验证,如果action类继承了ActionSupport类, 

28.     * 那么该action类将会继承ActionSupport的相关功能: 

29.      * 如,验证功能 

30.     * 执行流程是validate——>execute 

31.      */  

32.    @Override  

33.     public void validate() {  

34.        //retuslt  

35.         if(user.age>100||user.age<1){  

36.            this.addActionError("年龄不合法");  

37.         }  

38.        super.validate();  

39.     }        

40.}  

 

 

 

 

<%@ page language="java"contentType="text/html; charset=UTF-8"

    pageEncoding="UTF-8"%>

<%@ taglib prefix="s"uri="/struts-tags"%>

<!DOCTYPEhtml PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">

<html>

<head>

<metahttp-equiv="Content-Type"content="text/html; charset=UTF-8">

<title>注册</title>

</head>

<body>

 <s:actionerrorcssErrorStyle="errorMessage"/><!--此标签用于显示错误信息 -->

  <formaction="register.action"method="post">

  用户名:<inputtype="text"name="user.username"/><br>

  密  码:<inputtype="password"name="user.password"/><br>

  年 龄:<inputtype="text"name="user.age"/><br>

  邮 箱:<inputtype="text"name="user.email"/><br>

   <inputtype="submit"value="提交"/>

  </form>

</body>

</html>

 

 

 

18.拦截器

 

1.在action前后执行的代码。Struts2的核心功能都是通过拦截器来实现。

2.拦截器栈:由多个拦截器组成

3.作用:对于action的一些公关处理代码可以放到拦截器中实现。比如:权限控制,日志等等

4.多个拦截器直接按的执行是采用责任链设计模式实现

5.拦截器执行流程

     

6.      拦截器的实现步骤:

a)      编写拦截器(实现interceptor接口或者继承AbstractInterceptor类)

b)      在struts.xml中配置拦截器

c)      在action中引用拦截器

0 0
原创粉丝点击