注入 EntityManager 始终为 null
Injecting EntityManager always null
我正在尝试使用 CDI 将 EntityManager 注入我的应用程序,但在尝试使用它时 EntityManager 为空。
这是我的代码,我遵循了几个关于如何注入 EntityManager 的教程,并且我使用了与那些教程中相同的代码。
@Qualifier
@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.FIELD})
public @interface DevDatabase {
}
@Singleton
public class JPAResourceProducer {
@Produces
@PersistenceContext(unitName = "DevPU")
@DevDatabase
private EntityManager em;
}
persistence.xml
<persistence version="2.1" xmlns="http://xmlns.jcp.org/xml/ns/persistence" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/persistence http://xmlns.jcp.org/xml/ns/persistence/persistence_2_1.xsd">
<persistence-unit name="DevPU" transaction-type="RESOURCE_LOCAL">
<provider>org.hibernate.ejb.HibernatePersistence</provider>
<class>entity.MyEntity</class>
<exclude-unlisted-classes>false</exclude-unlisted-classes>
<properties>
<property name="javax.persistence.jdbc.url" value="jdbc:postgresql://localhost:5432/MyDB"/>
<property name="javax.persistence.jdbc.user" value="appuser"/>
<property name="javax.persistence.jdbc.driver" value="org.postgresql.Driver"/>
<property name="javax.persistence.jdbc.password" value="apppassword"/>
</properties>
</persistence-unit>
</persistence>
这就是我在 DAO 中使用它的方式
public abstract class GenericDAO<T> {
@DevDatabase
@Inject
private EntityManager em;
private final Class<T> entityClass;
public GenericDAO(Class<T> entityClass) {
this.entityClass = entityClass;
}
public void beginTransaction() {
em.getTransaction().begin();
}
}
具体的 DAO
public class MyEntityDAO extends GenericDAO<MyEntity> {
public MyEntityDAO() {
super(MyEntity.class);
}
}
当我调用示例 myEntityDao.beginTransaction()
时,在我的代码中某处,我得到一个 NullPointerException
,因为注入的 EntityManager
为空。
我的制作人有什么遗漏的吗?
@PersistenceContext
在像 tomcat 这样的 servlet 容器中不能开箱即用。它在 Java EE 容器中工作。
因此您的 EntityManager
字段保持为空,因为 @PersistencContext
在 Tomcat 中没有效果,即使使用 Weld-servlet。
您可以添加一个 ServletListener
到 bootstrap JPA 实现,在您的情况下可能是休眠。然后你可以通过@Inject
获得EntityManager
实例。
请注意,您还应该提供一个 JPA 实现(如 hibernate),就像您为 Weld 所做的那样。
您可以尝试这样做:Injecting EntityManager with a producer in tomcat
我正在尝试使用 CDI 将 EntityManager 注入我的应用程序,但在尝试使用它时 EntityManager 为空。
这是我的代码,我遵循了几个关于如何注入 EntityManager 的教程,并且我使用了与那些教程中相同的代码。
@Qualifier
@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.FIELD})
public @interface DevDatabase {
}
@Singleton
public class JPAResourceProducer {
@Produces
@PersistenceContext(unitName = "DevPU")
@DevDatabase
private EntityManager em;
}
persistence.xml
<persistence version="2.1" xmlns="http://xmlns.jcp.org/xml/ns/persistence" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/persistence http://xmlns.jcp.org/xml/ns/persistence/persistence_2_1.xsd">
<persistence-unit name="DevPU" transaction-type="RESOURCE_LOCAL">
<provider>org.hibernate.ejb.HibernatePersistence</provider>
<class>entity.MyEntity</class>
<exclude-unlisted-classes>false</exclude-unlisted-classes>
<properties>
<property name="javax.persistence.jdbc.url" value="jdbc:postgresql://localhost:5432/MyDB"/>
<property name="javax.persistence.jdbc.user" value="appuser"/>
<property name="javax.persistence.jdbc.driver" value="org.postgresql.Driver"/>
<property name="javax.persistence.jdbc.password" value="apppassword"/>
</properties>
</persistence-unit>
</persistence>
这就是我在 DAO 中使用它的方式
public abstract class GenericDAO<T> {
@DevDatabase
@Inject
private EntityManager em;
private final Class<T> entityClass;
public GenericDAO(Class<T> entityClass) {
this.entityClass = entityClass;
}
public void beginTransaction() {
em.getTransaction().begin();
}
}
具体的 DAO
public class MyEntityDAO extends GenericDAO<MyEntity> {
public MyEntityDAO() {
super(MyEntity.class);
}
}
当我调用示例 myEntityDao.beginTransaction()
时,在我的代码中某处,我得到一个 NullPointerException
,因为注入的 EntityManager
为空。
我的制作人有什么遗漏的吗?
@PersistenceContext
在像 tomcat 这样的 servlet 容器中不能开箱即用。它在 Java EE 容器中工作。
因此您的 EntityManager
字段保持为空,因为 @PersistencContext
在 Tomcat 中没有效果,即使使用 Weld-servlet。
您可以添加一个 ServletListener
到 bootstrap JPA 实现,在您的情况下可能是休眠。然后你可以通过@Inject
获得EntityManager
实例。
请注意,您还应该提供一个 JPA 实现(如 hibernate),就像您为 Weld 所做的那样。
您可以尝试这样做:Injecting EntityManager with a producer in tomcat