亚洲乱码中文字幕综合,中国熟女仑乱hd,亚洲精品乱拍国产一区二区三区,一本大道卡一卡二卡三乱码全集资源,又粗又黄又硬又爽的免费视频

ShardingSphere結(jié)合MySQL實現(xiàn)分庫分表的項目實踐

 更新時間:2024年03月14日 09:27:56   作者:nana_Wang123  
在實際開發(fā)中,如果表的數(shù)據(jù)過大我們需要把一張表拆分成多張表,本文主要介紹了使用ShardingSphere實現(xiàn)MySQL分庫分表,具有一定的參考價值,感興趣的可以了解一下

ShardingSphere介紹

Apache ShardingSphere 是一套開源的分布式數(shù)據(jù)庫中間件解決方案組成的生態(tài)圈,它由JDBC、Proxy和Sidecar(規(guī)劃中)這3款相互獨立,卻又能夠混合部署配合使用的產(chǎn)品組成。 它們均提供標(biāo)準(zhǔn)化的數(shù)據(jù)分片、分布式事務(wù)和數(shù)據(jù)庫治理功能,可適用于如 Java 同構(gòu)、異構(gòu)語言、云原生等各種多樣化的應(yīng)用場景。

  • 一套開源的分布式數(shù)據(jù)庫中間件解決方案
  • 有3個產(chǎn)品:JDBC、Proxy、Sidecar

分庫分表

當(dāng)我們使用讀寫分離、索引、緩存后,數(shù)據(jù)庫的壓力還是很大的時候,這就需要使用到數(shù)據(jù)庫拆分了。

  • 一般來說, MySQL推薦的單表數(shù)據(jù)量在500w ~ 800w, 超過800w則建議分表.
  • 或是在系統(tǒng)接口響應(yīng)時間明顯變慢, 并且通過代碼優(yōu)化, 改寫sql等形式無法獲得明顯提升, 且明確了性能瓶頸在數(shù)據(jù)庫時, 建議分表
  • 分庫則是在分表后單庫性能到達(dá)瓶頸后進(jìn)行, 如果個人或項目有錢任性的除外.分庫主要解決的是并發(fā)量大的問題。

垂直拆分

分表
表中的字段較多,一般將不常用的、 數(shù)據(jù)較大、長度較長的拆分到“擴展表“。一般情況加表的字段可能有幾百列,此時是按照字段進(jìn)行數(shù)豎直切。注意垂直分是列多的情況。

分庫
一個數(shù)據(jù)庫的表太多。此時就會按照一定業(yè)務(wù)邏輯進(jìn)行垂直切,比如用戶相關(guān)的表放在一個數(shù)據(jù)庫里,訂單相關(guān)的表放在一個數(shù)據(jù)庫里。注意此時不同的數(shù)據(jù)庫應(yīng)該存放在不同的服務(wù)器上,此時磁盤空間、內(nèi)存、TPS等等都會得到解決。

優(yōu)點:

  • 拆分后業(yè)務(wù)清晰,拆分規(guī)則明確。
  • 系統(tǒng)之間整合或擴展容易。
  • 數(shù)據(jù)維護(hù)簡單。

缺點:

  • 部分業(yè)務(wù)表無法 join,只能通過接口方式解決,提高了系統(tǒng)復(fù)雜度。
  • 受每種業(yè)務(wù)不同的限制存在單庫性能瓶頸,不易數(shù)據(jù)擴展跟性能提高。
  • 事務(wù)處理復(fù)雜。

水平拆分

分表
單表的數(shù)據(jù)量太大。按照某種規(guī)則(RANGE,HASH取模等),切分到多張表里面去。 但是這些表還是在同一個庫中,所以庫級別的數(shù)據(jù)庫操作還是有IO瓶頸。這種情況是不建議使用的,因為數(shù)據(jù)量是逐漸增加的,當(dāng)數(shù)據(jù)量增加到一定的程度還需要再進(jìn)行切分。比較麻煩。

分庫
水平分庫理論上切分起來是比較麻煩的,它是指將單張表的數(shù)據(jù)切分到多個服務(wù)器上去,每個服務(wù)器具有相應(yīng)的庫與表,只是表中數(shù)據(jù)集合不同。 水平分庫分表能夠有效的緩解單機和單庫的性能瓶頸和壓力,突破IO、連接數(shù)、硬件資源等的瓶頸。

優(yōu)點:

  • 不存在單庫大數(shù)據(jù),高并發(fā)的性能瓶頸。
  • 對應(yīng)用透明,應(yīng)用端改造較少。
  • 按照合理拆分規(guī)則拆分,join 操作基本避免跨庫。
  • 提高了系統(tǒng)的穩(wěn)定性跟負(fù)載能力。

缺點:

  • 拆分規(guī)則難以抽象。
  • 分片事務(wù)一致性難以解決。
  • 數(shù)據(jù)多次擴展難度跟維護(hù)量極大。
  • 跨庫 join 性能較差。

分片后的常見問題

數(shù)據(jù)傾斜
這個幾乎是無法避免的, 即使是id取模, 也會因為數(shù)據(jù)的刪除導(dǎo)致每張分表的數(shù)據(jù)不一樣, 或者id是UUID, 取模也會導(dǎo)致數(shù)據(jù)發(fā)生傾斜. 但是一般來說傾斜只要不是太離譜, 都在我們的接受范圍以內(nèi).

id生成策略
如果分片之前你的id是遞增的, 那么分片后你就無法保證id的全局唯一性, 這時比較常見的業(yè)內(nèi)方案就是UUID或者SnowFlake.
當(dāng)然如果想要排序和分頁, 就需要有個id生成器去統(tǒng)一集中生成連續(xù)的id(參考下文).

全路由
這個是最糟糕的情況, 這種情況會讓我們的查詢比分片之前還要慢, 可以在自定義的分片算法中校驗這種情況直接拋出異常, 然后coder們根據(jù)日志中的報錯來統(tǒng)計這部分sql加以改寫.

jpa級聯(lián)
如果jpa級聯(lián)中包含分表, 則需要拆除這種級聯(lián)關(guān)系, 以免導(dǎo)致上述全路由情況發(fā)生.

排序&分頁
如果只是單獨分頁, Sharding Sphere會剔除數(shù)據(jù)不寫入內(nèi)存, 實際上不會導(dǎo)致內(nèi)存的大量占用, 但如果加上排序, 那情況就不容樂觀了, 官方建議通過可以保證連續(xù)性的id去加以限制.

四種分片算法&五種分片策略

4種分片算法

精確分片算法
對應(yīng)PreciseShardingAlgorithm,用于處理使用單一鍵作為分片鍵的=與IN進(jìn)行分片的場景。需要配合StandardShardingStrategy使用。

范圍分片算法
對應(yīng)RangeShardingAlgorithm,用于處理使用單一鍵作為分片鍵的BETWEEN AND、>、<、>=、<=進(jìn)行分片的場景。需要配合StandardShardingStrategy使用。

復(fù)合分片算法
對應(yīng)ComplexKeysShardingAlgorithm,用于處理使用多鍵作為分片鍵進(jìn)行分片的場景,包含多個分片鍵的邏輯較復(fù)雜,需要應(yīng)用開發(fā)者自行處理其中的復(fù)雜度。需要配合ComplexShardingStrategy使用。

Hint分片算法
對應(yīng)HintShardingAlgorithm,用于處理使用Hint行分片的場景。需要配合HintShardingStrategy使用。

5種分片策略

標(biāo)準(zhǔn)分片策略
對應(yīng)StandardShardingStrategy。提供對SQL語句中的=, >, <, >=, <=, IN和BETWEEN AND的分片操作支持。StandardShardingStrategy只支持單分片鍵,提供PreciseShardingAlgorithm和RangeShardingAlgorithm兩個分片算法。PreciseShardingAlgorithm是必選的,用于處理=和IN的分片。RangeShardingAlgorithm是可選的,用于處理BETWEEN AND, >, <, >=, <=分片,如果不配置RangeShardingAlgorithm,SQL中的BETWEEN AND將按照全庫路由處理。

復(fù)合分片策略
對應(yīng)ComplexShardingStrategy。復(fù)合分片策略。提供對SQL語句中的=, >, <, >=, <=, IN和BETWEEN AND的分片操作支持。ComplexShardingStrategy支持多分片鍵,由于多分片鍵之間的關(guān)系復(fù)雜,因此并未進(jìn)行過多的封裝,而是直接將分片鍵值組合以及分片操作符透傳至分片算法,完全由應(yīng)用開發(fā)者實現(xiàn),提供最大的靈活度。

行表達(dá)式分片策略
對應(yīng)InlineShardingStrategy。使用Groovy的表達(dá)式,提供對SQL語句中的=和IN的分片操作支持,只支持單分片鍵。對于簡單的分片算法,可以通過簡單的配置使用,從而避免繁瑣的Java代碼開發(fā),如: t_user_$->{u_id % 8} 表示t_user表根據(jù)u_id模8,而分成8張表,表名稱為t_user_0t_user_7

Hint分片策略
對應(yīng)HintShardingStrategy。通過Hint指定分片值而非從SQL中提取分片值的方式進(jìn)行分片的策略。

不分片策略
對應(yīng)NoneShardingStrategy。不分片的策略。

ShardingSphere-JDBC

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

需要注意的是,分庫分表并不是由 ShardingSphere-JDBC 來做,它是用來負(fù)責(zé)操作已經(jīng)分完之后的 CRUD 操作。

水平分表實操(單分片鍵,分片類型:HASH_MODE)

環(huán)境使用:SpringBoot 2.7.12 + MybatisPlus + ShardingSphere-jdbc 5.2.0 + Druid連接池

本示例為單庫,庫內(nèi)有6個分表,并且按照order_id的hash值進(jìn)行取模計算得到實際表

添加Maven依賴

<dependency>
    <groupId>org.mybatis.spring.boot</groupId>
    <artifactId>mybatis-spring-boot-starter</artifactId>
    <version>2.2.2</version>
</dependency>

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter</artifactId>
</dependency>

<dependency>
    <groupId>com.zaxxer</groupId>
    <artifactId>HikariCP</artifactId>
</dependency>

<dependency>
    <groupId>com.mysql</groupId>
    <artifactId>mysql-connector-j</artifactId>
    <scope>runtime</scope>
</dependency>
<dependency>
    <groupId>org.apache.shardingsphere</groupId>
    <artifactId>shardingsphere-jdbc-core-spring-boot-starter</artifactId>
    <version>5.1.0</version>
</dependency>

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-test</artifactId>
    <scope>test</scope>
</dependency>

<dependency>
    <groupId>org.projectlombok</groupId>
    <artifactId>lombok</artifactId>
    <version>1.18.20</version>
</dependency>
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-logging</artifactId>
</dependency>

按照水平分表創(chuàng)建數(shù)據(jù)庫

CREATE TABLE `t_order_5`
(
    `order_id`    bigint NOT NULL AUTO_INCREMENT,
    `price`       double(12,2),
    `user_id`     int    NOT NULL,
    `address_id`  bigint NOT NULL,
    `city`        varchar(32) NULL DEFAULT NULL,
    `status`      tinyint NULL DEFAULT NULL,
    `interval_time` datetime NULL DEFAULT NULL,
    `creator`     varchar(32) NULL DEFAULT NULL,
    `create_time` datetime NULL DEFAULT NULL,
    `updater`     varchar(32) NULL DEFAULT NULL,
    `update_time` datetime NULL DEFAULT NULL,
    PRIMARY KEY (`order_id`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 1 CHARACTER SET = utf8 COLLATE = utf8_general_ci ROW_FORMAT = Dynamic

配置Sharding-jdbc分片策略

application.yml內(nèi)容:

spring:
  main:
    banner-mode: off

  shardingsphere:
    # 配置數(shù)據(jù)源,給數(shù)據(jù)源起別名ds
    datasource:
      ds:
        type: com.zaxxer.hikari.HikariDataSource
        driver-class-name: com.mysql.cj.jdbc.Driver
        jdbc-url: jdbc:mysql://localhost:3306/test?serverTimezone=UTC&useSSL=false&useUnicode=true&characterEncoding=UTF-8
        username: root
        password: 1234
      names: ds
    rules:
      sharding:
        binding-tables:
          - t_order,t_order_item
        broadcast-tables: t_address
        # 分片算法
        sharding-algorithms:
          t-order-algorithm:
            type: HASH_MOD
            props:
              sharding-count: '6'
          t-order-item-inline:
            type: INLINE
            props:
              algorithm-expression: t_order_item_$->{order_id % 2}
        tables:
        # 分表
          t_order:
            actual-data-nodes: ds.t_order_$->{0..5}   # 真實表名
            table-strategy:
              standard:
                sharding-algorithm-name: t-order-algorithm
                sharding-column: order_id   # 分片鍵
          t_order_item:
            actual-data-nodes: ds.t_order_item_$->{0..1}
            table-strategy:
              standard:
                sharding-algorithm-name: t-order-item-inline
                sharding-column: order_id
    props:
      sql-show: true



#mybatis-plus:
#  global-config:
#    banner: false
#    db-config:
#      id-type: assign_id  #使用雪花算法開啟數(shù)據(jù)入庫時ID自增
#      logic-delete-field: deleted
#      logic-delete-value: 1
#      logic-not-delete-value: 0
#  #開啟mp的日志(控制臺輸出)
#  configuration:
#    log-impl: org.apache.ibatis.logging.stdout.StdOutImpl

mybatis:
  mapper-locations: classpath*:/mappers/*-mapper.xml
  type-aliases-package: com.panliu.domain
  configuration:
    default-fetch-size: 20
    default-statement-timeout: 30
    map-underscore-to-camel-case: true
    use-generated-keys: true

測試代碼運行

@Slf4j
@SpringBootTest
public class OrderMapperTests {
    private final static String[] CITIES = {"shanghai", "beijing"};
    /**
     * -120000, 0, 18, 20000, 40000, 50000, 60000, 64000, 80000, 99000
     */
    private final static long[] PRICES = {-120000, 0, 18, 20000, 40000, 50000, 60000, 64000, 80000, 99000};
    @Autowired
    private OrderMapper orderMapper;

    @Test
    //@Disabled
    void save() {
        ThreadLocalRandom random = ThreadLocalRandom.current();

        Date[] dates = create();
        IntStream.range(0, 20).forEach(i -> {
            Order order = new Order();
            order.setOrderId(System.nanoTime() + i);
            order.setPrice(PRICES[i % PRICES.length]);
            order.setAddressId(i);
            order.setCity(CITIES[i % 2]);
            order.setUserId(Math.abs(random.nextInt()));
            order.setCreator("user.0" + i);
            order.setIntervalTime(dates[i % 5]);
            order.setUpdater(order.getCreator());
            log.info("====>{}", order);
            orderMapper.save(order);
        });
    }

    @Test
   // @Disabled
    void findAll() {
        List<Order> list = orderMapper.findAllAtPrice(60000);
        log.info("===>{}", list);
    }

    private Date[] create() {
        Date[] dates = new Date[6];

        try {
            Date date = DateUtils.parseDate("2023-08-14 00:00:00", Locale.CHINA, "yyyy-MM-dd HH:mm:ss");
            IntStream.range(0, 6).forEach(i -> dates[i] = DateUtils.addDays(date, i));
        } catch (ParseException e) {
            log.error("date parse fail: ", e);
        }
        return dates;
    }
}

運行結(jié)果

在這里插入圖片描述

在這里插入圖片描述

在這里插入圖片描述

復(fù)合分片(根據(jù)城市和order_id分片)

application.yml配置

rules:
  sharding:
    sharding-algorithms:
      t-order-algorithm:
        type: COMPLEX_INLINE
        props:
          algorithm-expression: t_order_$->{city}_$->{order_id % 2}
          sharding-columns: city,order_id
    tables:
      t_order:
        actual-data-nodes: ds.t_order_$->{['shanghai','beijing']}_$->{0..1}
        table-strategy:
          complex:
            sharding-algorithm-name: t-order-algorithm
            sharding-columns: city,order_id

分片結(jié)果

在這里插入圖片描述

在這里插入圖片描述

到此這篇關(guān)于使用ShardingSphere實現(xiàn)MySQL分庫分表的文章就介紹到這了,更多相關(guān)ShardingSphere MySQL分庫分表內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • Spring Boot整合FTPClient線程池的實現(xiàn)示例

    Spring Boot整合FTPClient線程池的實現(xiàn)示例

    這篇文章主要介紹了Spring Boot整合FTPClient線程池的實現(xiàn)示例,小編覺得挺不錯的,現(xiàn)在分享給大家,也給大家做個參考。一起跟隨小編過來看看吧
    2018-12-12
  • 關(guān)于maven環(huán)境的安裝及maven集成idea環(huán)境的問題

    關(guān)于maven環(huán)境的安裝及maven集成idea環(huán)境的問題

    Maven 是一個基于 Java 的工具,所以要做的第一件事情就是安裝 JDK。本文重點給大家介紹關(guān)于maven環(huán)境的安裝及和idea環(huán)境的集成問題,感興趣的朋友一起看看吧
    2021-09-09
  • Java+MySQL實現(xiàn)設(shè)計優(yōu)惠券系統(tǒng)

    Java+MySQL實現(xiàn)設(shè)計優(yōu)惠券系統(tǒng)

    這篇文章主要介紹了Java+MySQL實現(xiàn)設(shè)計優(yōu)惠券系統(tǒng),文章基于Java與MySQL的相關(guān)資料展開詳細(xì)的內(nèi)容介紹,具有一定的參考價值,需要的小伙伴可以參考一下
    2022-05-05
  • 因不會遠(yuǎn)程debug調(diào)試我被項目經(jīng)理嘲笑了

    因不會遠(yuǎn)程debug調(diào)試我被項目經(jīng)理嘲笑了

    這篇文章主要介紹了遠(yuǎn)程debug調(diào)試的相關(guān)內(nèi)容,本文給大家介紹的非常詳細(xì),對大家的學(xué)習(xí)或工作具有一定的參考借鑒價值,需要的朋友可以參考下
    2021-08-08
  • 解決poi導(dǎo)出excel無法打開文件的問題

    解決poi導(dǎo)出excel無法打開文件的問題

    這篇文章主要介紹了解決poi導(dǎo)出excel無法打開文件的問題,具有很好的參考價值,希望對大家有所幫助,如有錯誤或未考慮完全的地方,望不吝賜教
    2023-12-12
  • java實現(xiàn)桌球游戲

    java實現(xiàn)桌球游戲

    這篇文章主要為大家詳細(xì)介紹了java實現(xiàn)桌球游戲,文中示例代碼介紹的非常詳細(xì),具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2019-10-10
  • fastjson 使用方法詳細(xì)介紹

    fastjson 使用方法詳細(xì)介紹

    Fastjson是一個Java語言編寫的JSON處理器,由阿里巴巴公司開發(fā)。接下來通過本文給大家分享fastjson 使用方法詳細(xì)介紹,感興趣的朋友一起看看吧
    2017-11-11
  • 基于google zxing的Java二維碼生成與解碼

    基于google zxing的Java二維碼生成與解碼

    這篇文章主要為大家詳細(xì)介紹了基于google zxing的Java二維碼生成與解碼,具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2017-07-07
  • 自定義@RequestBody注解如何獲取JSON數(shù)據(jù)

    自定義@RequestBody注解如何獲取JSON數(shù)據(jù)

    這篇文章主要介紹了自定義@RequestBody注解如何獲取JSON數(shù)據(jù)問題,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教
    2023-04-04
  • 解決idea創(chuàng)建版本時只有Java21和Java17選項

    解決idea創(chuàng)建版本時只有Java21和Java17選項

    你是否在使用IntelliJ?IDEA創(chuàng)建新項目時遇到了只有Java?21和Java?17的選項?別擔(dān)心,我們的指南將為你提供解決方案,通過簡單的步驟,你將能夠選擇你需要的任何Java版本,繼續(xù)閱讀,讓我們開始吧!
    2024-03-03

最新評論