Will #PersistenceUnit close my EntityManagerFactory when application is destroyed? - java

If i use the following
#PersistenceUnit(unitName="mongo")
EntityManagerFactory emf;
EntityManager em = emf.createEntityManager();
Will this annotation make sure that the EntityManagerFactory closes gracefully when application is destroyed?

Yes an injected EntityManagerFactory is automatically closed by the container.

Related

How to make default EntityManager bean come from #Primary EntityManagerFactory in Spring project?

Scenario:
I have an application extending another application and so it has 2 DataSource and 2 EntityManagerFactory in it. The first EntityManagerFactory is created for the original application, and the second one is what is created and used in my extension. The application being extended uses many of its own jars and I am not looking at modifying any of the code in the original application's jars.
Bean definitions:
#Bean("em1")
#Primary
#PersistenceContext(unitName = "pc1")
public LocalContainerEntityManagerFactoryBean entityManagerFactory(
#Qualifier("ds1") DataSource dataSource) {
LocalContainerEntityManagerFactoryBean retVal = super.entityManagerFactory();
retVal.setDataSource(myDataSource);
retVal.setJpaProperties(Properties.getJpaProperties());
return retVal;
}
#Bean(name = "em2")
#PersistenceContext(unitName = "pc2")
public LocalContainerEntityManagerFactoryBean entityManagerFactory(
#Qualifier("ds2") DataSource dataSource) {
LocalContainerEntityManagerFactoryBean emf = new LocalContainerEntityManagerFactoryBean();
emf.setDataSource(dataSource);
emf.setPersistenceXmlLocation("classpath:persistence/persistence.xml");
return emf;
}
Issue:
I can successfully get an EntityManager from the second one in my classes by using
#PersistenceContext(unitName = "pc2")
protected EntityManager entityManager;
However when the original application tries to get an EntityManager in one of its libraries by
#Autowired
private EntityManager myEntityManager;
it throws a NoUniqueBeanDefinitionException saying it found 2 beans of type EntityManager
Question:
How can I make my #Primary EntityManagerFactory create an EntityManager that is also used by default? Or what other solution can I do to fix these conflicting beans without modifying the original application?

Attaching JavaSE EntityManager to JTA

I'm working with JBoss Wildfly as an application server on my JPA layer.
For technical requirements i need to get my entity persistence manager using the JavaSE/application managed approach. I. e.:
EntityManagerFactory emf = Persistence.createEntityManagerFactory("idelivery", properties);
EntityManager em = emf.createEntityManager();
MyEntity exUser= new MyEntity();
try{
Context context = new InitialContext();
UserTransaction userTransaction = (UserTransaction)context.lookup("java:comp/UserTransaction");
userTransaction.begin();
em.persist(exUser);
userTransaction.commit();
where in properties i set:
properties.put ("hibernate.dialect", "org.hibernate.dialect.Oracle10gDialect");
properties.put("javax.persistence.provider", "org.hibernate.jpa.HibernatePersistenceProvider");
properties.put("javax.persistence.transactionType", "JTA");
properties.put("javax.persistence.jtaDataSource", dataSourcePath);
The problem, of course, is with the code lines above I cannot bind the entitymanager to the container JTA transaction manager.
So my question is: is there some example or some way I can make the entity manager to join a complicated JTA transaction? I don't know... maybe with a CDI producer the way i can put the entitymanager inside the container context?
In Java EE environment, you may inject EntityManagerFactory and use it to create EntityManager with custom properties. Therefore, instead of
EntityManagerFactory emf = Persistence.createEntityManagerFactory("idelivery", properties);
EntityManager em = emf.createEntityManager();
you should do something like:
// inject emf from container
#PersistenceUnit("idelivery")
private EntityManagerFactory emf;
// and in your method create em with your properties...
EntityManager em = emf.createEntityManager(properties);

Managing Multiple Database Connections

I've been struggling with this problem for days,
Here is the scenario:
I have several databases, one for each of my customers, all of them with the same
structure(same tables and columns), so my application needs to decide at runtime with which one it needs to connect. I'm using JPA2, EclipseLink and EJB3.
My first attempt was to implement a custom EntityManager with all the logic to performs the operations on the right database, then I configured this EntityManager as an Stateless EBJ in order to make it possible to inject it with the #EBJ annotation (as described at this link: http://www.hostettler.net/blog/2012/11/20/multi-tenancy/). I coundn't make it work because it was throwing an exception when trying to inject the EntityManager.
So I decided to try something else, I've created EntityManagerFactory and I passed the
JTA_DATASOURCE to it(after decide at runtime which one to use), so it could connect to the
right database.
Here is the code:
#Stateless
#TransactionManagement(TransactionManagementType.CONTAINER)
public class TestEntDAO {
private EntityManager em;
private EntityManagerFactory emf;
#PostConstruct
public void init() {
em = getEntityManager();
}
public EntityManager getEntityManager() {
Map props = new HashMap();
props.put(PersistenceUnitProperties.TRANSACTION_TYPE, "JTA");
props.put(PersistenceUnitProperties.JTA_DATASOURCE, dataSourceName());
emf = Persistence.createEntityManagerFactory("testePU", props);
em = emf.createEntityManager();
return em;
}
public String dataSourceName(){
if(someCondition){
return "db1";
}else{
return "db2";
}
}
}
This worked perfectly, the only problem is that the transaction is not managed by the
container, so I had to explicitly mark the transaction's boundaries(call begin() and
commit()). I could just use the #PersistenceContext annotation to make it work, but then I
wouldn't have the EntityManagerFactory to pass the datasource.
Does anyone know of a way to use the Container-Managed Transactions(CMT) and still be able
to pass the datasource?
Maybe try to define 3 Data sources and 3 Persistence units.
<persistence-unit name="PU1">
<jta-data-source>jdbc/DS1</jta-data-source>
...
</persistence-unit>
<persistence-unit name="PU2">
<jta-data-source>jdbc/DS2</jta-data-source>
...
</persistence-unit>
<persistence-unit name="PU3">
<jta-data-source>jdbc/DS3</jta-data-source>
...
</persistence-unit>
And inject Entity manager from whatever Persistence unit you want.
#PersistenceContext(unitName = "PU2")
EntityManager em;
This should work, although I didn't test it.

How can I receive the persistence unit name of an EntityManager?

In a Java EE application I am using #PersistenceContext on an EJB3.0 SessionBean to let an EntityManager be autowired.
As I am using multiple Datasources, I want to programmatically determine the autowired PersistenceUnit name of the EntityManager. Any chance?
You can retrieve more than one entity manager in this way:
EntityManagerFactory emf = Persistence.createEntityManagerFactory("name your PU")
EntityManager em = emf.createEntityManager();
...
em.close();
emf.close();
But I do not know if a good solution. Annotation #PersistenceContext allows retrieve only one entity manager. But you may try create one class/stateless bean which will keep more than one PU, and take from him PU which you need. Maybe this little better than use EntityManagerFactory.

Hibernate EntityManagerFactory EntityManager

Can I create an EntityManager from EntityManagerFactory outside a bean. If so, how would I do it?
In a non-managed environment (this is what you mean by outside a bean, right?), then you typically use:
EntityManagerFactory emf = Persistence.createEntityManagerFactory("MyPu");
EntityManager em = emf.createEntityManager();
em.getTransaction().begin()
...
em.getTransaction().commit();
emf.close();
Check the other factory method allowing to pass properties as parameter (they will override any values that may have been configured elsewhere): Persistence.createEntityManagerFactory(String, Map).
See also
Using the Java Persistence API in Desktop Applications
An Introduction to Java Persistence for Client-Side Developers

Categories

Resources