Azure Functionsとアプリケーション設定: local.settings.jsonとhost.jsonとAzure KeyValut

Azure Functionsのアプリケーション設定について調べてみました。

はじめに

表題の件に関して、以下の想定で記載しています。

  • Azure Functions Runtime v2.x 以降
  • .NET Core 3.1

アプリケーション設定とは

アプリケーション設定 とはAzure Functionsを動かす際に参照する各種設定値です。 その値はAzure PortalでAzure Functionsの構成ページを開くと確認できます。 下図はその一例です。

./images/figure_01.png

local.settings.json とは

Azure Functionsのプロジェクトには開発環境でのアプリケーション設定を示す local.settings.json ファイルが登場します。 このファイルには例えばAzure Functionsが接続するAzure Storageを示す AzureWebJobsStorage などの項目があります。

例えばその AzureWebJobsStorage は以下のように記述すると接続先がAzure Storageエミュレーターになります。

1
2
3
4
5
6
7
{
  "IsEncrypted": false,
  "Values": {
	"AzureWebJobsStorage": "UseDevelopmentStorage=true",
	"FUNCTIONS_WORKER_RUNTIME": "dotnet"
  }
}

開発方法によってはエミュレーターではなく実際にAzure Storageに接続することもあるでしょう。その場合は下記のように記載します。1

1
2
3
4
5
6
7
{
  "IsEncrypted": false,
  "Values": {
    "AzureWebJobsStorage": "DefaultEndpointsProtocol=https;AccountName=xxxxx;AccountKey=xxxxxxx;EndpointSuffix=core.windows.net",
    "FUNCTIONS_WORKER_RUNTIME": "dotnet"
  }
}

その他については下記ををご参照ください。

local.settings.jsonでhost.jsonの値を上書きする

host.json の値は local.settings.json で上書きが可能です。

以下はApplication Insightsの設定を開発環境では無効にするMSのリファレンスから引用した例です。

1
2
3
4
5
6
7
8
{
    "IsEncrypted": false,
    "Values": {
        "AzureWebJobsStorage": "{storage-account-connection-string}",
        "FUNCTIONS_WORKER_RUNTIME": "{language-runtime}",
        "AzureFunctionsJobHost__logging__applicationInsights__samplingSettings__isEnabled":"false"
    }
}

詳しくは下記をご参照ください。

Azureからアプリケーション設定を取得してlocal.settings.jsonに保存する

AzureでホスティングしているAzure Functionsのアプリケーション設定は以下のツールでローカルにコピーできます。

コマンドの説明は以下の通りです。

1
2
3
4
5
6
7
$ func azure functionapp

Usage: func azure functionapp <action> [-/--options]

Actions: 
fetch-app-settings  Retrieve App Settings from your Azure-hosted Function App and store locally Aliases: fetch-app-settings, fetch
    <FunctionAppName> Function App name

インストール方法

macOS

1
2
3
4
5
6
7
8
# Azureにログインしていないと ~fetch-app-settings~ は使えない。既にインストール済みなら不要です。
brew install azure-cli 

# Azure Functions Core ToolsはHomebrewのメインストリーム?には含まれていないので追加します。
brew tap azure/functions

# Azure Functions Core Toolsのインストール。
brew install azure-functions-core-tools@3

Windows

1
npm i -g azure-functions-cli

Linuxユーザーも先述のリンク先に記載があります。

使い方

例えば、対象のAzure Functionsの名前が example-hiroakit-com-api の場合、以下のように使います。

macOS

1
2
3
4
5
6
7
8
# Azure Functionsのhost.jsonが存在するディレクトリに移動します。
cd your-project 

# azure-cliを使ってログイン。もちろんログイン済みなら不要です。
az login 

# Azureからアプリケーション設定を取得してlocal.settings.jsonに保存します。
func azure functionapp fetch-app-settings example-hiroakit-com-api

以下に注意点をまとめました。

*注意事項 *

  1. host.json がない場所で fetch-app-settings を実行すると次のエラーが発生します。

    • Unable to find project root. Expecting to find one of host.json, local.settings.json in project root.
  2. local.settings.jsonIsEncrypted が存在する場合、その値に左右されます。

    • trueの場合: 暗号化された状態で書き込まれる
    • falseの場合: 暗号化されていない状態で書き込まれる
  3. 当然ながら、Azureにログインしていない状態で fetch-app-settings を実行すると次のエラーが発生します。

    • Unable to connect to Azure. Make sure you have the `az` CLI or `Az.Accounts` PowerShell module installed and logged in and try again

Windows

  • TBD

実行結果サンプル

以下に実行結果のサンプルを示します。

次のサンプルのSecretSettingはAzure KeyValutの値です。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
{
  "IsEncrypted": true,
  "Values": {
    "APPINSIGHTS_INSTRUMENTATIONKEY": "ZeonZumDeikun==",
    "APPLICATIONINSIGHTS_CONNECTION_STRING": "ZeonZumDeikun==",
    "AzureWebJobsStorage": "ZeonZumDeikun==",
    "FUNCTIONS_EXTENSION_VERSION": "ZeonZumDeikun==",
    "FUNCTIONS_WORKER_RUNTIME": "ZeonZumDeikun==",
    "WEBSITE_CONTENTAZUREFILECONNECTIONSTRING": "ZeonZumDeikun==",
    "WEBSITE_CONTENTSHARE": "ZeonZumDeikun==",
    "SecretSetting": "CharAznable=="
  },
  "ConnectionStrings": {}
}

Azure KeyVault

前述のlocal.settings.jsonを復号すると以下になったとします。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
{
  "IsEncrypted": false,
  "Values": {
    :
    <中略>
    :  
    "SecretSetting": "@Microsoft.KeyVault(SecretUri=シークレット識別子)"
  },
  "ConnectionStrings": {}
}

アプリケーション設定を取得する

例として、C#で AzureWebJobsStorage の値を取得する場合を考えます。

  • local.settings.json でAzureWebJobsStorageを上書きしている場合はこのファイルから読み取ります。
  • host.json にしかAzureWebJobsStorageが存在しない場合はこのファイルから読み取ります。
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
string value = string.Empty;

try
{
    value = Environment.GetEnvironmentVariable("AzureWebJobsStorage", EnvironmentVariableTarget.Process);
}
catch
{
    throw;
}

return value;

Environment.GetEnvironmentVariableで以下の例外が発生する可能性があるため、上記の例ではTry & Catchを入れています。

  • ArgumentNullException
  • ArgumentException
  • SecurityException

同メソッドの第2引数で指定しているEnvironmentVariableTarget.Processに関しては例です。


1

私の近辺ではAzure Storageエミュレーターを活用している方は少なく、便利な使い方があったらぜひ教えてください