I want to persist a JPA entity to a MySQL database using JTA (container managed transactions) with EclipseLink on a Glassfish 3.1.2 application server. However, this is not working at all. The EclipseLink log shows that SELECT queries are executed correctly and that sequences are also updated. But no INSERT queries are executed after persist()
has been called.
EclipseLink logging:
persist() operation called on: my.package.name.MyEntity@d39a7b6.
TX beginTransaction, status=NO_TRANSACTION
TX Internally starting
external transaction has begun internally
Connection acquired from connection pool [default].
Execute query DataModifyQuery(name="SEQUENCE" sql="UPDATE SEQUENCE SET SEQ_COUNT = SEQ_COUNT + #PREALLOC_SIZE WHERE SEQ_NAME = #SEQ_NAME")
reconnecting to external connection pool
UPDATE SEQUENCE SET SEQ_COUNT = SEQ_COUNT + ? WHERE SEQ_NAME = ?
bind => [50, SEQ_GEN]|#]
Execute query ValueReadQuery(name="SEQUENCE" sql="SELECT SEQ_COUNT FROM SEQUENCE WHERE SEQ_NAME = #SEQ_NAME")
SELECT SEQ_COUNT FROM SEQUENCE WHERE SEQ_NAME = ?
bind => [SEQ_GEN]
local sequencing preallocation for SEQ_GEN: objects: 50 , first: 14.501, last: 14.550
Connection released to connection pool [default].
TX commitTransaction, status=STATUS_ACTIVE
TX Internally committing
So I can see the sequence updates in the MySQL database, but the table associated with MyEntity
remains empty.
Here is my entity class:
@Entity
@Table(name = "my_entity")
public class MyEntity implements Serializable, Cloneable {
@Id
@GeneratedValue
protected long id;
// (..) more fields
}
I'm using Java based Spring Configuration regarding the EntityManager, as follows:
@Configuration
public class EntityManagerConfiguration {
@Bean
public EntityManagerFactory entities() throws Exception {
LocalContainerEntityManagerFactoryBean theEntityManager = new LocalContainerEntityManagerFactoryBean();
theEntityManager.setPackagesToScan(MyEntity.class.getPackage().getName());
theEntityManager.setJtaDataSource(dataSource());
theEntityManager.setPersistenceUnitName("entities");
theEntityManager.setJpaVendorAdapter(jpaVendorAdapter());
theEntityManager.setJpaProperties(jpaProperties());
theEntityManager.afterPropertiesSet();
return theEntityManager.getNativeEntityManagerFactory();
}
@Bean
public Properties jpaProperties() {
Properties props = new Properties();
props.setProperty("eclipselink.ddl-generation", "create-tables");
props.setProperty("eclipselink.weaving", "false");
props.setProperty("eclipselink.logging.level", "FINEST");
props.setProperty("eclipselink.logging.parameters", "true");
props.setProperty("eclipselink.target-server", "SunAS9");
return props;
}
@Bean
public DataSource dataSource() throws Exception {
return (DataSource) JNDIUtils.getLocalJNDIResource("jdbc/entitiesDB");
}
@Bean
public JpaVendorAdapter jpaVendorAdapter() {
EclipseLinkJpaVendorAdapter theVendorAdapter = new EclipseLinkJpaVendorAdapter();
theVendorAdapter.setDatabase(Database.MYSQL);
return theVendorAdapter;
}
@Bean
public PlatformTransactionManager platformTransactionManager(){
return new JtaTransactionManager();
}
}
Note that persistence.xml
is not needed any more when using the setPackagesToScan()
method.
And finally, the code that calls the persist()
method:
@Repository
public class EntityRepository {
@PersistenceContext(unitName = "entities")
private EntityManager entityManager;
public void persist(MyEntity myEntity) {
entityManager.persist(myEntity);
}
}
I have read many similar questions on SO, but none of them seem to reflect my problem precise enough to be able to solve it. What am I missing here?