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

Spring笔记――16.Spring与Struts整合

2015-09-06 09:46 435 查看
启动Spring容器对于使用Spring的Web应用,我们无需手动创建Spring容器,而是通过配置文件声明式地创建,所以我们需要在web.xml中配置一下,借助ServletContextListener监听器来完成。该监听器嫩巩固在Web应用启动的时候回调自定义方法,该方法能够可以启动Spring容器。Spring提供了一个ContextLoaderListener,该监听器实现了ServletContextListener接口,它会在创建时自动查找WEB-INF/下的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/daoContext.xml,/WEB-INF/applicationContext.xml</param-value>
</context-param>

<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
Spring会根据指定位置的配置文件创建WebApplicatiContext对象,并保存在Web应用的ServletContext中。获取容器代码:
WebApplicationContext ctx=WebApplicationContextUtils.getWebApplicationContext(servletContext);

MVC框架与Spring整合的思考在轻量级的EE应用中,我们采用工厂模式,将控制器与业务逻辑组件的实现分离,从而提供更好的解耦。在采用工厂模式的访问策略中,所有的业务逻辑组件的创建由工厂负责,业务逻辑组件的运行也由工厂负责,而控制器只需要定位工厂实例即可。为了让action能够访问到Spring的业务逻辑组件,有两种策略:Spring负责管理Action,并利用依赖注入为控制器注入业务逻辑组件。
利用Spring的自动装配,Action将会自动从Spring容器中获取所需的业务逻辑组件。

让Spring管理控制器如果选择这种策略,我们就需要让Srping来管理Action,而不是struts2。核心控制器如何知道调用Spring容器中的Action,而不是自行创建Action实例呢?这里我们需要使用一个插件。在Struts2的lib中有一个struts2-spring-plugin包,这就是整合Srping与Struts2的插件。这个插件提供了一种伪Action。之前我们需要在struts2的配置文件中指明action的实现类,现在我们无需再指定实现类,而是指定Spring容器中的 Bean的ID,这样Struts2就不再自己创建Action,而是通过Spring容器去获得Action对象。下面就来看看一个Spring+Struts2的小程序吧。
文件结构图:


Action如下,省略了set与get方法:
public class LoginAction extends ActionSupport {
private String username;
private String password;
private MyService ms;

@Override
public String execute() throws Exception {
if (ms.validLogin(getUsername(), getPassword()) > 0) {
addActionMessage("successful!");
return SUCCESS;
}
return ERROR;
}
}
MyServiceImple这个业务逻辑组件如下:
public class MyServiceImpl implements MyService {

public int validLogin(String username, String pass) {
// TODO Auto-generated method stub
if (username.equals("cao") && pass.equals("123")) {
return 99;
}
return -1;
}
}
struts.xml如下
<struts>
<package name="cm" extends="struts-default">
<action name="login" class="loginAction">
<result name="success">/WEB-INF/loginpages/success.jsp</result>
<result name="error">/WEB-INF/loginpages/error.jsp</result>
</action>
</package>
</struts>
applicationContext.xml配置如下:
<beans
xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:p="http://www.springframework.org/schema/p"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.1.xsd"> 
<bean id="myService" class="com.cm.basic.MyServiceImpl"/>

<bean id="loginAction" class="com.cm.action.LoginAction" scope="prototype">
<property name="ms" ref="myService"/>
</bean>

</beans>
此外,正如之前所说,我们还需要在web.xml中配置一个listener,还有一个用于指示ApplicationContext.xml位置的常量。虽然这里我们的文件位置是默认搜索位置,但还是给出了常量配置。
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>/WEB-INF/applicationContext.xml</param-value>
</context-param>

<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>

从代码中我们可以看出,struts.xml不再负责生成action,而只保存了一个action在容器中的id。容器中配置了action,表明action由容器负责管理。struts架构的作用仅仅剩下了action与视图之间的连接。不过这种方法也有两个缺点。一个action在struts.xml中配置一次,容器中又配置一次,比较麻烦。另外action的业务逻辑组件接收容器注入,会导致程序可读性降低。

使用自动装配在自动装配策略下,Action还是由Spring插件创建,Spring插件在创建Action实例时,利用Spring的自动装配策略,将对应的业务逻辑组件注入Action实例中。这种整合策略的配置文件简单,但是控制器和逻辑组件耦合又提升到了代码层次,耦合较高。所谓的自动装配,就是让Spring自动管理Bean与Bean之间的依赖关系,无需使用ref属性来指定。通过设置struts.objectFactory.spring.autoWire常量可以改变Spring插件的自动装配策略,可以接受name、type、auto和constructor这几个值,分别对应byName、byTyep等策略。如果按照byName完成自动装配,此时的struts2配置文件与单独使用struts没有任何区别,也是指定action的实现类。而action中的业务逻辑组件的实例变量名必须与容器中的这个逻辑组件bean的id保持一致。只有这样,才能够按照byName的策略注入。不过这种方式也有一些缺点。Action与业务逻辑组件的耦合降低到代码层次,必须在配置文件中配置与Action中实例变量同名的组件bean,而这不利于高层次的解耦。另外action接收Spring容器的自动装配,程序的可读性差。本文出自 “指尖轻飞” 博客,谢绝转载!
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: