低调人
2017-11-24 14:36:01
Spring Boot之Web应用使用Spring-data-jpa多数据源配置
对于数据源的配置可以沿用上例Spring Boot学习(七)之Web应用使用jdbctemplate多数据源配置中DataSourceConfig的实现。
新增对第一数据源的JPA配置,注意两处注释的地方,用于指定数据源对应的Entity实体和Repository定义位置,用@Primary区分主数据源。
package com.xiaojingg; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Qualifier; import org.springframework.boot.autoconfigure.orm.jpa.JpaProperties; import org.springframework.boot.orm.jpa.EntityManagerFactoryBuilder; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.context.annotation.Primary; import org.springframework.data.jpa.repository.config.EnableJpaRepositories; import org.springframework.orm.jpa.JpaTransactionManager; import org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean; import org.springframework.transaction.PlatformTransactionManager; import org.springframework.transaction.annotation.EnableTransactionManagement; import javax.persistence.EntityManager; import javax.sql.DataSource; import java.util.Map; /** * 筱进GG */ @Configuration @EnableTransactionManagement @EnableJpaRepositories( entityManagerFactoryRef="entityManagerFactoryPrimary", transactionManagerRef="transactionManagerPrimary", basePackages= { "com.xiaojingg.domain.p" }) //设置Repository所在位置 public class PrimaryConfig { @Autowired @Qualifier("primaryDataSource") private DataSource primaryDataSource; @Primary @Bean(name = "entityManagerPrimary") public EntityManager entityManager(EntityManagerFactoryBuilder builder) { return entityManagerFactoryPrimary(builder).getObject().createEntityManager(); } @Primary @Bean(name = "entityManagerFactoryPrimary") public LocalContainerEntityManagerFactoryBean entityManagerFactoryPrimary (EntityManagerFactoryBuilder builder) { return builder .dataSource(primaryDataSource) .properties(getVendorProperties(primaryDataSource)) .packages("com.xiaojingg.domain.p") //设置实体类所在位置 .persistenceUnit("primaryPersistenceUnit") .build(); } @Autowired private JpaProperties jpaProperties; private Map<String, String> getVendorProperties(DataSource dataSource) { return jpaProperties.getHibernateProperties(dataSource); } @Primary @Bean(name = "transactionManagerPrimary") public PlatformTransactionManager transactionManagerPrimary(EntityManagerFactoryBuilder builder) { return new JpaTransactionManager(entityManagerFactoryPrimary(builder).getObject()); } }
新增对第二数据源的JPA配置,内容与第一数据源类似,具体如下:
package com.xiaojingg; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Qualifier; import org.springframework.boot.autoconfigure.orm.jpa.JpaProperties; import org.springframework.boot.orm.jpa.EntityManagerFactoryBuilder; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.data.jpa.repository.config.EnableJpaRepositories; import org.springframework.orm.jpa.JpaTransactionManager; import org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean; import org.springframework.transaction.PlatformTransactionManager; import org.springframework.transaction.annotation.EnableTransactionManagement; import javax.persistence.EntityManager; import javax.sql.DataSource; import java.util.Map; /** * 筱进GG */ @Configuration @EnableTransactionManagement @EnableJpaRepositories( entityManagerFactoryRef="entityManagerFactorySecondary", transactionManagerRef="transactionManagerSecondary", basePackages= { "com.xiaojingg.domain.s" }) //设置Repository所在位置 public class SecondaryConfig { @Autowired @Qualifier("secondaryDataSource") private DataSource secondaryDataSource; @Bean(name = "entityManagerSecondary") public EntityManager entityManager(EntityManagerFactoryBuilder builder) { return entityManagerFactorySecondary(builder).getObject().createEntityManager(); } @Bean(name = "entityManagerFactorySecondary") public LocalContainerEntityManagerFactoryBean entityManagerFactorySecondary (EntityManagerFactoryBuilder builder) { return builder .dataSource(secondaryDataSource) .properties(getVendorProperties(secondaryDataSource)) .packages("com.xiaojingg.domain.s") //设置实体类所在位置 .persistenceUnit("secondaryPersistenceUnit") .build(); } @Autowired private JpaProperties jpaProperties; private Map<String, String> getVendorProperties(DataSource dataSource) { return jpaProperties.getHibernateProperties(dataSource); } @Bean(name = "transactionManagerSecondary") PlatformTransactionManager transactionManagerSecondary(EntityManagerFactoryBuilder builder) { return new JpaTransactionManager(entityManagerFactorySecondary(builder).getObject()); } }
主数据源配置为spring.datasource.primary开头的配置,第二数据源配置为spring.datasource.secondary开头的配置。
package com.xiaojingg; import org.springframework.beans.factory.annotation.Qualifier; import org.springframework.boot.autoconfigure.jdbc.DataSourceBuilder; import org.springframework.boot.context.properties.ConfigurationProperties; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.context.annotation.Primary; import javax.sql.DataSource; /** * 筱进GG */ @Configuration public class DataSourceConfig { @Bean(name = "primaryDataSource") @Qualifier("primaryDataSource") @ConfigurationProperties(prefix="spring.datasource.primary") public DataSource primaryDataSource() { return DataSourceBuilder.create().build(); } @Bean(name = "secondaryDataSource") @Qualifier("secondaryDataSource") @Primary @ConfigurationProperties(prefix="spring.datasource.secondary") public DataSource secondaryDataSource() { return DataSourceBuilder.create().build(); } }
完成了以上配置之后,主数据源的实体和数据访问对象位于:com.xiaojingg.domain.p,次数据源的实体和数据访问接口位于:com.xiaojingg.domain.s。
分别在这两个package下创建各自的实体和数据访问接口
- 主数据源下,创建User实体和对应的Repository接口
package com.xiaojingg.domain.p; import javax.persistence.Column; import javax.persistence.Entity; import javax.persistence.GeneratedValue; import javax.persistence.Id; /** * 筱进GG */ @Entity public class User { @Id @GeneratedValue private Long id; @Column(nullable = false) private String name; @Column(nullable = false) private Integer age; public User(){} public User(String name, Integer age) { this.name = name; this.age = age; } public Long getId() { return id; } public void setId(Long id) { this.id = id; } public String getName() { return name; } public void setName(String name) { this.name = name; } public Integer getAge() { return age; } public void setAge(Integer age) { this.age = age; } } package com.xiaojingg.domain.p; import org.springframework.data.jpa.repository.JpaRepository; /** * 筱进GG */ public interface UserRepository extends JpaRepository<User, Long> { } 从数据源下,创建Message实体和对应的Repository接口 package com.xiaojingg.domain.s; import javax.persistence.Column; import javax.persistence.Entity; import javax.persistence.GeneratedValue; import javax.persistence.Id; /** * 筱进GG */ @Entity public class Message { @Id @GeneratedValue private Long id; @Column(nullable = false) private String name; @Column(nullable = false) private String content; public Message(){} public Message(String name, String content) { this.name = name; this.content = content; } public Long getId() { return id; } public void setId(Long id) { this.id = id; } public String getName() { return name; } public void setName(String name) { this.name = name; } public String getContent() { return content; } public void setContent(String content) { this.content = content; } } package com.xiaojingg.domain.s; import org.springframework.data.jpa.repository.JpaRepository; /** * 筱进GG */ public interface MessageRepository extends JpaRepository<Message, Long> { }
最后通过测试用例来验证使用这两个针对不同数据源的配置进行数据操作:
package com.xiaojingg; import com.xiaojingg.domain.p.User; import com.xiaojingg.domain.p.UserRepository; import com.xiaojingg.domain.s.Message; import com.xiaojingg.domain.s.MessageRepository; import org.junit.Assert; import org.junit.Before; import org.junit.Test; import org.junit.runner.RunWith; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.test.context.junit4.SpringRunner; /** * 筱进GG */ @RunWith(SpringRunner.class) @SpringBootTest public class SpringbootstudyDemo7SpringDataJpaMoreApplicationTests { @Autowired private UserRepository userRepository; @Autowired private MessageRepository messageRepository; @Before public void setUp() { } @Test public void test() throws Exception { userRepository.save(new User("aaa", 10)); userRepository.save(new User("bbb", 20)); userRepository.save(new User("ccc", 30)); userRepository.save(new User("ddd", 40)); userRepository.save(new User("eee", 50)); Assert.assertEquals(5, userRepository.findAll().size()); messageRepository.save(new Message("o1", "aaaaaaaaaa")); messageRepository.save(new Message("o2", "bbbbbbbbbb")); messageRepository.save(new Message("o3", "cccccccccc")); Assert.assertEquals(3, messageRepository.findAll().size()); } }
运行截图:
完成了!
评论

miaoshi LV16
1月7日
runandrun LV2
2020年8月22日
linguo
2020年8月1日
暂无贡献等级
lewiszz LV2
2020年6月16日
dhb123 LV5
2020年5月19日
已注销用户 LV34
2020年4月1日
yang131221
2020年2月26日
暂无贡献等级
WngYong
2019年12月31日
暂无贡献等级
javaggm LV13
2019年9月20日
gxcrownclown
2019年8月12日
暂无贡献等级