Azure Verified Module(AVM)を使ってBicepスクリプトの開発を効率化する
はじめに
本記事では、Azure Verified Module(以降、AVM)の概要と簡単な利用方法について記載します。
私自身、最近になってAVMを知って実際の業務でも使い始めたのですが、直接リソースステートメントで呼び出すよりもAVMのBicepリソースモジュールを呼び出すほうが保守性が高く、また開発効率も上がると感じたため紹介していきたいと思います。
QiitaやZennでAVMについて紹介している記事がなぜかあまり見当たらなかったので、この記事が少しでも参考になれば幸いです。
Azure Verified Module(AVM)とは
AVMとは、Microsoftによって開発・テストされ公開されているパブリックモジュールです。現在のところ、BicepとTerraformの両方で利用可能です。
それぞれ、ResourceModules、PatternModules、UtilityModulesの3つのカテゴリが存在しますが、本記事では主にResourceModulesに絞って記載していきます。
以下引用です。
Azure 検証済みモジュール (AVM) は、ベスト プラクティスとコンプライアンス要件を満たすために Microsoft によって開発およびサポートされる、Azure リソースをデプロイおよび管理するための一貫したアプローチを提供します。コードとしてのインフラストラクチャ (IaC) 用のこれらの定義済みの再利用可能なモジュールにより、Bicep と Terraform の両方で使用できる Azure リソースのデプロイと管理が容易になります。AVM は、Microsoft の Well-Architected Framework (WAF) への一貫性と準拠を保証し、クラウド インフラストラクチャ管理をより効率的かつ信頼性の高いものにします。
(引用:Azure Verified Modules | Microsoft Learn )
事前準備
- VSCode拡張機能のインストール
- Bicep拡張機能
- VSCodeのBicep拡張機能で、リソースステートメントと同様にAVMのBicep開発をサポートしてくれます。
- Azure MCP Server
- GithubCopilotでプロパティ情報を調べるのに重宝します。
- Bicep拡張機能
AVMの利用方法
WebAppをAVMでデプロイするスクリプト例
早速ですが、AVMを利用してWebAppをデプロイするBicepスクリプトの例を見ていきたいと思います。
基本的には、自前のBicepモジュールを呼び出すのと同じように、moduleステートメントでAVMのBicepリソースモジュールを呼び出します。
-
AVMモジュールの呼び出し部分
module asp 'br/public:avm/res/web/serverfarm:0.5.0' = { // existing code... } -
WebAppをデプロイするためのBicepスクリプトの例
/* Parameters */ param location string = resourceGroup().location param envName string = 'dev' // ASP Params param aspName string = 'asp-sample-01' param aspKind string = 'linux' param aspSku skuType = { skuName: 'P0v3' skuCapacity: 1 } param aspZoneRedundant bool = false // Web App Params param webAppName string = 'web-sample-01' param webAppKind string = 'app,linux' param webAppSiteConfig object = { linuxFxVersion: 'NODE|22-lts' } param webAppPublicNetworkAccess string = 'Enabled' /* Variables */ var deploymentSuffix = uniqueString(resourceGroup().id, deployment().name) /* Deployment */ module asp 'br/public:avm/res/web/serverfarm:0.5.0' = { name: 'avm-${aspName}-${deploymentSuffix}' params: { /* Required params */ name: aspName /* Optional params */ location: location kind: aspKind skuName: aspSku.skuName skuCapacity: aspSku.skuCapacity zoneRedundant: aspZoneRedundant tags: { Env: envName } } } resource existingAsp 'Microsoft.Web/serverfarms@2021-03-01' existing = { name: aspName dependsOn: [ asp ] } module webApp 'br/public:avm/res/web/site:0.19.2' = { name: 'avm-${webAppName}-deploy-${deploymentSuffix}' params: { /* Required params */ kind: webAppKind name: webAppName serverFarmResourceId: existingAsp.id /* Optional params */ location: location autoGeneratedDomainNameLabelScope: 'ResourceGroupReuse' siteConfig: { linuxFxVersion: webAppSiteConfig.linuxFxVersion } publicNetworkAccess: webAppPublicNetworkAccess tags: { Env: envName } } dependsOn: [ existingAsp ] } /* Types */ type skuType = { skuName: string! skuCapacity: int! } -
実際に作成されたリソース

このように、AVMモジュールを呼び出すだけでWebAppを作成することが可能です。
事前にリソースパラメータ設計をしておけば、そのパラメータを渡すようにスクリプトを考えるだけなので簡単ですね。
AVMでBicepスクリプトを作成する手順
AVMのBicepリソースモジュールは、GithubのAzure Verified Modulesリポジトリですべて公開されています。
開発方法としては、各リソースモジュールとプロバイダーのリファレンスを見ながら、必要なパラメータを洗い出してBicepスクリプトを作成していく形となります。
-
AVMのGithub Pagesから、作成したいリソースを探す。

-
AVMのリファレンス(README)を見ながら、必要なパラメータを洗い出してBicepスクリプトを作成する。

基本的には、AVMのREADMEに各モジュールの簡単なサンプルやパラメータの説明が記載されているので、そちらを参考にしながらスクリプトを作成していきます。
もしより詳しい情報が必要であれば、リソースプロバイダーのリファレンスを参照します。
- WebAppのパラメータリファレンス
- AVMリポジトリ:Web/Function Apps [Microsoft.Web/sites]
- リソースプロバイダー:Microsoft.Web/sites
AVMリソースモジュールの内部構造を見てみる
ここまでAVMの簡単な説明をしてきましたが、実際に利用する際にモジュールの中身がどうなっているかわからない状態では少し不安だと思うので、AVMのモジュールの内部構造がどうなっているか簡単に見ていきたいと思います。
例として、WebAppのkindプロパティを呼び出す流れを見ていきましょう。
-
モジュールの呼び出し
module webApp 'br/public:avm/res/web/site:0.19.2' = { // existing code... kind: 'app,linux' // existing code... } -
main.bicepでkindプロパティを受け取る
// 10行目あたり @description('Required. Type of site to deploy.') @allowed([ 'functionapp' // function app windows os 'functionapp,linux' // function app linux os 'functionapp,workflowapp' // logic app workflow 'functionapp,workflowapp,linux' // logic app docker container 'functionapp,linux,container' // function app linux container 'functionapp,linux,container,azurecontainerapps' // function app linux container azure container apps 'app,linux' // linux web app 'app' // windows web app 'linux,api' // linux api app 'api' // windows api app 'app,linux,container' // linux container app 'app,container,windows' // windows container app ]) param kind string -
main.bicepのリソース定義でkindプロパティを利用する
// 261行目あたり resource app 'Microsoft.Web/sites@2024-11-01' = { name: name location: location kind: kind // パラメータとして受け取った値を渡している tags: tags identity: identity // existing code... }
内部構造を見てみると、単純にリソースステートメントで「Microsoft.Web/sites@2024-11-01」を定義しているだけですね。また型定義がしっかりされていたり、パラメータを渡さない場合のデフォルト値も用意されているので、安全に利用できるようになっています。
APIバージョンも最新のものが利用されていて、アップデートも定期的に行われているようです。
メリット・デメリット
ここまでAVMの簡単な説明と利用方法、内部構造を見てきましたが、実際に利用するメリット・デメリットについても触れておきたいと思います。
メリット
- 開発効率が上がる
- AVMのBicepリソースモジュールを呼び出すだけで、複雑なリソースも簡単にデプロイできるため、開発効率が上がる。
- 保守性が高い
- Microsoftによって開発・テストされているため、信頼性が高く、保守性も高い。
- 商用利用が可能
- AVMはMITライセンスで公開されているため、商用利用も可能。
デメリット
- ある程度Azure/Bicepの知識が必要
- 実際に開発をしていく中で、パラメータやモジュールの仕様を確認することになるため、ある程度のAzure/Bicepの知識が必要になる。
- モジュールのバージョン管理が必要
- 新しいプロバイダーバージョンがリリースされた場合、AVMモジュールのバージョンを確かめて、必要に応じてバージョンの更新を行う必要がある。
まとめ
簡単な説明ではありましたが、AVMの導入イメージや利用するメリットについてご理解いただけましたでしょうか。
実際には、AVMは複雑なアーキテクチャをBicep化するとき(PrivateEndpoint,VNet統合,リソース間連携,RBACなど)により効果を発揮するものだと思うので、今後時間ができた際にはそういった例もご紹介できればと思います。
Discussion