Struts2在web.xml中配置为“/*”和“*.action,*.jsp”的差别

转载 2012年03月29日 00:16:22
Struts2在web.xml中配置为“/*”和“*.action,*.jsp”的差别

1、Struts2在web.xml中配置为“/*”和“*.action,*.jsp”的差别。 
2、There is no Action mapped for namespace / and action name ...的问题。 


分析(环境是Struts2.1.8.1): 
Struts2过滤器的配置有2种方式:
Java代码  
<filter-mapping>  
<filter-name>struts2</filter-name>  
<url-pattern>/*</url-pattern>  
</filter-mapping>  
  
  
<filter-mapping>  
<filter-name>struts2</filter-name>  
<url-pattern>*.action</url-pattern>  
</filter-mapping>  
<filter-mapping>  
<filter-name>struts2</filter-name>  
<url-pattern>*.jsp</url-pattern>  
</filter-mapping>  
 


那么这两种方式的配置,究竟有什么差别呢? 
首先,假如配置方式是*.action的话,一般应当同时配置*.jsp,因为如果不通过action而直接访问jsp页面的话,Struts2标签在解析的时候会获取当前线程ThreadLocal中的Dispatcher。而Dispatcher是在Struts过滤器中预设的。代码如下:
Java代码  
public static ValueStack getStack(PageContext pageContext) {  
HttpServletRequest req = (HttpServletRequest) pageContext.getRequest();  
ValueStack stack = (ValueStack) req.getAttribute(ServletActionContext.STRUTS_VALUESTACK_KEY);  
if (stack == null) {  
HttpServletResponse res = (HttpServletResponse) pageContext.getResponse();  
Dispatcher du = Dispatcher.getInstance();  
if (du == null) {  
throw new ConfigurationException("The Struts dispatcher cannot be found.  This is usually caused by "+  
"using Struts tags without the associated filter. Struts tags are only usable when the request "+  
"has passed through its servlet filter, which initializes the Struts dispatcher needed for this tag.");  
}  
//略...  
 




除了为当前线程预设Dispatcher以外,Struts2对“/*”的请求,在完成普通的“*.action”过滤的基础上,另外提供2点功能: 
第1点用于访问classpath中特定的静态资源; 
第2点支持无后缀名的Action请求; 
Struts2的标签有时候需要某些CSS、JS文件的支持,比如<s:head/>标签,可能就转换成:
Java代码  
<link rel="stylesheet" href="/demo/struts/xhtml/styles.css" type="text/css"/>  
<script src="/demo/struts/utils.js" type="text/javascript"></script>  
 
第1点功能带来的好处是可以把这些Struts2框架用到的CSS、JS文件打包在Struts2-core-***.jar文件中分发,使得Struts2的发布包对开发人员而言更加简洁。 
下面看一下StrutsPrepareAndExecuteFilter是怎样实现的: 
①将Dispatcher预设到线程的ThreadLocal变量上; 
②对于Action请求,直接execute.executeAction(request,response,mapping); 
③如果是/struts、或者/static开始的资源,则在classpath下查找特定的包下面的匹配资源; 
④其他的所有资源(包括直接访问的JSP、以及其他静态资源)转交过滤器链的下一个环节处理:chain.doFilter(request, response); 
上面所说的特定包,是指在
Java代码  
<filter>  
<filter-name>struts2</filter-name>  
<filter-class>  
org.apache.struts2.dispatcher.ng.filter.StrutsPrepareAndExecuteFilter  
</filter-class>  
<init-param>  
<param-name>packages</param-name>  
<param-value>eee</param-value>  
</init-param>  
</filter>  
 


中通过packages参数指定的包、以及 "org.apache.struts2.static template org.apache.struts2.interceptor.debugging static"这4个包。 
由于packages可配置,从而,如果有自己的classpath上的资源需要访问,或者需要更改Struts本身的静态资源时,只要把Classpath下相应的package设置在过滤器的初始参数中即可(这一条看上去好像没什么用处)。 


上面是使用/*时对静态资源的访问,那么使用*.action时如果需要的话,如何访问静态资源呢? 
很简单,只要把需要用到的静态资源解压缩到WebContent/struts目录下即可。 


第2点“支持无后缀名的Action请求”经常带来一些混乱,最典型的就是“/*”错误地拦截了其他的映射为无后缀名的Servlet请求。比如DWR、FCKEditor等都存在这种问题。 
比如,当访问“/demo/dwr”时,正常情况应该显示当前系统中对外暴露的JS方法的列表,但在Struts2的默认配置下,却得到“There is no Action mapped for namespace / and action name dwr.” 
又比如在默认配置下,访问http://localhost:8080/demo/hello.action 
和访问http://localhost:8080/demo/hello这两者是等同的。 
当然,也只有无后缀名的URL请求才会被Struts2当做是Action,这也是为什么/dwr无法访问,然而/dwr/interface.js可以访问的原因。 


具体的,看一下下面的代码就明白了:
Java代码  
//Struts2默认将“*.action”或者无后缀的URL当做Action  
protected List<String> extensions = new ArrayList<String>() {{ add("action"); add("");}};  
protected String dropExtension(String name, ActionMapping mapping) {  
if (extensions == null) {  
return name;  
}  
for (String ext : extensions) {  
if ("".equals(ext)) {  
// This should also handle cases such as /foo/bar-1.0/description. It is tricky to distinquish /foo/bar-1.0 but perhaps adding a numeric check in the future could work  
// request uri如果不包含扩展名的话,则匹配此情况  
int index = name.lastIndexOf('.');  
if (index == -1 || name.indexOf('/', index) >= 0) {  
return name;  
}  
} else {  
String extension = "." + ext;  
if (name.endsWith(extension)) {  
name = name.substring(0, name.length() - extension.length());  
mapping.setExtension(ext);  
return name;  
}  
}  
}  
return null;  
}  
 
那么,怎么解决此问题呢? 
有2种办法。 
第1种很简单,在Struts.properties中定义: 
struts.action.extension = action即可解决此问题。 
Struts2缺省配置对应于: 
struts.action.extension = action,(注意后面有个逗号) 
第2种是在Struts.properties中设置: 
struts.action.excludePattern = /dwr.*,/webEditor.*(注意,这儿是正则表达式,不是URL匹配模式,所以要写/dwr.*而不是/dwr/*) 
这种写法应配置StrutsPrepareAndExecuteFilter,配置FilterDispatcher是无效的。
在微博管家项目中,采用的是struts2.1.8,出现了jsp、js、css等文件加载失败等问题。通过以下配置解决:
struts.xml:
<constant name="struts.action.extension" value="" />
struts.properties:
struts.locale=zh_CN
struts.i18n.encoding=utf-8
struts.action.extension=,
struts.action.excludePattern = /js.*,/static.*(js和static文件夹是项目中js和css所在的目录)

相关文章推荐

Struts2配置详解_配置Action

Struts2的核心功能是action,对于开发人员来说,使用Struts2主要就是编写action,action类通常都要实现com.opensymphony.xwork2.Action接口,并实现...

Struts2 同时支持/* 和.do *.action 的匹配

Struts 配置文件的加载顺序     Struts-default.xml---> struts-plugin.xml--> struts.xml-->   struts.propertie...
  • Baple
  • Baple
  • 2015年09月07日 13:34
  • 3932

StrutsPrepareAndExecuteFilter过滤器和url-pattern设置详解

1.strut 过滤器FilterDispatcher是struts2.0.x到2.1.2版本的核心过滤器.! StrutsPrepareAndExecuteFilter是自2.1.3开始就替代了Fi...
  • jethai
  • jethai
  • 2016年08月28日 14:02
  • 1483

Filter与Struts2验证区别与使用

引用博客:http://www.cnblogs.com/jersey/archive/2011/05/04/2036567.html Struts2 权限验证 References:《...
  • WingBin
  • WingBin
  • 2012年10月12日 07:54
  • 1779

Sitemesh和Struts2结合时Filter的配制顺序

      Sitemesh和Struts2结合时要特别注意它们各自Filter的顺序,否则会导致双方都不能正常工作。而又由于Struts2在2.1.3之前使用的是FilterDispatcher,2...

Struts 项目中web.xml文件配置

web.xml文件对于配置任何Java Web应用都必需的。(1)配置Struts的ActionServlet元素来声明ActionServlet元素:用来定义Servlet的名称元素:用来指定Ser...
  • songqiu
  • songqiu
  • 2007年09月08日 01:03
  • 5872

web.xml配置action

直接web.xml里面配置action倒是没有见过。我们这是这样做的随便写一个JSP页面 在页面里面在转发到你要的Action web.xml jump.jsp jump.jsp里通过这段代...
  • jj88888
  • jj88888
  • 2015年08月24日 10:10
  • 948

action提交表单路径两种方法:web.xml设置和注解

action提交表单给servlet的方法:    ********** A代表servlet名字,不能写前边的各种包名字,前面的斜杠  /  也不能写。 方法一:web.xml法 首先...

[Struts2] 配置文件struts.xml和web.xml详解

配置文件struts.xml和web.xml。 其实要s
  • gopain
  • gopain
  • 2014年11月04日 21:31
  • 16549

structs2的web.xml和struct.xml两个配置文件的配置

structs
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:Struts2在web.xml中配置为“/*”和“*.action,*.jsp”的差别
举报原因:
原因补充:

(最多只允许输入30个字)