Azure Container Appsのワークロードプロファイルを試してみた

Azure Container AppsのワークロードプロファイルがGAしたので試してみました。

https://azure.microsoft.com/ja-jp/updates/generally-available-azure-container-apps-dedicated-plan/

https://azure.microsoft.com/ja-jp/updates/generally-available-azure-container-apps-support-for-udr-nat-gateway-and-smaller-subnets/

# ワークロードプロファイルとは
これまではAzure Container Appsでは従量課金プラン一択でしたが、ワークロードプロファイルが正式に利用できるようになりました。ワークロードプロファイルでは従量課金プランと専用プランの2種類が利用できます。ワークロードプロファイルでは従量課金も使える、という点が理解しづらくさせていますが、関係性を図示すると以下のような形になります。

![workload.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2850747/fe0a1cd6-5e3f-ffe5-e778-fc12cfa9d8e1.png)

ドキュメントやAzure Portalで表記ゆれしている箇所が結構あるので混乱しますが、上の図の関係性をおさえておくと読み解きやすくなると思います。

### 従量課金プラン
ワークロードプロファイルで使える従量課金プランは従量課金のみの環境で利用できていたものの進化版といえます。進化している点を列挙しますと、
1. コンテナに割り当てられるリソース上限が増えた（2vCPU→4vCPU、4GiBメモリ→8GiBメモリ）
1. UDR、NATGWが使えるようになった
1. 必要なサブネットの最小サイズが/23から/27になった

といった点が挙げられます。

1点目の割り当て可能リソースが増えた点は仕様上限アップなので、活用の幅が広がります。

2点目のUDR、NATGWが使えるようになった点は、特定の要件があるときに役立ちます。

**UDR**
必ずファイアウォールを通過させるという要件がある場合はUDRを使います。
[活用イメージはこちらです。](https://learn.microsoft.com/ja-jp/azure/container-apps/networking?tabs=azure-cli#user-defined-routes-udr)

**NATGW**
NATGWは送信元IPアドレスの固定化に役立ちます。Container Apps環境の送信元IPアドレスは固定されているように見えるのですが、どこかのタイミングで変わる可能性があるとドキュメントに記載があるため、送信元IPアドレスを固定する要件がある場合はNATGWと組み合わせることで実現できます。

> 送信 IP は時間の経過と同時に変化する可能性があります。 Container Apps 環境からの送信トラフィックに NAT ゲートウェイまたはその他のプロキシを使用することは、 ワークロード プロファイル環境でのみサポートされます。
＜引用元：[Azure Container Apps 環境でのネットワーク](https://learn.microsoft.com/ja-jp/azure/container-apps/networking?tabs=azure-cli#ports-and-ip-addresses)＞

3点目の必要なサブネット最小サイズが小さくなった点はネットワーク設計をする際に役立ちます。従来の従量課金プランでは最小のサイズが/23も必要であるため、コンテナが少量であったとしても/23割り当てる必要があり、ネットワーク設計の自由度が低くなっていました。ワークロードプロファイルの従量課金プランでは最小サイズが/27になったので、実行させるコンテナの量を考慮しながら柔軟なアドレス割り当てが可能となりました。システム的に予約されるIPがあるため、その分も考慮してサブネットサイズを検討します。詳細は[こちら](https://learn.microsoft.com/ja-jp/azure/container-apps/networking?tabs=azure-cli#subnet)を参考にしてください。

以上のように、ワークロードプロファイルの従量課金プランでは様々な改良が加えらえており、デメリットは特にないように見受けられます。今後はワークロードプロファイルが主流になっていくと考えられます。

### 専用プラン
専用プランは自分専用のコンテナ実行環境（Kubernatesでいうところのノード）を必要量に応じて用意できるものになっています。AppServiceプランやDedicated Hostのコンテナ版、というイメージでしょうか。専用プランのメリットは以下の通りです。
* 従量課金プランより多くのリソースをコンテナに割り当て可能（選択したインスタンスのサイズがコンテナに割り当て可能な上限になる）
* コンテナに任意のリソース割り当てができる（従量課金プランだとvCPUとメモリの値の組み合わせが決まっている）
* 他テナントと共用ではない専用インスタンス上で稼働する（＝環境の分離）
* コストの課金がコンテナ単位ではなく、ノード単位になる（デメリットにもなりうる）

コンテナに4vCPU/8GiB以上のリソースを割り当てる必要がある場合は専用プランを使います。しかし、コンテナ数が少ないとコスト効率が悪くなるため、小規模環境では使いにくいかと思います。可用性を考慮すると最低3インスタンスが望ましいため、コンテナ台数が少なくてリソースを余らせるような使い方だとコストが割高になります。

まずは従量課金プランが使えるか検討し、要件を満たせない場合は専用プランを考える、という流れになるかなと思います。

# 実際に試してみる

1. Container Apps環境はコンテナアプリ作成画面からでないと現状は作成できないため、コンテナアプリの管理画面へ行き、[作成]を選択します。
![01.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2850747/9c355403-b869-e21f-584f-7f4d22b679b8.png)

1. コンテナアプリの作成画面の下の方にContainer Apps環境の新規作成ボタンがあるので、クリックします。
![02.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2850747/e031bb95-0b6b-6f8a-b712-efdfc4d62be7.png)

1. 環境の種類は「ワークロードプロファイル」を選択します。ゾーン冗長は要件に合わせて選択します。
![03.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2850747/e9300575-29ef-2338-5cdc-00cb3bb2b829.png)

1. ワークロードプロファイルは一旦既定のまま進めます。既定で書かれている「Consumption」が従量課金プランのことです。英語のままになっているので、ここはそのうち表記が変わるかもしれません。
![04.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2850747/6b6faa34-95d0-a5ab-d1fb-08d396770775.png)

1. 監視の項目はログの出力先の指定です。Container Apps環境ではコンテナの標準出力ログとシステムログが出力されます。「Azureログ分析」を選択すると、指定したLog Analyticsへの出力になります。「Azure Monitor」を選択すると診断設定が設定できるようになり、Event Hubs/Log Analytics/ストレージアカウントへの出力を細かく指定できます。
![05.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2850747/dbd2854b-54a9-3100-1a99-198a5fca33e2.png)

1. ネットワークの設定です。テスト目的なので新規にVnetを作っていますが、実際に利用する場合はコンテナと通信が必要なリソースが所属するVnetを指定しましょう。ゾーン冗長が不要かつ、Vnet内のリソースとの通信が不要であればマネージドなVnetを利用することも可能です。
仮想IPは外部公開が必要であれば「外部」、Vnet内からの利用であれば「内部」を選択します。
インフラストラクチャリソーグループは空欄にしていると自動的に「ME_」が頭についたリソースグループが生成されて、動作に必要なリソースが格納されます。リソースグループ名を明示的に指定することも可能です。
![06.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2850747/5b73ab1e-aa8f-b825-89a5-f82f499b387a.png)

1. 以上でContainer Apps環境の設定は終わりです。コンテナアプリの作成画面に戻ってきます。必要な設定をおこなったら、次はコンテナの設定画面です。今回はテストなのでサンプルコンテナをそのまま使います。
![07.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2850747/7a438977-f015-d618-0a04-f409f1b70bd1.png)

1. 設定が一通り完了したのでデプロイします。
1. コンテナがデプロイされました。環境の種類は「ワークロードプロファイル」、ワークロードプロファイルは「Consumption」になっていることが確認できます。
![08.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2850747/1ba32dca-5124-5d68-c30b-49e6aaf4e0c2.png)

1. コンテナリソースの割り当て設定画面を確認してみると、CPU：4コア、メモリ：8GiBまで割り当てられるようになっていることが確認できました。
![09.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2850747/ae744c19-8457-48e7-b83f-5788607c1d12.png)

1. 専用プランを試してみます。作成したContainer Apps環境の管理画面へ遷移し、「ワークロードプロファイル」のメニューを選択し、「追加」ボタンをクリックします。
![10.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2850747/5cbde21a-ac58-e519-448d-74bdd641fcfd.png)


1. （プレビュー）という表記が残っているので、不安になりますが、更新漏れでしょう…。ワークロードプロファイルのサイズの「変更ボタン」を押すと、選択可能なインスタンスサイズ一覧が出てきますので、必要なものを選択します。今回はD4を選びます。
インスタンスについても自動スケーリングが可能となっており、運用環境では最小インスタンスが3以上推奨になっています。今回はテスト用途なので最小0、最大1にします。
余談）ノードと書いてくれた方がわかりやすい気がしますが、Container Apps環境ではコンテナ実行ノードをインスタンスと呼ぶようです。
![12.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2850747/e72b29d9-0647-ad39-d0ea-3eaa0bedcf48.png)
![11.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2850747/82b709da-e84f-3839-5f46-32aa8d6f0597.png)

1. ワークロードプロファイルが追加されました。
![13.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2850747/ca7c5fab-405f-2fa3-f475-9c10869fbcc3.png)


1. コンテナアプリの概要ページに戻り、ワークロードプロファイルを作成したものに変更してみます。
![08-2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2850747/135e493a-ef5e-7d61-a2db-6ecc61a61f79.png)
![14.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2850747/b04a36e9-b53c-321f-9bc7-968ce6729529.png)

1. ワークロードプロファイル変更後、コンテナの編集画面を開くと、コンテナに割り当てられるメモリ量が16GiBまで増えていることが確認できました。ワークロードプロファイルで作成したインスタンスのサイズがコンテナに割り当てられるリソースの上限になっていることがわかります。
また、従量課金プランではvCPUとメモリの値の組み合わせは決まったものしか指定できないという[制約](https://learn.microsoft.com/ja-jp/azure/container-apps/containers#configuration)がありますが、専用プランであればvCPUとメモリの値の組み合わせは任意に指定可能です。
![15.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2850747/dab3d6c8-55bc-ba2f-6a55-ad16c20eb89f.png)

1. インスタンスの上限を超えたリソースをコンテナに割り当てるとどうなるか試してみます。
まず先ほど作ったコンテナに上限いっぱいの16GiBメモリを割り当てた状態にします。そこからさらに同じワークロードプロファイルを指定してコンテナを新規で作成してみます。ワークロードプロファイルでインスタンスの最大値は1にしているので、割り当て可能なリソース不足の状態になっています。
コンテナアプリの作成画面では特にエラーにならず、コンテナはプロビジョニング中の状態になりますが、しばらくするとタイムアウトして失敗しました。やはりオーバーコミットはできず、リソースが足らないとプロビジョニング失敗するようです。コンテナ作成時には特にエラーにならないため、専用プランを利用する際にはワークロードプロファイルで利用可能なリソース量、コンテナに割り当てているリソース量を把握していないと予期せぬエラーに陥ってしまうリスクがあります。
![18.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2850747/61a90979-f846-7394-12e8-8c3e53758f91.png)
![19.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2850747/31e5862e-1a21-7f98-93c0-8144f3f214e1.png)

### 他に試したこと
* 専用プランのワークロードプロファイルから従量課金プランのワークロードプロファイルに変更することもできました。ただし、コンテナに割り当てているリソースを[従量課金プランで使える組み合わせ](https://learn.microsoft.com/ja-jp/azure/container-apps/containers#configuration)に変更してからでないとエラーになります。
* Container Apps環境で使っているサブネットにNATGWを関連付けても問題なく動作しました。従来の従量課金プランで同じことをすると通信がおかしくなるようで、エラー状態になりました。

# まとめ
実際に試してみてワークロードプロファイルの従量課金プランは従来の従量課金プランよりも使い勝手がよく、今後の主流になりそうだと感じました。専用プランはAKSほどガッツリしたものはいらないけど、マネージドなコンテナ環境を使いたい、という用途にはまりそうです。Container Appsはまだ西日本で使えなかったり、制約もまだまだ多いですが、気になるプレビュー中の機能も多く、拡充が進んでいる実感があります。今後も注目していきたいと思います。