自拍偷在线精品自拍偷,亚洲欧美中文日韩v在线观看不卡

從SQL Server到MySQL,近百億數(shù)據(jù)量遷移實(shí)戰(zhàn)

數(shù)據(jù)庫 SQL Server MySQL
本文主要向大家介紹,從 SQL Server 遷移到 MySQL 所面臨的問題和我們的解決方案。

我們成立于 2001 年,作為較早期的教育學(xué)習(xí)網(wǎng)站,當(dāng)時(shí)技術(shù)選型范圍并不大:Java 的版本是 1.2,C# 尚未誕生,MySQL 還沒有被 Sun 收購,版本號是 3.23。工程師們選擇了當(dāng)時(shí)最合適的微軟體系,并在日后的歲月里,逐步從 ASP 過度到 .net,數(shù)據(jù)庫也跟隨 SQL Server 進(jìn)行版本升級。

十幾年過去了,技術(shù)社區(qū)已經(jīng)發(fā)生了天翻地覆的變化。滬江部分業(yè)務(wù)還基本在 .net 體系上,這給業(yè)務(wù)持續(xù)發(fā)展帶來了一些限制,在人才招聘、社區(qū)生態(tài)、架構(gòu)優(yōu)化、成本風(fēng)險(xiǎn)方面都面臨挑戰(zhàn)。集團(tuán)經(jīng)過慎重考慮,發(fā)起了大規(guī)模的去 Windows 化項(xiàng)目。這其中包含兩個(gè)重點(diǎn)子項(xiàng)目:開發(fā)語言從 C# 遷移到 Java,數(shù)據(jù)庫從 SQL Server 遷移到 MySQL。

本文主要向大家介紹,從 SQL Server 遷移到 MySQL 所面臨的問題和我們的解決方案。

遷移方案的基本流程

設(shè)計(jì)遷移方案需要考量以下幾個(gè)指標(biāo):

  • 遷移前后的數(shù)據(jù)一致性;
  • 業(yè)務(wù)停機(jī)時(shí)間;
  • 遷移項(xiàng)目是否對業(yè)務(wù)代碼有侵入;
  • 需要提供額外的功能:表結(jié)構(gòu)重構(gòu)、字段調(diào)整。

經(jīng)過仔細(xì)調(diào)研,在平衡復(fù)雜性和業(yè)務(wù)方需求后,遷移方案設(shè)計(jì)為兩種:停機(jī)數(shù)據(jù)遷移和在線數(shù)據(jù)遷移。如果業(yè)務(wù)場景允許數(shù)小時(shí)的停機(jī),那么使用停機(jī)遷移方案,復(fù)雜度低,數(shù)據(jù)損失風(fēng)險(xiǎn)低。如果業(yè)務(wù)場景不允許長時(shí)間停機(jī),或者遷移數(shù)據(jù)量過大,無法在幾個(gè)小時(shí)內(nèi)遷移完成,那么就需要使用在線遷移方案了。

數(shù)據(jù)庫停機(jī)遷移的流程:

從SQL Server到MySQL,近百億數(shù)據(jù)量遷移實(shí)戰(zhàn)

 

停機(jī)遷移邏輯比較簡單,使用 ETL(Extract Translate Load) 工具從 Source 寫入 Target,然后進(jìn)行一致性校驗(yàn),***確認(rèn)應(yīng)用運(yùn)行 OK,將 Source 表名改掉進(jìn)行備份。

在線遷移的流程:

從SQL Server到MySQL,近百億數(shù)據(jù)量遷移實(shí)戰(zhàn)

 

在線遷移的方案稍微復(fù)雜一些,流程上有準(zhǔn)備全量數(shù)據(jù),然后實(shí)時(shí)同步增量數(shù)據(jù), 在數(shù)據(jù)同步跟上(延遲秒級別)之后,進(jìn)行短暫停機(jī)(Hang 住,確保沒有流量),就可以使用新的應(yīng)用配置,并使用新的數(shù)據(jù)庫。

需要解決的問題

從 SQL Server 遷移到 MySQL,核心是完成異構(gòu)數(shù)據(jù)庫的遷移。

基于兩種數(shù)據(jù)遷移方案,我們需要解決以下問題:

  • 兩個(gè)數(shù)據(jù)庫的數(shù)據(jù)結(jié)構(gòu)是否可以一一對應(yīng)?出現(xiàn)不一致如何處理?
  • MySQL 的使用方式和 SQL Server 使用方式是否一致?有哪些地方需要注意?
  • 如何確保遷移前后的數(shù)據(jù)一致性?
  • 在遷移中,如何支持?jǐn)?shù)據(jù)結(jié)構(gòu)調(diào)整?
  • 如何保證業(yè)務(wù)不停情況下,實(shí)現(xiàn)在線遷移?
  • 數(shù)據(jù)遷移后如果發(fā)現(xiàn)業(yè)務(wù)異常需要回滾,如何處理新產(chǎn)生的數(shù)據(jù)?

為了解決以上問題,我們需要引入一整套解決方案,包含以下部分:

  • 指導(dǎo)文檔 A:SQL Server 轉(zhuǎn)換 MySQL 的數(shù)據(jù)類型對應(yīng)表;
  • 指導(dǎo)文檔 B:MySQL 的使用方式以及注意點(diǎn);
  • 支持表結(jié)構(gòu)變更,從 SQL Server 到 MySQL 的 ETL 工具;
  • 支持 SQL Server 到 MySQL 的在線 ETL 工具;
  • 一致性校驗(yàn)工具;
  • 一個(gè)回滾工具。

讓我們一一來解決這些問題。

SQL Server 到 MySQL 指導(dǎo)文檔

非常幸運(yùn)的是,MySQL 官方早就準(zhǔn)備了一份如何從其他數(shù)據(jù)庫遷移到 MySQL 的白皮書。MySQL :: Guide to Migrating from Microsoft SQL Server to MySQL 里提供了詳盡的從 SQL Server 到 MySQL 的對應(yīng)方案。 包含了:

  • SQL Server to MySQL - Datatypes 數(shù)據(jù)類型對應(yīng)表;
  • SQL Server to MySQL - Predicates 邏輯算子對應(yīng)表;
  • SQL Server to MySQL - Operators and Date Functions 函數(shù)對應(yīng)表;
  • T-SQL Conversion Suggestions 存儲過程轉(zhuǎn)換建議。

需要額外處理的數(shù)據(jù)類型:

[[231189]]

 

在實(shí)際進(jìn)行中,還額外遇到了一個(gè)用來解決樹形結(jié)構(gòu)存儲的字段類型 Hierarchyid。這個(gè)場景需要額外進(jìn)行業(yè)務(wù)調(diào)整。

我們在內(nèi)部做了針對 MySQL 知識的摸底排查工作,并進(jìn)行了若干次的 MySQL 使用技巧培訓(xùn),將工程師對 MySQL 的認(rèn)知拉到一根統(tǒng)一的線。

關(guān)于存儲過程使用,我們和業(yè)務(wù)方也達(dá)成了一致:所有 SQL Server 存儲過程使用業(yè)務(wù)代碼進(jìn)行重構(gòu),不能在 MySQL 中使用存儲過程。原因是存儲過程增加了業(yè)務(wù)和 DB 的耦合,會讓維護(hù)成本變得極高。另外,MySQL 的存儲過程功能和性能都較弱,無法大規(guī)模使用。

***我們提供了一個(gè) MySQL 開發(fā)規(guī)范文檔,借數(shù)據(jù)庫遷移的機(jī)會,將之前相對混亂的表結(jié)構(gòu)設(shè)計(jì)做了統(tǒng)一約束(部分有業(yè)務(wù)綁定的設(shè)計(jì),在考慮成本之后沒有做調(diào)整)。

ETL 工具

ETL 的全稱是 Extract Translate Load(讀取、轉(zhuǎn)換、載入),數(shù)據(jù)庫遷移最核心過程就是 ETL 過程。如果將 ETL 過程簡化,去掉 Translate 過程,就退化為一個(gè)簡單的數(shù)據(jù)導(dǎo)入導(dǎo)出工具。我們可以先看一下市面上常見的導(dǎo)入導(dǎo)出工具,了解他們的原理和特性,方便我們選型。

MySQL 同構(gòu)數(shù)據(jù)庫數(shù)據(jù)遷移工具:

  • mysqldump 和 mysqlimport:MySQL 官方提供的 SQL 導(dǎo)入導(dǎo)出工具;
  • pt-table-sync:Percona 提供的主從同步工具;
  • XtraBackup:Percona 提供的備份工具。

異構(gòu)數(shù)據(jù)庫遷移工具:

  • Database migration and synchronization tools:國外一家提供數(shù)據(jù)庫遷移解決方案的公司;
  • DataX :阿里巴巴開發(fā)的數(shù)據(jù)庫同步工具;
  • yugong :阿里巴巴開發(fā)的數(shù)據(jù)庫遷移工具;
  • MySQL Workbench :MySQL 提供的 GUI 管理工具,包含數(shù)據(jù)庫遷移功能;
  • Data Integration - Kettle :國外的一款 GUI ETL 工具;
  • Ispirer :提供應(yīng)用程序、數(shù)據(jù)庫異構(gòu)遷移方案的公司;
  • DB2DB 數(shù)據(jù)庫轉(zhuǎn)換工具 :國產(chǎn)的一款商業(yè)數(shù)據(jù)庫遷移軟件;
  • Navicat Premium :經(jīng)典的數(shù)據(jù)庫管理工具,帶數(shù)據(jù)遷移功能;
  • DBImport :個(gè)人維護(hù)的遷移工具,非常簡陋,需要付費(fèi)。

看上去異構(gòu)數(shù)據(jù)庫遷移工具和方案很多,但經(jīng)過我們調(diào)研,其中不少是為老派的傳統(tǒng)行業(yè)服務(wù)的。比如 Kettle / Ispirerer,他們關(guān)注的特性,不能滿足互聯(lián)網(wǎng)公司對性能、遷移耗時(shí)的要求。簡單篩選后,以下幾款工具進(jìn)入了我們候選列表(為了做特性對比,加入幾個(gè)同構(gòu)數(shù)據(jù)庫遷移工具):

從SQL Server到MySQL,近百億數(shù)據(jù)量遷移實(shí)戰(zhàn)

 

由于異構(gòu)數(shù)據(jù)庫遷移,真正能夠進(jìn)入我們選型的只有 DataX / yugong / DB2DB / MySQL Workbench。經(jīng)過綜合考慮,我們最終選用了三種方案,DB2DB 提供小數(shù)據(jù)量、簡單模式的停機(jī)模式支持,足以應(yīng)付小數(shù)據(jù)量的停機(jī)遷移,開發(fā)工程師可以自助完成。DataX 為大數(shù)據(jù)量的停機(jī)模式提供服務(wù),使用 JSON 進(jìn)行配置,通過修改查詢 SQL,可以完成一部分結(jié)構(gòu)調(diào)整工程。yugong 的強(qiáng)大可定制性也為在線遷移提供了基礎(chǔ),我們在官方開源版本的基礎(chǔ)之上,增加了以下額外功能:

  • 支持 SQL Server 作為 Source 和 Target;
  • 支持 MySQL 作為 Source;
  • 支持 SQL Server 增量更新;
  • 支持使用 YAML 作為配置格式;
  • 調(diào)整 yugong 為 fat jar 模式運(yùn)行;
  • 支持表名、字段名大小寫格式變化,駝峰和下劃線自由轉(zhuǎn)換;
  • 支持表名、字段名細(xì)粒度自定義;
  • 支持復(fù)合主鍵遷移;
  • 支持遷移過程中完成 Range / Time / Mod / Hash 分表;
  • 支持新增、刪除字段。

關(guān)于 yugong 的二次開發(fā),我們也積累了一些經(jīng)驗(yàn),下文會詳細(xì)分享。

一致性校驗(yàn)工具

在 ETL 之后,需要有一個(gè)流程來確認(rèn)數(shù)據(jù)遷移前后是否一致。雖然理論上不會有差異,但是如果中間有程序異常,或者數(shù)據(jù)庫在遷移過程中發(fā)生操作,數(shù)據(jù)就會不一致。

業(yè)界有沒有類似的工具呢?有,Percona 提供了 pt-table-checksum 這樣的工具,這個(gè)工具設(shè)計(jì)從 master 使用 checksum 來和 slave 進(jìn)行數(shù)據(jù)對比。這個(gè)設(shè)計(jì)場景是為 MySQL 主從同步設(shè)計(jì),顯然無法完成從 SQL Server 到 MySQL 的一致性校驗(yàn)。盡管如此,它的一些技術(shù)設(shè)計(jì)特性也值得參考:

  • 一次檢查一張表;
  • 每次檢查表,將表數(shù)據(jù)拆分為多個(gè) trunk 進(jìn)行檢查;
  • 使用 REPLACE...SELECT 查詢,避免大表查詢的長時(shí)間帶來的不一致性;
  • 每個(gè) trunk 的查詢預(yù)期時(shí)間是 0.5s;
  • 動(dòng)態(tài)調(diào)整 trunk 大小,使用指數(shù)級增長控制大??;
  • 查詢超時(shí)時(shí)間 1s / 并發(fā)量 25;
  • 支持故障后斷點(diǎn)恢復(fù);
  • 在數(shù)據(jù)庫內(nèi)部維護(hù) src / diff,meta 信息;
  • 通過 Master 提供的信息自動(dòng)連接上 slave;
  • 必須 Schema 結(jié)構(gòu)一致。

我們選擇 yugong 作為 ETL 工具的一大原因也是因?yàn)樗峁┝硕喾N模式。支持 CHECK / FULL / INC / AUTO 四種模式。其中 CHECK 模式就是將 yugong 作為數(shù)據(jù)一致性檢查工具使用。yugong 工作原理是通過 JDBC 根據(jù)主鍵范圍變化,將數(shù)據(jù)取出進(jìn)行批量對比。

這個(gè)模式會遇到一點(diǎn)點(diǎn)小問題,如果數(shù)據(jù)庫表沒有主鍵,將無法進(jìn)行順序?qū)Ρ?。其?shí)不同數(shù)據(jù)庫有自己的邏輯主鍵,Oracle 有 rowid,SQL Server 有 physloc。這種方案可以解決無主鍵進(jìn)行比對的問題。

如何回滾

我們需要考慮一個(gè)場景,在數(shù)據(jù)庫遷移成功之后業(yè)務(wù)已經(jīng)運(yùn)行了幾個(gè)小時(shí),但是遇到了一些 Critical 級別的問題,必須回滾到遷移之前狀態(tài)。這時(shí)候如何保證這段時(shí)間內(nèi)的數(shù)據(jù)更新到老的數(shù)據(jù)庫里面去?

最樸素的做法是,在業(yè)務(wù)層面植入 DAO 層的打點(diǎn),將 SQL 操作記錄下來到老數(shù)據(jù)庫進(jìn)行重放。這種方式雖然直觀,但是要侵入業(yè)務(wù)系統(tǒng),直接被我們否決了。其實(shí)這種方式是 binlog statement based 模式,理論上我們可以直接從 MySQL 的 binlog 里面獲取數(shù)據(jù)變更記錄。以 row based 方式重放到 SQL Server。

這時(shí)候又涉及到逆向 ETL 過程,因?yàn)楹芸赡?Translate 過程中,做了表結(jié)構(gòu)重構(gòu)。我們的解決方法是,使用 Canal 對 MySQL binlog 進(jìn)行解析,然后將解析之后的數(shù)據(jù)作為數(shù)據(jù)源,將其中的變更重放到 SQL Server。

由于回滾的過程也是 ETL,基于 yugong,我們繼續(xù)定制了 SQL Server 的寫入功能,這個(gè)模式類似于在線遷移,只不過方向是從 MySQL 到 SQL Server。

其他實(shí)踐

我們在遷移之前做了大量壓測工作, 并針對每個(gè)遷移的 DB 進(jìn)行線上環(huán)境一致的全真演練。我們構(gòu)建了和生產(chǎn)環(huán)境機(jī)器配置一樣、數(shù)據(jù)量一樣的測試環(huán)境,并要求每個(gè)系統(tǒng)在上線之前都進(jìn)行若干次演練。演練之前準(zhǔn)備詳盡的操作手冊和事故處理方案。演練準(zhǔn)出的標(biāo)準(zhǔn)是:能夠在單次演練中不出任何意外,時(shí)間在估計(jì)范圍內(nèi)。通過演練我們保證了整個(gè)操作時(shí)間可控,減少操作時(shí)的風(fēng)險(xiǎn)。

為了讓數(shù)據(jù)庫的狀態(tài)能更為直觀地展現(xiàn)出來,我們對 MySQL / SQL Server 添加了細(xì)致的 Metrics 監(jiān)控。在測試和遷移過程中,可以便利地看到數(shù)據(jù)庫的響應(yīng)情況。

從SQL Server到MySQL,近百億數(shù)據(jù)量遷移實(shí)戰(zhàn)

 

從SQL Server到MySQL,近百億數(shù)據(jù)量遷移實(shí)戰(zhàn)

 

為了方便 DBA 快速 Review SQL。我們提供了一些工具,直接將代碼庫中的 SQL 拎出來,可以方便地進(jìn)行 SQL Review。再配合其他 SQL Review 工具,比如 Meituan-Dianping / SQLAdvisor,可以實(shí)現(xiàn)一部分自動(dòng)化,提高 DBA 效率,避免線上出現(xiàn)明顯的 Slow SQL。

小結(jié)

基于這幾種方案我們打了一套組合拳。經(jīng)過將近一年的使用,進(jìn)行了 28 個(gè)通宵,遷移了 42 個(gè)系統(tǒng),完成了包括用戶、訂單、支付、電商、學(xué)習(xí)、社群、內(nèi)容和工具的遷移。遷移的數(shù)據(jù)總規(guī)模接近百億,所有遷移項(xiàng)目均一次成功。遷移過程中積累了豐富的實(shí)戰(zhàn)經(jīng)驗(yàn),保障了業(yè)務(wù)快速向前發(fā)展。

在線遷移的原理和流程

上文介紹了從 SQL Server 到 MySQL 異構(gòu)數(shù)據(jù)庫遷移的基本問題和全量解決方案。全量方案可以滿足一部分場景的需求,但是這個(gè)方案仍然是有缺陷的:遷移過程中需要停機(jī),停機(jī)的時(shí)長和數(shù)據(jù)量相關(guān)。對于核心業(yè)務(wù)來說,停機(jī)就意味著損失。比如用戶中心的服務(wù),以它的數(shù)據(jù)量來使用全量方案,會導(dǎo)致遷移過程中停機(jī)若干個(gè)小時(shí)。而一旦用戶中心停止服務(wù),幾乎所有依賴于這個(gè)中央服務(wù)的系統(tǒng)都會停擺。

能不能做到無縫地在線遷移呢?系統(tǒng)不需要或者只需要極短暫的停機(jī)?作為有追求的技術(shù)人,我們一定要想辦法解決這些問題。

針對 Oracle 到 MySQL,市面上已經(jīng)有比較成熟的解決方案——alibaba 的 yugong 項(xiàng)目。在解決 SQL Server 到 MySQL 在線遷移之前,我們先研究一下 yugong 是如何做到 Oracle 的在線遷移。

下圖是 yugong 針對 Oracle 到 MySQL 的增量遷移流程:

從SQL Server到MySQL,近百億數(shù)據(jù)量遷移實(shí)戰(zhàn)

 

這其中有四個(gè)步驟:

  1. 增量數(shù)據(jù)收集(創(chuàng)建 Oracle 表的增量物化視圖);
  2. 進(jìn)行全量復(fù)制;
  3. 進(jìn)行增量復(fù)制(可并行進(jìn)行數(shù)據(jù)校驗(yàn));
  4. 原庫停寫,切到新庫。

Oracle 物化視圖(Materialized View)是 Oracle 提供的一個(gè)機(jī)制。一個(gè)物化視圖就是主庫在某一個(gè)時(shí)間點(diǎn)上的復(fù)制,可以理解為是這個(gè)時(shí)間點(diǎn)上的 Snapshot。當(dāng)主庫的數(shù)據(jù)持續(xù)更新時(shí),物化視圖的更新則是要通過獨(dú)立的批量更新完成,稱之為 refreshes。一批 refreshes 之間的變化,就可以對應(yīng)到數(shù)據(jù)庫的內(nèi)容變化情況。物化視圖經(jīng)常用來將主庫的數(shù)據(jù)復(fù)制到從庫,也常常在數(shù)據(jù)倉庫用來緩存復(fù)雜查詢。

物化視圖有多種配置方式,這里比較關(guān)心刷新方式和刷新時(shí)間。刷新方式有三種:

  • Complete Refresh:刪除所有數(shù)據(jù)記錄重新生成物化視圖;
  • Fast Refresh:增量刷新;
  • Force Refresh:根據(jù)條件判斷使用 Complete Refresh 和 Fast Refres。

刷新機(jī)制有兩種模式: Refresh-on-commit 和 Refresh-On-Demand。

Oracle 基于物化視圖,就可以完成增量數(shù)據(jù)的獲取,從而滿足阿里的數(shù)據(jù)在線遷移。將這個(gè)技術(shù)問題泛化一下,想做到在線增量遷移需要有哪些特性?

我們得到如下結(jié)論(針對源數(shù)據(jù)庫):

  • 增量變化:支持增量獲得增量數(shù)據(jù)庫變化;
  • 延遲:獲取變化數(shù)據(jù)這個(gè)動(dòng)作耗時(shí)需要盡可能低;
  • 冪等一致性:變化數(shù)據(jù)的消費(fèi)應(yīng)當(dāng)做到冪等,即不管目標(biāo)數(shù)據(jù)庫已有數(shù)據(jù)什么狀態(tài),都可以無差別消費(fèi)。

回到我們面臨的問題上來,SQL Server 是否有這個(gè)機(jī)制滿足這三個(gè)特性呢?答案是肯定的,SQL Server 官方提供了 CDC 功能。

CDC 的工作原理

什么是 CDC?CDC 全稱 Change Data Capture,設(shè)計(jì)目的就是用來解決增量數(shù)據(jù)的。它是 SQL Server 2008 新增的特性,在這之前可以使用 SQL Server 2005 中的 after insert / afterdelete/ after update Trigger 功能來獲得數(shù)據(jù)變化。

CDC 的工作原理如下:

從SQL Server到MySQL,近百億數(shù)據(jù)量遷移實(shí)戰(zhàn)

 

當(dāng)數(shù)據(jù)庫表發(fā)生變化時(shí)候,Capture process 會從 transaction log 里面獲取數(shù)據(jù)變化,然后將這些數(shù)據(jù)記錄到 Change Table 里面。有了這些數(shù)據(jù),用戶可以通過特定的 cdc 存儲查詢函數(shù)將這些變化數(shù)據(jù)查出來。

CDC 的數(shù)據(jù)結(jié)構(gòu)和基本使用

CDC 的核心數(shù)據(jù)就是那些 Change Table 了,這里我們給大家看一下Change Table 長什么樣,可以有個(gè)直觀的認(rèn)識。

通過以下的函數(shù)打開一張表(fruits)的 CDC 功能。

--
 enable cdc for dbsys.sp_cdc_enable_db;-- enable by tableEXEC 
sys.sp_cdc_enable_table @source_schema = N'dbo', @source_name = 
N'fruits', @role_name = NULL;-- list cdc enabled tableSELECT name, 
is_cdc_enabled from sys.databases where is_cdc_enabled = 1;

左右滑動(dòng)可完整查看

至此 CDC 功能已經(jīng)開啟,如果需要查看哪些表開啟了 CDC 功能,可以使用一下 SQL:

-- list cdc enabled tableSELECT name, is_cdc_enabled from sys.databases where is_cdc_enabled = 1;

左右滑動(dòng)可完整查看

開啟 CDC 會導(dǎo)致產(chǎn)生一張 Change Table 表 cdc.dbo_fruits_CT,這張表的表結(jié)構(gòu)如何呢?

.schema
 cdc.dbo_fruits_CTname default nullable type length 
indexed-------------- ------- -------- ------------ ------ 
-------__$end_lsn null YES binary 10 NO__$operation null NO int 4 
NO__$seqval null NO binary 10 NO__$start_lsn null NO binary 10 
YES__$update_mask null YES varbinary 128 NOid null YES int 4 NOname null
 YES varchar(255) 255 NO

左右滑動(dòng)可完整查看

這張表的 __ 開頭的字段是 CDC 所記錄的元數(shù)據(jù), id 和 name 是 fruits 表的原始字段。這意味著 CDC 的表結(jié)構(gòu)和原始表結(jié)構(gòu)是一一對應(yīng)的。

接下來我們做一些業(yè)務(wù)操作,讓數(shù)據(jù)庫的數(shù)據(jù)發(fā)生一些變化,然后查看 CDC 的 Change Table:

--
 1 stepDECLARE @begin_time datetime, @end_time datetime, @begin_lsn 
binary(10), @end_lsn binary(10);-- 2 stepSET @begin_time = '2017-09-11 
14:03:00.000';SET @end_time = '2017-09-11 14:10:00.000';-- 3 stepSELECT 
@begin_lsn = sys.fn_cdc_map_time_to_lsn('smallest greater than', 
@begin_time);SELECT @end_lsn = sys.fn_cdc_map_time_to_lsn('largest less 
than or equal', @end_time);-- 4 stepSELECT * FROM 
cdc.fn_cdc_get_all_changes_dbo_fruits(@begin_lsn, @end_lsn, 'all');

左右滑動(dòng)可完整查看

這里的操作含義是:

  1. 定義存儲過程中需要使用的 4 個(gè)變量;
  2. begintime / endtime 是 Human Readable 的字符串格式時(shí)間;
  3. beginlsn / endlsn 是通過 CDC 函數(shù)轉(zhuǎn)化過的 Log Sequence Number,代表數(shù)據(jù)庫變更的唯一操作 ID;
  4. 根據(jù) beginlsn / endlsn 查詢到 CDC 變化數(shù)據(jù)。

查詢出來的數(shù)據(jù)如下所示:

__$start_lsn
 __$end_lsn __$seqval __$operation __$update_mask id 
name-------------------- ---------- -------------------- ------------ 
-------------- -- ------0000dede0000019f001a null 0000dede0000019f0018 2
 03 1 apple0000dede000001ad0004 null 0000dede000001ad0003 2 03 2 
apple20000dede000001ba0003 null 0000dede000001ba0002 3 02 2 
apple20000dede000001ba0003 null 0000dede000001ba0002 4 02 2 
apple30000dede000001c10003 null 0000dede000001c10002 2 03 3 
apple40000dede000001cc0005 null 0000dede000001cc0002 1 03 3 apple4

左右滑動(dòng)可完整查看

可以看到 Change Table 已經(jīng)如實(shí)的記錄了我們操作內(nèi)容,注意 __$operation 代表了數(shù)據(jù)庫操作:

  • 1 刪除
  • 2 插入
  • 3 更新前數(shù)據(jù)
  • 4 更新后數(shù)據(jù)

根據(jù)查出來的數(shù)據(jù),我們可以重現(xiàn)這段時(shí)間數(shù)據(jù)庫的操作:

  • 新增了 id 為 1 / 2 的兩條數(shù)據(jù);
  • 更新了 id 為 2 的數(shù)據(jù);
  • 插入了 id 為 3 的數(shù)據(jù);
  • 刪除了 id 為 3 的數(shù)據(jù)。

CDC 調(diào)優(yōu)

有了 CDC 這個(gè)利器,意味著我們的方向是沒有問題的,終于稍稍吁了一口氣。但除了了解原理和使用方式,我們還需要深入了解 CDC 的工作機(jī)制,對其進(jìn)行壓測、調(diào)優(yōu),了解其極限和邊界,否則一旦線上出現(xiàn)不可控的情況,就會對業(yè)務(wù)帶來巨大損失。

我們先看看 CDC 的工作流程,就可以知道有哪些核心參數(shù)可以調(diào)整:

從SQL Server到MySQL,近百億數(shù)據(jù)量遷移實(shí)戰(zhàn)

 

上圖是 CDC Job 的工作流程:

  • 藍(lán)色區(qū)域是一次 Log 掃描執(zhí)行的***掃描次數(shù):maxscans number(maxscans);
  • 藍(lán)色區(qū)域同時(shí)被***掃描 transcation 數(shù)量控制:maxtrans;
  • 淺藍(lán)色區(qū)域是掃描間隔時(shí)間,單位是秒:pollinginterval。

這三個(gè)參數(shù)平衡著 CDC 的服務(wù)器資源消耗、吞吐量和延遲,根據(jù)具體場景,比如大字段,寬表,BLOB 表,可以調(diào)整從而達(dá)到滿足業(yè)務(wù)需要。他們的默認(rèn)值如下:

  • maxscan 默認(rèn)值 10;
  • maxtrans 默認(rèn)值 500;
  • pollinginterval 默認(rèn)值 5 秒。

CDC 壓測

掌握了能夠調(diào)整的核心參數(shù),我們即將對 CDC 進(jìn)行了多種形式的測試。在壓測之前,我們還需要確定關(guān)鍵的健康指標(biāo),這些指標(biāo)有:

  • 內(nèi)存:buffer-cache-hit / page-life-expectancy / page-split 等;
  • 吞吐:batch-requets / sql-compilations / sql-re-compilations / transactions count;
  • 資源消耗:user-connections / processes-blocked / lock-waits / checkpoint-pages;
  • 操作系統(tǒng)層面:CPU 利用率、磁盤 IO。

出于篇幅考慮,我們無法將所有測試結(jié)果貼出來,這里放一個(gè)在并發(fā) 30 下面插入一百萬數(shù)據(jù)(隨機(jī)數(shù)據(jù))進(jìn)行展示:

從SQL Server到MySQL,近百億數(shù)據(jù)量遷移實(shí)戰(zhàn)

 

從SQL Server到MySQL,近百億數(shù)據(jù)量遷移實(shí)戰(zhàn)

 

測試結(jié)論是,在默認(rèn)的 CDC 參數(shù)下面:

CDC 的開啟/關(guān)閉過程中會導(dǎo)致若干個(gè) Process Block,大流量請求下面(15k TPS)過程會導(dǎo)致約 20 個(gè)左右 Process Block。這個(gè)過程中對服務(wù)器的 IO / CPU 無明顯波動(dòng),開啟/關(guān)閉瞬間會帶來 mssql.sql-statistics.sql-compilations 劇烈波動(dòng)。CDC 開啟后,在大流量請求下面對 QPS / Page IO 無明顯波動(dòng),對服務(wù)器的 IO / CPU 也無明顯波動(dòng), CDC 開啟后可以在 16k TPS 下正常工作。

如果對性能不達(dá)標(biāo),官方有一些簡單的優(yōu)化指南:

  • 調(diào)整 maxscan maxtrans pollinginterval;
  • 減少在插入后立刻插入;
  • 避免大批量寫操作;
  • 限制需要記錄的字段;
  • 盡可能關(guān)閉 net changes;
  • 沒任務(wù)壓力時(shí)跑 cleanup;
  • 監(jiān)控 log file 大小和 IO 壓力,確保不會寫爆磁盤;
  • 要設(shè)置 filegroup_name;
  • 開啟 spcdcenable_table 之前設(shè)置 filegroup。

yugong 的在線遷移機(jī)制

截至目前為止,我們已經(jīng)具備了 CDC 這個(gè)工具,但是這僅僅提供了一種可能性,我們還需要一個(gè)工具將 CDC 的數(shù)據(jù)消費(fèi)出來,并喂到 MySQL 里面去。

還好有 yugong。Yugong 官方提供了 Oracle 到 MySQL 的封裝,并且抽象了 Source / Target / SQL Tempalte 等接口,我們只要實(shí)現(xiàn)相關(guān)接口,就可以完成從 SQL Server 消費(fèi)數(shù)據(jù)到 MySQL 了。

這里我們不展開,我后續(xù)還會專門寫一篇文章講如何在 yugong 上面進(jìn)行開發(fā)??梢蕴崆皠⊥敢幌?,我們已經(jīng)將支持 SQL Server 的 yugong 版本開源了。

如何回滾

數(shù)據(jù)庫遷移這樣的項(xiàng)目,我們不僅僅要保證單向從 SQL Server 到 MySQL 的寫入,同時(shí)要從 MySQL 寫入 SQL Server。

這個(gè)流程同樣考慮增量寫入的要素:增量消費(fèi)、延遲、冪等一致性。

MySQL 的 binlog 可以滿足這三個(gè)要素,需要注意的是,MySQL binlog 有三種模式,Statement based、Row based 和 Mixed。只有 Row based 才能滿足冪等一致性的要求。

確認(rèn)理論上可行之后,我們一樣需要一個(gè)工具將 binlog 讀取出來,并且將其轉(zhuǎn)化為SQL Server 可以消費(fèi)的數(shù)據(jù)格式,然后寫入 SQL Server。

我們目光轉(zhuǎn)到 alibaba 的另外一個(gè)項(xiàng)目 Canal。Canal 是阿里中間件團(tuán)隊(duì)提供的 binlog 增量訂閱 & 消費(fèi)組件。之所以叫組件,是由于 Canal 提供了 Canal-Server 應(yīng)用和 Canal Client Library,Canal 會模擬成一個(gè) MySQL 實(shí)例,作為 Slave 連接到 Master 上面,然后實(shí)時(shí)將 binlog 讀取出來。至于 binlog 讀出之后想怎么使用,權(quán)看用戶如何使用。

我們基于 Canal 設(shè)計(jì)了一個(gè)簡單的數(shù)據(jù)流,在 yugong 中增加了這么幾個(gè)功能:

  • SQL Server 的寫入功能
  • 消費(fèi) Canal 數(shù)據(jù)源的功能

Canal Server 中的 binlog 只能做一次性消費(fèi),內(nèi)部實(shí)現(xiàn)是一個(gè) Queue,為了滿足我們可以重復(fù)消費(fèi)數(shù)據(jù)的能力,我們還額外設(shè)計(jì)了一個(gè)環(huán)節(jié),將 Canal 的數(shù)據(jù)放到 Queue 中,在未來任意時(shí)間可以重復(fù)消費(fèi)數(shù)據(jù)。我們選擇了 Redis 作為這個(gè) Queue,數(shù)據(jù)流如下:

從SQL Server到MySQL,近百億數(shù)據(jù)量遷移實(shí)戰(zhàn)

 

***實(shí)踐

數(shù)據(jù)庫的遷移在去 Windows 中,是最容不得出錯(cuò)的環(huán)節(jié)。應(yīng)用是無狀態(tài)的, 出現(xiàn)問題可以通過回切較快地回滾。但數(shù)據(jù)庫的遷移就需要考慮周到,做好資源準(zhǔn)備,發(fā)布流程,故障預(yù)案處理。

考慮到多個(gè)事業(yè)部都需要經(jīng)歷這樣一個(gè)過程,我們項(xiàng)目組將每一個(gè)步驟都固化下來,形成了一個(gè)***實(shí)踐。我們的遷移步驟如下,供大家參考: 

從SQL Server到MySQL,近百億數(shù)據(jù)量遷移實(shí)戰(zhàn)

責(zé)任編輯:龐桂玉 來源: 今日頭條
相關(guān)推薦

2023-11-29 09:53:29

數(shù)據(jù)庫遷移SQL Server

2022-05-30 11:10:04

數(shù)據(jù)庫MySQL系統(tǒng)

2012-12-26 09:23:56

數(shù)據(jù)庫優(yōu)化

2021-04-07 10:20:31

MySQL數(shù)據(jù)庫命令

2016-05-09 10:27:36

MySQLHive數(shù)據(jù)遷移

2020-07-19 10:53:42

數(shù)據(jù)庫MySQL遷移

2018-12-10 09:05:06

Redis數(shù)據(jù)庫百億數(shù)據(jù)量

2022-11-07 12:22:00

2010-01-14 09:13:19

MySQL to SQ數(shù)據(jù)庫遷移

2017-04-07 13:30:54

2022-10-21 08:32:43

2009-03-19 09:44:07

SQL Server數(shù)據(jù)庫遷移數(shù)據(jù)庫

2011-04-29 14:30:23

2011-03-17 17:50:39

SQL Server數(shù)

2024-01-23 12:56:00

數(shù)據(jù)庫微服務(wù)MySQL

2012-05-21 10:23:36

2009-05-11 14:19:49

數(shù)據(jù)遷移OracleSQL Server

2018-09-06 16:46:33

數(shù)據(jù)庫MySQL分頁查詢

2024-08-22 14:16:08

2010-01-13 17:24:34

SQL Server遷
點(diǎn)贊
收藏

51CTO技術(shù)棧公眾號