您的位置:首页 > 编程语言 > Java开发

struts2笔记10-值栈

2016-04-05 20:55 567 查看
1、问题

提交页面:

<h4>注册产品</h4>
<form action="save.do" method="post">
pName:<input type="text" name="pName" /><br />
pDesc:<input type="text" name="pDesc" /><br />
pPrice:<input type="text" name="pPrice" /><br />
<input type="submit" value="submit" />
</form>


响应页面:

<h4>详细信息</h4>
Name:${pName}<br/><br/>
Desc:${pDesc}<br/><br/>
Price:${pPrice}<br/><br/>


${pName},${pDesc},${pPrice},写法简单优雅,优雅的背后肯定有故事,struts2在背后帮我们做了些什么?

2、StrutsRequestWrapper

(1)打印出request看看

request:<%=request %>


request:org.apache.struts2.dispatcher.StrutsRequestWrapper@37c4d046


(2)StrutsRequestWrapper源码

package org.apache.struts2.dispatcher;

import com.opensymphony.xwork2.ActionContext;
import com.opensymphony.xwork2.util.ValueStack;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletRequestWrapper;

import static org.apache.commons.lang3.BooleanUtils.isTrue;

public class StrutsRequestWrapper extends HttpServletRequestWrapper {

private static final String REQUEST_WRAPPER_GET_ATTRIBUTE = "__requestWrapper.getAttribute";
private final boolean disableRequestAttributeValueStackLookup;

/**
* The constructor
* @param req The request
*/
public StrutsRequestWrapper(HttpServletRequest req) {
this(req, false);
}

/**
* The constructor
* @param req The request
* @param disableRequestAttributeValueStackLookup flag for disabling request attribute value stack lookup (JSTL accessibility)
*/
public StrutsRequestWrapper(HttpServletRequest req, boolean disableRequestAttributeValueStackLookup) {
super(req);
this.disableRequestAttributeValueStackLookup = disableRequestAttributeValueStackLookup;
}

/**
* Gets the object, looking in the value stack if not found
*
* @param key The attribute key
*/
public Object getAttribute(String key) {
if (key == null) {
throw new NullPointerException("You must specify a key value");
}

if (disableRequestAttributeValueStackLookup || key.startsWith("javax.servlet")) {
// don't bother with the standard javax.servlet attributes, we can short-circuit this
// see WW-953 and the forums post linked in that issue for more info
return super.getAttribute(key);
}

ActionContext ctx = ActionContext.getContext();
Object attribute = super.getAttribute(key);

if (ctx != null && attribute == null) {
boolean alreadyIn = isTrue((Boolean) ctx.get(REQUEST_WRAPPER_GET_ATTRIBUTE));

// note: we don't let # come through or else a request for
// #attr.foo or #request.foo could cause an endless loop
if (!alreadyIn && !key.contains("#")) {
try {
// If not found, then try the ValueStack
ctx.put(REQUEST_WRAPPER_GET_ATTRIBUTE, Boolean.TRUE);
ValueStack stack = ctx.getValueStack();
if (stack != null) {
attribute = stack.findValue(key);
}
} finally {
ctx.put(REQUEST_WRAPPER_GET_ATTRIBUTE, Boolean.FALSE);
}
}
}
return attribute;
}
}


  从代码中可以看出,StrutsRequestWrapper重写了getAttribute,其中有一段核心代码如下:

ValueStack stack = ctx.getValueStack();
if (stack != null) {
attribute = stack.findValue(key);
}


  debug代码,可以看出${pName}等是从ValueStack中获取出来的

3、ValueStack

  首先这是一个接口,里面有两个关键声明方法

public abstract Map<String, Object> getContext();

public abstract CompoundRoot getRoot();


  debug代码,可以发现ValueStack包括两个核心属性



一个context,一个root,context里面包含的是一系列map,requestMap,applicationMap,sessionMap等;

root是一个CompoundRoot对象,其实也是个map,这里面包括的就是我们自己Action对象了



${pName}等正是从这里查出来的,并非从request中获取的。

 
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: