Struts2存取数据

ActionContext

ActionContext是strtuts2新设计出来的存储数据的容器,就是下面的 contextMap (Map)

它里面有其他域容器的引用(request,session,application,attr)


ActionContext是Action执行时的上下文,里面存放着Action在执行时需要用到的对象,我们也称之为广义值栈。

Struts2在每次执行Action之前都会创建新的ActionContext对象,为了保证我们使用的是同一个线程的ActionContext对象,就要考虑ActionContext的线程安全性。(保证取ActionContext对象时不会取到其他线程创建的ActionContext对象

ActionContext的线程安全性  

Struts2是如何保证ActionContext的线程安全性呢?  

看看ActionContext对象的源代码,示例如下:

public class ActionContext implements Serializable {
    static ThreadLocal actionContext = new ThreadLocal();
    public static ActionContext getContext() {
        return (ActionContext) actionContext.get();
	}
}


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

ServletContext

WEB容器在启动时,它会为每个WEB应用程序都创建一个对应的ServletContext对象,它代表当前web应用。

ServletContext,是一个全局的储存信息的空间,服务器开始,其就存在,服务器关闭,其才释放。

request,一个用户可有多个;session,一个用户一个;而servletContext,所有用户共用一个


ValueStack值栈存取数据

存数据

	public String execute(){
		//----获取ValueStack对象的引用----
		//方式一:获取HttpServletRequest对象,通过他的getAttribute方法获取,根据key struts.valueStack获取
		HttpServletRequest request = ServletActionContext.getRequest();
		ValueStack vs1 = (ValueStack)request.getAttribute("struts.valueStack");
		System.out.println(vs1.hashCode());
		
		//方式二:获取ActionContext,取出requestMap,然后通过map的get方法获取
		ActionContext context = ActionContext.getContext();
		Map<String, Object> requestAttribute = (Map<String, Object>) context.get("request");
		ValueStack vs2 = (ValueStack) requestAttribute.get("struts.valueStack");
		System.out.println(vs2.hashCode());
		
		//方式三:使用ActionContext对象的getValueStack方法
		ValueStack vs3 = context.getValueStack();
		System.out.println(vs3.hashCode());
		
		//压栈 存数据
		vs1.push(new Student("夏明",32));
		/**
		 * setValue(String expr,Object value)
		 * 	String expr:OGNL表达式
		 * 	Object value:要操作的数据
		 * 把数据存到哪里?
		 * 	看expr是否使用了#
		 * 	使用了#:把数据存到contextMap中
		 * 	没使用#:把数据存到ValueStack中
		 */
		vs2.setValue("#name", "张三");
		vs2.setValue("name", "李四");
		return SUCCESS;
	}
取数据

<%@page contentType="text/html; charset=utf-8" pageEncoding="utf-8"%>
<%@ taglib uri="/struts-tags" prefix="s"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
</head>
<body>
	<!-- 
		使用s:property来获取ValueStack的值
		value属性的取值是一个OGNL表达式,只能获取元素中的属性
		注意:取ValueStack中的属性时不使用#
		它是从栈顶逐个查找对象的属性,找到了就不继续找
 	-->
	<!-- 获取contextMap(大Map)时    #key名称 -->
	<s:property value="name" />
	<s:property value="age" />

	<s:debug />
</body>
</html>


contextMap存取数据

存数据

	public String index(){
		
		//----往contextMap存数据(大map)-----
		//得到ActionContext对象,从当前线程的局部变量中获取引用
		ActionContext context = ActionContext.getContext();
		//往contextMap中存数据(大map)
		context.put("contextMap", "存入context的数据");
		
		//----往session存数据(小map)-----
		//方式一:获取key为session的map
		Map<String, Object> sessionAttribute =context.getSession();//相当于 context.get("session")
		sessionAttribute.put("sessionMap1", "存入sessionMap1的数据");
		
		//方式二:直接使用原始的HttpSession对象
		HttpSession session = ServletActionContext.getRequest().getSession();
		session.setAttribute("sessionMap2", "存入sessionMap2的数据");
		
		//----往ServletContext存数据(小map)-----
		//方式一:获取key为application的map
		Map<String, Object> applicationAttribute = context.getApplication();//相当于 context.get("application")
		applicationAttribute.put("applicationMap1", "存入applicationMap1的数据");
		//方式二:直接使用原始的ServletContext对象
		ServletContext application = ServletActionContext.getServletContext();
		application.setAttribute("applicationMap2", "存入applicationMap2的数据");
		return SUCCESS;
	}
取数据

<%@page contentType="text/html; charset=utf-8" pageEncoding="utf-8"%>
<%@ taglib uri="/struts-tags" prefix="s"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
</head>
<body>
	<!-- 
		使用s:property来获取ActionContext的值
		value属性的取值是一个OGNL表达式
 	-->
	<!-- 获取contextMap(大Map)时    #key名称 -->
	<s:property value="#contextMap" />
	<!-- 获取contextMap(大Map)中的小Map时    #大Map的key.小Map的key -->
	<s:property value="#session.sessionMap1" />
	<s:property value="#session.sessionMap2" />
	<s:property value="#application.applicationMap1" />
	<s:property value="#application.applicationMap2" />

	<s:debug />
</body>
</html>

Strurs2对EL表达式的改变

使用方法

EL表达式:${name} 相当于 pageContext.findAttribute("name");

OGNL表达式:<s:property value="name"/>

查找顺序

EL表达式:page-->request-->session-->application

OGNL表达式:page-->request-->ValueStack-->contextMap-->session-->application

如在request域找到值,就不会继续往下找。

s:iterator:struts2的迭代标签

存数据

/**
 * s:iterator标签的使用
 * @author zhy
 *
 */
public class Demo4Action extends ActionSupport {
	//Action动作类的引用,默认情况下就在ValueStack的栈顶
	private List<Student> students;

	public String findAll(){
		//调用service层的方法,List findAllStudent()
		students = new ArrayList<Student>();
		students.add(new Student("张琛",23));
		students.add(new Student("于嵩楠",24));
		students.add(new Student("党安航",21));		
		return SUCCESS;
	}

	public List<Student> getStudents() {
		return students;
	}

	public void setStudents(List<Student> students) {
		this.students = students;
	}
	
	
}
取数据

  	<table width="500px" border="1" align="center">
  		<tr>
  			<th>序号</th>
  			<th>姓名</th>
  			<th>年龄</th>
  		</tr>
  		<%--s:iterator:struts2的迭代标签
  			属性详解:
  			begin,end,step和jstl的forEach标签是一样的 
  			value属性:要遍历的集合,是OGNL表达式。
  			var属性:取值就是一个字符串
  				如果写了该属性:把var的值作为key,把当前遍历的元素作为value。存到ActionContext这个大Map中
  				如果不写该属性:把当前遍历的元素压入栈顶
  			status属性:遍历时的一些计数信息。
  				int getIndex() 从0开始
  				int getCount() 从1开始
  				boolean isFirst() 
  				boolean isLast()
  				boolean isOdd()
  				boolean isEven()
  			--%>
  		<s:iterator value="students" var="s" status="vs" >
  			<tr>
  				<td><s:property value="#vs.index"/></td>
  				<td><s:property value="#s.name" /></td>
  				<td><s:property value="#s.age" /></td>
  			</tr>
  		</s:iterator>
  	</table>
  	<hr/>
  		<table width="500px" border="1" align="center">
  		<tr>
  			<th>序号</th>
  			<th>姓名</th>
  			<th>年龄</th>
  		</tr>
  		<s:iterator value="students" status="vs">
  			<tr>
  				<td><s:property value="#vs.count"/></td>
  				<td><s:property value="name" /></td>
  				<td><s:property value="age" /></td>
  			</tr>
  		</s:iterator>
  	</table>



评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值