EntityManager + #Transactional - spring

#Service
#Repository
#Transactional
public class VideoService {
#PersistenceContext
EntityManager entityManager;
public void save(Video video) {
Video video1 = new Video();
entityManager.persist(video1);
}
<persistence xmlns="http://java.sun.com/xml/ns/persistence" version="1.0">
<persistence-unit name="video_pu" transaction-type="RESOURCE_LOCAL" >
<provider>org.hibernate.ejb.HibernatePersistence</provider>
<properties>
<property name="hibernate.hbm2ddl.auto" value="create-drop" />
<property name="hibernate.dialect" value="org.hibernate.dialect.MySQLDialect" />
</properties>
</persistence-unit>
</persistence>
<bean id="dataSource"
class="org.springframework.jdbc.datasource.DriverManagerDataSource">
<property name="driverClassName" value="com.mysql.jdbc.Driver" />
<property name="url" value="jdbc:mysql://localhost/video" />
<property name="username" value="root" />
<property name="password" value="root" />
</bean>
<bean id="entityManagerFactory" class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
<property name="persistenceUnitName" value="video_pu"/>
<property name="dataSource" ref="dataSource" />
<property name="jpaVendorAdapter">
<bean class="org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter">
<property name="showSql" value="true" />
<property name="generateDdl" value="true" />
<property name="databasePlatform" value="org.hibernate.dialect.MySQLDialect" />
</bean>
</property>
</bean>
<bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager">
<property name="entityManagerFactory" ref="entityManagerFactory"/>
</bean>
<!-- enable the configuration of transactional behavior based on annotations -->
<tx:annotation-driven transaction-manager="transactionManager"/>
<!-- post-processors for all standard config annotations -->
<context:annotation-config/>
The transaction in service method save(Video video) is never started so also never commited. Where is the error? When I use EntityManagerFactory it works perfectly, but I don't want to explicitly begin and commit transaction. I want to use it with #Transactional annotation.

#beerbajay is correct, #Transactional will need a dynamic proxy to be created on your bean to apply the transactional logic, which can be created if your Service has an interface, since in your case it doesn't an alternate would be to instruct Spring to create class based proxy, the following way:
<tx:annotation-driven transaction-manager="transactionManager" proxy-target-class='true/>

Related

entitymanagerfactory is closed after refreshing ConfigurableApplicationContext

I'm building a web application using Spring MVC. I've been trying to come up with a way to customise some system properties and reload the web application without restarting the Tomcat server.
Currently, I'm doing this task by using refresh() method in ConfigurableApplicationContext and its working at the moment.
#Autowired
ConfigurableApplicationContext configurableApplicationContext;
..
public void reloadConfigurations() {
configurableApplicationContext.refresh();
}
However, if the user logs out after refreshing the system, then after that he will not able to login to the system again.
Here's the message I get as SPRING_SECURITY_LAST_EXCEPTION :
entitymanagerfactory is closed; nested exception is
java.lang.illegalstateexception: entitymanagerfactory is closed.
Can't see any other errors in system logs or tomcat log.
Here's the code
application-cotext.xml
<bean id="mysqlDataSource" class="org.springframework.jdbc.datasource.DriverManagerDataSource">
<property name="driverClassName" value="com.mysql.jdbc.Driver" />
<property name="url" value="${jdbc.url}"/>
<property name="username" value="${jdbc.username}"/>
<property name="password" value="${jdbc.password}"/>
</bean>
<bean id="entityManagerFactory"
class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean" destroy-method="destroy">
<property name="dataSource" ref="mysqlDataSource" />
<property name="persistenceUnitName" value="myAppMySql" />
<property name="packagesToScan" value="com.myApp.model" />
</bean>
<bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager">
<property name="entityManagerFactory" ref="entityManagerFactory" />
</bean>
persistence.xml
<persistence-unit name="myAppMySql" transaction-type="RESOURCE_LOCAL">
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
<class>com.myApp.model.SystemConfig</class>
<class>com.myApp.model.User</class>
<properties>
<property name="hibernate.dialect" value="org.hibernate.dialect.MySQL5InnoDBDialect"/>
<property name="hibernate.hbm2ddl.auto" value="update"/>
<property name="hibernate.show_sql" value="false"/>
<property name="hibernate.connection.pool_size" value="5"/>
<property name="hibernate.c3p0.min_size" value="5"/>
<property name="hibernate.c3p0.max_size" value="10"/>
</properties>
</persistence-unit>
Any ideas?? Thanks in advance

Spring 4 Jpa Hibernate - Can't Inject EntityManager

I guess I have the same problem as many people, but unsolved on most of cases. I will try anyway, hope you guys can help me.
The problem is in my repository when I try to inject que Entity Manager using #persistenceContext annotation and always comes null.
The stack:
Spring 4.2.5
Spring Data 1.10.1
Hibernate 5
This is my xml for Sprint data:
<bean id="entityManagerFactory" class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
<property name="dataSource" ref="dataSource" />
<property name="persistenceUnitName" value="conquerPU"/>
<property name="persistenceXmlLocation" value="classpath:META-INF/persistence.xml" />
<property name="packagesToScan" value="com.conquer.module" />
<property name="jpaVendorAdapter">
<bean class="org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter" />
</property>
<property name="jpaProperties">
<props>
<prop key="hibernate.hbm2ddl.auto">update</prop>
<prop key="hibernate.dialect">org.hibernate.dialect.PostgreSQL82Dialect</prop>
</props>
</property>
</bean>
<bean id="dataSource" class="org.springframework.jdbc.datasource.DriverManagerDataSource">
<property name="driverClassName" value="org.postgresql.Driver" />
<property name="url" value="jdbc:postgresql://localhost:5432/conquer" />
<property name="username" value="app" />
<property name="password" value="10203040" />
</bean>
<bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager">
<property name="entityManagerFactory" ref="entityManagerFactory" />
</bean>
<tx:annotation-driven />
<bean id="persistenceExceptionTranslationPostProcessor" class="org.springframework.dao.annotation.PersistenceExceptionTranslationPostProcessor" />
<jpa:repositories base-package="com.conquer.module" entity-manager-factory-ref="entityManagerFactory" transaction-manager-ref="transactionManager"/>
This is my application context.xml
<context:annotation-config/>
<context:component-scan base-package="com">
<context:include-filter type="aspectj" expression="com.*" />
</context:component-scan>
<!-- a HTTP Session-scoped bean exposed as a proxy -->
<bean id="sessionData" class="com.conquer.common.SessionData" scope="session">
<aop:scoped-proxy/>
</bean>
<!--Hibernate persistence interceptor - Used for audit data-->
<bean id="hibernateInterceptor" class="com.conquer.module.security.interceptor.HibernateInterceptor"></bean>
<!--Application Context to be used anywhere-->
<bean id="applicationContextProvder" class="com.conquer.common.ApplicationContextProvider"/>
<!-- SpringMVC -->
<import resource="spring-mvc.xml"/>
<!-- SpringData -->
<import resource="spring-jpa.xml"/>
<!-- SpringSecurity -->
<import resource="spring-security.xml"/>
This is my repository
#Repository
#Transactional
public class BaseRepositoryImpl<T, ID extends Serializable> implements BaseRepository<T, ID> {
#PersistenceContext
public EntityManager em;
public RepositoryFactorySupport baseFactory;
public BaseRepository<T, ID> baseRepository;
public BaseRepositoryImpl() {
System.out.println("BASE REPOSITORY RUNNING...");
this.baseFactory = new JpaRepositoryFactory(em);
this.baseRepository = this.baseFactory.getRepository(BaseRepository.class);
}
// Implementations here ...
}
This is my persistence.xml
<?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="conquerPU" transaction-type="RESOURCE_LOCAL">
<provider>org.hibernate.ejb.HibernatePersistence</provider>
<properties>
<property name="hibernate.dialect" value="org.hibernate.dialect.PostgreSQL82Dialect"/>
<property name = "hibernate.show_sql" value = "true" />
<property name="hibernate.hbm2ddl.auto" value="update"/>
<property name="hibernate.ejb.interceptor" value="com.conquer.module.security.interceptor.HibernateInterceptor"/>
</properties>
</persistence-unit>
</persistence>
Although this question is quite old, we faced with this problem as well and solved it by adding this bean to our application context:
<bean class="org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor"/>
The documentation for context:annotation-config clearly states that this should not be necessary, but in our case it was (albeit we use Spring 4.2 inside Eclipse Virgo 3.7 with Gemini Blueprint, so this setup is probably far from mainstream).

Spring/Hibernate JPA NamedQuery not found

I have a weird issue: entity manager can't create named query, I'm getting java.lang.IllegalArgumentException: Named query not found while methods, like find() and merge(), works. createQuery() also works. I'm using Hibernate as JPA provider and Spring as DI container. Code and configs are follows:
spring-beans.xml:
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context"
xmlns:tx="http://www.springframework.org/schema/tx"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-2.5.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context.xsd
http://www.springframework.org/schema/tx
http://www.springframework.org/schema/tx/spring-tx-3.0.xsd">
<context:component-scan base-package="org.example.testapp.database" />
<bean id="newsForm" class="org.example.testapp.presentation.form.NewsForm">
<property name="newsMessage" ref="news" />
<property name="newsList">
<list>
<ref bean="news" />
</list>
</property>
</bean>
<bean name="news" class="org.example.testapp.model.News">
</bean>
<bean name="/news" class="org.example.testapp.presentation.action.NewsAction"
scope="prototype">
<property name="dao" ref="dao" />
</bean>
<bean id="dao" class="org.example.testapp.database.dao.JpaHibernateNewsDao"
scope="singleton">
</bean>
<bean id="entityManagerFactory"
class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
<property name="dataSource" ref="dataSource" />
<property name="packagesToScan" value="org.example.testapp.model"/>
<property name="jpaVendorAdapter" ref="jpaVendorAdapter" />
</bean>
<bean id="jpaVendorAdapter"
class="org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter">
<property name="database" value="ORACLE" />
<property name="showSql" value="true" />
<property name="generateDdl" value="false" />
<property name="databasePlatform" value="org.hibernate.dialect.Oracle10gDialect" />
</bean>
<bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource">
<property name="driverClassName" value="oracle.jdbc.driver.OracleDriver" />
<property name="url" value="jdbc:oracle:thin:#localhost:1521:xe" />
<property name="username" value="login" />
<property name="password" value="password" />
</bean>
<bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager">
<property name="dataSource" ref="dataSource" />
<property name="entityManagerFactory" ref="entityManagerFactory" />
</bean>
<context:annotation-config/>
<tx:annotation-driven transaction-manager="transactionManager" />
news.java
#Entity
#NamedQueries({
#NamedQuery(name="News.select", query="select n from News n order by news_date" ),
#NamedQuery(name="News.delete", query="delete from News where id in :value_list")
})
#Table(name="news")
public class News {
jpadao.java
public class JpaHibernateNewsDao implements Dao {
#PersistenceContext
private EntityManager entityManager;
#SuppressWarnings("unchecked")
#Override
#Transactional
public List<News> getList() throws DaoException {
List<News> news = entityManager.createNamedQuery("News.select").getResultList();
return news;
}
Found a answer: Spring just didn't see #Entity, so there was really no such #NamedQuery. Now I have to figure, why this config didn't work:
<bean id="entityManagerFactory"
class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
<property name="dataSource" ref="dataSource" />
<property name="packagesToScan" value="org.example.testapp.model"/>
<property name="jpaVendorAdapter" ref="jpaVendorAdapter" />

Spring JPA/Hibernate in standalone app

I am utilizing spring in non web application and I am using hibernate for working with DB. Problem I am experiencing is that while "registerShutdownHook();" does close spring context container it does not properly shut down and close resources for JPA so my connections to DB are getting maxed out.
<bean id="entityManagerFactory" class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
<property name="dataSource" ref="dataSource" />
<property name="persistenceUnitName" value="pu" />
<property name="jpaVendorAdapter">
<bean class="org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter">
<property name="generateDdl" value="false" />
<property name="showSql" value="false" />
<property name="databasePlatform" value="org.hibernate.dialect.MySQL5Dialect" />
</bean>
</property>
</bean>
<bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager">
<property name="entityManagerFactory" ref="entityManagerFactory"/>
</bean>
<tx:annotation-driven transaction-manager="transactionManager"/>
<bean class="org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor" />
<bean class="org.springframework.dao.annotation.PersistenceExceptionTranslationPostProcessor"/>
I use configuration presented above to fire up JPA layer and use "#Transactional" annotations to inject EM's into DAO's.
Maybe someone could help me out what am I missing or how should I handle proper closing of JPA sessions in standalone environment ?
Thank you,
P.S. Exception I am getting is: java.net.SocketException: No buffer space available (maximum connections reached?): connect
1.Create transaction manager as follow :
<bean id="entityManagerFactory" class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean" >
<property name="persistenceUnitName" value="persistanceUnit"/>
<property name="dataSource" ref="dataSource"/>
<property name="persistenceXmlLocation" value="classpath:persistence.xml"/>
<property name="jpaVendorAdapter">
<bean class="org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter">
<property name="showSql" value="${db.orm.showsql}" />
<property name="generateDdl" value="${db.orm.generateDdl}" />
<property name="database" value="${db.type}"/>
<property name="databasePlatform" value="${db.orm.dialect}" />
</bean>
</property>
<property name="jpaProperties">
<props>
<prop key="hibernate.hbm2ddl.auto">create</prop>
</props>
</property>
</bean>
2.use persistance.xml(should be in classpath)
<?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="persistanceUnit" transaction-type="RESOURCE_LOCAL">
<description>Oracle db Persistence Unit</description>
<class>com.company.YourModelClass</class>
<properties/>
</persistence-unit>
</persistence>
3.Add following annotation in applicationContext.xml
<context:component-scan base-package="com.yourcompany.basepackage" />
4.annoatate your Entitymanager in service class like:
#PersistenceContext
private EntityManager em = null;
5.Inject TrasnsactionManager to :
private PlatformTransactionManager platformTransactionManager = null;
6.persist object like:
platformTransactionManager .persist(obj);
This is another example of application Context.xml with JPA. It works fine for me.
<context:property-placeholder location=”classpath:jdbc.properties”/>
<!– Connection Pool –>
<bean id=”dataSource” destroy-method=”close”>
<property name=”driverClass” value=”${jdbc.driverClass}”/>
<property name=”jdbcUrl” value=”${jdbc.url}”/>
<property name=”user” value=”${jdbc.username}”/>
<property name=”password” value=”${jdbc.password}”/>
</bean>
<!– JPA EntityManagerFactory –>
<bean id=”entityManagerFactory”
p:dataSource-ref=”dataSource”>
<property name=”jpaVendorAdapter”>
<bean>
<property name=”database” value=”${jdbc.database}”/>
<property name=”showSql” value=”${jdbc.showSql}”/>
</bean>
</property>
</bean>
<!– Transaction manager for a single JPA EntityManagerFactory (alternative to JTA) –>
<bean id=”transactionManager”
p:entityManagerFactory-ref=”entityManagerFactory”/>
<!– Activates various annotations to be detected in bean classes for eg #Autowired–>
<context:annotation-config/>
<!– enable the configuration of transactional behavior based on annotations –>
<tx:annotation-driven transaction-manager=”transactionManager”/>
<!– Property Configurator –>
<bean id=”propertyConfigurer”>
<property name=”location” value=”jdbc.properties”/>
</bean>
<context:component-scan base-package=”com.test.dao”/>
</beans>

entitymanager is null on DAO class

I am trying to implement Spring MVC 3 +EclipseLink JPA 2
When I call saveUser for example it returns that
NullPointerException, EntityManager is
null
:
public class UserDAO {
#PersistenceContext
private EntityManager em;
public void setEntityManager(EntityManager em) {
this.em = em;
}
#Transactional
public User saveUser(User user){
return em.merge(user);
}
My config is:
<bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager">
<property name="entityManagerFactory" ref="entityManagerFactory" />
<property name="dataSource" ref="dataSource"></property>
</bean>
<bean id="entityManagerFactory"
class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
<property name="dataSource" ref="dataSource" />
<property name="persistenceUnitName" value="application" />
<property name="jpaVendorAdapter">
<bean
class="org.springframework.orm.jpa.vendor.EclipseLinkJpaVendorAdapter">
<property name="showSql" value="true" />
<property name="databasePlatform" value="org.eclipse.persistence.platform.database.MySQLPlatform" />
<property name="generateDdl" value="false" />
</bean>
</property>
<property name="loadTimeWeaver">
<bean
class="org.springframework.instrument.classloading.SimpleLoadTimeWeaver" />
</property>
</bean>
<bean id="dataSource"
class="org.springframework.jdbc.datasource.DriverManagerDataSource">
<property name="username" value=".." />
<property name="password" value=".." />
<property name="driverClassName" value="com.mysql.jdbc.Driver" />
<property name="url"
value="jdbc:mysql://..." />
</bean>
Also have
<context:component-scan base-package="com.elasticbeanstalk.mypackage" />
<context:annotation-config />
It does initialize JPA during Tomcat startup. Why am I see NPE? Could I miss something?
If you instantiate the UserDAO manually, nothing will be injected by Spring. If the DAO is in a package which is under your base-package of <context:component-scan ../> then you can simply autowire it into your Controller. If not, either modify the base-package or also you can define the DAO in the appcontext manually, then you can autowire as well.

Resources