(仮) ブログ

主にWeb Apps や、Azure PaaS サービス を使う際に役立ちそうなことを書こうと思っています。

Azure Web Apps のファイルシステムについて (Windows と Linux)

今日はもういろんなところで話されている Azure Web Apps のファイル システムについて話してみようと思います。基本的には、Web Apps on WindowsLinux も同じようです。 ここに書いてあることをまとめてみました。

github.com

目次

その前に Azure Web Apps のアーキテクチャについて少し

まず、Azure Web Apps はスケールユニットと呼ばれるサーバー群に分かれています。Web Apps は各リージョンにあるこのスケールユニットのいずれかに所属しています。 これらはスタンプとも呼ばれており日本語での詳しい説明は、Azure App Service の リージョンとスタンプ、IP アドレスについて – Japan Azure PaaS Support Blogに書いてあります。

さらにこのスケールユニットは、リクエストを振り分ける FrontEnd や、アプリケーションを実行する WebWorker、ファイルを保存しておく FileServers など複数の役割を持つインスタンスで構成されています。

詳しくは Azure - Inside the Azure App Service Architecture で書かれています。

今回、一番大事なことはアプリケーションが実行される WebWorker インスタンスと、ファイルが保存されている Storage をマウントした FileServer のインスタンスは分かれているということです。

Web Apps のアプリケーションの保存先

私たちが Web Apps をホストするときは、そのコンテンツは D:\home\site\wwwroot に保存されており、このデータは FileServer インスタンスにマウントされた Azure Storage 上に保存されています。(上記参照)

ユーザーがポータルから Kudu サイトにアクセスした場合、編集可能な領域は、D:\home 以下になります。Web Apps on Linux や、Web App for Containers の場合 /home になりますが、Web App for Containers の場合後述する設定が必要のようです。

docs.microsoft.com

アプリケーションの実行時

アプリケーションが実行される際には、この Storage 内のデータがWebWorker インスタンス上にロードされます。

D:\home 以下でファイルの読み書きが発生した場合、WebWorker インスタンス <-> FileServers インスタンスの通信が発生します。スケールアウトで WebWorker インスタンスが複数になっている場合は、それぞれの WebWorker インスタンスが同じ FileServers インスタンスを参照します。(上記参照)

github.com

この構成の利点は、それぞれの WebWorker インスタンスが同じ FileServers インスタンスを参照するため、ファイルの一貫性が保たれることです。このため、あるインスタンスで行った変更が、その他のインスタンスにすぐ反映されます。 また、アプリケーションが新たにデプロイされた場合、そのコンテンツは Storage に永続的に保存されますので、前回下記で紹介したような再起動が発生した場合には、デプロイ時のコンテンツの反映が即座に行われます。

keyomura.hatenablog.com

一方で、巷ではこのストレージの読み書きが非常に遅いとも言われています。加えてアプリケーションのディレクトリに複数インスタンスから読み書きを行う場合、あるインスタンスの処理中に別インスタンスからの書き込みが来て処理がバッティングしてしまったと聞いたこともあります。ここら辺は Azure Web Apps に限らずどの環境でもあり得る話だと思います。

一時ファイル用のディレクトリを利用することもできる

通常のFile Storage を利用する以外にも、Web Apps にはもう一つローカルドライブと呼ばれる一時的なファイルの保存が可能なディレクトリ (D:\local\AppData や、D:\local\Temp など) 持っています。 これは WebWorkers インスタンス自体が持つディレクトリのため、これらのディレクトリ上でファイルを読み書きした場合は、 FileServers インスタンスとの通信がなくなり、ファイルの読み書き動作が早くなります。

なお、このローカルドライブは、Basic プラン以上の App Service Plan の場合、100GB 以上利用することが可能だそうです。(Free、Shared、Consumption の場合は 500 MB)

Azure Web Apps では、ローカルキャッシュ機能を利用することで、ローカルドライブ上にコピーしたアプリケーションを実行することができます。

docs.microsoft.com

ただ、一方で注意しなくてはいけないのが、ローカルドライブに保存された内容はそのインスタンスでしか利用できず、また、再起動した場合には削除されるということです。

このため、大事なデータなんかは、Azure Storage や SQL Database にちゃんと外部に保存しておきましょう。

Azure Web App for Containers の場合

Azure Web App for Containers の場合、ユーザー側が作成したコンテナを App Service の基盤上で動作させます。WebWoker インスタンス上で実行され、/home 以下はデフォルトではマウントされておりません。マウントしたいのであれば、WEBSITES_ENABLE_APP_SERVICE_STORAGE=true の設定を追加する必要があります。 ※ Web Apps on Linux では、デフォルトで /home がマウントされています。

docs.microsoft.com

Web Apps on Linux と、Azure Web App for Containers の違いはこちら

azure.microsoft.com

まとめ

  • Azure Web Apps では、アプリケーションを実行する WebWorker インスタンスと、ファイルを保存する FileServer インスタンスが分かれている
  • FileServer インスタンにあるネットワークドライブを参照するようにしている場合、複数インスタンス間のファイルの一貫性が保たれ、更新が即座に反映される
  • Local Cache を有効にしてローカルドライブを参照する場合、ファイルの読み書き動作が速くなるがその変更はインスタンス間で共有されない。

Web Apps (Windows) の場合、基本的にファイルの読み込みしか行わず、ログやデータを外部に保存している場合には ローカルキャッシュ機能を利用することをお勧めします。 一方で、D:\home 以下にガンガン書き込みをするようなアプリの場合は、ローカルキャッシュ機能を利用すると、再起動が起きたタイミングで今まで編集していたものが全て無くなってしまうということもあり得ますので、十分注意したほうがいいですね。