2024年4月17日发(作者:)

struts2 中action 如何获取jsp 页面参数

1. ActionContext

1. ActionContext

在Struts2 开发中,除了将请求参数自动设置到Action 的字段中,我们往往也需要在Action

里直接获取请

求(Request)或会话 (Session)的一些信息,甚至需要直接对JavaServlet Http 的请求

(HttpServletRequest),响应(HttpServletResponse)操作. 我们需要在Action 中取得request 请求

数"username"的值:

ActionContext context = text();

Map params = ameters();

String username = (String) ("username");

ActionContext(Context)是Action 执行时的上下文,上下文可

看作是一个容器(其实我们这里的容器就是一个Map 而已),它存放的是Action 在执行时需

要用到的对象.

一般情况, 我们的ActionContext 都是通过: ActionContext context = (ActionContext)

();来获取的.我们再来看看这里的actionContext 对象的创建:

static ThreadLocal actionContext = new ActionContextThreadLocal();

ActionContextThreadLocal 是实现ThreadLocal 的一个内部类.ThreadLocal 可以命名为"线程

局部变

量",它为每一个使用该变量的线程都提供一个变量值的副本,使每一个线程都可以独立地改

变自己的副本,

而不会和其它线程的副本冲突.这样,我们 ActionContext 里的属性只会在对应的当前请求线

程中可见,从

而保证它是线程安全的.

通过ActionContext 取得HttpSession: Map session =

text().getSession();

2. ServletActionContext

ServletActionContext(k. ServletActionContext),这个类直接继承了

我们上面介绍的ActionContext,它提供了直接与Servlet 相关对象访问的功能,它可以取得的

对象有:

(1)rvletRequest : HTTPservlet 请求对象

(2)rvletResponse : HTTPservlet 相应对象

(3)tContext : Servlet 上下文信息

(4)tConfig : Servlet 配置对象

(5)ntext : Http 页面上下文

如何从ServletActionContext 里取得Servlet 的相关对象:

<1>取得HttpServletRequest 对象: HttpServletRequest request = ServletActionContext.

getRequest();

<2>取得HttpSession 对象: HttpSession session = ServletActionContext.

getRequest().getSession();

3. ServletActionContext 和ActionContext 联系

ServletActionContext 和ActionContext 有着一些重复的功能,在我们的Action 中,该如何去

抉择呢?我

们遵循的原则是:如果ActionContext 能够实现我们的功能,那最好就不要使用

ServletActionContext,

让我们的Action 尽量不要直接去访问Servlet 的相关对象.

注意:在使用ActionContext 时有一点要注意: 不要在Action 的构造函数里使用

text(),因为这个时候ActionContext 里的一些值也许没有设置,这时通过

ActionContext 取得的值也许是null;同样,HttpServletRequest req =

uest()也不要放在构造函数中,也不要直接将req 作为类变量给

其赋值。

至于原因,我想是因为前面讲到的static ThreadLocal actionContext = new

ActionContextThreadLocal(),从这里我们可以看出ActionContext 是线程安全的,而

ServletActionContext 继承自ActionContext,所以ServletActionContext 也线程安全,线程安

全要

求每个线程都独立进行,所以req 的创建也要求独立进行,所以

uest()

这句话不要放在构造函数中,也不要直接放在类中,而应该放在每个具体的方法体中(eg:

login()、

queryAll()、insert()等),这样才能保证每次产生对象时独立的建立了一个req。

4. struts2 中获得request、response 和session

(1)非IoC 方式

方法一:使用Context 类,通过它的静态方法getContext()获取当前

Action

的上下文对象。

ActionContext ctx = text();

("liuwei", "andy"); //ribute("liuwei", "andy");

Map session = sion(); //session

HttpServletRequest request = (_REQUEST);

HttpServletResponse response =

(_RESPONSE);

细心的朋友可以发现这里的session 是个Map 对象, 在Struts2 中底层的session 都被封装

成了Map 类

型. 我们可以直接操作这个Map 对象进行对session的写入和读取操作, 而不用去直接操作

HttpSession

对象.

方法二:使用tActionContext 类

public class UserAction extends ActionSupport {

//其他代码片段

private HttpServletRequest req;

// private HttpServletRequest req = uest(); 这条语句放在这个位

置是错误的,同样把这条语句放在构造方法中也是错误的。

public String login() {

req = uest(); //req 的获得必须在具体的方法中实现

user = new User();

(uid);

sword(password);

if (n(user)) {

sion().setAttribute("user", user);

return SUCCESS;

}

return LOGIN;

}

public String queryAll() {

req = uest(); //req 的获得必须在具体的方法中实现

uList = ll();

sion().setAttribute("uList", uList);

return SUCCESS;

}

//其他代码片段

}

(2)IoC 方式(即使用Struts2 Aware 拦截器)

要使用IoC 方式,我们首先要告诉IoC 容器(Container)想取得某个对象的意愿,通过实现

相应的接口做

到这点。

public class UserAction extends ActionSupport implements SessionAware,

ServletRequestAware, ServletResponseAware {

private HttpServletRequest request;

private HttpServletResponse response;

public void setServletRequest(HttpServletRequest request) {

t = request;

}

public void setServletResponse(HttpServletResponse response) {

se = response;

}

public String execute() {

HttpSession session = sion();

return SUCCESS;

}

}__