springboot 配置双数据源

springboot 配置双数据源[编程语言教程]

spring boot 链接两个数据源,操作两个数据库

本文章使用的是持久化框架为JPA,所以数据源也是基于JPA。采用的是SpringBoot2 + SpringDataJPA + MySQL + 双数据源!

 

一、双数据源的适用场景:

1、主从库分离(数据库读写分离)

2、数据迁移

3、系统版本升级,数据库升级到另外一款

 

二、application.properties中配置

#mysql数据源
spring.datasource.one.type= com.alibaba.druid.pool.DruidDataSource
spring.datasource.one.jdbc-url= jdbc:mysql://localhost:3306/hongtianyu_sync?useSSL=false&serverTimezone=Asia/Shanghai
spring.datasource.one.username= root
spring.datasource.one.password= root
spring.datasource.one.driver-class-name= com.mysql.cj.jdbc.Driver
#spring.datasource.one.database:mysql
#sqlserver数据源
#spring.datasource.two.type=com.alibaba.druid.pool.DruidDataSource
spring.datasource.two.jdbc-url = jdbc:mariadb://192.168.7.22:3309/power?useSSL=false&serverTimezone=Asia/Shanghai
spring.datasource.two.username = zhongfu
spring.datasource.two.password = zhongfu
spring.datasource.two.driver-class-name = org.mariadb.jdbc.Driver

 

 

三、读取application.properties配置的两个数据源,并将其注入到Spring的IOC容器中

 

@Configuration
public class DataSourceConfig {
?
   /**
    *
    * @return
    * @explains mysql 数据源
    */
   @Primary
   @Bean(name = "oneDataSource")
   @Qualifier(value = "oneDataSource")
   @ConfigurationProperties(prefix = "spring.datasource.one")
   public DataSource mysqlDataSource() {
       return DataSourceBuilder.create().build();
  }
   
   /**
    *
    * @return
    * @explains mariaDB数据源
    */
   @Bean(name = "twoDataSource")
   @Qualifier(value = "twoDataSource")
   @ConfigurationProperties(prefix = "spring.datasource.two")
   public DataSource mariaDataSource() {
       return DataSourceBuilder.create().build();
  }
}

注解解释:

@Configuration:SpringBoot启动将该类作为配置类,同配置文件一起加载

@Bean:将该实体注入到IOC容器中

@Qualifier:指定数据源名称,与Bean中的name属性原理相同,主要是为了确保注入成功

@Primary:指定主数据源

@ConfigurationProperties:将配置文件中的数据源读取到方法中,进行build

 

 

四、以类的方式配置两个数据源

 

(1)主数据源(对应DataSourceConfig类中的oneDataSource)

@Configuration
@EnableTransactionManagement
@EnableJpaRepositories(
entityManagerFactoryRef = "entityManagerFactoryOne",//EntityManagerFactory引用
transactionManagerRef = "transactionManagerOne",//transactionManager引用
basePackages = {"com.diyuan.sync.dao"}) //设置oneDataSource应用到的包,设置DAO接口层所在包位置
public class OneDataSourceConfig {
/**
* @explains 注入mysql数据源
*/
@Autowired
@Qualifier("oneDataSource")
private DataSource oneDataSource;
/**
* @explains 注入jpa配置实体
*/
@Autowired
private JpaProperties jpaProperties;
@Autowired
   private HibernateProperties hibernateProperties;

@Primary
@Bean(name = "entityManagerOne")
public EntityManager entityManager(EntityManagerFactoryBuilder builder) {
return entityManagerFactoryOne(builder).getObject().createEntityManager();
}
/**
*
* @param builder
* @return 实体管理工厂
* @explains 配置EntityManagerFactory实体
* packges [email protected]
* persistenceUnit 持久性单元的名称 如果只建立一个EntityManagerFactory 可以省略。如果有多个 则应该给不同的名字
* properties 标准jpa或供应商特定配置的通用属性 这些属性覆盖构造函数中提供的任何值
*/
@Primary
@Bean(name = "entityManagerFactoryOne")
public LocalContainerEntityManagerFactoryBean entityManagerFactoryOne(EntityManagerFactoryBuilder builder) {
return builder
.dataSource(oneDataSource)
.properties(getVendorProperties())//获取jpa配置
//.properties(hibernateProperties.determineHibernateProperties(getVendorProperties2(oneDataSource), new HibernateSettings()))
.packages("com.diyuan.sync.model")//设置实体类所在位置
.persistenceUnit("onePersistenceUnit")//持久化单位名称
//.persistenceUnit("primaryPersistenceUnit")
.build();
}
/**
*
* @return
* @explains
*/
// private Map<String, String> getVendorProperties2(DataSource dataSource){
// jpaProperties.setDatabase(Database.MYSQL);
// Map<String, String> map = new HashMap<>();
// map.put("hibernate.dialect", "org.hibernate.dialect.MySQL5Dialect");
// map.put("hibernate.hbm2ddl.auto", "update");
// map.put("hibernate.physical_naming_strategy", "org.hibernate.boot.model.naming.PhysicalNamingStrategyStandardImpl");
// //jpaProperties.setProperties(map);
// //hibernateProperties.determineHibernateProperties(map, new HibernateSettings());
// return map;
// }
   //获取Properties设置中的jpa设置
private Map<String, Object> getVendorProperties(){
Map<String,Object> ret = hibernateProperties.determineHibernateProperties(
               jpaProperties.getProperties(), new HibernateSettings());
ret.put("hibernate.dialect", "org.hibernate.dialect.MySQL5Dialect");
ret.put("hibernate.cglib.use_reflection_optimizer", "false");
return ret;
}
/**
*
* @param builder
* @return 事务管理器
* @explains 配置事务transactionManager
*/
@Primary
@Bean(name = "transactionManagerOne")
public PlatformTransactionManager transactionManagerPrimary(EntityManagerFactoryBuilder builder) {
return new JpaTransactionManager(entityManagerFactoryOne(builder).getObject());
}
}
?

(2)从(次)数据源

?
@Configuration
@EnableTransactionManagement
@EnableJpaRepositories(
entityManagerFactoryRef = "entityManagerFactoryTwo",
transactionManagerRef = "transactionManagerTwo",
basePackages = {"com.diyuan.sync.transferDao"})
public class TwoDataSourceConfig {
@Resource
@Qualifier("twoDataSource")
private DataSource twoDataSource;
@Resource
private JpaProperties jpaProperties;
@Resource
   private HibernateProperties hibernateProperties;

@Bean(name = "entityManagerTwo")
public EntityManager entityManager(EntityManagerFactoryBuilder builder) {
return entityManagerFactoryTwo(builder).getObject().createEntityManager();
}
@Bean(name = "entityManagerFactoryTwo")
public LocalContainerEntityManagerFactoryBean entityManagerFactoryTwo(EntityManagerFactoryBuilder builder) {
return builder
.dataSource(twoDataSource)
.properties(getVendorProperties())
.packages("com.diyuan.sync.transferModel")
.persistenceUnit("twoPersistenceUnit")
//.persistenceUnit("primaryPersistenceUnit")
.build();
}
private Map<String, Object> getVendorProperties(){
Map<String,Object> ret = hibernateProperties.determineHibernateProperties(
               jpaProperties.getProperties(), new HibernateSettings());
ret.put("hibernate.dialect", "org.hibernate.dialect.MariaDBDialect");
ret.put("hibernate.cglib.use_reflection_optimizer", "false");
return ret;
}
@Bean(name = "transactionManagerTwo")
public PlatformTransactionManager transactionManagerPrimary(EntityManagerFactoryBuilder builder) {
return new JpaTransactionManager(entityManagerFactoryTwo(builder).getObject());
}
}

 

这两个类主要配置每个数据源,包括事务管理器、以及实体管理器等配置。

注:必须要指定DAO接口所在的包以及实体类所在的包。每个数据源主要操作它指定的资源(DAO接口CURD、实体类)

 

 

五、注意点:

1、SpringBoot启动类必须关闭 –程序启动加载的仓库(@EnableJpaRepositories),因为在数据源配置类中已经开启了。如果没有去掉,程序会跑不起来!

2、如果需要对数据源连接的表进行DDL(正向生成表、程序启动动态更新表),需要在PrimaryConfig类中 / SecondaryConfig类中的getVendorProperties()方法中进行手动设置(此教程都已设置好了!)

springboot 配置双数据源

原文:https://www.cnblogs.com/xiaomodaydayup/p/15135787.html

hmoban主题是根据ripro二开的主题,极致后台体验,无插件,集成会员系统
自学咖网 » springboot 配置双数据源