SpringBoot整合MybatisPius实现数据库多数据源及读写分离

一 . 概述

dynamic-datasource的具体介绍请查看dynamic-datasource官网
dynamic-datasource-spring-boot-starter 是一个基于springboot的快速集成多数据源的启动器。其支持 Jdk 1.7+, SpringBoot 1.4.x 1.5.x 2.0.x。

1.1 特性

  • 数据源分组,适用于多种场景 纯粹多库 读写分离 一主多从 混合模式。
  • 内置敏感参数加密和启动初始化表结构schema数据库database。
  • 提供对Druid,Mybatis-Plus,P6sy,Jndi的快速集成。
  • 简化Druid和HikariCp配置,提供全局参数配置。
  • 提供自定义数据源来源接口(默认使用yml或properties配置)。
  • 提供项目启动后增减数据源方案。
  • 提供Mybatis环境下的 纯读写分离 方案。
  • 使用spel动态参数解析数据源,如从session,header或参数中获取数据源。(多租户架构神器)
  • 提供多层数据源嵌套切换。(ServiceA >>> ServiceB >>> ServiceC,每个- - Service都是不同的数据源)
  • 提供 不使用注解 而 使用 正则 或 spel 来切换数据源方案(实验性功能)。

1.2 约定

  • 本框架只做 切换数据源 这件核心的事情,并不限制你的具体操作,切换了- - 数据源可以做任何CRUD。
  • 配置文件所有以下划线 _ 分割的数据源 首部 即为组的名称,相同组名称的- - 数据源会放在一个组下。
  • 切换数据源可以是组名,也可以是具体数据源名称。组名则切换时采用负载均衡算法切换。
  • 默认的数据源名称为 master ,你可以通过 spring.datasource.dynamic.primary 修改。
  • 方法上的注解优先于类上注解。

二 . spring-boot整合

2.1 步骤一: 导入工具包



        
            com.baomidou
            dynamic-datasource-spring-boot-starter
            2.5.6
        

2.2 yml配置

spring:
  datasource:
    dynamic:
      primary: master #设置默认的数据源或者数据源组,默认值即为master
      strict: false #设置严格模式,默认false不启动. 启动后在未匹配到指定数据源时候回抛出异常,不启动会使用默认数据源.
      datasource:
        master:
          url: jdbc:mysql://xx.xx.xx.xx:3306/dynamic
          username: root
          password: 123456
          driver-class-name: com.mysql.jdbc.Driver
        slave_1:
          url: jdbc:mysql://xx.xx.xx.xx:3307/dynamic
          username: root
          password: 123456
          driver-class-name: com.mysql.jdbc.Driver
        slave_2:
          url: ENC(xxxxx) # 内置加密,使用请查看详细文档
          username: ENC(xxxxx)
          password: ENC(xxxxx)
          driver-class-name: com.mysql.jdbc.Driver
          schema: db/schema.sql # 配置则生效,自动初始化表结构
          data: db/data.sql # 配置则生效,自动初始化数据
          continue-on-error: true # 默认true,初始化失败是否继续
          separator: ";" # sql默认分号分隔符
          
       #......省略
       #以上会配置一个默认库master,一个组slave下有两个子库slave_1,slave_2

其他主从方式配置模板

# 多主多从                      纯粹多库(记得设置primary)                   混合配置
spring:                               spring:                               spring:
  datasource:                           datasource:                           datasource:
    dynamic:                              dynamic:                              dynamic:
      datasource:                           datasource:                           datasource:
        master_1:                             mysql:                                master:
        master_2:                             oracle:                               slave_1:
        slave_1:                              sqlserver:                            slave_2:
        slave_2:                              postgresql:                           oracle_1:
        slave_3:                              h2:                                   oracle_2:

2.3 数据源切换使用

@DS 可以注解在方法上和类上,同时存在方法注解优先于类上注解。
强烈建议只注解在service实现上。

注解 结果
没有@DS 默认数据源
@DS("dsName") dsName可以为组名也可以为具体某个库的名称

示例

在service实现层

@Service
@DS("slave")
public class UserServiceImpl implements UserService {

  @Autowired
  private JdbcTemplate jdbcTemplate;

  public List> selectAll() {
    return  jdbcTemplate.queryForList("select * from user");
  }
  
  @Override
  @DS("slave_1")
  public List> selectByCondition() {
    return  jdbcTemplate.queryForList("select * from user where age >10");
  }
}

三. 第三方继承

3.1 集成Druid

springBoot2.x默认使用HikariCP,但在国内Druid的使用者非常庞大,此项目特地对其进行了适配,完成多数据源下使用Druid进行监控。
注意 :主从可以使用不同的数据库连接池,如 master使用Druid监控,从库使用HikariCP。如果不配置连接池type类型,默认是 Druid优先于HikariCP 。

3.1.1 项目引入 druid-spring-boot-starter 依赖


    com.alibaba
    druid-spring-boot-starter
    1.1.10

3.1.2 排除 原生Druid的快速配置类。

@SpringBootApplication(exclude = DruidDataSourceAutoConfigure.class)
public class Application {
  public static void main(String[] args) {
    SpringApplication.run(Application.class, args);
  }
}

某些springBoot的版本上面可能无法排除(尝试使用以下方式排除)

spring:
  autoconfigure:
    exclude: com.alibaba.druid.spring.boot.autoconfigure.DruidDataSourceAutoConfigure
  • 为什么要排除DruidDataSourceAutoConfigure ?

DruidDataSourceAutoConfigure会注入一个DataSourceWrapper,其会在原生的spring.datasource下找url,username,password等。而我们动态数据源的配置路径是变化的。

3.1.2 YML配置

spring:
  datasource:
    druid:
      stat-view-servlet:
        enabled: true
        url-pattern: /druid/*
        #  是否可以使用重置功能
        reset-enable: false
        login-username: admin
        login-password: admin
        #  允许访问的id
        allow: 127.0.0.1
        #  和名单
        deny: ""
    dynamic:
      druid: #以下是全局默认值,可以全局更改
        # druid 配置
        # 初始化连接数
        initial-size: 5
        # 最大连接数
        max-active: 10
        # 最少连接数
        min-idle: 3
        #      配置监控统计拦截器 日志配置  Slf4j  logback
        #      stat 监控数据库性能
        #      wall  用于防火墙
        #      日志先关 slf4j  logback  log4j  log4j2
        filters: stat,wall,slf4j
        web-stat-filter:
          enabled: true
          url-pattern:  /*
          # 排除不拦截的 请求
          exclusions: "*.js,/druid/*"
      datasource:
        master:
          username: root
          password: 123456
          driver-class-name: com.mysql.jdbc.Driver
          url: jdbc:mysql://106.13.221.151:3316/test?useUnicode=true&characterEncoding=UTF-8&serverTimezone=Asia/Shanghai
          druid: # 以下参数针对每个库可以重新设置druid参数
            initial-size: 5
            validation-query: select 1 FROM DUAL #比如oracle就需要重新设置这个
            public-key: #(非全局参数)设置即表示启用加密,底层会自动帮你配置相关的连接参数和filter。
        slave_1:
          username: ****
          password: ****
          driver-class-name: com.mysql.jdbc.Driver
          url: jdbc:mysql://106.13.221.151:3317/test?useUnicode=true&characterEncoding=UTF-8&serverTimezone=Asia/Shanghai
          druid:
            # druid 配置
            # 初始化连接数
            initial-size: 5
            # 最大连接数
            max-active: 10
            # 最少连接数
            min-idle: 3

程序入口开启mappe扫描

@SpringBootApplication(exclude = DruidDataSourceAutoConfigure.class)
@MapperScan("com.example.demo.mapper")
public class DemoApplication {
    public static void main(String[] args) {
        SpringApplication.run(DemoApplication.class, args);
    }
}

3.2 集成HikariCP

HikariCP官方地址
SpringBoot 2.+ 默认引入了HikariCP,除非对版本有要求无需再次引入。
使用SpringBoot 1.5.x的版本需手动引入,对应的版本请根据自己环境和HikariCP官方地址自行选择。

3.2.1 YML配置

spring:
  datasource:
    dynamic:
      hikari:  # 全局hikariCP参数,所有值和默认保持一致。(现已支持的参数如下,不清楚含义不要乱设置)
        catalog:
        connection-timeout:
        validation-timeout:
        idle-timeout:
        leak-detection-threshold:
        max-lifetime:
        max-pool-size:
        min-idle:
        initialization-fail-timeout:
        connection-init-sql:
        connection-test-query:
        dataSource-class-name:
        dataSource-jndi-name:
        schema:
        transaction-isolation-name:
        is-auto-commit:
        is-read-only:
        is-isolate-internal-queries:
        is-register-mbeans:
        is-allow-pool-suspension:
        data-source-properties: #以下属性仅为演示(默认不会引入)
          serverTimezone: Asia/Shanghai
          characterEncoding: utf-8
          useUnicode: true
          useSSL: false
          autoReconnect: true
          cachePrepStmts: true
          prepStmtCacheSize: 250
          prepStmtCacheSqlLimit: 2048
          useServerPrepStmts: true
          useLocalSessionState: true
          rewriteBatchedStatements: true
          cacheResultSetMetadata: true
          cacheServerConfiguration: true
          elideSetAutoCommits: true
          maintainTimeStats: false
          allowPublicKeyRetrieval: true
        health-check-properties:
      datasource:
        master:
          username: root
          password: 123456
          driver-class-name: com.mysql.jdbc.Driver
          url: jdbc:mysql://xx.xx.xx.xx:3306/dynamic?characterEncoding=utf8&useSSL=false
          hikari: # 以下参数针对每个库可以重新设置hikari参数
            max-pool-size:
            idle-timeout:
#           ......

你可能感兴趣的:(SpringBoot整合MybatisPius实现数据库多数据源及读写分离)