springboot(二十二)-sharding-jdbc-读写分离

前面我们使用sharding-jdbc配置了分库分表。sharding-jdbc还有个用法,就是实现读写分离。

什么时候需要或者可以使用读写分离?

当我们的项目所使用的数据库查询的访问量,访问频率,及访问的并发量远大于修改的时候,我们需要将访问数据库的方式读写分离。比如我们使用的微博,更多人都只是刷一刷,发布微博动态的次数还是远小于我们刷微博的次数的。

sharding-jdbc

sharding-jdbc较于MyCat,我认为最大的优势是:sharding-jdbc是轻量级的第三方工具,我们只需要在项目中引用指定的jar包即可,然后根据项目的业务需要配置分库分表或者读写分离的规则和方式。

我们开始实现读写分离:

一. 先准备好数据库

我们在自己本地新建三个一毛一样的数据库database0,database1,database2.然后这三个数据库里各建一张user表:

CREATE TABLE `user` (
  `id` bigint(64) NOT NULL AUTO_INCREMENT,
  `city` varchar(20) NOT NULL,
  `name` varchar(20) NOT NULL,
  PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=102 DEFAULT CHARSET=utf8;

-- ----------------------------
-- Records of user
-- ----------------------------
INSERT INTO `user` VALUES ('100', 'beijing', 'dalaoyang');---database0数据
INSERT INTO `user` VALUES ('101', 'beijing', 'dalaoyang');---database0数据
INSERT INTO `user` VALUES ('101', 'beijing', 'dalaoyang');---database1数据
INSERT INTO `user` VALUES ('101', 'beijing', 'dalaoyang');---database2数据

因为是例子,我们三个database就放在同一台电脑的同一个数据库中了。实际情况下,使用到sharding-jdbc来做读写分离的话,一定是拥有海量数据的项目,一般会又多台数据库服务器。因为这些服务器需要实现数据同步。关于数据同步,后面再说。

二. 新建springboot项目吧

1.pom.xml

<?xml version="1.0" encoding="UTF-8"?>
<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/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>
  
    <groupId>com.dalaoyang</groupId>
    <artifactId>springboot2_shardingjdbc_dxfl</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <name>springboot2_shardingjdbc_dxfl</name>
    <description>springboot2_shardingjdbc_dxfl</description>

    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>1.5.9.RELEASE</version>
        <relativePath/> <!-- lookup parent from repository -->
    </parent>

    <properties>
        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
        <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
        <java.version>1.8</java.version>
    </properties>

    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>
        <dependency>
            <groupId>org.mybatis.spring.boot</groupId>
            <artifactId>mybatis-spring-boot-starter</artifactId>
            <version>1.3.1</version>
        </dependency>

        <dependency>
            <groupId>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
            <scope>runtime</scope>
        </dependency>
        <dependency>
            <groupId>org.mybatis.spring.boot</groupId>
            <artifactId>mybatis-spring-boot-starter</artifactId>
            <version>1.1.1</version> 
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
        </dependency>

        <dependency>
              <groupId>io.shardingjdbc</groupId>
              <artifactId>sharding-jdbc-spring-boot-starter</artifactId>
              <version>2.0.0.M3</version>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-devtools</artifactId>
            <optional>true</optional>
        </dependency>
        <dependency>
            <groupId>com.alibaba</groupId>
            <artifactId>druid</artifactId>
            <version>1.1.3</version>
        </dependency>
        <dependency>
            <groupId>commons-dbcp</groupId>
            <artifactId>commons-dbcp</artifactId>
            <version>1.4</version>
        </dependency>
        <dependency>
            <groupId>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
        </dependency>

        <!-- https://mvnrepository.com/artifact/com.alibaba/fastjson -->
        <dependency>
            <groupId>com.alibaba</groupId>
            <artifactId>fastjson</artifactId>
            <version>1.2.47</version>
        </dependency>

    </dependencies>

    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
            </plugin>
        </plugins>
    </build>


</project>

这里主要是加上sharding-jdbc-spring-boot-starter的启动器,注意版本就好。

这里插上一句,很多人都说现在的程序员必须要会,并且使用springboot,除了springboot自身的各种优势和便利意外,你会发现,很多优秀的第三方工具都自觉加入了springboot的怀抱,springboot要使用这些第三方工具包的时候,只需要在pom文件中注入对应的依赖就可。除了这个sharding-jdbc,还有比如,redis,solr,mybatis,kafka,elasticsearch等等等等,很多很多。

用起来就一个字“爽的呀批”;

 

2.application.yml

server:
  port: 8084
sharding:
  jdbc:
    datasource:
      names: ds0,ds1,ds2
      ds0:
        type: com.alibaba.druid.pool.DruidDataSource
        driver-class-name: com.mysql.jdbc.Driver
        url: jdbc:mysql://localhost:3306/database0
        username: root
        password: 1234
      ds1:
        type: com.alibaba.druid.pool.DruidDataSource
        driver-class-name: com.mysql.jdbc.Driver
        url: jdbc:mysql://localhost:3306/database1
        username: root
        password: 1234
      ds2:
        type: com.alibaba.druid.pool.DruidDataSource
        driver-class-name: com.mysql.jdbc.Driver
        url: jdbc:mysql://localhost:3306/database2
        username: root
        password: 1234
    config:
      sharding:
        props:
          sql.show: true
      masterslave:
        load-balance-algorithm-type: round_robin
        name: dataSource
        master-data-source-name: ds0
        slave-data-source-names: ds1,ds2

配置三个数据源,然后主数据库为ds0,从数据库为ds1和ds2.

主数据库是修改操作使用的,从数据库是查询使用的。这是默认的。

然后从数据库的配置规则是轮询(round_robin),配置规则还有一个:随机(random)

3.访问接口提供下

@RestController
public class UserController {

    @Autowired
    private UserMapper userMapper;

    @GetMapping("save")
    public void save(){
        User user = new User();
        user.setName("dalaoyang");
        user.setCity("beijing");
        userMapper.insertSelective(user);
    }

    @GetMapping("getAll")
    public Object getAll(){
        return userMapper.selectAll();
    }
}

其他的启动类啊,service,mapper之类的就写了,没啥特别的。详细的下载代码。

测试

启动项目,多次访问localhost:8084/getAll。

得到的数据为:

[{"id":10001,"city":"beijing","name":"dalaoyang1"}]和
[{"id":10002,"city":"beijing","name":"dalaoyang2"}]

 

轮番出现,这就说明数据库ds1和ds2被轮询访问。

再多次访问localhost:8084/save

看数据库,你会发现插入的数据都保存在ds0中。

那么这时可以说,我们实现了读写分离。

代码下载地址:https://gitee.com/fengyuduke/my_open_resources/blob/master/springboot2_shardingjdbc_dxfl.zip

 

上一篇:关系型数据库-MySQL进阶(三)数据分片


下一篇:分库分表-sharding-jdbc笔记