当前位置: 移动技术网 > IT编程>开发语言>Java > Struts2 在Action中操作数据

Struts2 在Action中操作数据

2019年09月05日  | 移动技术网IT编程  | 我要评论

 

servlet存储数据的方式

在servlet中,使用servletcontext对象来存储整个webapp的数据,servletcontext中直接存储整个webapp的公共数据,可使用set|get|removeattribute()来操作数据。

此外servletcontext中还有3类众多的小对象:

  • servletconfig     一个servletconfig存储一个servlet的初始化配置参数
  • request   一个request存储一个用户的请求参数
  • session   一个session存储一个用户的会话信息

这3类对象也用于存储数据,也有对应的set|get|removeattribute()方法。

一共是4类对象,这4类对象均使用map来存储数据,这个map叫做域。

 

 

 

 

action操作数据的方式

action是用来代替servlet的,servlet用servletcontext来存储数据,action用actioncontext来存储数据。

 actioncontext context = actioncontext.getcontext();

        //设置、修改、获取参数
        context.put("age",18);
        int age =(int) context.get("age");   //返回值是object,需要强转

 

 

actioncontext本身可以存储数据,actioncontext中也有其他的域对象。

 actioncontext context = actioncontext.getcontext();
        
        map<string, object> application = context.getapplication();  //获取servletcontext的map对象,即application域
        map<string, object> session = context.getsession();  //获取session对象的map对象,即session域
        httpparameters parameters = context.getparameters();   //获取所有的请求参数,此对象相当于el内置的param、params对象

map对象、httpparameters对象均有put()、get()、remove()方法,可通过这些方法来操作数据。

 

 

 

 

 

获取原生的servlet对象,通过原生的servlet对象来操作数据

struts2提供了三种方式,来获取原生的servlet对象。

1、actioncontext本身可以存储数据,也可以获取servletcontext、request、response三个原生的servlet对象:

 actioncontext context = actioncontext.getcontext();

        //获取原生的servlet对象。因为get()返回值是object,所以均需强转
        servletcontext servletcontext = (servletcontext) context.get("com.opensymphony.xwork2.dispatcher.servletcontext");
        httpservletrequest request = (httpservletrequest) context.get("com.opensymphony.xwork2.dispatcher.httpservletrequest");
        httpservletresponse response = (httpservletresponse) context.get("com.opensymphony.xwork2.dispatcher.httpservletresponse");

 

 

2、key太复杂,记不住,所以struts2提供了工具类servletactioncontext:

//均为servletactioncontext类的静态方法
        servletcontext servletcontext = servletactioncontext.getservletcontext();
        httpservletrequest request = servletactioncontext.getrequest();
        httpservletresponse response = servletactioncontext.getresponse();

 

 

3、通过实现接口来获取

public class loginaction extends actionsupport implements servletcontextaware {

    @override
    public string execute() throws exception {
        return super.execute();
    }

    @override
    public void setservletcontext(servletcontext servletcontext) {

    }
}

实现servletcontextaware接口,只需实现一个方法。tomcat会获取并传入一个servletcontext对象,我们要做的就是写一个servletcontext类型的成员变量,把传入的值赋给它,这样这个action中就可以直接使用servletcontext对象了(成员变量)。

public class loginaction extends actionsupport implements servletcontextaware {
    private servletcontext servletcontext;

    @override
    public string execute() throws exception {
        return super.execute();
    }

    @override
    public void setservletcontext(servletcontext servletcontext) {
        this.servletcontext=servletcontext;
    }
}

 

要使用servletcontext对象,就实现servletcontextaware接口;

要使用httpservletrequest对象,就实现servletrequestaware接口;

要使用httpservletresponset对象,就实现servletresponseaware接口;

可同时实现这些接口。

 

其实第2、3种方式底层都是:调用第一种方式获取原生的servlet对象,返回。

 

 

 

 

 

actioncontext对象的生命周期

  •  servlet是线程不安全的。在webapp运行期间,一个servlet只有一个实例,所有请求(用户)共享这个实例的成员变量,容易引发问题,通常的做法是把可能会被多个用户修改的变量写在方法体中(局部变量)。基于servlet的struts1也是不安全的。

  • struts2是线程安全的。在webapp运行期间,struts2会为每一个请求创建一个新的action实例,处理完这个请求,对应的action实例就销毁。

  • actioncontext对象随action对象的创建而创建,随action对象的销毁而销毁。即actioncontext与servlet中原生的request对象的生命周期一致,所以存储数据可以用actioncontext代替servlet的request。可以用actioncontext来传递数据,但请求参数并不会放在actioncontext的数据区域,不能  actioncontext.getcontext().get("xxx")这样来获取请求参数。

 

 

 

 

 

action中获取请求参数的方式

 1、获取原生的request对象,通过request对象来获取请求参数

httpservletrequest request = servletactioncontext.getrequest();
string name = request.getparameter("name");

 

 

2、通过actioncontext获取httpparameters对象,再通过httpparameters对象来获取请求参数

actioncontext context = actioncontext.getcontext();
        httpparameters parameters = context.getparameters();
        parameter name = parameters.get("name");

获取的参数是parameter类型。httpparameters相当于一个map。

 

 

 

3、属性驱动

public class loginaction extends actionsupport {
    private string name;
    private integer age;  //尽管有自动拆箱、装箱,还是尽量用包装类型

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

    @override
    public string execute() throws exception {
        return null;
    }

}

将要使用的请求参数写成action的成员变量,并提供setter、getter方法,以及为action提供空参的构造器。

请求参数都是string类型,会先将请求参数转换为对应的成员变量的类型,再调用setter方法赋给对应的成员变量。

只适用于8种基础类型、date类型,date类型对字符串格式有要求,比如2019-09-01。

要求请求参数的name(表单字段的name)与成员变量的变量名相同。

    name:<input type="text" name="name"><br />
    age:<input type="text" name="age"><br />

属性驱动的缺点:要使用的请求参数很多时,action中会有大量的成员变量、getter、setter方法,很繁杂。

 

 

 

 

4、对象驱动

将要使用的请求参数封装到一个javabean(实体类)中,作为action的成员变量,action要提供对应的getter、setter方法以及空参构造器:

public class loginaction extends actionsupport {
    private user user;

    public user getuser() {
        return user;
    }

    public void setuser(user user) {
        this.user = user;
    }

    @override
    public string execute() throws exception {
        system.out.println(user.getname());
        return null;
    }

}

 

 

需要提供javabean(实体类),这个实体类要具有getter、setter方法、空参构造器:

public class user {
    private string name;
    private string age;

    public string getname() {
        return name;
    }

    public void setname(string name) {
        this.name = name;
    }

    public string getage() {
        return age;
    }

    public void setage(string age) {
        this.age = age;
    }
}

 

 

表单字段的name属性要加上对象名:

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

name属性的写法与之前不同,可能不习惯。

 

 

 

 

5、模型驱动

public class loginaction extends actionsupport implements modeldriven<user> {
    //需要显式创建(new出来),否则为null。
    private user user=new user();

    @override
    public user getmodel() {
        //返回接受请求参数的对象
        return user;
    }

    @override
    public string execute() throws exception {
        return null;
    }

}

需要实现modeldriver<t>接口,只需实现getmodel()方法,返回接受请求参数的对象。

需要显式创建接受请求参数的对象,否则这个对象为null,使用这个对象时会引发空指针异常。但不用给这个对象提供setter、getter方法。

 

依然需要提供javabean(实体类)。

 

表单字段的name属性使用原来的写法:

    name:<input type="text" name="name"><br />
    age:<input type="text" name="age"><br />

 

模型驱动的缺点:只能有一个model,只能将请求参数封装到一个实体类中。对象驱动则可以有多个对象,可以将参数封装到多个对象中。

 

 

 

 

6、使用集合封装请求参数

原生的servlet是将请求参数封装到request中,httpparameters是将请求参数封装到httpparameters中,属性驱动是将请求参数封装到action的多个成员变量中,对象驱动、模型驱动都是将请求参数封装到javabean中。

此外还可以使用集合(list或map)来封装请求参数。

 

  • 使用list封装请求参数

public class loginaction extends actionsupport{
    private list<string> list;

    public list<string> getlist() {
        return list;
    }

    public void setlist(list<string> list) {
        this.list = list;
    }

    @override
    public string execute() throws exception {
        return null;
    }

}

需要提供getter、setter方法。

 

表单字段的name属性指定list对象:

    name:<input type="text" name="list"><br />
    age:<input type="text" name="list"><br />

会把请求字段存储到一个list中,第一个字段存储为list的第一个元素,第二个字段存储为第二个元素......以此类推。

 

可以指定存储位置:

    name:<input type="text" name="list"><br />
    age:<input type="text" name="list[3]"><br />
    tel:<input type="tel" name="list"><br />
    

[name字段的值,tel字段的值,null,age字段的值]

指定了下标的,存储在指定的位置上;没有指定下标的,从前往后,存储在闲置的位置(null)上。

 

 

  • 使用map封装请求参数

public class loginaction extends actionsupport{
    private map<string,string> map;

    public map<string, string> getmap() {
        return map;
    }

    public void setmap(map<string, string> map) {
        this.map = map;
    }

    @override
    public string execute() throws exception {
        return null;
    }

}

需要提供getter、setter方法。

 

表单字段:

    name:<input type="text" name="map['name']"><br />
    age:<input type="text" name="map['age']"><br />

map是以键值对来存储字段的,所以还需指定key。map对象['key']。

 

 

 

 

原生的servlet对象是给servlet用的,使用struts2就尽量使用action的方式操作数据。但操作cookie还是原生的servlet对象方便一些。

action中的域(map)与servlet的域对应,在jsp中同样可以使用el表达式取出域中的值。

 

如对本文有疑问, 点击进行留言回复!!

相关文章:

验证码:
移动技术网