LoginSignup
0
0

大量ファイルによるBlob Trigger起動遅延の防止方法

Posted at

背景

IoT機器から送信されるさまざまなファイルをBlob Storageに取り込み、Azure FunctionsのBlob Triggerを用いて処理を行っています。システムをリリースした数年前は数分以内に処理が完了しており1、システムの特性上、特に問題はありませんでした。

しかしながら、ここ1年ほどでファイル数が大幅に増え2、取り込みの遅延が数時間から場合によっては1日以上に及び、データを利用しているシステムに影響が出始めていました。

結論

以下の記事を参考にして、Event Gridを経由してBlob Triggerを起動することで、ほぼ遅延がなくなりました。

原因

Blob Triggerは、ポーリングと待ち時間に記載されているように、10,000ファイルごとにポーリングを実施し、変化を検出しています。つまり、保存されているファイルが多くなると、それだけ遅延が増加することになります。

Blob Triggerの設定はhost.jsonに記載することができます。そこで、ポーリング間隔を短くしたり、スキャンするファイル数を変更できないか調べましたが、host.json 設定にある通り、これらの設定を変更することはできないようでした。

実際の作業

前提としてFunctions、Blob Storageは作成済みです。そのため、Event Gridの有効化、Blob Storageのイベント設定、Functionsのパラメータ追加を実施しました。

Event Gridの有効化

最初の時点ではEvent Gridが有効化されていないので、Microsoft.EventGridを検索し、三点リーダから「登録」をクリックします。
image.png

1分ほどすると設定が完了し、状態がregisteredに変わります。
image.png

これで準備はOKです。

Functionsのパラメータ追加

Functionsの設定を行う前にMicrosoft.Azure.Functions.Worker.Extensions.Storage.Blobsのバージョンを5.x以上にします。

次にBlob Trigger属性のパラメータにSource = BlobTriggerSource.EventGridを追加します。

  [FunctionName("LogToDatabase")]
  public void Run(
      [BlobTrigger(
          "logs/{id}/{year}-{month}-{day}-{hour}-{minute}-{second}.txt",
+         Source  = BlobTriggerSource.EventGrid,
          Connection = "LogConnectionString"
      )] Stream myBlob,
      string id,
      int year,
      int month,
      int day,
      int hour,
      int minute,
      int second,
      int blobTrigger,
      ILogger log)
  {
  }

Azure Event Grid Viewerのデプロイ

Azure-Samples/azure-event-grid-viewer を利用すると、Event Gridが発行するイベントを簡単に確認できます。リソースもApp ServiceプランとApp Serviceしかデプロイしないので、後片付けも簡単です。

Blob Storageの設定

ストレージアカウント左メニューの「イベント」でイベントの発行を設定できます。
image.png

「+イベントサブスクリプション」から、イベントを作成する。

image.png

エンドポイント

デバッグ環境

エンドポイントを先ほど作成したAzure Event Grid ViewerのURL+/api/updatesとします。

本番環境

https://<FUNCTION_APP_NAME>.azurewebsites.net/runtime/webhooks/blobs?functionName=BlobTriggerEventGrid&code=<BLOB_EXTENSION_KEY>

この例で、 を関数アプリの名前に置き換え、 をポータルから取得した値に置き換えます。 関数に別の名前を使用した場合は、必要に応じて functionName クエリ文字列を変更する必要もあります。

フィルター

Functionsが1つだけであったとしても、Triggerのフォーマットと異なる形式を送ってしまうとエラーになってしまうため、正しく指定します。デバッグ環境で正しく送信されることを確認してからエンドポイントを本番環境に変更することをお勧めします3

image.png

Azure Event Grid Viewerでの確認

ストレージアカウントにファイルをアップロードすると、Azure Event Grid Viewerにイベントが発行され、データが確認できます。

image.png

コンテナを指定したい場合は「次で始まるサブジェクト」に /blobServices/default/containers/<container name>を指定しておくといいです。高度なフィルターでも様々な設定ができるので便利でした。

雑感

FunctionsのBlob Triggerを改善しないといけないと思いつつ、放置してしまっていました。今回、Event Grid経由にしたことでシステムの遅延を大幅に改善できてよかったと思います。

  1. 従量課金プランではありませんでしたが、当時から送信されるファイルが多かったため、処理が完了するまでに時間がかかっていました。

  2. Storage Explorerからフォルダー統計を取得したところ、現時点で1,000万ファイルを超えていました。

  3. Functionsで設定したフォーマットと異なる場合でも実行されるということに気づかず、数千回のエラーを発生させてしまいました…。

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0