【问题标题】:No session found for current thread, Spring 3.1 & Hibernate 4未找到当前线程、Spring 3.1 和 Hibernate 4 的会话
【发布时间】:2013-11-19 18:26:12
【问题描述】:

我正在尝试在演示独立应用程序中使用 Spring 委托的 Hibernate 事务,使用 DAO 层服务层强>.

我已经正确设置了配置,并且我已经对 DAO 方法上 @Transactional 注释的使用进行了单元测试工作正常,但是当我将此注释移动到 服务层我得到一个:

org.hibernate.HibernateException: No Session found for current thread

我提供了我的代码中最相关的部分,希望你能给我一个提示以了解这里发生了什么。

applicationContext.xml

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

    <!-- delegat transactions -->
    <bean id="transactionManager"
          class="org.springframework.orm.hibernate4.HibernateTransactionManager">
        <property name="sessionFactory" ref="sessionFactory"/>
    </bean>

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

    <!-- sessionFactory config -->
    <bean id="sessionFactory" class="org.springframework.orm.hibernate4.LocalSessionFactoryBean">
        <property name="dataSource" ref="dataSource"/>        
        <property name="mappingDirectoryLocations">
            <list>  
                 <value>classpath:com/genericdao/hbm</value>
            </list>
        </property>
        <property name="hibernateProperties">
            <props>
                <prop key="hibernate.dialect">org.hibernate.dialect.SybaseAnywhereDialect</prop>
                <!--prop key="hibernate.transaction.factory_class">org.hibernate.transaction.JDBCTransactionFactory</prop--><!-- i tried commenting this line -->                
                <prop key="hibernate.show_sql">true</prop>
                <prop key="hibernate.format_sql">true</prop>                    
                <prop key="hibernate.current_session_context_class">org.springframework.orm.hibernate4.SpringSessionContext</prop><!-- i know this is provided by default -->
            </props>
        </property>
    </bean>

    <bean id="dataSource" class="org.springframework.jdbc.datasource.DriverManagerDataSource">
        ... i provide here configuration
    </bean>                  
</beans>

道层

getSession() 只是执行 sessionFactory.getCurrentSession(); sessionFactoryGenericDaoHibernateImpl 中自动装配

@Repository("userLoginDao")
public class UserLoginDaoImpl extends GenericDaoHibernateImpl<UserLogin, Integer> implements UserLoginDao{            

    @Override
    //@Transactional(readOnly=true) // This works when i unit-test!! But I don't want to use @Transactional here!!
    public List<UserLogin> findAll() {        
        boolean active = TransactionSynchronizationManager.isActualTransactionActive(); // always true if i use @Transactional

        Query query = getSession().createQuery("from UserLogin");

        return (List<UserLogin>) query.list();
    }                  
}

服务层

@Service("pruebaService")
public class PruebaServiceImpl implements PruebaService{

    private static final ApplicationContext ctx;

    static{
        ctx = new ClassPathXmlApplicationContext("applicationContext.xml");
    }   

    /**********************************************************
     * HERE i want to use @Transactional, but it doesn't work because
     * i get the org.hibernate.HibernateException: No Session found for current thread
     * when i test invocation of this method...
     * NOTE: I want to state, that if i uncomment the Dao @Transactional line
     * then this works!!, but as i mentioned before i really don't want to have transactions on DAO methods, just Service Methods!!
     */
    @Override
    @Transactional(readOnly=true) 
    public List<UserLogin> obtenerTodasLasCuentas() {
        UserLoginDao bean = (UserLoginDao) ctx.getBean("userLoginDao");
        List<UserLogin> result = bean.findAll();
        return result;
    }
}

我确实对这个主题进行了搜索,但我找不到合适的输入...希望您能提供帮助...谢谢。

更新:

这是我正在使用的测试相关代码

测试代码

@Test
public void selectTest(){
    pruebaService = (PruebaService) ctx.getBean("pruebaService");            
    Assert.assertNotNull(pruebaService); // This assert is good, so i know service is properly injected            
    List<UserLogin> result = pruebaService.obtenerTodasLasCuentas();            
    Assert.assertNotNull(result); // This line is never reached because of the exception i mentioned!!
}

【问题讨论】:

  • Service类在什么包里?
  • @SotiriosDelimanolis 可能是在正确的轨道上。如果 Spring 没有构建您的 PruebaServiceImpl 类,那么它将看不到 @Transactional 注释并且无法创建必要的方面。
  • @SotiriosDelimanolis @Pace 服务在com.genericdao.service 上,所以实际上它是创建的,它看到@Transactional 因为当我测试TransactionSynchronizationManager.isActualTransactionActive()(DAO findAll 方法)时,它总是评估为真
  • 请告诉我们您在哪里注入或使用 Service 类。
  • 我认为这是因为 base-package="com.genericdao" 。

标签: java spring hibernate


【解决方案1】:

好的,我完成了这项工作,我只是将服务修改为:

@Service("pruebaService")
public class PruebaServiceImpl implements PruebaService{

    private @Autowired UserLoginDao userLoginDao; // injected by Spring when I create the ApplicationContext in my unit-testing class


    @Override
    @Transactional(readOnly=true) 
    public List<UserLogin> obtenerTodasLasCuentas() {        
        List<UserLogin> result = userLoginDao.findAll();
        return result;
    }
}

这是因为误导了两次创建(一次在我的服务中,一次在我的单元测试课程中):

new ClassPathXmlApplicationContext("applicationContext.xml");

如果您还有其他要指出的...我真的很感谢您的 cmets...非常感谢您的帮助

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2015-05-28
    • 2014-01-10
    • 2013-06-21
    • 1970-01-01
    • 2014-08-16
    • 1970-01-01
    • 2015-04-04
    相关资源
    最近更新 更多