繁体   English   中英

PersistenceContext不注入EntityManager

[英]PersistenceContext not injecting EntityManager

尝试通过注释PersistenceContext访问EntityManager时出现NullPointerException

import javax.ejb.Stateless;
import javax.persistence.EntityManager;
import javax.persistence.PersistenceContext;
import javax.persistence.criteria.CriteriaBuilder;
import javax.persistence.criteria.CriteriaQuery;

@Stateless
public class UserService {

    @PersistenceContext(unitName = "jcrdb")
    private EntityManager em;

    ...
}

我的persistence.xml在路径src/main/webapp/META-INF

<?xml version="1.0" encoding="UTF-8"?>
<persistence version="1.0"
    xmlns="http://java.sun.com/xml/ns/persistence" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://java.sun.com/xml/ns/persistence http://java.sun.com/xml/ns/persistence/persistence_1_0.xsd">
    <persistence-unit name="jcrdb" transaction-type="RESOURCE_LOCAL">
        <provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
        <!-- <jta-data-source>jdbc/jcrdb</jta-data-source> -->
        <exclude-unlisted-classes>false</exclude-unlisted-classes>
        <properties>
            <property name="hibernate.show_sql" value="true" />
            <property name="hibernate.format_sql" value="true" />
            <!-- this tell Hibernate to update the DDL when it starts, very useful 
                for development, dangerous in production -->
            <property name="hibernate.hbm2ddl.auto" value="update" />
            <property name="javax.persistence.logging.level" value="INFO" />
            <property name="javax.persistence.jdbc.driver" value="org.postgresql.Driver" />
            <property name="javax.persistence.jdbc.url" value="jdbc:postgresql://127.0.0.1:5432/jcrdb" />
            <property name="javax.persistence.jdbc.user" value="jcr_admin" />
            <property name="javax.persistence.jdbc.password" value="q1w2e3r4" />
            <!-- <property name="tomee.jpa.factory.lazy" value="true" />-->
        </properties>
    </persistence-unit>
</persistence>

User类:

@Entity
@Table(name = "Users")
public class User {

    @Id
    @GeneratedValue(generator = "increment")
    @GenericGenerator(name = "increment", strategy = "increment")
    private int UserId;
    private String alias;
    private String email;
    @OneToOne(fetch = FetchType.LAZY)
    private Person person;
    @OneToMany
    private List<Role> roles;

    public User() {

    }

    // constructor, getters, setters...
}

像这样直接获取EntityManager没问题:

EntityManagerFactory entityManagerFactory = Persistence.createEntityManagerFactory("jcrdb");
em = entityManagerFactory.createEntityManager();

我尝试在码头和tomEE中运行它。

在我看来,ejb-stuff无法正常工作。 我在这里想念什么(这是所有新知识)?

如果持久单元是RESOURCE_LOCAL,则必须使用EntityManagerFactory

@PersistenceUnit    
private EntityManagerFactory emf;

您可以参考问题和答案以获取全部详细信息。

有时发生这种情况是因为Spring没有注册PersistenceAnnotationBeanPostProcessor 要解决此问题,您可以手动定义它,如下所示:

<bean class="org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor"/>

默认的PersistenceAnnotationBeanPostProcessor将由<context:annotation-config/><context:component-scan/> XML标签注册。

您在哪里获取该persistence.xml文件? 我知道如果您在Java中进行配置(而不是XML配置),该如何选择呢?

@Bean
public LocalContainerEntityManagerFactoryBean entityManagerFactoryBean()
{
LocalContainerEntityManagerFactoryBean factory =
new LocalContainerEntityManagerFactoryBean();
factory.setPersistenceXmlLocation(
"classpath:...../persistence.xml"
);
//factory.setPersistenceUnitName("whatever");
factory.setJpaVendorAdapter(new HibernateJpaVendorAdapter());
factory.setDataSource(this.springJpaDataSource());
return factory;
}

您还需要设置数据源:

@Bean
public DataSource springJpaDataSource()
{
DriverManagerDataSource dataSource = new DriverManagerDataSource();
dataSource.setUrl("jdbc:mysql://localhost/ABCXYZ");
dataSource.setUsername("tomcatUser");
dataSource.setPassword("password1234");
return dataSource;
}

另外,您将需要在配置文件上使用@EnableTransactionManagement批注

如果要摆脱persistence.xml并需要在Java中完全进行持久性配置,则需要用以下代码替换上面返回LocalContainerEntityManagerManagerBean的代码:

@Bean
public LocalContainerEntityManagerFactoryBean entityManagerFactoryBean()
{
Map<String, Object> properties = new Hashtable<>();
properties.put("javax.persistence.schema-generation.database.action",
"none");
HibernateJpaVendorAdapter adapter = new HibernateJpaVendorAdapter();
adapter.setDatabasePlatform("org.hibernate.dialect.MySQL5InnoDBDialect");
LocalContainerEntityManagerFactoryBean factory =
new LocalContainerEntityManagerFactoryBean();
factory.setJpaVendorAdapter(adapter);
factory.setDataSource(this.springJpaDataSource());
factory.setPackagesToScan("com.wrox.site.entities");
factory.setSharedCacheMode(SharedCacheMode.ENABLE_SELECTIVE);
factory.setValidationMode(ValidationMode.NONE);
Configuring Persistence in Spring Framework ❘ 605
factory.setJpaPropertyMap(properties);
return factory;
}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM