Spring框架可以很方便地整合其他MVC框架,如常用的JSP、WebWork、Struts等Web框架。
Spring整合了其他框架后,应用中不仅可以使用被整合框架的功能,还可以享用Spring提供的服务。
导入必要的类库
要使用Spring整合Struts2框架,除了需要导入Spring和Struts2框架必要的类库外,还必须导入支持整合的特定类库。
①导入Spring框架的必要及特定类库
②导入Struts2框架的必要及特定类库
配置web.xml文件
使用Spring框架整合Struts2框架,需要在web.xml中进行一些特殊的配置。
任何使用Struts2的应用,web.xml中都必须配置一个FilterDispatcher,作为核心控制器。
<filter>
<filter-name>FilterDispatcher</filter-name>
<filter-class>org.apache.struts2.dispatcher.FilterDispatcher</filter-class>
</filter>
<filter-mapping>
<filter-name>FilterDispatcher</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
使用Spring框架整合Struts2框架,依然需要加载Spring的配置文件(如applicationContext.xml文件),
从而使用IoC容器装配应用中需要使用的bean。
因此,需要在web.xml文件中配置一个listener来完成加载Spring配置文件的功能
<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
上述配置信息中配置了监听器ContertLoaderListener,默认情况下,监听器ContertLoaderListener将加载WEB-INF目录下的applicationContext.xml文件。
如果Spring框架的配置文件不是默认的applicationContext.xml文件,而是其他自定义的文件,就可以配置上下文参数context-param指定特定的配置文件,
如下所示:
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>/WEB-INF/classes/applicationContext.xml</param-value>
</context-param>
上下文参数的名字是contextConfigLocation,值是配置文件的目录。
修改Struts2框架的Action类
使用Spring整合Struts2框架的核心思想就是讲Struts2的Action实例交给Spring框架的IoC容器装配管理。
因此需要修改Struts2框架的Action类,提供必要的setter方法以注入Action类需要的属性。
LoginAction以前的实现方式:
<pre name="code" class="java">
public String execute(){
CustomerServiceImpl cs = new CustomerServiceImpl();cs.setDao(new CustomerDAOHibImpl());boolean flag=cs.login(custname, pwd);if(flag){return "success";}else{return "fail";}}
Action实例可以通过Ioc容器进行管理装配,修改LoginAction类:
public class LoginAction {
private String custname;
private String pwd;
private CustomerService service;
public void setService(CustomerService service) {
this.service = service;
}
public String execute(){
boolean flag=service.login(custname, pwd);
if(flag){
return "success";
}else{
return "fail";
}
}
}
修改后,上述代码中的LoginAction类中声明了CustomerService类型的属性service,并提供了setService方法进行注入。
execute方法中不需要创建并装配service实例,而是直接使用service实例调用业务逻辑。
service实例的创建和装配将通过Spring的IoC容器完成。
修改struts.properties文件
Spring框架整合Struts2框架后,Struts2的Action将在IoC容器中被实例化及装配。
为了让Struts2框架“知晓”这一信息,需要在Struts.properties文件中配置Struts2的常量,如下所示:
struts.objectFactory=spring
通过上述配置,指定了Struts2的对象工厂是Spring框架的IoC容器。
修改stuts.xml文件
<struts>
<package name="action" extends="struts-default">
<action name="Login" class="LoginAction">
<result name="success">/welcome.jsp</result>
<result name="fail" >/index.jsp</result>
</action>
<action name="Register" class="RegisterAction" >
<result name="regsuccess">/index.jsp</result>
<result name="regfail" >/register.jsp</result>
<result name="input" >/register.jsp</result>
</action>
<action name="ViewAll" class="ViewAllAction">
<result name="success">/allcustomers.jsp</result>
</action>
</package>
</struts>
此时class属性将不再是该Action对应的实际类型,只要是合法的标记符即可,将于applicationContext.xml中Action的bean的id对应。
修改applicationContext.xml文件
<bean id="LoginAction" class="action.LoginAction" scope="prototype">
<property name="service">
<ref bean="service"></ref>
</property>
</bean>
强调的是,Struts2的Action类必须指定scope="prototype",因为Action类通过实例封装了请求参数和其他属性,
如果不指定scope="prototype",则默认为单例范围,那么将出现多次请求值实例化一个Action实例的情况,
这将引起混乱。