EntityManagerHolder无法转换为org.springframework.orm.hibernate5.SessionHolder

时间:2018-07-11 21:17:19

标签: spring hibernate spring-boot hibernate-search hibernate-ogm

我正在使用以下代码通过Hibernate配置Spring:

@SpringBootApplication
@Configuration
@EnableTransactionManagement
public class ContextServer {

    @Bean
    public LocalSessionFactoryBean getSessionFactory() {
        LocalSessionFactoryBean sessionFactory = new LocalSessionFactoryBean();

        try {
            sessionFactory.setDataSource(dataSource());
        } catch (NamingException e) {
            e.printStackTrace();
        }
        sessionFactory.setPackagesToScan(new String[] { "org.plugin.database.models" });
        sessionFactory.setHibernateProperties(hibernateProperties());
        // factoryBean.setAnnotatedClasses(User.class, Authorities.class);

        return sessionFactory;
    }

    @Bean
    public DataSource dataSource() throws NamingException {
        return (DataSource) new JndiTemplate().lookup("java:/global/production_gateway");
    }

    private final Properties hibernateProperties() {
        final Properties hibernateProperties = new Properties();
        hibernateProperties.setProperty("hibernate.hbm2ddl.auto", "create-drop");
        hibernateProperties.setProperty("hibernate.dialect", "org.hibernate.dialect.MariaDBDialect");
        hibernateProperties.setProperty("hibernate.show_sql", "true");
        hibernateProperties.setProperty("hibernate.format_sql", "true");

        return hibernateProperties;
    }

    @Bean
    public HibernateTransactionManager getTransactionManager() {
        HibernateTransactionManager transactionManager = new HibernateTransactionManager();
        transactionManager.setSessionFactory(getSessionFactory().getObject());
        return transactionManager;
    }
}

我以这种方式使用工厂:

@Component("authorize")
@Transactional
public class AuthorizeService implements MessageProcessor {

    @Autowired
    SessionFactory sessionFactory;


    @Override
    public void processMessage(.....) {     

        Session session = sessionFactory.getCurrentSession();
    }

但是我得到了例外:

java.lang.ClassCastException: 
org.springframework.orm.jpa.EntityManagerHolder cannot be cast to 
org.springframework.orm.hibernate5.SessionHolder

我找到了以下答案: ClassCastException: org.springframework.orm.jpa.EntityManagerHolder cannot be cast to org.springframework.orm.hibernate5.SessionHolder

Spring 4 + Hibernate 5 = org.springframework.orm.jpa.EntityManagerHolder cannot be cast to org.springframework.orm.hibernate5.SessionHolder

还有其他可以使用的解决方案吗?上面的解决方案是快速的技巧。

1 个答案:

答案 0 :(得分:2)

随着Hibernate 5.2的发布,SessionFactory扩展了EntityManagerFactory接口。这导致SessionFactory也是EntityManagerFactory

在以前的休眠版本中并非如此。

简单的解决方案是将休眠版本降级到<5.2版本,因为Spring 5.0没有解决方案(Spring 5.1中将提供解决方案)。

或者甚至更好的是不要使用普通的SessionFactory并让Spring Boot自动配置EntityManagerFactory(如果检测到休眠,默认情况下完成),然后使用它代替普通的Hibernate。