From 3cc4fb96c1debdf633070acd15bf3257fee32727 Mon Sep 17 00:00:00 2001 From: DOHA Date: Sat, 31 Jan 2015 19:19:29 +0200 Subject: [PATCH] fix jpa multiple db --- spring-jpa/pom.xml | 7 --- .../baeldung/config/MultipleDBJPAConfig.java | 54 ------------------- .../org/baeldung/config/MyJtaPlatform.java | 22 -------- .../org/baeldung/config/ProductConfig.java | 13 +++-- .../java/org/baeldung/config/UserConfig.java | 15 ++++-- .../multiple/model/product/Product.java | 8 +++ .../persistence/multiple/model/user/User.java | 10 ++++ .../persistence-multiple-db.properties | 11 ++++ .../service/JPAMultipleDBTest.java | 34 ++++++++++-- 9 files changed, 81 insertions(+), 93 deletions(-) delete mode 100644 spring-jpa/src/main/java/org/baeldung/config/MultipleDBJPAConfig.java delete mode 100644 spring-jpa/src/main/java/org/baeldung/config/MyJtaPlatform.java create mode 100644 spring-jpa/src/main/resources/persistence-multiple-db.properties diff --git a/spring-jpa/pom.xml b/spring-jpa/pom.xml index 0e55c9988f..8fd41db223 100644 --- a/spring-jpa/pom.xml +++ b/spring-jpa/pom.xml @@ -52,13 +52,6 @@ 1.6.0.RELEASE compile - - - - com.atomikos - transactions-jta - 3.9.3 - diff --git a/spring-jpa/src/main/java/org/baeldung/config/MultipleDBJPAConfig.java b/spring-jpa/src/main/java/org/baeldung/config/MultipleDBJPAConfig.java deleted file mode 100644 index fc0cb8fb8e..0000000000 --- a/spring-jpa/src/main/java/org/baeldung/config/MultipleDBJPAConfig.java +++ /dev/null @@ -1,54 +0,0 @@ -package org.baeldung.config; - -import javax.transaction.TransactionManager; -import javax.transaction.UserTransaction; - -import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.context.annotation.Bean; -import org.springframework.context.annotation.ComponentScan; -import org.springframework.context.annotation.Configuration; -import org.springframework.context.annotation.DependsOn; -import org.springframework.core.env.Environment; -import org.springframework.transaction.PlatformTransactionManager; -import org.springframework.transaction.annotation.EnableTransactionManagement; -import org.springframework.transaction.jta.JtaTransactionManager; - -import com.atomikos.icatch.jta.UserTransactionImp; -import com.atomikos.icatch.jta.UserTransactionManager; - -@Configuration -@ComponentScan({ "org.baeldung.persistence.multiple" }) -@EnableTransactionManagement -public class MultipleDBJPAConfig { - @Autowired - private Environment env; - - public MultipleDBJPAConfig() { - super(); - } - - @Bean(name = "userTransaction") - public UserTransaction userTransaction() { - final UserTransactionImp userTransactionImp = new UserTransactionImp(); - return userTransactionImp; - } - - @Bean(name = "atomikosTransactionManager") - public TransactionManager atomikosTransactionManager() { - final UserTransactionManager userTransactionManager = new UserTransactionManager(); - MyJtaPlatform.transactionManager = userTransactionManager; - - return userTransactionManager; - } - - @Bean(name = "transactionManager") - @DependsOn({ "userTransaction", "atomikosTransactionManager" }) - public PlatformTransactionManager transactionManager() { - final UserTransaction userTransaction = userTransaction(); - - MyJtaPlatform.transaction = userTransaction; - - final TransactionManager atomikosTransactionManager = atomikosTransactionManager(); - return new JtaTransactionManager(userTransaction, atomikosTransactionManager); - } -} diff --git a/spring-jpa/src/main/java/org/baeldung/config/MyJtaPlatform.java b/spring-jpa/src/main/java/org/baeldung/config/MyJtaPlatform.java deleted file mode 100644 index 2d00f782ad..0000000000 --- a/spring-jpa/src/main/java/org/baeldung/config/MyJtaPlatform.java +++ /dev/null @@ -1,22 +0,0 @@ -package org.baeldung.config; - -import javax.transaction.TransactionManager; -import javax.transaction.UserTransaction; - -import org.hibernate.engine.transaction.jta.platform.internal.AbstractJtaPlatform; - -public class MyJtaPlatform extends AbstractJtaPlatform { - - public static TransactionManager transactionManager; - public static UserTransaction transaction; - - @Override - protected TransactionManager locateTransactionManager() { - return transactionManager; - } - - @Override - protected UserTransaction locateUserTransaction() { - return transaction; - } -} diff --git a/spring-jpa/src/main/java/org/baeldung/config/ProductConfig.java b/spring-jpa/src/main/java/org/baeldung/config/ProductConfig.java index d5f582fc20..4853303ae0 100644 --- a/spring-jpa/src/main/java/org/baeldung/config/ProductConfig.java +++ b/spring-jpa/src/main/java/org/baeldung/config/ProductConfig.java @@ -11,14 +11,16 @@ import org.springframework.context.annotation.PropertySource; import org.springframework.core.env.Environment; import org.springframework.data.jpa.repository.config.EnableJpaRepositories; import org.springframework.jdbc.datasource.DriverManagerDataSource; +import org.springframework.orm.jpa.JpaTransactionManager; import org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean; import org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter; +import org.springframework.transaction.PlatformTransactionManager; import com.google.common.base.Preconditions; @Configuration @PropertySource({ "classpath:persistence-multiple-db.properties" }) -@EnableJpaRepositories(basePackages = "org.baeldung.persistence.multiple.dao.product", entityManagerFactoryRef = "productEntityManager", transactionManagerRef = "transactionManager") +@EnableJpaRepositories(basePackages = "org.baeldung.persistence.multiple.dao.product", entityManagerFactoryRef = "productEntityManager", transactionManagerRef = "productTransactionManager") public class ProductConfig { @Autowired private Environment env; @@ -36,8 +38,6 @@ public class ProductConfig { final HibernateJpaVendorAdapter vendorAdapter = new HibernateJpaVendorAdapter(); em.setJpaVendorAdapter(vendorAdapter); final HashMap properties = new HashMap(); - properties.put("hibernate.transaction.jta.platform", MyJtaPlatform.class.getName()); - properties.put("javax.persistence.transactionType", "JTA"); properties.put("hibernate.hbm2ddl.auto", env.getProperty("hibernate.hbm2ddl.auto")); properties.put("hibernate.dialect", env.getProperty("hibernate.dialect")); em.setJpaPropertyMap(properties); @@ -56,4 +56,11 @@ public class ProductConfig { return dataSource; } + @Bean(name = "productTransactionManager") + public PlatformTransactionManager transactionManager() { + final JpaTransactionManager transactionManager = new JpaTransactionManager(); + transactionManager.setEntityManagerFactory(productEntityManagerFactory().getObject()); + return transactionManager; + } + } diff --git a/spring-jpa/src/main/java/org/baeldung/config/UserConfig.java b/spring-jpa/src/main/java/org/baeldung/config/UserConfig.java index d7edcc7072..379e8485ce 100644 --- a/spring-jpa/src/main/java/org/baeldung/config/UserConfig.java +++ b/spring-jpa/src/main/java/org/baeldung/config/UserConfig.java @@ -7,18 +7,21 @@ import javax.sql.DataSource; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; +import org.springframework.context.annotation.Primary; import org.springframework.context.annotation.PropertySource; import org.springframework.core.env.Environment; import org.springframework.data.jpa.repository.config.EnableJpaRepositories; import org.springframework.jdbc.datasource.DriverManagerDataSource; +import org.springframework.orm.jpa.JpaTransactionManager; import org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean; import org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter; +import org.springframework.transaction.PlatformTransactionManager; import com.google.common.base.Preconditions; @Configuration @PropertySource({ "classpath:persistence-multiple-db.properties" }) -@EnableJpaRepositories(basePackages = "org.baeldung.persistence.multiple.dao.user", entityManagerFactoryRef = "userEntityManager", transactionManagerRef = "transactionManager") +@EnableJpaRepositories(basePackages = "org.baeldung.persistence.multiple.dao.user", entityManagerFactoryRef = "userEntityManager", transactionManagerRef = "userTransactionManager") public class UserConfig { @Autowired private Environment env; @@ -36,8 +39,6 @@ public class UserConfig { final HibernateJpaVendorAdapter vendorAdapter = new HibernateJpaVendorAdapter(); em.setJpaVendorAdapter(vendorAdapter); final HashMap properties = new HashMap(); - properties.put("hibernate.transaction.jta.platform", MyJtaPlatform.class.getName()); - properties.put("javax.persistence.transactionType", "JTA"); properties.put("hibernate.hbm2ddl.auto", env.getProperty("hibernate.hbm2ddl.auto")); properties.put("hibernate.dialect", env.getProperty("hibernate.dialect")); em.setJpaPropertyMap(properties); @@ -56,4 +57,12 @@ public class UserConfig { return dataSource; } + @Primary + @Bean(name = "userTransactionManager") + public PlatformTransactionManager transactionManager() { + final JpaTransactionManager transactionManager = new JpaTransactionManager(); + transactionManager.setEntityManagerFactory(userEntityManagerFactory().getObject()); + return transactionManager; + } + } diff --git a/spring-jpa/src/main/java/org/baeldung/persistence/multiple/model/product/Product.java b/spring-jpa/src/main/java/org/baeldung/persistence/multiple/model/product/Product.java index 3db96ed9dc..8490ed397d 100644 --- a/spring-jpa/src/main/java/org/baeldung/persistence/multiple/model/product/Product.java +++ b/spring-jpa/src/main/java/org/baeldung/persistence/multiple/model/product/Product.java @@ -2,8 +2,10 @@ package org.baeldung.persistence.multiple.model.product; import javax.persistence.Entity; import javax.persistence.Id; +import javax.persistence.Table; @Entity +@Table(schema = "spring_jpa_product") public class Product { @Id @@ -41,4 +43,10 @@ public class Product { this.price = price; } + @Override + public String toString() { + final StringBuilder builder = new StringBuilder(); + builder.append("Product [name=").append(name).append(", id=").append(id).append("]"); + return builder.toString(); + } } diff --git a/spring-jpa/src/main/java/org/baeldung/persistence/multiple/model/user/User.java b/spring-jpa/src/main/java/org/baeldung/persistence/multiple/model/user/User.java index 9cdc1fe311..305568bad8 100644 --- a/spring-jpa/src/main/java/org/baeldung/persistence/multiple/model/user/User.java +++ b/spring-jpa/src/main/java/org/baeldung/persistence/multiple/model/user/User.java @@ -1,11 +1,14 @@ package org.baeldung.persistence.multiple.model.user; +import javax.persistence.Column; import javax.persistence.Entity; import javax.persistence.GeneratedValue; import javax.persistence.GenerationType; import javax.persistence.Id; +import javax.persistence.Table; @Entity +@Table(schema = "spring_jpa_user") public class User { @Id @@ -14,6 +17,7 @@ public class User { private String name; + @Column(unique = true, nullable = false) private String email; private int age; @@ -54,4 +58,10 @@ public class User { this.age = age; } + @Override + public String toString() { + final StringBuilder builder = new StringBuilder(); + builder.append("User [name=").append(name).append(", id=").append(id).append("]"); + return builder.toString(); + } } \ No newline at end of file diff --git a/spring-jpa/src/main/resources/persistence-multiple-db.properties b/spring-jpa/src/main/resources/persistence-multiple-db.properties new file mode 100644 index 0000000000..d59956ba03 --- /dev/null +++ b/spring-jpa/src/main/resources/persistence-multiple-db.properties @@ -0,0 +1,11 @@ +# jdbc.X +jdbc.driverClassName=com.mysql.jdbc.Driver +user.jdbc.url=jdbc:mysql://localhost:3306/spring_jpa_user?createDatabaseIfNotExist=true +product.jdbc.url=jdbc:mysql://localhost:3306/spring_jpa_product?createDatabaseIfNotExist=true +jdbc.user=tutorialuser +jdbc.pass=tutorialmy5ql + +# hibernate.X +hibernate.dialect=org.hibernate.dialect.MySQL5Dialect +hibernate.show_sql=false +hibernate.hbm2ddl.auto=create-drop diff --git a/spring-jpa/src/test/java/org/baeldung/persistence/service/JPAMultipleDBTest.java b/spring-jpa/src/test/java/org/baeldung/persistence/service/JPAMultipleDBTest.java index 2937abb4d1..4c6b02ec3d 100644 --- a/spring-jpa/src/test/java/org/baeldung/persistence/service/JPAMultipleDBTest.java +++ b/spring-jpa/src/test/java/org/baeldung/persistence/service/JPAMultipleDBTest.java @@ -1,8 +1,8 @@ package org.baeldung.persistence.service; import static org.junit.Assert.assertNotNull; +import static org.junit.Assert.assertNull; -import org.baeldung.config.MultipleDBJPAConfig; import org.baeldung.config.ProductConfig; import org.baeldung.config.UserConfig; import org.baeldung.persistence.multiple.dao.product.ProductRepository; @@ -12,15 +12,15 @@ import org.baeldung.persistence.multiple.model.user.User; import org.junit.Test; import org.junit.runner.RunWith; import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.dao.DataIntegrityViolationException; import org.springframework.test.context.ContextConfiguration; import org.springframework.test.context.junit4.SpringJUnit4ClassRunner; import org.springframework.test.context.transaction.TransactionConfiguration; import org.springframework.transaction.annotation.Transactional; @RunWith(SpringJUnit4ClassRunner.class) -@ContextConfiguration(classes = { MultipleDBJPAConfig.class, UserConfig.class, ProductConfig.class }) -@Transactional -@TransactionConfiguration(transactionManager = "transactionManager") +@ContextConfiguration(classes = { UserConfig.class, ProductConfig.class }) +@TransactionConfiguration public class JPAMultipleDBTest { @Autowired private UserRepository userRepository; @@ -29,9 +29,11 @@ public class JPAMultipleDBTest { private ProductRepository productRepository; @Test + @Transactional("userTransactionManager") public void whenCreatingUser_thenCreated() { User user = new User(); user.setName("John"); + user.setEmail("john@test.com"); user.setAge(20); user = userRepository.save(user); @@ -39,6 +41,29 @@ public class JPAMultipleDBTest { } @Test + @Transactional("userTransactionManager") + public void whenCreatingUsersWithSameEmail_thenRollback() { + User user1 = new User(); + user1.setName("John"); + user1.setEmail("john@test.com"); + user1.setAge(20); + user1 = userRepository.save(user1); + assertNotNull(userRepository.findOne(user1.getId())); + + User user2 = new User(); + user2.setName("Tom"); + user2.setEmail("john@test.com"); + user2.setAge(10); + try { + user2 = userRepository.save(user2); + } catch (final DataIntegrityViolationException e) { + } + + assertNull(userRepository.findOne(user2.getId())); + } + + @Test + @Transactional("productTransactionManager") public void whenCreatingProduct_thenCreated() { Product product = new Product(); product.setName("Book"); @@ -48,4 +73,5 @@ public class JPAMultipleDBTest { assertNotNull(productRepository.findOne(product.getId())); } + }