Flex Consumption のサイト更新戦略

Flex 従量課金プランでAzure Functionsを使用してアプリをホストする場合は、実行中のインスタンスに更新プログラムをデプロイする方法を制御できます。 サイトの更新は、コードの展開、アプリケーション設定の変更、またはその他の構成プロパティの変更を行うたびに発生します。 Flex 従量課金プランには構成設定 (SiteUpdateStrategy) が用意されており、これらの更新中に関数アプリでダウンタイムが発生するかどうかと、進行中の実行がどのように処理されるかを制御できます。

Flex 従量課金プランでは、現在、次の更新戦略がサポートされています。

  • 再作成: 最新の変更でアプリを更新した後、実行中のすべてのインスタンスを再起動します。 この方法では、インスタンスがリサイクルされ、他のAzure Functions ホスティング プランからの既定の動作が保持されている間、短いダウンタイムが発生する可能性があります。
  • ローリング アップデート: インスタンスをバッチでドレインして置き換えることで、ダウンタイムゼロのデプロイを実現します。 進行中の実行は、強制終了なしで自然に完了します。

戦略の比較

次の表は、2 つのサイト更新戦略を比較しています。

考慮事項 再作成 ローリング アップデート
稼働停止時間 再起動後にアプリがゼロからスケールアウトする場合の短いダウンタイム ダウンタイムの期間なし
進行中の実行 強制終了 60 分間のスケールイン猶予期間内に完了できます (HTTP 関数は 230 秒のタイムアウトに制限されます)
展開時間 高速 - インスタンスは直ちに再起動されます 低速 - インスタンスは一定の間隔でバッチで更新されます
旧バージョンとの互換性 一度に 1 つのバージョンが実行されるため、必要ありません 変更は、特にステートフル ワークロードや重大な変更の場合に下位互換性がある必要があります
設定方法 既定の動作(他のホスティング プランと一致) オプトイン構成
次の場合に使用... ✔ 高速デプロイが必要です。
✔ 短いダウンタイムは許容されます。
✔ 破壊的変更をデプロイしており、クリーンな再起動が必要です。
✔ 関数はステートレスであり、中断を処理できます。
✔ ダウンタイムなしのデプロイが必要です。
✔ 中断できない実行時間の長い関数または重要な関数があります。
✔ 変更内容は下位互換性があります。
✔ 進行中の実行は保持する必要があります。

戦略の動作を更新する

次の表は、2 つの戦略の更新プロセスを比較したものです。

戦略を再作成する ローリング更新の戦略
1. サイトの更新 (コードまたは構成の変更) が関数アプリに適用されます。
2. 再作成戦略は、実行中のインスタンスを新しい変更で更新するためにトリガーされます。
3.プラットフォームは、すべてのライブインスタンスとドレインインスタンスを強制的に再起動します。
4. スケーリング システムは、更新されたバージョンで新しいインスタンスのプロビジョニングをすぐに開始します (元のインスタンスはバックグラウンドでプロビジョニング解除されている可能性があります)。
1. サイトの更新 (コードまたは構成の変更) が関数アプリに適用されます。
2. ローリングアップデート戦略は、実行中のインスタンスを新しい変更で更新するためにトリガーされます。
3. プラットフォームは、すべてのライブ インスタンスをバッチに割り当てます。
4. 一定の間隔で、プラットフォームはインスタンスの 1 つのバッチをドレインします。 ドレインすると、実行中の実行を完了できる間 (最大 1 時間の最大実行時間) にインスタンスが新しいイベントを受け入れなくなります。
5. 同時に、スケーリング プラットフォームは、ドレインされる容量を補うために、更新版を実行する新しいインスタンスをプロビジョニングします。
6. このプロセスは、すべてのライブ インスタンスが更新バージョンを実行するまで続行されます。

次の表は、2 つの戦略の主な特性を比較しています。

戦略を再作成する ローリング更新の戦略
  • 短時間のダウンタイム: インスタンスの再起動とスケールアウト中にアプリを使用できません。
  • 実行の中断: 進行中の実行は直ちに終了します。
  • 完了通知なし: インスタンス ログを監視して、元のインスタンスがログの出力を停止するタイミングを追跡します。
  • ダウンタイムなし: デプロイはバッチで実行されるため、強制終了なしで実行が完了します。
  • 非同期操作: ドレインとスケールアウトは、互いの完了を待たずに同時に行われます。 スケールアウトは、次のドレイン間隔の前に行われるとは限りません。
  • 重なり合う更新: 更新が進行中であっても、追加のローリング更新を開始できます。 最新でないインスタンスはすべてドレインされ、最新バージョンのみがスケールアウトされます。
  • 動的スケーリング: プラットフォームは、更新中の現在の需要に基づいてインスタンス数を調整します。
  • プラットフォーム管理容量: 需要が増加すると、プラットフォームはドレインするよりも多くのインスタンスをプロビジョニングします。 需要が減少すると、現在のニーズを満たすために必要なインスタンスのみが作成されます。 この方法により、リソースの使用を最適化しながら、継続的な可用性が確保されます。

ローリングアップデート戦略に関する考慮事項

ローリング アップデート戦略を使用する場合は、これらの現在の動作と制限事項に留意してください。

  • プラットフォームで管理されるパラメーター: プラットフォームは、ローリング 更新の動作を決定するパラメーター (バッチ数、バッチあたりのインスタンス数、バッチ数、ドレイン間隔など) を制御します。 これらのパラメーターは、パフォーマンスと信頼性を最適化するために変更される可能性があります。
  • GA リージョンでは、戦略を変更しても何も起こりません: ローリング更新が一般提供されているリージョンでは、siteUpdateStrategy.type を変更しても、それ自体ではサイトの更新はトリガーされません。 事前に戦略を安全に更新し、次のコードまたは構成のデプロイに適用することができます。 ローリング 更新プログラムがまだロールアウトされているリージョンでは、戦略の変更は他の構成変更と同様に扱われ、 前 の戦略を使用するサイトの更新がトリガーされます。新しい戦略は、次のデプロイ以降に適用されます。
  • リアルタイム監視なし: 現在、ドレインしているインスタンスの数、残っているバッチの数、現在の進行状況の割合を把握することはできません。
  • 完了通知なし: ただし、インスタンス ログを監視して、更新が完了したときに見積もることができます。
  • 単一インスタンスのシナリオ: 1 つのインスタンスで実行されているアプリでは、再作成と同様の短いダウンタイムが発生しますが、進行中の実行はまだ完了しています。
  • Durable Functions: 更新中にバージョンを混在させると、Durable オーケストレーションで予期しない動作が発生する可能性があるため、明示的な orchestration バージョンの一致戦略を使用します。
  • コードとしてのインフラストラクチャ: コードと構成の変更を一緒にデプロイすると、重複する可能性のある複数のローリング更新がトリガーされます。
  • 下位互換性: ローリング アップデートの移行期間中に、変更が以前のバージョンで動作することを確認します。

更新戦略を構成する

SiteUpdateStrategyの子である functionAppConfig サイト設定を使用して、アプリの更新戦略を設定できます。 既定では、SiteUpdateStrategy.type は Recreateに設定されます。 この設定を構成するには、API バージョン 2023-12-01 以降の Azure CLI 2.87.0 以降、Bicep、または ARM テンプレートを使用します。

ローリング更新を有効にするには、 az functionapp update-strategy config set コマンドを使用します。

az functionapp update-strategy config set \
  --name MyFunctionApp \
  --resource-group MyResourceGroup \
  --type RollingUpdate

サイトの更新の監視

サイトの更新完了を示す組み込みのシグナルはありません。 Application Insights の KQL クエリをベスト エフォート アプローチとして使用して、ローリング 更新の進行状況を見積もることができます。

ローリング アップデートの進行状況の監視

これらの KQL クエリでは、Application Insights ログ内のインスタンスの更新を追跡することで、ローリング更新の進行状況のおおよその見積もりを提供します。 このアプローチには大きな制限があり、運用環境の自動化には依存しないでください。

// Rolling update completion check
let deploymentStart = datetime('2025-10-30T19:00:00Z'); // Set to your deployment start time
let checkInterval = 10s; // How often you run this query
let buffer = 30s; // Safety buffer for instance detection
//
// Get original instances (active before deployment)
let originalInstances = 
    traces
    | where timestamp between ((deploymentStart - buffer) .. deploymentStart)
    | where cloud_RoleInstance != ""
    | summarize by InstanceId = cloud_RoleInstance;
//
// Get currently active instances
let currentInstances = 
    traces
    | where timestamp >= now() - checkInterval
    | where cloud_RoleInstance != ""
    | summarize by InstanceId = cloud_RoleInstance;
//
// Check completion status
currentInstances
| join kind=leftouter (originalInstances | extend IsOriginal = true) on InstanceId
| extend IsOriginal = isnotnull(IsOriginal)
| summarize 
    OriginalStillActiveInstances = make_set_if(InstanceId, IsOriginal),
    NewInstances = make_set_if(InstanceId, not(IsOriginal)),
    OriginalStillActiveCount = countif(IsOriginal),
    NewCount = countif(not(IsOriginal)),
    TotalOriginal = toscalar(originalInstances | count)
| extend 
    RollingUpdateComplete = iff(OriginalStillActiveCount == 0, "YES", "NO"),
    PercentComplete = round(100.0 * (1.0 - todouble(OriginalStillActiveCount) / todouble(TotalOriginal)), 1)
| project RollingUpdateComplete, PercentComplete, OriginalStillActiveCount, NewCount

推定にこのクエリを使用する方法:

  1. 関数アプリに関連付けられている Application Insights リソースの [ログ] ブレードに、このクエリを貼り付けます。
  2. サイトの更新で成功が返されたときのタイムスタンプに deploymentStart を設定します。
  3. クエリを定期的に実行して進行状況を見積もる。 ポーリング間隔を、関数の平均実行時間以上に設定し、クエリの checkInterval 変数がこのポーリング頻度と一致することを確認します。
  4. このクエリは、おおよその値を返します。

RollingUpdateComplete: すべての元のインスタンスが置き換えられるかどうかの最適な見積もりPercentComplete: 置き換えられる元のインスタンスの推定割合OriginalStillActiveCount: 実行中の元のインスタンスの推定数NewCount: 現在アクティブな新しいインスタンスの数

これらのクエリを使用する場合は、次の制限事項に注意してください。

  1. タイミング ギャップ: deploymentStart 時間は、サイトの更新プログラムが成功を返すタイミングを表しますが、実際のローリング 更新がすぐに開始されない場合があります。 このギャップの間、スケールアウト イベントは元のバージョンを実行しているインスタンスをプロビジョニングします。 クエリでは、 deploymentStartでアクティブなインスタンスのみが追跡されるため、これらの新しい元のバージョンのインスタンスは監視されないため、誤った完了シグナルが発生する可能性があります。
  2. ログベースの検出: この方法では、インスタンスの状態を直接クエリするのではなく、アプリケーション ログに依存してインスタンスの状態を推論します。 インスタンスは実行中でも、アクティブにログを記録していない可能性があり、元のインスタンスがまだアクティブだが、 checkInterval ウィンドウ内でログが出力されなかった場合に、誤った完了シグナルが発生します。

運用環境の推奨事項: ダウンタイムなしのデプロイが重要な場合は、ローリング 更新プログラムを使用します。 後続の手順に進む前に、デプロイ パイプラインで更新の完了を待機する必要がないことを確認します。 より速く予測可能な更新タイミングが必要で、短いダウンタイムを許容できる場合は、再作成を使用します。

FAQ

サイトの更新戦略に関する一般的な質問を次に示します。

ローリング アップデートと展開スロットはどのように違いますか?

デプロイ スロットとは異なり、ローリング更新では追加のインフラストラクチャは必要ありません。 ダウンタイムなしのデプロイの場合は、 siteUpdateStrategy.type を "RollingUpdate" に設定します。

ローリング 更新では進行中の実行が保持されますが、デプロイ スロットはスワップ中に終了します。 サイトの特定のプロパティ と固定設定はスワップできないため、運用スロットを直接変更する必要があります。

デプロイ スロットとは異なり、ローリング更新プログラムでは、変更をカナリア テストしたりやライブ トラフィックの割合のルーティングを行うための別の環境は提供されません。 これらの機能が必要な場合は、Elastic Premium などのデプロイ スロットをサポートするプランを使用するか、Traffic Manager の背後で個別の Flex Consumption アプリを管理します。

サイトの更新プログラムをロールバックするにはどうすればよいですか?

現在、サイト更新プログラムをロールバックする機能はありません。 ロールバックが必要な場合は、コードまたは構成の以前の状態で別のサイト更新を開始します。 完全なガイドについては、 不適切な Flex 従量課金プランのデプロイからの復旧を参照してください。

タイマー トリガーはどのように処理されますか?

タイマー トリガーは、シングルトンの性質を維持します。 タイマーによってトリガーされる関数アプリがドレインとしてマークされると、新しいタイマー関数が最新バージョンで実行されます。

ローリング アップデート中にランタイム エラーが表示される

新しいインスタンスの起動に失敗した場合、またはランタイム エラーが発生した場合は、変更したアプリケーション コード、依存関係、構成設定、または環境変数に問題がある可能性があります。

問題を解決するには、最後に既知の正常なバージョンを再デプロイしてランタイムを復元します。 次に、再使用する前に、開発環境またはステージング環境で提案された変更をテストします。 エラー ログを確認して、問題の原因となった特定の変更を特定します。

次のステップ