当前位置 博文首页 > RtxTitanV的博客:SpringBoot2.x SpringDataJpa多数据源配置及使

    RtxTitanV的博客:SpringBoot2.x SpringDataJpa多数据源配置及使

    作者:[db:作者] 时间:2021-07-07 12:39

    SpringDataJpa使用单数据源时的SpringBoot配置很简单,但是随着业务量发展,单个数据库可能不能满足我们的业务需求,这时候一般会对数据库进行拆分或引入其他数据库,此时单数据源就不能满足我们的需求,需要配置多个数据源。

    在使用SpringBoot2.x进行SpringDataJpa多数据源配置之前,对SpringBoot2.x集成SpringDataJpa还不熟悉的朋友,可以先参考SpringBoot2.x 集成 SpringDataJpa。下面就开始进行SpringDataJpa多数据源配置及使用,其中SpringBoot使用的2.2.2.RELEASE版本,添加依赖在这里就不再表述了。

    一、编写配置文件

    application.yml中进行如下配置:

    spring:
      # 多数据源数据库连接配置
      datasource:
        # 第一数据源配置
        primary:
          jdbc-url: jdbc:mysql://127.0.0.1:3306/test1?serverTimezone=GMT%2B8&useUnicode=true&characterEncoding=utf8&autoReconnect=true&allowMultiQueries=true
          driver-class-name: com.mysql.cj.jdbc.Driver
          username: root
          password: root
        # 第二数据源配置
        secondary:
          jdbc-url: jdbc:mysql://127.0.0.1:3306/test2?serverTimezone=GMT%2B8&useUnicode=true&characterEncoding=utf8&autoReconnect=true&allowMultiQueries=true
          driver-class-name: com.mysql.cj.jdbc.Driver
          username: root
          password: root
      # jpa相关配置
      jpa:
        database: mysql
        show-sql: true
        generate-ddl: true
        hibernate:
          ddl-auto: update
        database-platform: org.hibernate.dialect.MySQL5InnoDBDialect
    

    二、编写多数据源的配置类

    1.多数据源配置类

    package com.rtxtitanv.config;
    
    import org.springframework.boot.autoconfigure.orm.jpa.HibernateProperties;
    import org.springframework.boot.autoconfigure.orm.jpa.HibernateSettings;
    import org.springframework.boot.autoconfigure.orm.jpa.JpaProperties;
    import org.springframework.boot.context.properties.ConfigurationProperties;
    import org.springframework.boot.jdbc.DataSourceBuilder;
    import org.springframework.context.annotation.Bean;
    import org.springframework.context.annotation.Configuration;
    import org.springframework.context.annotation.Primary;
    
    import javax.annotation.Resource;
    import javax.sql.DataSource;
    import java.util.Map;
    
    /**
     * @author rtxtitanv
     * @version 1.0.0
     * @name com.rtxtitanv.config.DataSourceConfig
     * @description 多数据源配置类
     * @date 2020/1/7 19:19
     */
    @Configuration
    public class DataSourceConfig {
    
        @Resource
        private JpaProperties jpaProperties;
        @Resource
        private HibernateProperties hibernateProperties;
    
        /**
         * 配置第一数据源
         *
         * @return 数据源
         */
        @Bean(name = "primaryDataSource")
        @Primary // 标识为主数据源
        // prefix:指定yml配置文件中配置项的前缀
        @ConfigurationProperties(prefix = "spring.datasource.primary")
        public DataSource primaryDataSource() {
            // 这种方式默认只满足spring的配置方式,如果使用其他数据库连接池,需独立获取配置
            return DataSourceBuilder.create().build();
        }
    
        /**
         * 配置第二数据源
         *
         * @return 数据源
         */
        @Bean(name = "secondaryDataSource")
        @ConfigurationProperties(prefix = "spring.datasource.secondary")
        public DataSource secondaryDataSource() {
            return DataSourceBuilder.create().build();
        }
    
        /**
         * 配置 组合jpaProperties和hibernateProperties配置的map对象
         *
         * @return 组合jpaProperties和hibernateProperties配置的map
         */
        @Bean(name = "vendorProperties")
        public Map<String, Object> getVendorProperties() {
            return hibernateProperties.determineHibernateProperties(jpaProperties.getProperties(), new HibernateSettings());
        }
    }
    

    2.第一数据源配置类

    package com.rtxtitanv.config;
    
    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.annotation.Resource;
    import javax.persistence.EntityManager;
    import javax.sql.DataSource;
    import java.util.Map;
    
    /**
     * @author rtxtitanv
     * @version 1.0.0
     * @name com.rtxtitanv.config.PrimaryConfig
     * @description 第一数据源配置类
     * @date 2020/1/7 19:21
     */
    @Configuration
    @EnableTransactionManagement
    // entityManagerFactoryRef:指定实体管理器工厂,transactionManagerRef:指定事务管理器
    // basePackages:指定该数据源的repository所在包路径
    @EnableJpaRepositories(entityManagerFactoryRef = "entityManagerFactoryPrimary",
        transactionManagerRef = "transactionManagerPrimary", basePackages = {"com.rtxtitanv.repository.primary"})
    public class PrimaryConfig {
    
        @Resource(name = "primaryDataSource")
        private DataSource primaryDataSource;
        @Resource(name = "vendorProperties")
        private Map<String, Object> vendorProperties;
    
        /**
         * 配置第一数据源实体管理工厂的bean
         *
         * @param builder EntityManagerFactoryBuilder
         * @return LocalContainerEntityManagerFactoryBean
         */
        @Bean(name = "entityManagerFactoryPrimary")
        @Primary // 标识为主数据源(主库对应的数据源)
        public LocalContainerEntityManagerFactoryBean entityManagerFactoryPrimary(EntityManagerFactoryBuilder builder) {
            return builder.dataSource(primaryDataSource)
                // 指定组合jpaProperties和hibernateProperties配置的map对象
                .properties(vendorProperties)
                // 指定该数据源的实体类所在包路径
                .packages("com.rtxtitanv.model.primary").persistenceUnit("primaryPersistenceUnit").build();
        }
    
        /**
         * 配置第一数据源实体管理器
         *
         * @param builder EntityManagerFactoryBuilder
         * @return EntityManager
         */
        @Bean(name = "entityManagerPrimary")
        @Primary
        public EntityManager entityManagerPrimary(EntityManagerFactoryBuilder builder) {
            return entityManagerFactoryPrimary(builder).getObject().createEntityManager();
        }
    
        /**
         * 配置第一数据源事务管理器
         *
         * @param builder EntityManagerFactoryBuilder
         * @return PlatformTransactionManager
         */
        @Bean(name = "transactionManagerPrimary")
        @Primary
        public PlatformTransactionManager transactionManagerPrimary(EntityManagerFactoryBuilder builder) {
            return new JpaTransactionManager(entityManagerFactoryPrimary(builder).getObject());
        }
    }
    

    3.第二数据源配置类

    package com.rtxtitanv.config;
    
    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.annotation.Resource;
    import javax.persistence.EntityManager;
    import javax.sql.DataSource;
    import java.util.Map;
    
    /**
     * @author rtxtitanv
     * @version 1.0.0
     * @name com.rtxtitanv.config.SecondaryConfig
     * @description 第二数据源配置类
     * @date 2020/1/7 19:21
     */
    @Configuration
    @EnableTransactionManagement
    // entityManagerFactoryRef:指定实体管理器工厂,transactionManagerRef:指定事务管理器
    // basePackages:指定该数据源的repository所在包路径
    @EnableJpaRepositories(entityManagerFactoryRef = "entityManagerFactorySecondary",
        transactionManagerRef = "transactionManagerSecondary", basePackages = {"com.rtxtitanv.repository.secondary"})
    public class SecondaryConfig {
    
        @Resource(name = "secondaryDataSource")
        private DataSource secondaryDataSource;
        @Resource(name = "vendorProperties")
        private Map<String, Object> vendorProperties;
    
        /**
         * 配置第二数据源实体管理工厂的bean
         *
         * @param builder EntityManagerFactoryBuilder
         * @return LocalContainerEntityManagerFactoryBean
         */
        @Bean(name = "entityManagerFactorySecondary")
        public LocalContainerEntityManagerFactoryBean entityManagerFactorySecondary