溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊(cè)×
其他方式登錄
點(diǎn)擊 登錄注冊(cè) 即表示同意《億速云用戶(hù)服務(wù)條款》

SpringBoot項(xiàng)目中如何實(shí)現(xiàn)MySQL讀寫(xiě)分離

發(fā)布時(shí)間:2023-05-18 11:49:50 來(lái)源:億速云 閱讀:116 作者:iii 欄目:編程語(yǔ)言

這篇“SpringBoot項(xiàng)目中如何實(shí)現(xiàn)MySQL讀寫(xiě)分離”文章的知識(shí)點(diǎn)大部分人都不太理解,所以小編給大家總結(jié)了以下內(nèi)容,內(nèi)容詳細(xì),步驟清晰,具有一定的借鑒價(jià)值,希望大家閱讀完這篇文章能有所收獲,下面我們一起來(lái)看看這篇“SpringBoot項(xiàng)目中如何實(shí)現(xiàn)MySQL讀寫(xiě)分離”文章吧。

    1、MySQL主從復(fù)制

    但我們仔細(xì)觀察我們會(huì)發(fā)現(xiàn),當(dāng)我們的項(xiàng)目都是用的單體數(shù)據(jù)庫(kù)時(shí),那么就可能會(huì)存在如下問(wèn)題:

    • 讀和寫(xiě)所有壓力都由一臺(tái)數(shù)據(jù)庫(kù)承擔(dān), 壓力大

    • 數(shù)據(jù)庫(kù)服務(wù)器磁盤(pán)損壞則 數(shù)據(jù)丟失 ,單點(diǎn)故障

    為了解決上述提到的兩個(gè)問(wèn)題,我們可以準(zhǔn)備兩 (多) 臺(tái)MySQL,一臺(tái)主( Master )服務(wù)器,一臺(tái)從( Slave )服務(wù)器,主庫(kù)的 數(shù)據(jù)變更 (寫(xiě)、更新、刪除這些操作) ,需要 同步 到從庫(kù)中 (主從復(fù)制) 。而用戶(hù)在訪問(wèn)我們項(xiàng)目時(shí),如果是 寫(xiě)操作 (insert、update、delete),則直接操作 主庫(kù) ;如果是 讀操作 (select) ,則直接操作從庫(kù),這種結(jié)構(gòu)就是 讀寫(xiě)分離 啦。

    SpringBoot項(xiàng)目中如何實(shí)現(xiàn)MySQL讀寫(xiě)分離

    在這種讀寫(xiě)分離的結(jié)構(gòu)中,從庫(kù)是可以有多個(gè)的

    1.1、介紹

    MySQL主從復(fù)制是一個(gè) 異步 的復(fù)制過(guò)程,底層是基于Mysql數(shù)據(jù)庫(kù)自帶的 二進(jìn)制日志 功能。就是一臺(tái)或多臺(tái)MySQL數(shù)據(jù)庫(kù)(slave,即 從庫(kù) )從另一臺(tái)MySQL數(shù)據(jù)庫(kù)(master,即 主庫(kù) )進(jìn)行日志的復(fù)制,然后再解析日志并應(yīng)用到自身,最終實(shí)現(xiàn) 從庫(kù) 的數(shù)據(jù)和 主庫(kù) 的數(shù)據(jù)保持一致。MySQL主從復(fù)制是 MySQL數(shù)據(jù)庫(kù)自帶功能,無(wú)需借助第三方工具。

    二進(jìn)制日志:

    二進(jìn)制日志(BINLOG)記錄了所有的 DDL(數(shù)據(jù)定義語(yǔ)言)語(yǔ)句和 DML(數(shù)據(jù)操縱語(yǔ)言)語(yǔ)句,但是不包括數(shù)據(jù)查詢(xún)語(yǔ)句。此日志對(duì)于災(zāi)難時(shí)的數(shù)據(jù)恢復(fù)起著極其重要的作用,MySQL的主從復(fù)制, 就是通過(guò)該binlog實(shí)現(xiàn)的。默認(rèn)MySQL是未開(kāi)啟該日志的。

    MySQL復(fù)制過(guò)程分成三步:
    • MySQL master 將數(shù)據(jù)變更寫(xiě)入二進(jìn)制日志( binary log )

    • slave將master的binary log拷貝到它的中繼日志( relay log

    • slave重做中繼日志中的事件,將數(shù)據(jù)變更反映它自己的數(shù)據(jù)

    SpringBoot項(xiàng)目中如何實(shí)現(xiàn)MySQL讀寫(xiě)分離

    1.2、主從庫(kù)搭建

    在環(huán)境搭建之前,我們需要準(zhǔn)備好兩臺(tái)服務(wù)器,如果生活富裕使用的是兩臺(tái)云服務(wù)器的時(shí)候記得要開(kāi)放安全組,即防火墻;如果是比狗子我生活好點(diǎn)但也是用的虛擬機(jī)的話,記得別分這么多內(nèi)存啟動(dòng)藍(lán)屏了(別問(wèn)怎么知道的)

    這里就不給大家展示數(shù)據(jù)庫(kù)的安裝和防火墻的操作了,這個(gè)我感覺(jué)網(wǎng)上好多資源都能夠滿足遇到的問(wèn)題,在搭建主從庫(kù)的時(shí)候有在網(wǎng)上見(jiàn)到過(guò)說(shuō)MySQL版本要一致的,我也沒(méi)太留意直接就在之前的MySQL上操作了,大家可以自己去驗(yàn)證一下。

    1.2.1、主庫(kù)配置

    服務(wù)器:192.168.150.100(別試了黑不了的,這是虛擬機(jī)的ip)

    1、修改Mysql數(shù)據(jù)庫(kù)的配置文件 vim /etc/my.cnf

    在打開(kāi)的文件中加入下面兩行,其中的server-id不一定是100,確保唯一即可
    log-bin=mysql-bin   #[必須]啟用二進(jìn)制日志
    server-id=100       #[必須]服務(wù)器唯一ID

    SpringBoot項(xiàng)目中如何實(shí)現(xiàn)MySQL讀寫(xiě)分離

    2、重啟Mysql服務(wù)

    這里有三個(gè)方法都能重啟MySQL,最簡(jiǎn)單的無(wú)疑就是一關(guān)一開(kāi):

    net stop mysql;net start mysql;
    systemctl restart mysqld
    service mysqld restart

    3、創(chuàng)建數(shù)據(jù)同步的用戶(hù)并授權(quán)

    登錄進(jìn)去MySQL之后才能夠執(zhí)行下面的命令,因?yàn)檫@是SQL命令,Linux不認(rèn)識(shí)這玩意是啥。

    GRANT REPLICATION SLAVE ON *.* to '用戶(hù)名'@'開(kāi)放的地址' identified by '密碼';
    eg: GRANT REPLICATION SLAVE ON *.* to 'masterDb'@'%' identified by 'Master@123456';
    記得刷一下權(quán)限
    FLUSH PRIVILEGES;

    4、查看master同步狀態(tài)

    這個(gè)時(shí)候還 不用退出MySQL ,因?yàn)橄旅娴拿钸€是SQL命令,執(zhí)行下面的SQL,可以拿到我們后面需要的兩個(gè)重要參數(shù)。

    show master status;

    SpringBoot項(xiàng)目中如何實(shí)現(xiàn)MySQL讀寫(xiě)分離

    執(zhí)行完這一句SQL之后,==不要再操作主庫(kù)!不要再操作主庫(kù)!不要再操作主庫(kù)!==重要的事情說(shuō)三遍,因?yàn)樵俨僮髦鲙?kù)之后可能會(huì)導(dǎo)致紅框中的 兩個(gè)屬性值會(huì)發(fā)生變化 ,后面如果發(fā)生了錯(cuò)誤可能就和這里有那么兩毛錢(qián)關(guān)系了。

    1.2.2、從庫(kù)配置

    服務(wù)器:192.168.150.101(別試了黑不了的,這也是虛擬機(jī)的ip)

    1、 修改Mysql數(shù)據(jù)庫(kù)的配置文件 vim /etc/my.cnf

    SpringBoot項(xiàng)目中如何實(shí)現(xiàn)MySQL讀寫(xiě)分離

    這里要注意server-id和主庫(kù)以及其他從庫(kù)都不能相同,否則后面將會(huì)配置不成功。

    2、重啟Mysql服務(wù)

    這里有三個(gè)方法都能重啟MySQL,最簡(jiǎn)單的無(wú)疑就是一關(guān)一開(kāi):

    net stop mysql;net start mysql;
    systemctl restart mysqld
    service mysqld restart

    3、設(shè)置主庫(kù)地址及同步位置

    登錄進(jìn)去MySQL之后才能夠執(zhí)行下面的命令,因?yàn)檫@是SQL命令

    設(shè)置主庫(kù)地址和同步位置
    change master to master_host='192.168.150.100',master_user='masterDb',master_password='Master@123456',master_log_file='mysql-bin.000010',master_log_pos=68479;
    記得記得開(kāi)啟從庫(kù)配置
    start slave;

    參數(shù)說(shuō)明:

    • master_host: 主庫(kù)的 IP地址

    • master_user: 訪問(wèn)主庫(kù)進(jìn)行主從復(fù)制的 用戶(hù)名 ( 上面在主庫(kù)創(chuàng)建的 )

    • master_password: 訪問(wèn)主庫(kù)進(jìn)行主從復(fù)制的用戶(hù)名對(duì)應(yīng)的 密碼

    • master_log_file: 從哪個(gè) 日志文件 開(kāi)始同步 ( 即1.2.1中第4步獲取的 File )

    • master_log_pos: 從指定日志文件的哪個(gè) 位置 開(kāi)始同步 ( 即1.2.1中第4步獲取的 Position )

    4、查看從數(shù)據(jù)庫(kù)的狀態(tài)

    這個(gè)時(shí)候還 不用退出MySQL ,因?yàn)橄旅娴拿钸€是SQL命令,執(zhí)行下面的SQL,可以看到從庫(kù)的狀態(tài)信息。通過(guò)狀態(tài)信息中的 Slave_IO_runningSlave_SQL_running 可以看出主從同步是否就緒,如果這兩個(gè)參數(shù)全為 Yes ,表示主從同步已經(jīng)配置完成。

    show slave status\G;
    1.3、坑位介紹
    1.3.1、UUID報(bào)錯(cuò)

    這可能是由于linux 是復(fù)制出來(lái)的,MySQL中還有一個(gè) server_uuid 是一樣的,我們也需要修改。 vim /var/lib/mysql/auto.cnf

    1.3.2、server_id報(bào)錯(cuò)

    這應(yīng)該就是各位大牛設(shè)置server_id的時(shí)候不小心設(shè)置相同的id了,修改過(guò)來(lái)就行,步驟在上面的配置中。

    1.3.3、同步異常解決

    這是狗子在操作過(guò)程中搞出來(lái)的一個(gè)錯(cuò)誤……

    出錯(cuò)的原因是在主庫(kù)中刪除了用戶(hù)信息,但是在從庫(kù)中同步的時(shí)候失敗導(dǎo)致同步停止,下面記錄自己的操作(是在進(jìn)入MySQL的操作且是從庫(kù))。

    MASTER_LOG_POS
    STOP SLAVE;
    SET GLOBAL SQL_SLAVE_SKIP_COUNTER=1;
    START SLAVE;
    SHOW SLAVE STATUS\G;

    在數(shù)據(jù)庫(kù)中操作時(shí),一定要注意當(dāng)前所在的數(shù)據(jù)庫(kù)是哪個(gè),作為一個(gè)良好的實(shí)踐:在SQL語(yǔ)句前加 USE dbname 。

    操作不規(guī)范,親人兩行淚……

    2、項(xiàng)目中實(shí)現(xiàn)

    2.1、ShardingJDBC

    Sharding-JDBC定位為 輕量級(jí)Java框架 ,在Java的JDBC層提供的額外服務(wù)。 它使用客戶(hù)端直連數(shù)據(jù)庫(kù),以 jar包 形式提供服務(wù),無(wú)需額外部署和依賴(lài),可理解為增強(qiáng)版的JDBC驅(qū)動(dòng), 完全兼容JDBC和各種ORM框架

    使用Sharding-JDBC可以在程序中輕松的實(shí)現(xiàn)數(shù)據(jù)庫(kù) 讀寫(xiě)分離 。

    Sharding-JDBC具有以下幾個(gè)特點(diǎn):

    • 適用于任何基于JDBC的ORM框架,如:JPA, Hibernate, Mybatis, Spring JDBC Template或直接使用JDBC。

    • 支持任何第三方的數(shù)據(jù)庫(kù)連接池,如:DBCP, C3P0, BoneCP, Druid, HikariCP等。

    • 支持任意實(shí)現(xiàn)JDBC規(guī)范的數(shù)據(jù)庫(kù)。目前支持MySQL,Oracle,SQLServer,PostgreSQL以及任何遵循SQL92標(biāo)準(zhǔn)的數(shù)據(jù)庫(kù)。

    下面我們將用ShardingJDBC在項(xiàng)目中實(shí)現(xiàn)MySQL的讀寫(xiě)分離。

    2.2、依賴(lài)導(dǎo)入

    在pom.xml文件中導(dǎo)入ShardingJDBC的依賴(lài)坐標(biāo)

    <!--sharding-jdbc-->
    <dependency>
        <groupId>org.apache.shardingsphere</groupId>
        <artifactId>sharding-jdbc-spring-boot-starter</artifactId>
        <version>4.0.0-RC1</version>
    </dependency>
    2.3、配置文件

    在application.yml中增加數(shù)據(jù)源的配置

    spring:
      shardingsphere:
        datasource:
          names:
            master,slave
          # 主數(shù)據(jù)源
          master:
            type: com.alibaba.druid.pool.DruidDataSource
            driver-class-name: com.mysql.cj.jdbc.Driver
            url: jdbc:mysql://192.168.150.100:3306/db_test?useUnicode=true&characterEncoding=utf-8&useSSL=false
            username: root
            password: 123456
          # 從數(shù)據(jù)源
          slave:
            type: com.alibaba.druid.pool.DruidDataSource
            driver-class-name: com.mysql.cj.jdbc.Driver
            url: jdbc:mysql://192.168.150.101:3306/db_test?useUnicode=true&characterEncoding=utf-8&useSSL=false
            username: root
            password: 123456
        masterslave:
          # 讀寫(xiě)分離配置,設(shè)置負(fù)載均衡的模式為輪詢(xún)
          load-balance-algorithm-type: round_robin
          # 最終的數(shù)據(jù)源名稱(chēng)
          name: dataSource
          # 主庫(kù)數(shù)據(jù)源名稱(chēng)
          master-data-source-name: master
          # 從庫(kù)數(shù)據(jù)源名稱(chēng)列表,多個(gè)逗號(hào)分隔
          slave-data-source-names: slave
        props:
          sql:
            show: true #開(kāi)啟SQL顯示,默認(rèn)false
      # 覆蓋注冊(cè)bean,后面創(chuàng)建數(shù)據(jù)源會(huì)覆蓋前面創(chuàng)建的數(shù)據(jù)源
      main:
        allow-bean-definition-overriding: true
    2.4、測(cè)試跑路

    這時(shí)我們就可以對(duì)我們項(xiàng)目中的配置進(jìn)行一個(gè)測(cè)試,下面分別調(diào)用一個(gè)更新接口和一個(gè)查詢(xún)接口,通過(guò)查看日志中記錄的數(shù)據(jù)源來(lái)判斷是否能夠按照我們預(yù)料中的跑。

    以上就是關(guān)于“SpringBoot項(xiàng)目中如何實(shí)現(xiàn)MySQL讀寫(xiě)分離”這篇文章的內(nèi)容,相信大家都有了一定的了解,希望小編分享的內(nèi)容對(duì)大家有幫助,若想了解更多相關(guān)的知識(shí)內(nèi)容,請(qǐng)關(guān)注億速云行業(yè)資訊頻道。

    向AI問(wèn)一下細(xì)節(jié)

    免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如果涉及侵權(quán)請(qǐng)聯(lián)系站長(zhǎng)郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。

    AI