spring boot使用sharding jdbc的配置方式

本文介绍了spring boot使用sharding jdbc的配置方式,分享给大家,具体如下:

说明

要排除DataSourceAutoConfiguration,否则多数据源无法配置

@SpringBootApplication
@EnableAutoConfiguration(exclude={DataSourceAutoConfiguration.class})
public class Application {

  public static void main(String[] args) {
   SpringApplication.run(Application.class, args);
  }

}

配置的多个数据源交给sharding-jdbc管理,sharding-jdbc创建一个DataSource数据源提供给mybatis使用

官方文档:http://shardingjdbc.io/index_zh.html

步骤

配置多个数据源,数据源的名称最好要有一定的规则,方便配置分库的计算规则

@Bean(initMethod="init", destroyMethod="close", name="dataSource0")
@ConfigurationProperties(prefix = "spring.datasource")
public DataSource dataSource0(){
  return new DruidDataSource();
}

@Bean(initMethod="init", destroyMethod="close", name="dataSource1")
@ConfigurationProperties(prefix = "spring.datasource2")
public DataSource dataSource1(){
  return new DruidDataSource();
}

配置数据源规则,即将多个数据源交给sharding-jdbc管理,并且可以设置默认的数据源,当表没有配置分库规则时会使用默认的数据源

@Bean
public DataSourceRule dataSourceRule(@Qualifier("dataSource0") DataSource dataSource0,
    @Qualifier("dataSource1") DataSource dataSource1){
  Map<String, DataSource> dataSourceMap = new HashMap<>();
  dataSourceMap.put("dataSource0", dataSource0);
  dataSourceMap.put("dataSource1", dataSource1);
  return new DataSourceRule(dataSourceMap, "dataSource0");
}

配置数据源策略和表策略,具体策略需要自己实现

@Bean
public ShardingRule shardingRule(DataSourceRule dataSourceRule){
  //表策略
  TableRule orderTableRule = TableRule.builder("t_order")
      .actualTables(Arrays.asList("t_order_0", "t_order_1"))
      .tableShardingStrategy(new TableShardingStrategy("order_id", new ModuloTableShardingAlgorithm()))
      .dataSourceRule(dataSourceRule)
      .build();
  TableRule orderItemTableRule = TableRule.builder("t_order_item")
      .actualTables(Arrays.asList("t_order_item_0", "t_order_item_1"))
      .tableShardingStrategy(new TableShardingStrategy("order_id", new ModuloTableShardingAlgorithm()))
      .dataSourceRule(dataSourceRule)
      .build();
  //绑定表策略,在查询时会使用主表策略计算路由的数据源,因此需要约定绑定表策略的表的规则需要一致,可以一定程度提高效率
  List<BindingTableRule> bindingTableRules = new ArrayList<BindingTableRule>();
  bindingTableRules.add(new BindingTableRule(Arrays.asList(orderTableRule, orderItemTableRule)));
  return ShardingRule.builder()
      .dataSourceRule(dataSourceRule)
      .tableRules(Arrays.asList(orderTableRule, orderItemTableRule))
      .bindingTableRules(bindingTableRules)
      .databaseShardingStrategy(new DatabaseShardingStrategy("user_id", new ModuloDatabaseShardingAlgorithm()))
      .tableShardingStrategy(new TableShardingStrategy("order_id", new ModuloTableShardingAlgorithm()))
      .build();
}

创建sharding-jdbc的数据源DataSource,MybatisAutoConfiguration会使用此数据源

@Bean("dataSource")
public DataSource shardingDataSource(ShardingRule shardingRule){
  return ShardingDataSourceFactory.createDataSource(shardingRule);
}

需要手动配置事务管理器(原因未知)

//需要手动声明配置事务
@Bean
public DataSourceTransactionManager transactitonManager(@Qualifier("dataSource") DataSource dataSource){
  return new DataSourceTransactionManager(dataSource);
}

分库策略的简单实现,接口:DatabaseShardingAlgorithm

import java.util.Collection;
import java.util.LinkedHashSet;

import com.dangdang.ddframe.rdb.sharding.api.ShardingValue;
import com.dangdang.ddframe.rdb.sharding.api.strategy.database.SingleKeyDatabaseShardingAlgorithm;
import com.google.common.collect.Range;

/**
 * Created by fuwei.deng on 2017年5月11日.
 */
public class ModuloDatabaseShardingAlgorithm implements SingleKeyDatabaseShardingAlgorithm<Long> {

  @Override
  public String doEqualSharding(Collection<String> databaseNames, ShardingValue<Long> shardingValue) {
   for (String each : databaseNames) {
      if (each.endsWith(shardingValue.getValue() % 2 + "")) {
        return each;
      }
    }
    throw new IllegalArgumentException();
  }

  @Override
  public Collection<String> doInSharding(Collection<String> databaseNames, ShardingValue<Long> shardingValue) {
   Collection<String> result = new LinkedHashSet<>(databaseNames.size());
    for (Long value : shardingValue.getValues()) {
      for (String tableName : databaseNames) {
        if (tableName.endsWith(value % 2 + "")) {
          result.add(tableName);
        }
      }
    }
    return result;
  }

  @Override
  public Collection<String> doBetweenSharding(Collection<String> databaseNames, ShardingValue<Long> shardingValue) {
   Collection<String> result = new LinkedHashSet<>(databaseNames.size());
    Range<Long> range = (Range<Long>) shardingValue.getValueRange();
    for (Long i = range.lowerEndpoint(); i <= range.upperEndpoint(); i++) {
      for (String each : databaseNames) {
        if (each.endsWith(i % 2 + "")) {
          result.add(each);
        }
      }
    }
    return result;
  }

}

分表策略的基本实现,接口:TableShardingAlgorithm

import java.util.Collection;
import java.util.LinkedHashSet;

import com.dangdang.ddframe.rdb.sharding.api.ShardingValue;
import com.dangdang.ddframe.rdb.sharding.api.strategy.table.SingleKeyTableShardingAlgorithm;
import com.google.common.collect.Range;

/**
 * Created by fuwei.deng on 2017年5月11日.
 */
public class ModuloTableShardingAlgorithm implements SingleKeyTableShardingAlgorithm<Long> {

  @Override
  public String doEqualSharding(Collection<String> tableNames, ShardingValue<Long> shardingValue) {
   for (String each : tableNames) {
      if (each.endsWith(shardingValue.getValue() % 2 + "")) {
        return each;
      }
    }
    throw new IllegalArgumentException();
  }

  @Override
  public Collection<String> doInSharding(Collection<String> tableNames, ShardingValue<Long> shardingValue) {
   Collection<String> result = new LinkedHashSet<>(tableNames.size());
    for (Long value : shardingValue.getValues()) {
      for (String tableName : tableNames) {
        if (tableName.endsWith(value % 2 + "")) {
          result.add(tableName);
        }
      }
    }
    return result;
  }

  @Override
  public Collection<String> doBetweenSharding(Collection<String> tableNames, ShardingValue<Long> shardingValue) {
   Collection<String> result = new LinkedHashSet<>(tableNames.size());
    Range<Long> range = (Range<Long>) shardingValue.getValueRange();
    for (Long i = range.lowerEndpoint(); i <= range.upperEndpoint(); i++) {
      for (String each : tableNames) {
        if (each.endsWith(i % 2 + "")) {
          result.add(each);
        }
      }
    }
    return result;
  }

}

至此,分库分表的功能已经实现

读写分离

读写分离需在创建DataSourceRule之前加一层主从数据源的创建

// 构建读写分离数据源, 读写分离数据源实现了DataSource接口, 可直接当做数据源处理.
// masterDataSource0, slaveDataSource00, slaveDataSource01等为使用DBCP等连接池配置的真实数据源
DataSource masterSlaveDs0 = MasterSlaveDataSourceFactory.createDataSource("ms_0",
          masterDataSource0, slaveDataSource00, slaveDataSource01);
DataSource masterSlaveDs1 = MasterSlaveDataSourceFactory.createDataSource("ms_1",
          masterDataSource1, slaveDataSource11, slaveDataSource11);

// 构建分库分表数据源
Map<String, DataSource> dataSourceMap = new HashMap<>(2);
dataSourceMap.put("ms_0", masterSlaveDs0);
dataSourceMap.put("ms_1", masterSlaveDs1);

// 通过ShardingDataSourceFactory继续创建ShardingDataSource

强制使用主库时

HintManager hintManager = HintManager.getInstance();
hintManager.setMasterRouteOnly();
// 继续JDBC操作

强制路由

  1. 使用ThreadLocal机制实现,在执行数据库操作之前通过HintManager改变用于计算路由的值
  2. 设置HintManager的时候分库和分表的策略必须同时设置,并且设置后需要路由的表都需要设置用于计算路由的值。比如强制路由后需要操作t_order和t_order_item两个表,那么两个表的分库和分表的策略都需要设置
HintManager hintManager = HintManager.getInstance();
hintManager.addDatabaseShardingValue("t_order", "user_id", 1L);
hintManager.addTableShardingValue("t_order", "order_id", order.getOrderId());
hintManager.addDatabaseShardingValue("t_order_item", "user_id", 1L);
hintManager.addTableShardingValue("t_order_item", "order_id", order.getOrderId());

事务

  1. sharding-jdbc-transaction实现柔性事务(默认提供了基于内存的事务日志存储器和内嵌异步作业),可结合elastic-job(sharding-jdbc-transaction-async-job)实现异步柔性事务
  2. 没有与spring结合使用的方式,需要自己封装

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持我们。

您可能感兴趣的文章:

  • 玩转spring boot 结合AngularJs和JDBC(4)
  • Spring Boot JDBC 连接数据库示例
  • Spring Boot中使用jdbctemplate 操作MYSQL数据库实例
  • 详解spring boot中使用JdbcTemplate
  • SpringBoot用JdbcTemplates访问Mysql实例代码
  • 基于spring boot 1.5.4 集成 jpa+hibernate+jdbcTemplate(详解)
  • springboot使用JdbcTemplate完成对数据库的增删改查功能
(0)

相关推荐

  • Spring Boot中使用jdbctemplate 操作MYSQL数据库实例

    最近在学习使用Spring Boot连接数据库,今天学习了使用jdbctemplate 操作MYSQL数据库,下面就留个笔记 不废话,先来代码 pom文件: <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org

  • SpringBoot用JdbcTemplates访问Mysql实例代码

    本文介绍springboot通过jdbc访问关系型MySQL,通过spring的JdbcTemplate去访问. 准备工作 jdk 1.8 maven 3.0 idea mysql 初始化mysql: -- create table `account` DROP TABLE `account` IF EXISTS CREATE TABLE `account` ( `id` int(11) NOT NULL AUTO_INCREMENT, `name` varchar(20) NOT NULL,

  • 基于spring boot 1.5.4 集成 jpa+hibernate+jdbcTemplate(详解)

    1.pom添加依赖 <!-- spring data jpa,会注入tomcat jdbc pool/hibernate等 --> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-data-jpa</artifactId> </dependency> <dependency> <

  • 详解spring boot中使用JdbcTemplate

    本文将介绍如何将spring boot 与 JdbcTemplate一起工作. Spring对数据库的操作在jdbc上面做了深层次的封装,使用spring的注入功能,可以把DataSource注册到JdbcTemplate之中. JdbcTemplate 是在JDBC API基础上提供了更抽象的封装,并提供了基于方法注解的事务管理能力. 通过使用SpringBoot自动配置功能并代替我们自动配置beans. 数据源配置 在maven中,我们需要增加spring-boot-starter-jdbc

  • springboot使用JdbcTemplate完成对数据库的增删改查功能

    首先新建一个简单的数据表,通过操作这个数据表来进行演示 DROP TABLE IF EXISTS `items`; CREATE TABLE `items` ( `id` int(11) NOT NULL AUTO_INCREMENT, `title` varchar(255) DEFAULT NULL, `name` varchar(10) DEFAULT NULL, `detail` varchar(255) DEFAULT NULL, PRIMARY KEY (`id`) ) ENGINE

  • Spring Boot JDBC 连接数据库示例

    文本将对在spring Boot构建的Web应用中,基于MySQL数据库的几种数据库连接方式进行介绍. 包括JDBC.JPA.MyBatis.多数据源和事务. JDBC 连接数据库 1.属性配置文件(application.properties) spring.datasource.url=jdbc:mysql://localhost:3306/test spring.datasource.username=root spring.datasource.password=123456 sprin

  • 玩转spring boot 结合AngularJs和JDBC(4)

    参考官方例子:http://spring.io/guides/gs/relational-data-access/  一.项目准备 在建立mysql数据库后新建表"t_order" SET FOREIGN_KEY_CHECKS=0; -- ---------------------------- -- Table structure for `t_order` -- ---------------------------- DROP TABLE IF EXISTS `t_order`;

  • spring boot使用sharding jdbc的配置方式

    本文介绍了spring boot使用sharding jdbc的配置方式,分享给大家,具体如下: 说明 要排除DataSourceAutoConfiguration,否则多数据源无法配置 @SpringBootApplication @EnableAutoConfiguration(exclude={DataSourceAutoConfiguration.class}) public class Application { public static void main(String[] arg

  • Spring Boot中使用JDBC Templet的方法教程

    前言 Spring 的 JDBC Templet 是 Spring 对 JDBC 使用的一个基本的封装.他主要是帮助程序员实现了数据库连接的管理,其余的使用方式和直接使用 JDBC 没有什么大的区别. 业务需求 JDBC 的使用大家都比较熟悉了.这里主要为了演示在 SpringBoot 中使用 Spring JDBC Templet 的步骤,所以我们就设计一个简单的需求.一个用户对象的 CURD 的操作.对象有两个属性,一个属性是id,一个属性是名称.存储在 MySQL 的 auth_user

  • Spring Boot使用Druid和监控配置方法

    Spring Boot默认的数据源是:org.apache.tomcat.jdbc.pool.DataSource Druid是Java语言中最好的数据库连接池,并且能够提供强大的监控和扩展功能. 下面来说明如何在 Spring Boot 中配置使用Druid (1)添加Maven依赖 (或jar包)\ <dependency> <groupId>com.alibaba</groupId> <artifactId>druid</artifactId&g

  • Spring Boot实战教程之自动配置详解

    前言 大家应该都有所了解,随着Ruby.Groovy等动态语言的流行,相比较之下Java的开发显得格外笨重.繁多的配置.低下的开发效率.复杂的部署流程以及第三方技术集成难度大等问题一直被人们所诟病.随着Spring家族中的新星Spring Boot的诞生,这些问题都在逐渐被解决. 个人觉得Spring Boot中最重要的两个优势就是可以使用starter简化依赖配置和Spring的自动配置.下面这篇文章将给大家详细介绍Spring Boot自动配置的相关内容,话不多说,来一起看看详细的介绍. 使

  • spring boot 注入 property的三种方式(推荐)

    以前使用spring的使用要注入property要配置PropertyPlaceholder的bean对象.在springboot除  了这种方式以外还可以通过制定 配置ConfigurationProperties直接把property文件的 属性映射到 当前类里面. @ConfigurationProperties(prefix = "mypro", merge = true, locations = { "classpath:my.properties" })

  • Spring Boot 2.0多数据源配置方法实例详解

    两个数据库实例,一个负责读,一个负责写. datasource-reader: type: com.alibaba.druid.pool.DruidDataSource url: jdbc:mysql://192.168.43.61:3306/test?useUnicode=true&characterEncoding=utf8&autoReconnect=true&useSSL=false username: icbc password: icbc driver-class-na

  • Spring Boot项目搭建的两种方式

    什么是Spring Boot Spring Boot 是由 Pivotal 团队提供的全新框架,其设计目的是用来简化新 Spring 应用的初始搭建以及开发过程.该框架使用了特定的方式来进行配置,从而使开发人员不再需要定义样板化的配置.用我的话来理解,就是 Spring Boot 其实不是什么新的框架,它默认配置了很多框架的使用方式,就像 Maven 整合了所有的 Jar 包,Spring Boot 整合了所有的框架. 使用 Spring Boot有什么好处 其实就是简单.快速.方便!平时如果我

  • spring boot 使用profile来分区配置的操作

    spring boot 使用profile来分区配置 很多时候,我们项目在开发环境和生成环境的环境配置是不一样的,例如,数据库配置,在开发的时候,我们一般用测试数据库,而在生产环境的时候,我们是用正式的数据,这时候,我们可以利用profile在不同的环境下配置用不同的配置文件或者不同的配置 spring boot允许你通过命名约定按照一定的格式(application-{profile}.properties)来定义多个配置文件,然后通过在application.properyies通过spri

  • 详解Spring Boot中如何自定义SpringMVC配置

    目录 前言 一.SpringBoot 中 SpringMVC 配置概述 二.WebMvcConfigurerAdapter 抽象类 三.WebMvcConfigurer 接口 四.WebMvcConfigurationSupport 类-自定义配置 五.WebMvcAutoConfiguration 配置类 – 自动化配置 六.@EnableWebMvc 注解 七.总结 前言 在 Spring Boot 框架中只需要在项目中引入 spring-boot-starter-web 依赖,Spring

  • Spring Boot 详细分析Conditional自动化配置注解

    目录 1. Spring Boot Condition功能与作用 2. Conditional条件化系列注解介绍 3. Conditional条件化注解的实现原理 4. Conditional核心之matches匹配接口 5. Conditional核心之条件化注解具体实现 6. 总结 1. Spring Boot Condition功能与作用 @Conditional是基于条件的自动化配置注解, 由Spring 4框架推出的新特性. 在一个服务工程, 通常会存在多个配置环境, 比如常见的DEV

随机推荐