ActionContext

一.再探广义值栈

1.ActionContext的线程安全性

我们知道Struts2 在每次执行Action之前都会创建新的ActionContext,在同一个线程里ActionContext里面的属性唯一,这样Action就可以在多线程中使用。

我们在ActionContext的源码中可以找到下面语句:

  static ThreadLocal actionContext = new ThreadLocal();

ThreadLocal又称为 线程局部变量,它为每一个使用该变量的线程都提供一个变量值副本,是每一个线程都可以独立地改变自己的副本而不会和其他线程发生冲突。

存放在ActionContext里的数据都存放在这个ThreadLocal的属性中,而这个属性只会在对应的当前请求线程中可见,从而保证数据是线程安全的。

2.访问的其实是map
Struts2 框架将与web相关的很多对象重新进行了包装。
比如将HttpSession对象重新包装成了一个Map对象,里面存放着Session中的数据,提供这个Map给Action使用。 因为框架的包装,让Action可以完全和web层解耦。

注意:ActionContext不能在普通的java应用程序中使用。因为ActionContext包装的都是Web的数据,在java应用程序中运行的时候,没有web环境的响应和数据,会抛出错误。访问其他的Web对象的值也是与此类似,用户通过ActionContext去访问的都是包装后的Map。

3.使用SessionAware接口
除了前面学过的方式,Struts2还提供另外一种简单的方式:使用SessionAware接口来访问存储于ActionContext中的数据, 该接口通过使用IoC/DI来为Action注入Session Map在程序里面直接使用这个Map来操作数据。

Action实现SessionAware接口,该接口告知Struts2在Action执行之前要设置Session Map,通过servletConfig拦截器来实现的,这个拦截器在defaultStack里面就有。

此接口的源码如下:

package org.apache.struts2.interceptor;

import java.util.Map;

public interface SessionAware
{

    public abstract void setSession(Map map);
}

为了能够在普通的Java应用中运行并测试Action,推荐大家使用SessionAware的方式来访问HttpSession。这样我们在通过main方法运行或测试的时候就可以直接调用setSession方法传入模拟的会话数据,就不会出现execute方法中抛出空指针的异常了。

例子:

package cn.javass.hello.struts2impl.action;
import java.util.Map;

import org.apache.struts2.interceptor.SessionAware;

import com.opensymphony.xwork2.ActionSupport;

import bean.Session;
import bean.UserModel;

public class HelloWorldAction extends ActionSupport implements SessionAware{

	private Map<String,Object>session;
	
	private String account;
	private String password;
	private String submitFlag;
	private UserModel user=new UserModel();
	public void setSession(Map<String,Object>session)
	{
		this.session=session;
	}
	public String execute() throws Exception{
		
		//session.setUsers(user);
		session.put("sessionTestKey","测试session");
		
		
		this.businessExecute();
		
		return this.SUCCESS;
	}
	public void businessExecute()
	{
		System.out.println("用户输入的参数为==="+"account="+account+"password="+password+"submitFlag="+submitFlag);
	}
	public String getAccount()
	{
		return account;
	}
	public void setAccount(String account)
	{
		this.account=account;
	}
	public String getPassword()
	{
		return password;
	}
	public void setPassword(String password)
	{
		this.password=password;
	}
	public String getSubmitFlag()
	{
		return submitFlag;
	}
	public void setSubmitFlag(String submitFlag)
	{
		this.submitFlag=submitFlag;
	}
}

welcome.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
</head>
<body>
<%@taglib prefix="s" uri="/struts-tags" %>

欢迎账号为<s:property value="account"/>的朋友来访<br/>

会话中的值:<s:property value="#session['sessionTestKey']"/>


</body>
</html>

在这里插入图片描述
和SessionAware类似,用户可以使用RequestAware来获取包装请求对象的attribute中的值的Map;
等等。更多的可以看看Struts2的API文档。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

程序员小牧之

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值