精品欧美一区二区三区在线观看 _久久久久国色av免费观看性色_国产精品久久在线观看_亚洲第一综合网站_91精品又粗又猛又爽_小泽玛利亚一区二区免费_91亚洲精品国偷拍自产在线观看 _久久精品视频在线播放_美女精品久久久_欧美日韩国产成人在线

實戰:Springboot3+ShardingSphere5.2.1生產級分庫分表實現

數據庫 其他數據庫
我們完成了在DailyMart中集成分庫分表功能的實踐,大家在實施分庫分表過程中一定要結合自己的業務實際選擇合理的分片鍵,分片鍵的好壞決定了你分庫分表架構方案的好壞。

大家好,我是飄渺。

隨著業務的不斷發展,DailyMart每天產生的銷售訂單已經達到了約100萬,并且呈持續增長趨勢。按照這樣的發展速度,每年的數據量將達到約4億左右。目前,DailyMart采用的是MySQL單表進行存儲,但鑒于業務的快速發展,我們迫切需要對其進行分庫分表的改造。今天,我們來探討如何實現分庫分表功能,以及相關的步驟和注意事項。

這是本系列文章的第31篇,歡迎持續關注。

對于分庫分表的相關知識,我的星球分庫分表專欄有詳細的介紹說明,強烈推薦大家加入學習。

分庫分表的核心在于合理選擇分片鍵以及快速定位非分片鍵的數據。

分片鍵的選擇

DailyMart作為一個ToC的業務系統,大部分業務訪問都是基于用戶ID進行的,比如登錄用戶查看自己的購買記錄等。因此,對于訂單模塊我們決定以用戶ID作為分片鍵。

在訂單模塊中,訂單主表 CUSTOMER_ORDER 和訂單明細表 ORDER_ITEM 是最核心的兩張表,由于它們經常會一起使用,我們也需要將訂單明細表的用戶字段 CUSTOMER_ID 作為分片鍵,以確保基于用戶維度的查詢在單個分片上完成。下面是一個示例SQL:

SELECT * FROM CUSTOMER_ORDER ORDER
LEFT JOIN ORDER_ITEM ITEM ON ORDER.order_sn = ITEM.order_sn
WHERE ORDER.customer_id = 2846741676215238657
ORDER BY create_time DESC LIMIT 10

非分片鍵查詢

既然確定使用用戶ID作為分片鍵,大部分查詢都需要帶上CUSTOMER_ID作為查詢條件。但在實際使用中,經常會根據訂單編號ORDER_SN進行精確查詢,比如庫存扣減、支付后的反查等。在默認情況下,根據訂單編號(非分片鍵)進行查詢將需要在所有分片上進行查詢,然后對結果進行聚合,顯然這樣的查詢效率是很低的。

為了解決這個問題,業界一般采用基因法來解決,即將分片鍵的信息保存在想要查詢的列中,這樣通過查詢的列就能直接知道數據所在的分片信息。

基因法的原理是 對一個數取余2的n次方,那么余數就是這個數的二進制的最后n位數。

以訂單表為例,對訂單表我們根據CUSOMER_ID將其拆成16張表,采用CUSOMER_ID % 16的方式來進行數據庫路由,這里的CUSOMER_ID % 16,其本質是CUSOMER_ID的最后4個bit位 log(16,2) = 4 決定這行數據落在哪個分片上,這4個bit就是分片基因。

基于這一理論,基因法有兩種具體的實現:

基因替換法

  1. 在生成訂單編號ORDER_SN時,先使用一種分布式ID生成算法生成前60bit
  2. 計算出分片基因:分庫基因是CUSTOMER_ID的最后4個bit,log(16,2) = 4,即1001
  3. 將分庫基因加入到ORDER_SN的最后4個bit(上圖中粉色部分)
  4. 拼裝成最終的64bit訂單ORDER_SN(上圖中藍色部分)

圖片圖片

這樣保證了同一個用戶創建的所有訂單都落到了同一個分片上,ORDER_SN的最后4個bit都相同,通過CUSTOMER_ID %16 能夠定位到分片,通過ORDER_SN % 16也能定位到分片。

基因替換法可能會導致ORDER_SN重復,以雪花算法為例,假設同一個用戶在一毫秒內創建了 2 個訂單,這樣生產的序列號相差1,替換掉基因后對應的二進制都相同了,導致ORDER_SN也是重復的。但這種情況非常少見,除非是機器人刷單。當然如果要徹底杜絕訂單編號重復問題可以使用下面介紹的基因拼接法。

基因拼接法

基因拼接法更簡單,就是在構建訂單編號時直接將用戶基因拼接在生成的ID后面,即:ORDER_SN = string(ORDER_SN + CUSTOMER_ID)

假設開始生成的訂單號是3531318506608209922,用戶ID為2846741676215238658,那最終生成的編號為35313185066082099222846741676215238658。為了減少長度,我們可以只取用戶ID的最后6位進行拼接,生成的編號為3531318506608209922238658,這樣可以支持2^6=64個分片。

那么此時如果根據 ORDER_SN 進行查詢:

SELECT * FROM CUSTOMER_ORDER
WHERE ORDER_SN = '3531318506608209922238658';

由于字段 ORDER_SN 的設計中直接包含了分片鍵信息,所以我們可以直接通過分片鍵部分直接定位到分片上。

基因拼接法的缺點是,對應的鍵會變大一些,存儲也會相應變大,但是卻可以大大提升后續的查詢效率,這種空間換時間的設計,總體上看是非常值得的。

實際上淘寶的訂單號也是這樣構建的,如下圖所示,訂單的最后6位都是607041,所以大概率推測出:

  1. 淘寶訂單表的分片鍵是用戶 ID;
  2. 淘寶訂單表,訂單表的主鍵包含用戶 ID,也就是分片信息。這樣通過訂單號進行查詢,可以獲得分片信息,從而查詢 1 個分片就能得到最終的結果。

圖片圖片

代碼實現

在DailyMart中選擇使用shardingsphere實現分庫分表功能,不過為了方便演示,我在這里只進行分表操作。

1、首先,將原始訂單表和訂單明細表分別拆成4個表

圖片圖片

2、在訂單模塊基礎設施層中引入shardingsphere,

<dependency>
  <groupId>org.apache.shardingsphere</groupId>
  <artifactId>shardingsphere-jdbc-core-spring-boot-starter</artifactId>
  <version>5.2.1</version>
</dependency>

3、編寫復合分片算法,實現基于order_sn和customer_id的查詢

public class OrderGenComplexTableAlgorithm implements ComplexKeysShardingAlgorithm<Comparable<?>> {
  ...
    @Override
    public Collection<String> doSharding(Collection<String> availableTargetNames, ComplexKeysShardingValue<Comparable<?>> shardingValue) {

        Map<String, Collection<Comparable<?>>> columnNameAndShardingValuesMap = shardingValue.getColumnNameAndShardingValuesMap();

        Collection<String> result = new LinkedHashSet<>(availableTargetNames.size());

        if(MapUtils.isNotEmpty(columnNameAndShardingValuesMap)){
            // 獲取用戶ID
            Collection<Comparable<?>> userIdCollection = columnNameAndShardingValuesMap.get(USER_ID_COLUMN);
            //用戶分片
            if(CollectionUtils.isNotEmpty(userIdCollection)){
                userIdCollection.stream().findFirst().ifPresent(comparable -> {
                    long tableNameSuffix = (Long) comparable % shardingCount;
                    result.add(shardingValue.getLogicTableName() + "_" + tableNameSuffix);
                });
            }else {
                Collection<Comparable<?>> orderSnCollection = columnNameAndShardingValuesMap.get(ORDER_ID_COLUMN);
                orderSnCollection.stream().findFirst().ifPresent(comparable -> {
                    String orderSn = String.valueOf(comparable);
                    //獲取用戶基因
                    String substring = orderSn.substring(Math.max(0, orderSn.length() - 6));
                    long tableNameSuffix = Long.parseLong(substring) % shardingCount;
                    result.add(shardingValue.getLogicTableName() + "_" + tableNameSuffix);
                });
            }
        }
        return result;
    }
  ...
}

在上述代碼中,當通過用戶ID進行查詢時直接通過分片鍵取模定位分片,如果是基于訂單查詢先獲取用戶基因,再根據用戶基因取模定位分片。

4、在application.yaml中配置分庫分表

spring:
  shardingsphere:
    datasource:
      names: ds0
      ds0:
        type: com.zaxxer.hikari.HikariDataSource
        driver-class-name: org.mariadb.jdbc.Driver
    rules:
      sharding:
        sharding-algorithms:
          order-gen-complex-sharding:
            type: CLASS_BASED
            props:
              strategy: COMPLEX
              algorithmClassName: com.jianzh5.dailymart.module.order.infrastructure.config.OrderGenComplexTableAlgorithm
              sharding-count: 4
        tables:
          customer_order:
            actual-data-nodes: ds0.customer_order_$->{0..3}
            table-strategy:
              complex:
                sharding-algorithm-name: order-gen-complex-sharding
                sharding-columns: order_sn,customer_id
          order_item:
            actual-data-nodes: ds0.order_item_$->{0..3}
            table-strategy:
              complex:
                sharding-algorithm-name: order-gen-complex-sharding
                sharding-columns: order_sn,customer_id

通過上述步驟,在訂單模塊中已經集成了分庫分表功能,接下來編寫兩個接口對其進行測試。

測試

在訂單模塊的接口層我們定義了兩個接口用于模擬實際的業務場景:1、獲取指定用戶的訂單分頁列表;2、根據訂單編號獲取訂單詳情。

接口定義如下:

@Operation(summary = "根據用戶ID分頁查詢訂單")
@GetMapping("/api/pd/order/page")
public PageResponse<OrderRespDTO> pageQuery(@Valid OrderPageQueryDTO orderPageQueryDTO) {
  return orderService.findListByUserId(orderPageQueryDTO);
}


@Operation(summary = "根據訂單號查詢訂單詳情")
@GetMapping("/api/pd/order/{orderSn}")
public OrderRespDTO getOrderBySn(@PathVariable("orderSn") String orderSn) {
  return orderService.getOrderBySn(orderSn);
}

通過運行結果可知,根據用戶訂單獲取分頁列表時直接根據Customer_id取模,只需要一次查詢即可定位。

圖片圖片

當根據訂單號查詢訂單詳情時,根據用戶基因取模,同樣也只需要一次查詢即可定位。

圖片圖片

小結

通過以上步驟,我們完成了在DailyMart中集成分庫分表功能的實踐,大家在實施分庫分表過程中一定要結合自己的業務實際選擇合理的分片鍵,分片鍵的好壞決定了你分庫分表架構方案的好壞。

責任編輯:武曉燕 來源: JAVA日知錄
相關推薦

2024-03-08 08:43:30

2023-08-11 08:59:49

分庫分表數據數據庫

2020-11-17 08:08:34

分庫分表

2022-10-10 17:37:59

分庫分表訂單業務

2020-07-30 17:59:34

分庫分表SQL數據庫

2022-06-30 07:34:46

分庫分表外賣訂單系統

2011-08-16 14:41:33

蘋果iPad3

2019-11-12 09:54:20

分庫分表數據

2022-10-11 17:51:49

分庫分表數據庫

2021-09-08 09:48:39

數據庫工具技術

2022-07-01 10:37:18

分庫分表數據庫

2021-08-31 20:21:11

VitessMySQL分庫

2020-11-18 09:39:02

MySQL數據庫SQL

2025-02-10 08:20:09

2022-07-11 08:16:47

NewSQL關系數據庫系統

2021-01-26 05:37:08

分庫分表內存

2020-07-28 09:04:09

NewSQL分庫分表

2024-07-26 00:16:11

2025-04-01 08:45:00

2021-07-28 15:44:52

Java開發數據庫
點贊
收藏

51CTO技術棧公眾號

欧美一区二区播放| 亚洲视频在线观看三级| 97在线视频一区| 能免费看av的网站| 91麻豆精品国产91久久久更新资源速度超快| 亚洲人成影院在线观看| 国产成人看片| 国产精品第六页| 欧美日本中文| 国产亚洲精品成人av久久ww | 新67194成人永久网站| 亚洲亚裔videos黑人hd| 亚洲精品乱码久久久久久9色| 永久免费毛片在线播放| 成人免费视频在线观看| 极品日韩久久| 国产免费黄色录像| 视频一区中文字幕| 久久久久久久久久久成人| 免费看黄色av| 激情av综合| 4438x成人网最大色成网站| 婷婷五月综合缴情在线视频| 91社区在线观看播放| 成人18精品视频| 成人欧美在线视频| 蜜臀99久久精品久久久久小说| 欧美日韩亚洲一区三区| 色一区av在线| 精品无码在线观看| 日韩精品a在线观看91| 欧美一级一区二区| the porn av| 芒果视频成人app| 亚洲高清免费视频| 色哟哟免费网站| 男人天堂久久久| 日本一区二区三区久久久久久久久不 | 老司机av福利| 精品乱码一区二区三四区视频 | 国产精品女主播一区二区三区| 久久精品夜夜夜夜夜久久| 国产成人精品亚洲精品| 91麻豆文化传媒在线观看| 中文字幕av一区二区三区佐山爱| 久久精品亚洲a| 欧美人与牲禽动交com| 久久九九全国免费| 精品视频一区二区| www.国产视频| 国产乱子伦一区二区三区国色天香| 国产精品久久99久久| 黄色在线免费观看| 亚洲在线观看| 97在线视频观看| 亚洲一区 视频| 亚洲欧洲一区| 午夜精品www| 国产在线精品观看| 先锋a资源在线看亚洲| 4p变态网欧美系列| 成人av网站在线播放| 日韩黄色免费电影| 日本亚洲欧美三级| 日本熟妇乱子伦xxxx| 伊人久久大香线蕉av超碰演员| 国产亚洲精品久久久久久777 | 亚洲精品成人图区| 亚洲高清三级视频| 成人免费观看视频在线观看| 婷婷激情一区| 这里只有精品免费| 亚洲黄色小说在线观看| 欧美大奶一区二区| 亚洲日韩欧美视频一区| 国产三级在线观看完整版| 青青草成人影院| 久久精品电影一区二区| 欧美日韩人妻精品一区二区三区| 1024日韩| 国产精品高潮呻吟视频| 99久久久无码国产精品免费| 岛国av在线一区| 欧美日韩国产三区| 免费大片在线观看www| 一区二区成人在线视频| 久久久久久久久久久久久国产精品| 88xx成人永久免费观看| 5月丁香婷婷综合| 无码国产69精品久久久久网站| 自拍视频一区| 久久视频在线看| 日本高清www免费视频| 日韩电影在线观看一区| 国产精品theporn88| 国产永久免费高清在线观看 | 久久久久久激情| 9久re热视频在线精品| 国产剧情久久久久久| 成人黄色在线观看视频| 久久久久久久电影| 国产手机视频在线观看| 伊人色综合一区二区三区影院视频| 欧美日韩三级在线| 国产高潮视频在线观看| 日韩欧美午夜| 欧美一级大片在线免费观看| 一二三区在线播放| 99精品视频一区二区| 亚洲精品中文字幕在线| 欧美freesex黑人又粗又大| 在线不卡中文字幕播放| 星空大象在线观看免费播放| 天天影视欧美综合在线观看| 国产va免费精品高清在线| 精品国产免费无码久久久| 久久久久久97三级| 丰满的少妇愉情hd高清果冻传媒| 国产一区精品福利| 亚洲欧美资源在线| 在线观看 中文字幕| 免费成人av资源网| 91视频在线免费观看| 婷婷在线免费观看| 一区二区三区毛片| 日韩 国产 一区| 清纯唯美日韩| 日韩av电影在线免费播放| 高清乱码毛片入口| 国产精品白丝在线| 亚洲最大综合网| 男男gay无套免费视频欧美| 久久免费观看视频| www香蕉视频| 亚洲男同性视频| 国内自拍第二页| 欧美xxav| 成人字幕网zmw| 美女黄视频在线观看| 欧美中文字幕一二三区视频| 37p粉嫩大胆色噜噜噜| 99在线观看免费视频精品观看| 俄罗斯精品一区二区| 国产剧情在线| 欧美一二三在线| 婷婷社区五月天| 国内精品写真在线观看| 亚洲一区二区在线看| 久久人人视频| 亚洲人a成www在线影院| 国产91国语对白在线| 久久久不卡影院| 国产免费观看高清视频| 欧美日韩另类图片| 欧美在线一区二区视频| 你懂的在线免费观看| 色综合色综合色综合色综合色综合 | 欧美视频观看一区| 综合在线影院| 色婷婷久久av| 国产绳艺sm调教室论坛| 亚洲色图清纯唯美| 粗大的内捧猛烈进出视频| 欧美成人精品| 国产日韩精品一区观看| 色吧亚洲日本| 中文字幕亚洲欧美日韩高清| 一本色道久久综合亚洲| 亚洲精品视频在线看| 欧美性猛交xx| 国产精品亚洲综合久久| 欧美一卡2卡3卡4卡无卡免费观看水多多| 亚洲同志男男gay1069网站| 亚洲视频在线观看视频| 91丨porny丨在线中文 | 日韩免费av网站| 国产精品卡一卡二| 国产一级片中文字幕| 亚洲人成人一区二区三区| 欧美精品亚洲| 亚洲男男av| 孩xxxx性bbbb欧美| 噜噜噜在线观看播放视频| 欧美欧美欧美欧美首页| 国产一级aa大片毛片| 久久久久久免费网| 永久免费的av网站| 在线播放一区| 亚洲精品久久久久久一区二区| 一区二区亚洲视频| 国产精品第一第二| 影院在线观看全集免费观看| 亚洲免费电影一区| 国产99久久九九精品无码免费| 精品国产1区2区| 国产成人自拍网站| 91美女在线观看| 久久久久久久久久一区二区| 亚洲黄色三级| 中文字幕99| 一区三区在线欧| 高清日韩一区| 国产欧美自拍| 欧美在线视频观看| 亚洲综合影视| 色小说视频一区| 欧美美女色图| 亚洲风情亚aⅴ在线发布| 中文字幕一区二区久久人妻| 午夜免费久久看| 少妇影院在线观看| 欧美国产亚洲另类动漫| 影音先锋人妻啪啪av资源网站| 久久 天天综合| 欧美一级黄色片视频| 亚洲视频一区| 日本xxx免费| 日韩伦理视频| 日产国产精品精品a∨| 丝袜久久网站| 国产伦精品一区二区三区视频孕妇| 亚洲精品成a人ⅴ香蕉片| 国产不卡一区二区在线播放| а√在线中文网新版地址在线| 美女av一区二区三区| √天堂资源地址在线官网| 亚洲欧美日韩精品| 四虎精品在线| 亚洲电影中文字幕| 成人午夜视频一区二区播放| 3d成人h动漫网站入口| 正在播放亚洲精品| 色爱区综合激月婷婷| 国产精品自拍99| 天天爽夜夜爽夜夜爽精品视频| 九九九免费视频| 一区二区三区资源| 国语对白在线播放| ...av二区三区久久精品| 中文字幕第二区| 日本一区二区三区四区在线视频| 法国空姐电影在线观看| 91在线一区二区| 久久久久久久久免费看无码| av亚洲精华国产精华| 无码国产精品一区二区免费式直播| 国产精品99久| 涩视频在线观看| 成人一区二区视频| 91精品小视频| 91在线丨porny丨国产| 亚洲做受高潮无遮挡| 久久久99精品久久| 国产又黄又粗的视频| 国产精品久久久久毛片软件| 亚洲女同二女同志奶水| 国产精品短视频| tube国产麻豆| 亚洲电影一区二区三区| 国产成人亚洲欧洲在线| 欧美性猛交xxxx乱大交| 欧美超碰在线观看| 欧美色爱综合网| 国产人妖一区二区| 精品国内二区三区| 天堂91在线| 中文字幕久久亚洲| 麻豆网站在线看| 操91在线视频| 狠狠操一区二区三区| 日本午夜人人精品| 亚洲欧洲专区| 国产精品视频在线免费观看| 色婷婷综合久久久久久| 日韩av图片| 中文字幕午夜精品一区二区三区 | 国产精品一区视频网站| 欧美三级午夜理伦三级小说| 日韩精品资源| 欧美私人啪啪vps| 女人和拘做爰正片视频| 青青草一区二区三区| 粗大的内捧猛烈进出视频| 久久一区二区三区国产精品| 黄视频网站免费看| 精品福利在线视频| 国产又黄又粗又猛又爽| 日韩成人免费视频| 免费观看在线午夜影视| 4388成人网| 成人午夜888| 欧美不卡三区| 欧美精品91| 嫩草av久久伊人妇女超级a| 国产一区不卡在线| 久久av无码精品人妻系列试探| 1区2区3区欧美| www.国产色| 日韩一区二区电影网| 男人的天堂在线视频| 欧美黑人国产人伦爽爽爽| 浪潮色综合久久天堂| 99国产超薄丝袜足j在线观看 | 成人一区二区在线观看| 天美传媒免费在线观看| 丁香五六月婷婷久久激情| 亚洲中文一区二区三区| 精品香蕉在线观看视频一| 中文在线字幕免费观看| 国产精品视频一区二区三区四| 黄色免费大全亚洲| 天堂av免费看| 免费看欧美女人艹b| 朝桐光av一区二区三区| 亚洲欧美偷拍三级| 伊人网视频在线| 亚洲免费人成在线视频观看| 日本高清在线观看视频| 成人福利免费观看| 国产亚洲欧美日韩在线观看一区二区| 国产一区二区三区在线免费| 久久99精品视频| 成年人在线免费看片| 日韩欧美国产激情| 日韩在线视频观看免费| 欧美激情精品久久久久久蜜臀| 在线日韩三级| 杨幂一区欧美专区| 蜜臀av性久久久久蜜臀aⅴ| 在线观看福利片| 精品日本美女福利在线观看| 男人的天堂a在线| 欧美日韩成人在线观看| 日本超碰一区二区| 爱爱爱视频网站| 久久激情综合网| 女人裸体性做爰全过| 欧美中文字幕一二三区视频| 国产日产精品久久久久久婷婷| 国产91精品高潮白浆喷水| 看全色黄大色大片免费久久久| 免费网站在线观看视频| 国产高清不卡一区| 免费在线观看av网址| 精品久久久久久久人人人人传媒 | av资源久久| 性生交免费视频| 国产精品久久久久一区二区三区共| 在线观看中文字幕av| 色噜噜亚洲精品中文字幕| 日韩精品一区二区三区av| 亚洲制服中文| 国产剧情一区在线| 久久婷婷一区二区| 亚洲韩国青草视频| 电影网一区二区| 先锋影音亚洲资源| 国模大尺度一区二区三区| 国产精品老熟女一区二区| 亚洲精品一区二区三区香蕉 | 亚洲高清影视| 国产吃瓜黑料一区二区| 五月天亚洲精品| 国产在线视频网站| 成人国产精品一区二区| 欧美88av| 玖玖爱在线精品视频| 91国偷自产一区二区使用方法| 最新97超碰在线| 99视频在线| 久久国产直播| fc2ppv在线播放| 亚洲第一色在线| 怡红院成人在线| 喜爱夜蒲2在线| 99久久久免费精品国产一区二区| 精品视频一二三区| 久久伊人免费视频| 偷拍视屏一区| 拔插拔插华人永久免费| 亚洲国产中文字幕| lutube成人福利在线观看| 91黄色国产视频| 亚洲影院免费| 日本一级二级视频| 亚洲国产三级网| 亚洲色图综合| www国产精品内射老熟女| 国产精品国产三级国产a| 成人毛片在线免费观看| 国产精品免费久久久| 国内自拍一区| 久久久久久成人网| 日韩欧美国产成人一区二区| 日韩一区精品| 精品丰满人妻无套内射| 国产精品乱子久久久久| 无码国产精品一区二区色情男同| 国产精品久久久久久久一区探花| 国产在线成人|