Struts2学习笔记

struts2的知识总结:2011-12-05
strtus2是综合了struts1和webwork上而成的一个全新框架,并不是struts1的扩展。

首先,先看一下web.xml文件的作用:

每一个web应用的WEB-INF路径下的web.xml文件被称为配置描述符,这个web.xml对于Java Web非常重要,每个Java Web应用都必须包含一个web.xml文件,且必须放在WEB-INF路径下。


对于Java Web应用而言,WEB-INF是一个特殊的文件夹,Web容器会包含该文件夹下的内容,客户端浏览器无法访问WEB-INF下的任何内容。


Java Web应用的绝大部分内容都由web.xml文件来配置管理,下面的内容都需要通过web.xml文件进行配置管理:


配置Jsp

配置和管理Servlet

配置和管理Listener

配置和管理Filter

配置标签库

配置JSP属性

除此之外,web.xml还负责配置、管理如下常用的内容:

配置和管理JAAS授权认证

配置和管理资源引用

Web应用首页


另外,每一个web框架都应该在web.xml中配置成一个servlet或者是filter,这样这个框架才会在这个web项目中产生作用。


添加struts2的应用:

在web.xml中添加struts2的核心Filter。

<?xml version="1.0" encoding="UTF-8"?>
<web-app version="2.5" xmlns="http://java.sun.com/xml/ns/javaee"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://java.sun.com/xml/ns/javaee 
    http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd">	 
        
        <!--定义Struts2的FilterDispatcher的Filter-->
	<filter>
		<!--定义核心Filter的名字-->
		<filter-name>Struts2</filter-name>
		<!--定义核心Filter的实现类-->
		<filter-class>Struts2.dispatcher.FilterDispatcher</filter-class>
	</filter>
	<!--FilterDispatcher用来初始化Struts2并且处理所有请求-->
	<filter-mapping>
		<filter-name>Struts2</filter-name>
		<url-pattern>/*</url-pattern>
	</filter-mapping>

</web-app>
在web.xml文件中定义Servlet或者Filter拦截用户请求,通常这个Servlet或Filter是该框架的核心,负责拦截所有用户的请求。

由于Web应用是基于请求/相应架构的应用,所以不管哪个MVC Web框架,都需要在web.xml中配置该框架的核心Servlet或Filter,这样才可以让该框架介入Web应用中。

在web的类加载路径下防止struts.xml配置文件:

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE struts PUBLIC "-//Apache Software Foundation//DTD Struts Configuration 2.0//EN" "http://struts.apache.org/dtds/struts-2.0.dtd">
<struts>
    <!--指定全局国际化资源文件的base名-->
    <constant name="struts.custom.i18n.resources" value="messageResource" />
    <!--指定国际化编码所使用的字符集-->
    <constant name="struts.i18n.encoding" value="UTF-8" />
</struts>
上面配置文件中制定国际化资源文件的base名为messageResource,所以我们还应该为该应用提供一个messageResource_zh_CN.properties文件。


处理用户的请求:


核心的Servlet或者Filter接收到用户的请求后,通常会对用户请求进行简单预处理,例如解析、封装参数等,然后通过反射来创建Action实例,并调用Action制定的方法(Struts1通常是execute,struts2可以是任意方法)来处理用户请求。

这里又有一个问题,当filter拦截到用户请求后,它如何知道创建哪个Action实例呢?这里有两种解决方案:

(1)利用配置文件:

(2)利用约定:称为“零配置”


常量配置:

struts2除了使用struts2.xml文件来管理配置外,还可以使用struts.properties文件来管理配置,该文件定义了Struts2框架的大量属性,开发者可以通过改变这些属性来满足应用的需求。同样只要将struts.properties文件放在Web应用的类加载路径下,Struts2框架就可以加载该文件。其中的default.properties文件在struts-core的jar包中org/apaceh/struts2/目录下的default.properties文件,修改该文件中的配置就可以修改对应的struts的配置。这个相见另一篇文章。呵呵~

Struts2会默认加载类加载路径下的struts.xml、struts-default.xml、struts-plugin.xml三类文件,其中struts.xml是开发者定义的默认配置文件,struts-default.xml是struts2框架自带的配置文件,而struts-plugin.xml则是struts2插件的默认配置文件。


有些开发者不喜欢使用struts.properties文件,Struts2也允许在struts.xml文件中管理struts2属性。在struts.xml文件中通过常量配置一样可以配置这些属性。如下:

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE struts PUBLIC "-//Apache Software Foundation//DTD Struts Configuration 2.0//EN" "http://struts.apache.org/dtds/struts-2.0.dtd">
<struts>
    <!--通过constant元素配置struts2的属性-->
    <constant name="struts.custom.i18n.resources" value="mess" />
    <!--通过include属性导入其他配置文件-->
    <include file="struts-part1.xml"/>
 </struts>

该属性指定了应用所需的国际化资源文件的baseName为mess。

除此之外,当我们在web.xml文件配置FilterDispatcher时也可以配置Struts2属性,此时采用为FilterDispatcher配置初始化参数的方式来配置struts2属性,如下代码:


<?xml version="1.0" encoding="UTF-8"?>
<web-app version="2.5" xmlns="http://java.sun.com/xml/ns/javaee"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://java.sun.com/xml/ns/javaee 
    http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd">	 
        
        <!--定义Struts2的FilterDispatcher的Filter-->
	<filter>
		<!--定义核心Filter的名字-->
		<filter-name>Struts2</filter-name>
		<!--定义核心Filter的实现类-->
		<filter-class>Struts2.dispatcher.FilterDispatcher</filter-class>
        <init-param>
            <param-name>struts.custom.i18n.resources</param-name>
            <param-value>mess</param-value>
        </init-param>
        </filter>
	<!--FilterDispatcher用来初始化Struts2并且处理所有请求-->
	<filter-mapping>
		<filter-name>Struts2</filter-name>
		<url-pattern>/*</url-pattern>
	</filter-mapping>

</web-app>

综上所述,struts2提供了三种方式来管理Struts2的属性:既可以通过struts.properties文件来配置Struts2属性;也可以通过在struts.xml文件中配置constant元素来配置Struts2属性;还可以在web.xml文件中配置Struts2属性。通常推荐在struts.xml文件中定义Struts2属性,而不是在struts.properties中定义,之所以保留properties文件,只是为了保持与WebWork的向后兼容性。


Action接口和ActionSupport基类:

struts2提供了一个Action接口,这个接口定义了Struts2的Action处理类应该实现的规范。

public interface Action {

        public static final String ERROR = "error";

        public static final String INPUT = "input";

        public static final String LOGIN = "login";

        public static final String NONE = "none";

        public static final String SUCCESS = "success";

        public String execute() throws Exception;

}

另外Struts2还提供一个Action接口的一个实现类,ActionSupport

ActionSupport是一个默认的Action实现类,该类里已经提供了许多默认方法,这些默认方法包含很多方法,如果继承了这个类,会大大降低开发的复杂度。

Struts2访问ServletAPI,一共有三种方式;

Strust2的action没有与任何的servletAPI耦合,这是struts2的一个改良之处,因为Action类不再与ServletAPI耦合,从而能更轻松地测试该Action。

但对于web应用的控制器而言,不访问ServletAPI几乎是不可能的,例如跟踪HTTPSession状态等。Struts2提供了一种更轻松的方式来访问ServletAPI。Web应用中通常需要访问的ServletAPI就是HTTPServletRequest、HTTPSession和ServletContext,这三个类分别代码JSP内置对象中的request、session和application。


方式一:Struts2提供了一个ActionContext类,Struts2的Action可以通过该类来访问ServletAPI

public String execute() {
	ActionContext ctx = ActionContext.getContext();
	Integer counter = (Integer)ctx.getApplication().get("counter");
	ctx.getApplication().put("counter",counter);//${applicationScope.counter}
	ctx.getSession().put("user",username);//${sessionScope.user}
	ctx.put("tip","服务器的提示信息");//${requestScope.tip}
}

上述的Action成功操作request、session和application范围的属性。


方式二:Action直接访问ServletAPI

虽然struts2提供了ActionContext来访问ServletAPI,但这种访问毕竟不是直接获得ServletAPI的实例。为了在Action中直接访问ServletAPI,Struts2还提供了如下几个接口。

ServletContextAware//实现该接口的Action可以直接访问Web应用的ServletContext接口

ServletResponseAware//实现该接口的Action可以直接访问服务器响应的HttpServletResponse实例。

ServletRequestAware//实现该接口的Action可以直接访问用户请求的HttpServletRequest实例。


项目中的例子

public abstract interface IBaseAction extends Preparable, ServletResponseAware, ServletRequestAware
{
  public abstract String list()
    throws Exception;

  public abstract String edit()
    throws Exception;

  public abstract String save()
    throws Exception;

  public abstract String delete()
    throws Exception;
}


public class BaseAction extends ActionSupport implements IBaseAction {

    public HttpServletResponse response = null;
    public HttpServletRequest request = null;
    
    public void setServletRequest(HttpServletRequest arg0) {
        this.request = arg0;
    }
    
    @Override
    public void setBundleContext(BundleContext context) {
        this.context = context;
    }

    public void setServletResponse(HttpServletResponse arg0) {
        this.response = arg0;
    }
}
方式三:除了上述两种方法之外,Strut2还提供了一个ServletActionContext工具类,这个类包含了几个静态方法

static PageContext getPageContext() //:取得Web应用的PageContext对象

static HttpServletRequest getRequest()//:取得Web应用的HttpServletRequest对象

static HttpServletResponse getResponse()//:取得Web应用的HttpServletResponse对象

static ServletContext getServletContext()//:取得Web应用的ServletContext对象


借助于ServletActionContext类的帮助,开发者也可以在Action中直接访问ServletAPI,并可避免Action类需要实现XxxAware接口--虽然如此,但该Action依然与ServletAPI直接耦合,一样不利于高层次的解耦。


注意点:


虽然可以在Action类中获取HttpServletResponse,但如果希望通过HttpServletResponse来生成服务器响应是不可能的,因为Action只是业务控制器。即如果在Action中书写如下代码:

//用于在Servlet中直接生成响应的代码

response.getWriter().println("Hello World");


上面代码在标准的Servlet中会生成对客户端的响应,但在struts2的Action中没有任何实际意义。



struts支持下面几种结果类型:

Type的值可以填写如下几种:

1:chain       Action链接的结果类型

2:chart       整合JfreeChart的结果类型

3:dispatcher   JSP整合的结果类型

4:freemarker   FreeMarker整合的结果类型

5:httpheader   控制特殊的HTTP行为的结果类型

6:jasper       JasperReports整合的结果类型

7:jsf          与JSF整合的的结果类型

8:redirect      直接跳转到其它URL的结果类型

9:redurectAction 用于直接跳转到其它Action的结果类型

10:stream       向浏览器返回一个InputStrean(一般用于文件下载)

11:tiles         与Tiles整合的结果类型

12:velocity      与Vlocity整合的结果类型

13:xslt          与XML/XSLT整合的结果类型

14:plainText      用于显示某个页面的原始代码的结果类型

有一篇文档另有详细说明。




Struts2的零配置:在项目中的web.xml中

        <filter>
		<filter-name>action2</filter-name>
		<filter-class>com.glodon.gboat.web.filter.ExtractedFilterDispatcher</filter-class>
		<init-param>
			<param-name>actionPackages</param-name>
			<param-value>com.glodon.gets.crms.action</param-value>
		</init-param>
	</filter>
actionPackages是默认的Action存放的包,多个包用逗号隔开。


Action的结果集使用注解的形式@Results进行跳转,还用@NameSpace定义命名空间。这个在项目中已经大量使用,现如今才真正明白了其中的原理。


你可能感兴趣的:(exception,struts,servlet,String,filter,action)