2013-10-04 3 views
0

Я хочу интегрировать Struts 2, Hibernate и Spring. Я сделал предыдущий пример проекта с Hibernate, Spring, Spring MVC. И все получилось отлично. Теперь я хочу заменить Spring MVC Struts 2. И у меня есть следующая проблема. У меня есть класс LoginAction с полем @Autowired private UserService userService. Класс UserService содержит поле UserDAO поля, которое также аннотируется как Autowired. UserDAO содержит SessionFactory, который тоже аннотируется. Я уверен, что правильность расположений верна. И applicationContext.xml также прав. Потому что, когда я делаю некоторые изменения в этом файле, у меня есть исключения. Tomcat запускается без ошибок и показывает мне страницу входа. Но когда я попытался вызвать методы класса UserService, у меня появился NPE, потому что этот объект имеет значение null. Почему Spring не установил этот объект? Мой код: applicationContext.xml:@Autowired не задает поле -> NullPointerException

<beans xmlns="http://www.springframework.org/schema/beans" 
xmlns:context="http://www.springframework.org/schema/context" 
xmlns:mvc="http://www.springframework.org/schema/mvc" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
xmlns:tx="http://www.springframework.org/schema/tx" 
xsi:schemaLocation=" 
    http://www.springframework.org/schema/beans  
    http://www.springframework.org/schema/beans/spring-beans-3.2.xsd 
    http://www.springframework.org/schema/context 
    http://www.springframework.org/schema/context/spring-context-3.2.xsd 
    http://www.springframework.org/schema/mvc 
    http://www.springframework.org/schema/mvc/spring-mvc-3.2.xsd 
    http://www.springframework.org/schema/tx 
    http://www.springframework.org/schema/tx/spring-tx-3.2.xsd"> 

<tx:annotation-driven transaction-manager="transactionManager" /> 

<context:annotation-config /> 

<context:component-scan base-package="com"/> 

<bean id="userDAO" class="com.example.dao.impl.hibernate.HibernateUserDAO" /> 
<bean id="userService" class="com.example.service.impl.UserServiceImpl" /> 

<bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource" 
    destroy-method="close"> 
    <property name="driverClassName" value="org.h2.Driver" /> 
    <property name="url" value="jdbc:h2:~/database" /> 
    <property name="username" value="user" /> 
    <property name="password" value="user" /> 
</bean> 
<bean name="sessionFactory" 
    class="org.springframework.orm.hibernate3.annotation.AnnotationSessionFactoryBean"> 
    <property name="dataSource" ref="dataSource" /> 
    <property name="annotatedClasses"> 
     <list> 
      <value>com.example.entity.User</value> 
     </list> 
    </property> 
    <property name="hibernateProperties"> 
     <value> 
      hibernate.dialect=org.hibernate.dialect.H2Dialect 
      hibernate.show_sql=true 
     </value> 
    </property> 
</bean> 
<bean id="transactionManager" 
    class="org.springframework.orm.hibernate3.HibernateTransactionManager"> 
    <property name="sessionFactory" ref="sessionFactory" /> 
</bean> 

web.xml

<?xml version="1.0" encoding="UTF-8"?> 
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://java.sun.com/xml/ns/javaee" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd" version="2.5"> 
<welcome-file-list> 
<welcome-file>/WEB-INF/pages/login.jsp</welcome-file> 
</welcome-file-list> 
<listener> 
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class> 
</listener> 
<filter> 
<filter-name>struts2</filter-name> 
    <filter-class> 
      org.apache.struts2.dispatcher.ng.filter.StrutsPrepareAndExecuteFilter 
    </filter-class> 
</filter> 
<filter-mapping> 
    <filter-name>struts2</filter-name> 
    <url-pattern>/*</url-pattern> 
</filter-mapping> 

<context-param> 
<param-name>contextConfigLocation</param-name> 
<param-value> 
     /WEB-INF/applicationContext.xml 
     </param-value> 
</context-param> 
</web-app> 

LoginAction класс:

@Controller 
public class LoginAction extends ActionSupport { 
private String login; 
private String password; 
@Autowired 
private UserService userService; 

@Override 
public String execute() throws Exception { 
    User user = null; 
    try { 
     user = userService.findByLogin(login); 
    } catch (Exception e) { 
     e.printStackTrace(); 
    } 
    if (user != null) { 
     return user.getPassword().equals(password) ? SUCCESS : ERROR; 
    } 
    return ERROR; 
} 
// getters and setters 
} 

UserService класс реализации:

@Service 
public class UserServiceImpl implements UserService { 
@Autowired 
private UserDAO userDAO; 

@Override 
@Transactional 
public User findByLogin(String login) throws SQLException { 
    return userDAO.findByLogin(login); 
} } 

И UserDAO осущ класс:

@Repository 
public class HibernateUserDAO implements UserDAO { 
@Autowired 
public SessionFactory sessionFactory; 
@Override 
public User findByLogin(String login) throws SQLException { 
    return sessionFactory.getCurrentSession().createCriteria(User.class) 
       .add(Restrictions.eq("login", login)).list().get(0); 
} } 

Struts confiration прекрасно, потому что она реагирует правильно. Почему весна не задавала поля? Есть идеи?

<struts> 
<constant name="struts.devMode" value="true" /> 
<package name="default" namespace="/" extends="struts-default"> 
    <action name="login" class="com.example.web.action.LoginAction"> 
     <result name="success">/WEB-INF/pages/cabinet.jsp</result> 
     <result name="error">/WEB-INF/pages/login.jsp</result> 
     <result name="input">/WEB-INF/pages/login.jsp</result> 
    </action> 
</package> 

+2

Использовали ли вы зависимость интеграции интеграции пружин в своем приложении? похоже, что он не работает прямо из коробки, заменив слой весны mvc на слой стойки. – Zeus

+0

Опубликовать файл 'struts.xml'. –

+0

Я отправил его прямо сейчас –

ответ

1

Как @SotiriosDelimanolis сказал, что вы mixing вещи. Вот вы:

  1. удалить @Controller annotaion из классов вашего контроллера.
  2. проверьте, у вас уже есть struts2-spring-plugin в вашем пути к классу. NOTE: Версия плагина должна быть такой же, как ваша версия strut2.
  3. make должен ли вы определить свои весенние бобы в application-context.xml, независимо от явного или дополнительного сканирования компонентов.
  4. проверить, есть ли

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

    определены в вашем web.xml

получайте удовольствие!Вот link из REFERENCE

1

Вы Путаете. Spring создаст контекст, потому что вы объявили ContextLoaderListener, но Struts создаст свой собственный стек классов Action (ActionSupport) из вашего конфигурационного файла struts.xml. Другими словами, он создает свой собственный объект LoginAction.

+0

Вы не можете быть уверены в том, что не увидите 'struts.xml'. –

+0

@AleksandrM Уверен, что? Я могу быть уверен, что 'struts.xml' не может ссылаться на beans внутри Spring' ApplicationContext'. –

+0

@SotiriosDelimanolis Struts2 знает, как создать экземпляр действия из-за его контейнера, но делегирует весну 'BeanFactory', потому что Spring плагин изменяет настройку struts.ObjectFactory. –

0

Вы не используете весенний MVC (не используя сервлет диспетчера в web.xml); но вы пытаетесь использовать аннотации MVC api, такие как @Controller в сервлете Action. Как это должно работать?

+0

Я просто хочу заменить Spring MVC Struts2. И я стараюсь это делать –

+0

Попробуйте использовать @Component вместо @Controller и проверьте, разрешает ли он это. Но я очень сомневаюсь в этом. – pravat

+0

'@ Controller' не является аннотацией Spring MVC, это аннотация для Spring. Тот факт, что Spring MVC используется, не имеет значения. Однако ему нужно объявить свои действия прототипом. –

Смежные вопросы