1.启动spring容器
为了让spring容器随Web应用的启动而自动启动,借助于ServletContextListener监听器即可完成,该监听器可以在Web应用启动时回调自定义方法,该方法就可以启动spring容器。spring提供了一个ContextLoaderListener,该监听器实现了ServletContextListener接口。该类可以作为Listener使用,它会在创建时自动查找WEB-INF/下的applicationContext.xml文件。因此,如果只有一个配置文件,并且文件名为applicationContext.xml,则只需在web.xml文件中配置如下配置片段:
<listener>
<listener-class>
org.springframework.web.context.ContextLoaderListener
</listener-class>
</listener>
如果有多个配置文件需要载入,则考虑使用<context-param.../>
元素来确定配置文件的文件名。ContextLoaderListener加载时,会查找名为contextConfigLocation的初始化参数。
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>/WEB-INF/doContext.xml,/WEB-INF/applicationContext.xml</param-value>
</context-param>
<listener>
<listener-class>
org.springframework.web.context.ContextLoaderListener
</listener-class>
</listener>
spring根据指定的配置文件创建WebApplicationContext对象,并将其保存在Web应用的ServletContext中。
//获取当前Web应用启动的spring容器
WebApplicationContext ctx = WebApplicationContextUtils.getWebApplicationContext(servletContext);
2.让spring管理控制器
进入struts2项目的lib目录下,可以找到一个struts2-spring-plugin-2.3.16.3.jar文件,这个JAR包就是struts2整合spring的插件,简称spring插件。
在struts.xml文件中配置Action时,struts2提供的spring插件允许指定class属性时,不再指定Action的实际实现类,而是指定为spring容器中的Bean ID。这样strust2不再自己负责创建Action实例,而是直接通过spring容器去获取Action对象。
public class LoginAction extends ActionSupport{
private MyService ms;
public void setMs(MyService ms){
this.ms = ms;
}
}
上面的代码提供了一个MyService组件,并为该组件提供了一个setter方法,通过该setter方法,就可让spring来管理Action和MyService组件的依赖关系,避免了控制器和业务组件之间的硬编码耦合。
spring容器为控制器注入业务逻辑组件,这也是spring和struts2整合的关键所在。
struts.xml
<package name="" extends="struts-default">
<action name="login" class="loginAction">
<result name="success">/WEB-INF/content/success.jsp</result>
</action>
</package>
applicationContext.xml
<beans>
<bean id="myService" class=""/>
<bean id="loginAction" class="com.hyq.action.LoginAction" scope="prototype" p:ms-ref="myService"/>
</beans>
当spring管理struts2的Action时,一定要配置scope属性为prototype,因为Action里包含了请求的状态信息,必须为每个请求对应一个Action。
3.使用自动装配
在自动装配策略下,Action还是由spring插件创建,spring插件在创建Action实例时,利用spring的自动装配策略,将对应的业务逻辑组件注入Action实例中。
所谓自动装配,即让spring自动管理Bean与Bean之间的依赖关系,无须使用ref显示指定依赖Bean。
通过设置struts.objectFactory.spring.autoWire常量可以改变spring插件的自动装配策略,默认使用按byName自动装配。
struts.xml
<package name="" extends="struts-default">
<action name="login" class="com.hyq.action.LoginAction">
<result name="success">/WEB-INF/content/success.jsp</result>
</action>
</package>
applicationContext.xml
<!-- 定义一个业务逻辑组件,实现类MyServiceImopl.此处的id必须与Action的setter方法名对应-->
<bean id="ms" class="com.hyq.service.MyServiceImpl"/>
因为在配置业务逻辑组件时,指定了该业务逻辑组件的id为ms,所以spring插件可以在创建Action实例时将该业务逻辑组件注入给Action实例。