ちょっと前のブログに、Azure App Service (Linux)でSidecarパターンが実装できる、という記事がポストされてた。
Microsoft Build 2024のこのセッションでも紹介されてた(21:42から)。
Sidecarパターン
ザックリSidecarパターンというのは、
- メインであるWeb アプリケーション
- 他のサービスとのやり取りとかログ記録とかのユーティリティ的な機能
というような機能を、それぞれ別のコンテナとして実装して、1.のコンテナーから2.のコンテナーを呼び出す設計パターンのこと。
これまで、App Serviceにデプロイできるカスタムコンテナーは基本的には一つだけだったけど、冒頭のブログ/Buildのセッションでは、App Serviceで複数のコンテナーをデプロイする仕組みの紹介してる。
# 実際はKuduやEasyAuth用途などのマネージドなコンテナーがアプリとは別にある。
# 後述するようにマルチコンテナーを動かす方法もある。
Bicep
仕組みとしては、ARMのレベルでいろいろ追加しているらしい。
ブログ内ではJSONのARMテンプレートが紹介されている。
BicepでSidecarパターンのApp Serviceを書くと、例えばメインコンテナー1つ、サイドカーコンテナー2つ、計3つのコンテナーをを動かす場合、こんな感じなる。
resource webApp 'Microsoft.Web/sites@2021-02-01' = { name: webAppName location: location properties: { serverFarmId: appServicePlan.id siteConfig: { linuxFxVersion: 'sitecontainers' // ・・・ (a) } } resource mainApplicationContainer 'sitecontainers@2021-02-01' = { // ・・・ (b) name: 'mainContainer' properties: { image: '<メインコンテナー>' // ・・・ (c) targetPort: 80 isMain: true // ・・・ (d) trueなので、これがメインコンテナー } } resource sidecarContainer1 'sitecontainers@2021-02-01' = { name: 'sidecar1' properties: { image: '<サイドカーコンテナー1>' targetPort: 4000 isMain: false // falseなのでサイドカーコンテナー } } resource sidecarContainer2 'sitecontainers@2021-02-01' = { name: 'sidecar2' properties: { image: '<サイドカーコンテナー2>' targetPort: 5000 isMain: false // falseなので サイドカーコンテナー } } }
これまでのApp Serviceのテンプレートでは見ない点がいくつかある。
linuxFxVersion
= sitecontainers
まずMicrosoft.Web/sites
リソースの linuxFxVersion
プロパティの値(上記Bicep内のa)が新しい。
これまでここには、コンテナーイメージやランタイムの情報、例えばnginx:latest
とかNODE|20-lts
などの値が入っていた。
今回のマルチコンテナーのApp Serviceの場合は、ここにsitecontainers
という文字列が入る。
ちなみに、この sitecontainers
を設定したApp ServiceをAzureポータルで開くとこう表示される。
Runtime Stack
の値が-
から始まっていたり、Publishing model
がCode
になっているのは、まだポータルの対応が追い付いていないだけだろうか。
※既定のランタイムやカスタムコンテナー
- 既定のランタイムの場合 (例: Node.js 20 LTS)
- カスタムコンテナーの場合(例: nginxのイメージ)
サブリソースタイプ Microsoft.Web/sites/sitecontainers
次に、新しいMicrosoft.Web/sites
のサブリソースタイプ sitecontainers
(同b)。
この"Microsoft.Web/sites/sitecontainers
"リソース (長い。以降はsitecontainers
リソース)がコンテナーのイメージ名やタグ、待ち受けしているポートの情報を持っている(同c)。
メインのアプリケーションコンテナー含め、App Serviceの中で動かしたいそれぞれのコンテナーに対応している。
また sitecontainers
リソースには、isMain
プロパティがある(同d)。
App Service へのリクエストは、このisMain
がtrue
になっているsitecontainers
リソースのコンテナーへルーティングされる。
その他のsitecontainers
リソース(Sidecarとして使われるコンテナー)では、isMain
がfalse
にする。
スケーリング
sitecontainer
リソースを使ったマルチコンテナーの場合、1つのインスタンスの中では、メインのアプリコンテナ含めsitecontainer
リソースの数だけコンテナが動く。
なので、App Service (Plan)をスケールアウトしてインスタンスを追加すると、追加されたインスタンスの中でまたsitecontainer
リソースに対応したコンテナが動き出す。
上記のBicepの例の場合は、1つのApp Serviceリソースにsitecontainers
リソースを3つ定義しているので、1インスタンスに3つのコンテナーが動く。
さらに、3インスタンスにスケールアウトすると、それぞれのインスタンスで3つのコンテナーが動くことになる。
App Service Planへの影響
App Service Planの各SKUは、一応そのプラン上で動かすアプリ数の上限目安がある。
learn.microsoft.com
App Service on Linuxの場合、コンテナ数に置き換えて案内してた。
sitecontainers
リソースを使ったマルチコンテナーの場合、sitecontainers
の数だけそのApp Service Plan上でコンテナーが動きSidecar用途のコンテナーとはいえメモリーもCPUも使うので、このアプリ数にも影響が出るだろう。
ところでマルチコンテナーと言えば
Docker ComposeとかKubernetesとかだけど、両方ともプレビューながらApp Serviceで動かすことができる*1。
App Serviceのマルチコンテナー対応は割と歴史があり、調べてみると2018年にはプレビューリリースされていた。
azure.github.io
「Docker Composeの設定ファイルをbase64エンコード済みで4000文字まで」というなかなかピンと来ない制限はあるものの、公式ドキュメントもまだあるので今でも動くはず。
この文字数制限は、自分がサポートエンジニアしてた頃から「もっと拡大してほしい」という要望がでてた。
でも、あれから5年以上経っても拡大する気配はないので、たぶん永遠のプレビューなんだろう。
そういうマイクロサービス的なマルチコンテナーは、今回のApp Serviceでのマルチコンテナー対応のターゲットではない、というのは注意。
AKS/ACAを使おう。
*1:どれだけの人が知ってるだろうか。