【項目經驗】資料移轉總結

來源:互聯網
上載者:User

在產品迭代初期或者系統重構時期,業務模型的調整帶來資料結構的變化,資料移轉不可避免。做好資料移轉需要考慮周全,且準備充分,做好預案,否則如果出現資料不一致問題,錯誤修正成本高,同時核心業務資料的錯誤,會引起客戶/業務方的投訴,團隊也會承受巨大的壓力。

本文結合最近一個實際項目的資料資料移轉過程,講述了踩過的坑,加上自己的一些思考得出的一些方法論,最後給出了資料移轉個指令碼的一個執行個體

目標

確保新用戶端訪問新業務模型時能否正常查詢之前的資料,如訂單等;不會出現資料不一致。

原則
  • 影響可控 —— 只對需要遷移對資料做修改,不能影響到其他資料;不到萬不得已,不會允許停機遷移資料,因此遷移視窗期越短越好,減少遷移視窗期使用者行為帶來的資料問題;
  • 可回退 —— 一旦發現遷移資料有問題,可以回退到之前的資料狀態;
  • 可追溯 —— 出現問題,能夠有日誌或者備份資料可查;資料庫的binlog,遷移程式的log可以作為依據;
  • 可測試 —— 遷移方案必須可測試,要滿足可測試,那麼遷移方案必須是通用型的方案。
思路
  • 先備份,再遷移;
  • 遷移後需要做資料比對,確保資料一致性;
  • 出現問題,考慮是否做回退【並不是所有情境都能直接回退】;
  • 如果業務量大,為避免使用者行為和資料移轉產生衝突,考慮停服務遷移。
步驟
  • 備份 —— 將待遷移資料備份到bak表,任何在遷移過程中會被修改的資料應當被備份,任何在insert情境被當著原資料使用的資料應當被備份;
  • 遷移 —— 遷移指令碼 / 程式 只對bak表中的目標資料做操作;
  • 驗證 —— 遷移完成後,需要做資料核對,確保資料一致性;
  • 回退 —— 回退指令碼同樣只對bak表中的目標資料做操作,且行為和遷移指令碼行為相反。
方案的選擇資料庫指令碼

在資料量小,業務情境簡單的情況下非常適合,簡單輕量級,通過sql指令碼完成資料移轉非常合適。但如下幾點需要認真思考:

  1. 能否寫成通用sql?如果不能放棄;因為為不同環境準備不同的指令碼,破壞了‘可測試’這一原則;
  2. 被操作的資料量是否太多?如果過多(通常超過1萬條就很多了),可能導致指令碼提交逾時;
  3. 業務情境是否複雜?如果涉及到的表過多(超過3張),指令碼的執行存在先後順序,這時候通過人為保證,風險會大大增加;
  4. 測試環境和線上環境的sql執行工具/環境是否一致?如果不一致(很多公司的DBA工具會對一些文法和格式作出限制,比如不能有換行,注釋中不能有半形分號等),則也會破壞掉‘可測試’這一原則;
  5. 線上sql執行流程是否冗長?如果流程冗長(公司的流程可能要求需要TL和DBA的審批,DBA作為第三方資源依賴不可控),且指令碼多,會拉長資料移轉的視窗期,業務風險大大增加,破壞了‘影響可控’的原則。
遷移程式

和‘資料庫指令碼’方法相反,撰寫的‘遷移程式’能夠避開這些缺點,更適合於業務情境複雜,資料量大的情境。

方案對比

指令碼

程式

備忘

通用性

不完全

完全

如:依賴第三方資料時,指令碼無法做到通用

複雜情境支援

不適合

適合

複雜業務情境指令碼不適合,如迴圈調用,第三方系統資料,多表依賴等

大資料量支援

不適合

適合

大資料量可能導致指令碼提交逾時,通常超過1萬條不宜使用指令碼,大多數dba工具通常也會對操作的資料量做限制

開發成本隨複雜度增長

指數

線性

 

無論採用‘資料庫指令碼’還是‘遷移程式’,都需要遵循上面的‘原則’和步驟。

思考

資料移轉和應用程式發布的先後順序?

在業務量大的情況下,資料移轉過程中,資料被使用者行為修改了怎麼辦?

遷移失敗,什麼情況下做回退,什麼情況下不能做回退?

踩過的坑

在轉贈2.0項目中,前期對資料移轉的業務複雜度預估不足,選擇了‘資料庫指令碼’方式,踩了不少坑:

  1. 在測試環境測試通過的sql指令碼,無法直接線上上環境執行,原因是線上資料庫工具對sql格式和內容校正更為嚴格(不允許有換行等);
  2. 測試過程中發現,需要實現為一個訂單迴圈產生多個券碼的情境,雖通過sql間接實現,但是複雜度很高,開發成本增大;
  3. 由於sql較多且複雜度高(如:使用insert select),需要經過TL和DBA的雙重審批,拉長了資料移轉視窗。
遷移指令碼樣本

業務情境:將訂單表中訂單狀態為2和3的訂單狀態更新為4

backup
create table order_bak like order;insert into order_bak select * from order where status in (2,3);
註:order為業務表,order_bak為備份表;目標是將訂單狀態為3的訂單更新為4。migration
update order set status = 4 where id in (select id from order_bak);

註:如果直接對order原表進行操作,一旦錯誤,無法復原。

check
select count(*) as cont from order where status != 4 and id in (select id from order_bak);

註:如果cont > 1則需要考慮資料移轉是否成功

rollbak
update order o inner join order_bak bak on o.id = bak.id set o.status = bak.status;

註:如果遷移後-->復原前,有使用者行為更改status狀態,則不能直接rollback ,需要具體情況具體分析;實在避免不了,且此類資料很多,則考慮停服務遷移了。

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.