講演資料
試行錯誤の新アーキテクチャ移行
楽天では11年前から、同社サービスの画像を格納、API連携で提供するストレージサービスを運用してきた。フロントの楽天サービスが画像をリクエストすると、楽天データセンター内にあるプロキシサーバーのSquid(*1)からVarnish(*2)内のキャッシュに問い合わせが実行され、キャッシュがなければリバースプロキシのPerlbal(*3)経由でMySQLやMogileFS(*4)へのAPIを叩き、結果を返すといった構成だ。
*1 Squid
*2 Varnish Cache
*3 Perbal proxy
*4 MofileFS
「課題はさまざまあった。メンテナンスやバージョンアップの計画が難しく、アクセス負荷が増えたときの増強も大変。また、MogileFSには大量のデータが格納されており、容量の問題から仮想ディスクではなく物理ディスクを使っていたが、足りなくなったり、故障すると交換するしかない昔ながらのスタイルだった」(柳本氏)
この旧アーキテクチャを、Microsoft Azureを使って刷新した。まず、CDN(Contents Delivery Network)にキャッシュを置き、Microsoft Azure上のTraffic Manager(*5)でロードバランシングしながら、KubernetesのAPIポッド経由でMogileFSから代替したAzure Blob Storage(*6)へデータを格納または取得を実施。メタデータについては、Azure ExpressRoute(*7)経由で楽天データセンター内のMySQLに問い合わせる構成にした。
*5 Traffic Manager:DNSベースのロードバランサー
*6 Azure Blob Storage:オブジェクトストレージサービス
*7 Azure ExpressRoute:オンプレミスとクラウドを閉域網で接続
「実は最初、SquidとVarnishをKubernetes内にポッドで残して、分散KVストレージやセグメンテーションなどを提供するHashiCorp Consulでサービスをディスカバリし、Varnishが死んでもコンフィグの書き換えや自動復旧をやるような構成を考えていた。でも、構成を組んだあとで、Azureはアウトプット時に課金されるので、この構成だと課金がかさんでいくシステムなんじゃないかと気付いた」(柳本氏)
Varnishでキャッシュする意味がなかったと苦笑いしながら、CDNのキャッシュで90%はリクエストに返せるように設計し直したと柳本氏は明かす。
「クラウドを活用するときは、課金の仕組みをしっかり確認し、構成にもよるがキャッシュは効率的な形で配置。また、アーキテクチャはシンプルに保つようにするのが最適と学んだ」(柳本氏)
ちなみに、楽天データセンター側にMySQLを置いた理由について、柳本氏は「Azure Database for MySQLはハードウェア障害時に予告なしで中断するほか、メンテナンスは不定回数、10数秒の停止を事前予告なしで実施するから」とし、計画停止など調整が可能な自社データセンターで落ち着いたと述べた。
これに対して日本マイクロソフトの新井庸介氏は、「Azure Database for MySQLの計画メンテナンスにおいて、事前通知やタイミングの指定が現状行えないのはそのとおり」と説明。だが改善は進んでおり、最大72時間前に通知するプレビューがまずUKとUSで始まっている(*8)。またメンテナンスタイミングについては、Azure Synapse Analytics(旧称 SQL DW)、Azure Cache for Redis、Azure VM(on Azure Dedicated Host(*9))等、既に指定可能なサービスはあり、順次他サービスでも実現していきたいとした。
*8 Azure Database for MySQL:計画メンテナンスの通知(Preview)について
*9 Azure Dedicated Host:専用サーバーをサービスとして提供するクラウドサービス
これを受けて柳本氏は、「計画停止にせよ障害にせよ。そもそも論としてデータベースも落ちるものだという前提で、例えば前段にメッセージングやキューイングの仕組みを導入することも考えたい」と考えを述べた。
データ移行についても大変だったと柳本氏は言う。旧MogileFSには約15億レコード、約260TBのデータが格納されていた。これをどう移行させるかで悩んでいたところ、マイクロソフトからAzure Data Boxを紹介されたと柳本氏は述べた。Azure Data Boxはオフラインでデータ転送するためのハードウェアで、7TB・80TB・770TBの3種類から選べる。
「日本では7TBと80TBが利用できる。260TBであれば80TBモデルを複数台使えばいけるかなと思ったが、残念ながら今回の要件にはあわなかった」(新井氏)
採用を見送った理由は、Rails 6系のActive Storage(*10)機能を使っている関係上、データ移動とメタデータの更新をセットで行う必要があったからである。単純にコピーして移すことができず、結局はネットワーク越しで順次移行していると柳本氏は説明する。
*10 Active Storage概要
だが、これもなかなか手ごわく、ネットワーク帯域の圧迫を最小限に抑える、Active Storageのメタデータ更新中にイメージをつかんでいるせいでメモリリークを起こさないように気を付ける、スキーマの変更の有無で苦労レベルは変わるので注意するなど、「気を遣いながら原始的にゴリゴリやっている」と明かす。
「特にデータが大量であれば、新しいアプリケーションを完全に違うバージョンで提供することにして、アプリケーションごとに切り替える方がうまくいくように感じる」(柳本氏)
なお、最近東日本でGAになったAzure Stack Edge(*11)であれば、エッジ側でデータを処理しメタデータを生成する等が可能と新井氏は言う。AI/ML、Stream Analytics、FunctionsなどのクラウドサービスをAzure Stack Edge上で利用し、単なるデータコピー以上の柔軟な処理が可能という。紹介を聞いて柳本氏も興味を示し、タイミングが合えば試してみたいと述べた。
*11 Azure Stack Edge
マイクロサービスとマルチリージョン構成
マイクロサービス自体は、これまでRailsのroutesから各ファンクションに振り分けていたものを、routesとファンクションを一組にしてポッドに分けて、共通のMySQLに問い合わせる構成にしたという。
マイクロサービスへの移行を決めた理由について、柳本氏はファンクションのリクエスト量の差に応じた構成を組めること、トラブル時に範囲を特定して影響を最小限に抑えやすいこと、コードがそれぞれ独立していて量も少ないためポッドの起動が速くなること、並列で開発できて工数短縮ができることなどを挙げた。
マイクロサービスで確実に必要なものは、「間違いなくサービスメッシュ」と柳本氏は断言する。サービスが増えると管理は必須。同社ではIstio+Helm ver2で運用しているという。そして、ネットワーク周りの可視化では、Kiali(*12)を採用。また、Elasticsearchにログすべてを集約して、Elastic APMのクライアントを組み合わせて監視、オブザーバビリティを高めている。
デプロイは、Prometheusの情報を引っ張ってカナリアリリース/デプロイ(新機能を一部ユーザーのみに公開し、問題がなければ段階的に全展開するデプロイ方法)を実施するFlagger(*13)を採用。このほか、Kubernetesのステータス監視にPrometheusを活用。「PrometheusからGrafanaに渡してデータをチェック。本番環境に関するアラートはSlackに投げて、ステージングは社内で使っているMicrosoft TeamsにWebhookで飛ばしている」(柳本氏)
*12 Kiali:Service mesh observability and configuration
*13 Flagger:Progressive Delivery Operator for Kubernetes
ちなみに、Availability Zone構成のAKSにおいて、kubenetでIstioが上がらないトラブルが発生し、現在はAzure CNI(Container Networking Interface)を使っていると柳本氏(*14)。kubenetであればノードにIPアドレスを割り当てて、配下のポッドはNAT変換で処理されるが、Azure CNIではすべてのポッドにAzure仮想ネットワークのサブネットからIPアドレスが割り当てられ、さらに配下のポッドの最大数に合わせてIPアドレスが事前予約される。そのため、IPアドレス不足に陥る可能性があるので、詳細な計画が必要だ。
*14
・Azure Kubernetes サービス (AKS) で kubenet ネットワークを構成する
・Azure Kubernetes サービス (AKS) で Azure CNI ネットワークを構成する
続いて高可用性構成について、サービス全体はJapan West(JW)とJapan East(JE)のマルチリージョン構成で、Azure Traffic Managerでロードバランシングしていることを説明した。
「JEではアベイラビリティゾーンを利用、JWはシングルゾーンでAKS(Azure Kubernetes Service)を構成している」(柳本氏)
これを受けて新井氏は、Azureにおける高可用性構成について説明した。AzureではシングルVM構成、可用性セット、可用性ゾーン、マルチリージョンの4レベルの高可用性構成を提供しており、必要なサービスレベルにあわせて選択できること、また高可用構成における負荷分散やレプリケーションのための様々な機能やサービスが紹介された。
そして最後は、CI/CDパイプラインだ。
「GitHubレポジトリにタグを打つとCircleCIが検知してテストを実行(RSpec)、Kanikoでビルドイメージを作成。これをJFrog Artifactoryにプッシュしたら、マニフェストに対してステージングのタグを付与し、AKSステージングにプッシュする。このビルドイメージを使って環境変数をいろいろ調整し、プロダクションにアダプトしている。YAML設定ファイルはkustomizeで管理していて、kubectlの-kオプションで動かしている。カナリアデプロイメント用のマニフェストも、kustomize配下に配置した」(柳本氏)
以上が、楽天のマイクロサービスの最新状況だ。今後について柳本氏は、次を検討中と述べた。
- マスターデータベースがシングルポイント障害になりがちなので、YouTubeのバックエンドでも採用されている分散型MySQLのVitessを使ってみたい
- メッセージングで、Apache Kafkaよりも運用が楽そうなNATSをデータベースの前に置くような使い方を試してみたい
- オブザーバビリティでは、ユーザーの障害を検知しやすくするため、Open TelemetryとJaegerを組み合わせて使ってみたい
- ポッドやノードなどの障害時の対応に備えて、カオスエンジニアリングを実施したい
まだまだ試したいことは山盛りのようだ。
「マイクロソフトでは、Azure上にマイクロサービスを構築する方法(*15)やAKSのBCP/DRのベストプラクティス集(*16)など、役立つ情報が多く掲載されている。ぜひこちらも参考にしてもらえれば幸いだ」(新井氏)
*15 Azure Kubernetes Service (AKS) 上のマイクロサービス アーキテクチャ
*16 Azure Kubernetes Service (AKS) での事業継続とディザスター リカバリーに関するベストプラクティス
お問い合わせ
日本マイクロソフト株式会社
-
【クラウドデベロッパーちゃんねる】
- クラウドを使って開発するITの開発者・デベロッパーの皆様へ様々な技術情報をお届けするYouTubeチャンネル
-
【Microsoft Learn】
- Microsoft Azureについて学習できる無料のオンライン トレーニング コンテンツ一覧
-
【開発者コミュニティ ニュースレター】
- マイクロソフトが配信しているニュースレターで、最新テクノロジ記事、技術ドキュメント、および開発者イベントなど、世界の情報を月イチで配信
楽天株式会社
-
部署紹介サイト
- ECに関連するプラットフォームの開発や、フリマアプリのラクマ、楽天ペイ(オンライン決済)などの様々なサービスを行っているECインキュベーション開発部の紹介。東京、大阪、札幌での各種ポジションも紹介しています。