Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Update Billion Records

ta1kt0me
October 27, 2023

Update Billion Records

Kaigi on Rails 2023

ta1kt0me

October 27, 2023
Tweet

More Decks by ta1kt0me

Other Decks in Programming

Transcript

  1. • Monolith Ruby on Rails • Sidekiq • AWS •

    CloudFront • S3 • ECS • Aurora MySQL • DynamoDB • Elasticache for Redis • etc … Backend構成要素
  2. 課題を深掘り 更新対象の指定 • 処理対象のfrom/to にテーブルのidカラム(PK)の値を指定 • Idに Snow fl ake

    ID を利⽤ • 64ビットの整数値、timestampに基づいて⽣成される時系列ソート済みのID • Twitter の TweetのIDで利⽤されていた • TimeTreeの場合、timestampにcreated_atを使っている • 1億件分更新したい場合、⼤体1億件分の期間の from, to をこのフォーマットに変換して指定 + ————— —————— ——— ——— — —— — —— — —— ——— — —— ——— — —— — —+ | timestamp (41ビット) | ゾーンID (10ビット) | シーケンス番号 (13ビット) | + ————— —————— ——— ——— — —— — —— — —— ——— — —— ——— — —— — —+ 例)timestampに “2020-01-01 00:00:00.000 UTC”、ゾーンIDに”10”、シーケンス番号に”1”を指定 10110111101011110011001101110100000000000 0000001010 0000000000001 => 13235854403174481921
  3. 全体像 ①rails runnerで起動処理実⾏ • 更新対象の from/to • 分割期間 • Jobの同時起動数

    ②from/toの分割リストをRedisにpush ④更新対象のfrom/toを pop、なければ終了 ⑤更新 ③⾮同期Jobを登録 ⑥⾮同期Jobを登録
  4. 全体像 ①rails runnerで起動処理実⾏ • 更新対象の from/to • 分割期間 • Jobの同時起動数

    ④更新対象のfrom/toをpop(   ) ③⾮同期Jobを登録 ②from/toの分割リストをRedisにpush
  5. 全体像 ①rails runnerで起動処理実⾏ • 更新対象の from/to • 分割期間 • Jobの同時起動数

    ④更新対象のfrom/toをpop ⑤更新 ③⾮同期Jobを登録 ②from/toの分割リストをRedisにpush
  6. 全体像 ①rails runnerで起動処理実⾏ • 更新対象の from/to • 分割期間 • Jobの同時起動数

    ⑤更新 ⑥⾮同期Jobを登録 ③⾮同期Jobを登録 ④更新対象のfrom/toをpop ②from/toの分割リストをRedisにpush
  7. 全体像 ①rails runnerで起動処理実⾏ • 更新対象の from/to • 分割期間 • Jobの同時起動数

    ⑤更新 ⑥⾮同期Jobを登録 ③⾮同期Jobを登録 ④更新対象のfrom/toをpop ②from/toの分割リストをRedisにpush
  8. 全体像 ①rails runnerで起動処理実⾏ • 更新対象の from/to • 分割期間 • Jobの同時起動数

    ⑦更新対象のfrom/toをpop(  ) ⑤更新 ③⾮同期Jobを登録 ⑥⾮同期Jobを登録 ②from/toの分割リストをRedisにpush
  9. 全体像 ①rails runnerで起動処理実⾏ • 更新対象の from/to • 分割期間 • Jobの同時起動数

    ⑦更新対象のfrom/toをpopできない ⑤更新 ③⾮同期Jobを登録 ⑥⾮同期Jobを登録 ②from/toの分割リストをRedisにpush
  10. 全体像 ①rails runnerで起動処理実⾏ • 更新対象の from/to • 分割期間 • Jobの同時起動数

    ⑧分割リストのデータを削除 ⑤更新 ③⾮同期Jobを登録 ⑥⾮同期Jobを登録 ②from/toの分割リストをRedisにpush
  11. 全体像 ①rails runnerで起動処理実⾏ • 更新対象の from/to • 分割期間 • Jobの同時起動数

    ⑧分割リストのデータを削除 ⑤更新 ③⾮同期Jobを登録 ⑥⾮同期Jobを登録 ②from/toの分割リストをRedisにpush
  12. 学び ⼤量データの変更には時間がかかる • ⻑期戦になるので関係者の理解が必要 • ⼩さなデータで簡単なことでも、後に回せば回すほどもっと⾟くなる ⼩さく試して進める • PoCのフィードバックサイクルを素早く回す •

    可能であれば⼩さいデータセットから始め、少しずつ⼤きくして問題を捉えていく 選択肢を広げるためのinputの⼤切さ • 改善のヒントは様々な場所に潜んでいるので広く、深く探す • 前例や背景、変更対象や関連のドメインの把握、制限やトレードオフの理解、少数の異常データの存在
  13. 他の全件更新に適⽤できるか? 🙅 or 🙆 • 🙆 適⽤できたケースもある • 😰 変更対象が今回と同じでもさらにデータが増え続けたら…

    • 🙅 READよりもWRITE(更新)が多いケースはLockが多発して使えなかった • 🧐 変更内容や対象の特性次第で前例に捉われずに考え続ける
  14. end