2017-03-01 257 views
-2

我有基于Spring的应用程序,我需要让Hibernate工作。所以我得到了启发本教程:A Guide to Hibernate with Spring 4和我创建的java类(我想配置Hibernate XML-以内):使用JPA配置创建Spring bean的空指针异常

package com.mycompany.cmms.web.config; 



import java.util.Properties; 

import javax.persistence.EntityManagerFactory; 
import javax.sql.DataSource; 

import org.springframework.context.annotation.Bean; 
import org.springframework.context.annotation.Configuration; 
import org.springframework.dao.annotation.PersistenceExceptionTranslationPostProcessor; 
import org.springframework.jdbc.datasource.DriverManagerDataSource; 
import org.springframework.orm.jpa.JpaTransactionManager; 
import org.springframework.orm.jpa.JpaVendorAdapter; 
import org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean; 
import org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter; 
import org.springframework.transaction.PlatformTransactionManager; 
import org.springframework.transaction.annotation.EnableTransactionManagement; 

@Configuration 
@EnableTransactionManagement 
public class PersistanceJPAConfig { 


    @Bean 
    public EntityManagerFactory entityManagerFactory() { 
     LocalContainerEntityManagerFactoryBean em = new LocalContainerEntityManagerFactoryBean(); 
     em.setDataSource(dataSource()); 
     em.setPackagesToScan(new String[] { "com.vsb.cmms.domain" }); 

     JpaVendorAdapter vendorAdapter = new HibernateJpaVendorAdapter(); 
     em.setJpaVendorAdapter(vendorAdapter); 
     em.setJpaProperties(additionalProperties()); 

     return em.getObject(); 
    } 

    @Bean 
    public DataSource dataSource(){ 
     DriverManagerDataSource dataSource = new DriverManagerDataSource(); 
     dataSource.setDriverClassName("org.postgresql.Driver"); 
     dataSource.setUrl("jdbc:postgresql://localhost:5432/cmms"); 
     dataSource.setUsername("postgres"); 
     dataSource.setPassword("xxx"); 
     return dataSource; 
    } 



    @Bean 
    public PlatformTransactionManager transactionManager(EntityManagerFactory emf){ 
     JpaTransactionManager transactionManager = new JpaTransactionManager(); 
     transactionManager.setEntityManagerFactory(emf); 

     return transactionManager; 
    } 

    @Bean 
    public PersistenceExceptionTranslationPostProcessor exceptionTranslation(){ 
     return new PersistenceExceptionTranslationPostProcessor(); 
    } 

    Properties additionalProperties() { 
     Properties properties = new Properties(); 
     properties.setProperty("hibernate.hbm2ddl.auto", "create-drop"); 
     properties.setProperty("hibernate.dialect", "org.hibernate.dialect.PostgreSQLDialect"); 
     properties.setProperty("hibernate.query.factory_class", "org.hibernate.hql.internal.classic.ClassicQueryTranslatorFactory"); 
     return properties; 
    } 
} 

但是当我建立并启动我的应用程序,我得到这个错误:

org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'transactionManager' defined in com.vsb.cmms.web.config.PersistanceJPAConfig: Invocation of init method failed; nested exception is java.lang.IllegalArgumentException: 'entityManagerFactory' or 'persistenceUnitName' is required 
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1583) 
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:545) 
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:482) 
at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:306) 
at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:230) 
at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:302) 
at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:197) 
at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:751) 
at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:861) 
at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:541) 
at org.springframework.web.context.ContextLoader.configureAndRefreshWebApplicationContext(ContextLoader.java:444) 
at org.springframework.web.context.ContextLoader.initWebApplicationContext(ContextLoader.java:326) 
at org.springframework.web.context.ContextLoaderListener.contextInitialized(ContextLoaderListener.java:107) 
at org.apache.catalina.core.StandardContext.listenerStart(StandardContext.java:4717) 
at org.apache.catalina.core.StandardContext.startInternal(StandardContext.java:5179) 
at org.apache.catalina.util.LifecycleBase.start(LifecycleBase.java:183) 
at org.apache.catalina.core.ContainerBase$StartChild.call(ContainerBase.java:1404) 
at org.apache.catalina.core.ContainerBase$StartChild.call(ContainerBase.java:1394) 
at java.util.concurrent.FutureTask.run(FutureTask.java:266) 
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142) 
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617) 
at java.lang.Thread.run(Thread.java:745) 
Caused by: java.lang.IllegalArgumentException: 'entityManagerFactory' or 'persistenceUnitName' is required 
at org.springframework.orm.jpa.JpaTransactionManager.afterPropertiesSet(JpaTransactionManager.java:304) 
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.invokeInitMethods(AbstractAutowireCapableBeanFactory.java:1642) 
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1579) 
... 21 more 

错误是说需要'entityManagerFactory'或'persistenceUnitName'。但实体管理器工厂应通过entityManagerFactory()提供。 当我debbuged硫豆我注意到em.getObject()返回null,并可能导致错误,虽然我不知道为什么会发生这种情况。我正在使用Spring 4和Hibernate 5.2.3.Final。

+2

“'entityManagerFactory'或'persistenceUnitName'是必需的”。那不清楚的是什么?你在哪里看到一个NullPointerException? – Tunaki

+0

我注意到,但这个错误是由entityManagerFactory(),因为它返回null导致我的问题是:为什么以及如何解决它。 –

+0

你可以检查用@Entity注解的类是否存在于这个包中com.vsb.cmms.domain – pkoli

回答

0

entityManagerFactory()方法确实不应该叫#getObject()而是你应该写:

@Bean 
public LocalContainerEntityManagerFactoryBean entityManagerFactory() { 
    LocalContainerEntityManagerFactoryBean em = new LocalContainerEntityManagerFactoryBean(); 
    em.setDataSource(dataSource()); 
    em.setPackagesToScan(new String[] { "com.vsb.cmms.domain" }); 

    JpaVendorAdapter vendorAdapter = new HibernateJpaVendorAdapter(); 
    em.setJpaVendorAdapter(vendorAdapter); 
    em.setJpaProperties(additionalProperties()); 

    // just return the bean here 
    return em; 
} 

春处理该工厂bean自动给你EntityManagerFactory实例。

+0

如果我改变它的错误消失但EntityManager或EntityManagerFacotry在我的DAO类中为null。 –

+0

你是用'@ PersistenceContext'注入它吗? – Naros

0

就在互联网的深处发现... 如果你想使XML少Hibernate的配置有机会轻松地控制会话(会话应用程序或会话交易),那么你可能想看看this

请注意,代码,因为它是完美的,直到休眠5.2版本