施工管理サービスの非同期処理基盤をBlue/Greenデプロイ化しました[前編]

施工管理サービスの非同期処理基盤をBlue/Greenデプロイ化しました&#x5b前編&#x5d|ANDPAD Advent Calendar 2022 この記事はANDPAD Advent Calendar 2022の 24 日目の記事です。

こんにちは、アンドパッドSWEの あかりです。昨日が初めてのブログ投稿だったのですが、2夜連続での投稿です。23日と24日の枠を押さえて、25日の枠をプレゼントとして残すというサンタ的な計らいをしております。(←トリを飾る度胸がなかっただけ。チキンだけに。)

※ 滑り出しは好調ですが、内容は至極真面目です。

1. 概要

最近、アンドパッドで最も古くから稼働している施工管理サービスについて、その非同期処理基盤をBlue/Greenデプロイ化しました。このデプロイフローの変更は大きく2段階を踏んで実現しており、本記事では、その前半部分にあたる、非同期処理基盤から定期実行ジョブの処理基盤を抽出・分離した話について説明します。

2. 前提の説明

2-1. インフラの概要

元々の施工管理サービスのインフラ概要は下図の通りでした。
左はユーザーリクエストが非同期ジョブをトリガして処理する様子を表しており、右は定期実行ジョブをスケジュールして処理する様子を表しています。

インフラの概要図

上図からもわかるように、施工管理サービスには3種類のサーバが存在しており、それぞれ以下のような役割を担っていました。

サーバ 説明
frontサーバ ユーザーからのリクエストを同期的に処理するサーバ
backサーバ 非同期ジョブを実行するサーバ
schedulerサーバ 定期実行ジョブをエンキューするサーバ

なお、施工管理サービスでは、非同期処理の実装にSidekiqを利用しており、定期実行ジョブの実装にsidekiq-schedulerを利用しています。また、redis-namespaceというgemを利用しており、あたかもRedisにnamespaceが張られているかのようにアプリケーションに見せています。(以降、Redisのnamespaceと表現します。)

2-2. デプロイフロー

デプロイフローは下図に示す通りで、frontサーバのみがBlue/Greenデプロイ化されており、下表に示す3段階を経てデプロイが進むようになっていました。

元々のデプロイフロー

段階 説明
社内公開 新環境のfrontサーバが起動し、社内ネットワーク経由のリクエストのみ、新環境のfrontサーバへルーティングされるようになる。
全体公開 backサーバとschedulerサーバがRollingUpdateされ、全てのリクエストが新環境のfrontサーバへルーティングされるようになる。
旧環境の削除 旧環境のfrontサーバが削除される。

なお、注意点としては、この時点では非同期処理を担うbackサーバがBlue/Greenデプロイ化されていないので、Redisのデータベース、および、namespaceは全てのサーバで1つのものを共有していました。

3. 要件整理とインフラ構成の検討

3-1. 要件

まず初めに、backサーバをBlue/Greenデプロイ化したときに満たすべき要件について整理し、以下2つの要件をインフラ側でサポートする決断1をしました。

  1. 定期実行ジョブの唯一性

  2. 定期実行ジョブの実行保証

まず一つ目ですが、これは、定期実行ジョブが重複せずにスケジューリングされることをインフラ側で保証するという意味です。定期実行ジョブの中には、アプリケーションとして冪等性の担保が怪しいロジックが複数存在していました。ですので、アプリケーション側のロジックに冪等性担保を期待するのではなく、インフラ側でも定期実行ジョブの唯一性を保証する方針を採用しました。

また、二つ目ですが、これは定期実行ジョブがスキップされずに確実に実行されることをインフラ側で保証するという意味です。定期実行ジョブの中には、例えば、ユーザー通知を行うジョブが含まれており、ジョブがスキップされるとユーザーに直に影響が出るものが複数存在していました。ですので、定期実行ジョブが確実に実行されることをインフラ側で保証する方針を採用しました。

3-2. インフラ構成

3-2-1. 既存のインフラ構成を変更しない場合

最初に、インフラ構成を変えずにbackサーバのみをBlue/Greenデプロイ化できるのかを検討しました。そして、この場合、3-1節で整理した2つの要件を同時に満たすことはできないと判明し、 backサーバをBlue/Greenデプロイ化するためにインフラ構成を変更する必要があることがわかりました。

まず、既存のインフラ構成では定期実行ジョブの唯一性と定期実行ジョブの実行保証が同時には実現できない理由を説明します。この場合のデプロイフローは、下図のようになります。図中の赤線はRedisのデータベース、ないし、namespaceの境界を表しており、backサーバをBlue/Greenデプロイ化する場合に必要になるものです。

デプロイフロー
(既存のインフラ構成を変更しない場合)

一見すると、問題なくbackサーバのBlue/Greenデプロイ化が達成できているように見えます。ですが、実は、全体公開時のschedulerサーバの挙動に焦点を当てると、ここに落とし穴があることがわかります。 例えば、全体公開時にschedulerサーバをRollingUpdateすることを考えます。そうすると、下図のように、必ずBlue環境のschedulerサーバとGreen環境のschedulerサーバとが同居する瞬間が発生します。そして、このBlue環境とGreen環境のschedulerサーバが同居した瞬間に定期実行ジョブのスケジューリング処理が走ると、Blue環境とGreen環境のそれぞれにジョブがエンキューされてしまうことになり、この意味でスケジュールされるジョブの唯一性が損なわれてしまいます。

参照するRedisのnamespaceが異なる新旧のschedulerサーバが同居する瞬間

一方で、全体公開時にschedulerサーバをRecreateする場合を考えてみます。すると、短い時間ですが、Blue環境にもGreen環境にもschedulerサーバが存在しない期間ができてしまいます。そして、万が一、この期間中に何らかの定期実行ジョブのスケジューリング時刻を迎えてしまうと、そのジョブはスケジュールされないままスキップされてしまうことになります。この意味で、ジョブの実行保証ができないことがわかります。

したがって、既存のインフラ構成を変更しないまま、backサーバをBlue/Greenデプロイ化することはできないと判断しました。

3-2-2. 定期実行ジョブの処理基盤を分離する場合

インフラ構成を変えずにbackサーバをそのままBlue/Greenデプロイ化すると、定期実行ジョブの要件を満たせなくなってしまうことが前節から明らかになりました。ですので、解決策としては、非同期処理基盤から定期実行ジョブを処理する基盤を抽出することが自然に考えられました。

この場合のインフラ構成とデプロイフローを下図に示します。構成の変更点としては大きく二点あり、一つは、定期実行ジョブをbackサーバではなく、新しく追加したworkerサーバで処理させることです。そして、もう一つは、定期実行ジョブの処理基盤用のRedis namespaceを作成し、schedulerサーバとworkerサーバにそちらを参照させることです。

デプロイフロー
(定期実行ジョブの処理基盤を分離する場合)

こうすることで、schedulerサーバとworkerサーバをRollingUpdateさせて、下図のように全体公開時に新環境と旧環境のサーバが共存する瞬間があったとしても、sidekiq-schedulerの機能として定期実行ジョブの唯一性が保証されるようになります。加えて、RollingUpdateなので定期実行ジョブの瞬断も起きず、3-1節で説明した両方の要件が満たされることになりました。

新旧の定期実行ジョブの処理基盤が同居する瞬間

4. 定期実行ジョブの処理基盤を分離するフロー

目標とするインフラ構成が決定したので、続いて、その構成への移行フローを検討しました。

非同期処理基盤から定期実行ジョブの処理基盤を分離させることによる動作変更は大きいため、安全を期して、次の二段階に分けてリリースを行うこととしました。

  1. 定期実行ジョブの処理基盤(定期実行ジョブ用のRedisのnamespaceを参照するschedulerサーバとworkerサーバ)をリリースし、その基盤上でダミージョブを定期実行させる。

  2. 1で動作確認をしっかり行った後、定期実行ジョブを既存の非同期処理基盤から定期実行ジョブの処理基盤へ移植する。

この様子を下図に示します。

定期実行ジョブの処理基盤を分離するフロー

こうすることで、特段の問題なく非同期処理基盤から定期実行ジョブの処理基盤を分離することに成功しました。

5. まとめ

この記事では、アンドパッドで最も古くから稼働している施工管理サービスの非同期処理基盤をBlue/Greenデプロイ化する前段階として、定期実行ジョブの処理基盤とユーザーリクエストがトリガする非同期ジョブの実行基盤とを分離した話について説明しました。実際に、ユーザーリクエストがトリガする非同期ジョブの実行基盤をBlue/Greenデプロイ化する話については、また後日記事にまとめてご報告するつもりです!ぜひ、お楽しみに〜

最後に

アンドパッドでは、様々な技術要素を活用して開発に取り組んでいます。 一緒に開発、挑戦していただける方を大募集しておりますので興味のある方は下記をご覧ください!

engineer.andpad.co.jp

hrmos.co

ANDPAD Advent Calendar 2022最終日となる明日は、Quality Controlの髙木さんからのテストデータ作成自動化についての紹介です。 最後までお楽しみに!


  1. もちろん、他にも満たすべき要件はありますが、説明の都合上、他の要件は省略しています。