ファイルを保護する方法を学ぶ

Firebase Storage には、Firabase Storage セキュリティ ルールと呼ばれる宣言型パスベースのセキュリティ モデルがあり、これを使用してすばやく簡単にファイルを保護することができます。

ルールについて

Firebase Storage セキュリティ ルールは、Firebase Storage に格納されているファイルの読み取りアクセス権や書き込みアクセス権を持つユーザーを決定します。また、ファイルの構成方法やファイルに含まれるメタデータの種類も決定します。基本のルールは allow ルールです。これは、次の例に示すように、オプションで指定されている条件を満たす場合に、read リクエストと write リクエストを許可します。

// If no condition is specified, the rule evaluates to true
allow read;

// Rules can optionally specify a condition
allow write: if <condition>;

// Rules can also specify multiple request methods
allow read, write: if <condition>;

パスの照合

Storage セキュリティ ルールでは、match を使用して、Firebase Storage 内のファイルにアクセスするためのファイルパスを照合します。また、match を使用して完全なパスまたはワイルドカード パスと照合することができ、ルールをネストすることもできます。リクエスト メソッドを許可する照合ルールがない場合や、条件が false になる場合、リクエストは拒否されます。

完全一致

// Exact match for "images/profilePhoto.png"
match /images/profilePhoto.png {
  allow write: if <condition>;
}

// Exact match for "images/croppedProfilePhoto.png"
match /images/croppedProfilePhoto.png {
  allow write: if <other_condition>;
}

ネストされた一致

// Partial match for files that start with "images"
match /images {
  // Exact match for "images/profilePhoto.png"
  match /profilePhoto.png {
    allow write: if <condition>;
  }

  // Exact match for "images/croppedProfilePhoto.png"
  match /croppedProfilePhoto.png {
    allow write: if <other_condition>;
  }
}

ワイルドカードの一致

ルールでは、match を使用して、ワイルドカードを使ったパターンと照合させることもできます。ワイルドカードは名前付き変数で、1 つの文字列(profilePhoto.png など)や複数のパスセグメント(images/profilePhoto.png など)を表します。

ワイルドカードは、{string} のように、ワイルドカード名を中かっこで囲んで作成します。複数セグメントのワイルドカードは、{path=**} のようにワイルドカード名に =** を追加して宣言することができます。

// Partial match for files that start with "images"
match /images {
  // Exact match for "images/*"
  // e.g. images/profilePhoto.png is matched
  match /{imageId} {
    // This rule only matches a single path segment (*)
    // imageId is a string that contains the specific segment matched
    allow read: if <condition>;
  }

  // Exact match for "images/**"
  // e.g. images/users/user:12345/profilePhoto.png is matched
  // images/profilePhoto.png is also matched!
  match /{allImages=**} {
    // This rule matches one or more path segments (**)
    // allImages is a path that contains all segments matched
    allow read: if <other_condition>;
  }
}

複数のルールが 1 つのファイルと一致する場合、結果は、すべてのルール評価の結果の OR になります。つまり、ルールのどれかでファイルの一致が true になると、結果は true になります。

上記のルールでは、ファイル "images/profilePhoto.png" は condition または other_condition が true になると、読み取り可能になります。これに対して、ファイル "images/users/user:12345/profilePhoto.png" に影響する条件は other_condition の結果だけです。

ワイルドカード変数は、match の指定ファイル名またはパス認証から参照することができます。

// Another way to restrict the name of a file
match /images/{imageId} {
  allow read: if imageId == "profilePhoto.png";
}

Storage セキュリティ ルールはカスケード処理されません。ルールは、リクエストパスと、ルールで指定されているパスが一致する場合のみ評価されます。

リクエストの評価

アップロード、ダウンロード、メタデータの変更、削除は、Firebase Storage に送信される request を使用して評価されます。request 変数には、リクエストが行われるファイルパス、リクエストの受信時間、新しい resource 値(リクエストが書き込みの場合)が含まれます。HTTP ヘッダーと認証状態も含まれます。

また、request オブジェクトには、ユーザーに固有の ID と request.auth オブジェクト内の Firebase Authentication ペイロードが含まれます。これらについては、このドキュメントのユーザーベースのセキュリティのセクションで詳しく説明します。

request オブジェクトのプロパティの完全なリストは次のとおりです。

プロパティ 説明
auth マップ<文字列, 文字列> ユーザーのログイン時に uid(ユーザーに固有の ID)と token(Firebase Authentication JWT クレームのマップ)を提供します。それ以外の場合は、null になります。
params マップ<文字列, 文字列> リクエストのクエリ パラメータを含むマップです。
path パス リクエストの実行先のパスを表す path です。
resource マップ<文字列, 文字列> write リクエスト時にのみ指定される新しいリソース値です。
time タイムスタンプ リクエスト評価時のサーバー時刻を表すタイムスタンプです。

これらのプロパティの詳細なドキュメントは、Firebase Storage セキュリティ ルール API リファレンスから入手できます。

リソースの評価

ルールを評価するときに、アップロード、ダウンロード、変更、または削除するファイルのメタデータも評価したい場合があります。メタデータを評価すると複雑で効果的なルールを作成できるので、特定のコンテンツ タイプを持つファイルだけをアップロードしたり、特定のサイズよりも大きなファイルだけを削除したりすることができます。

Firebase Storage セキュリティ ルールは、resource オブジェクト内のファイル メタデータを提供します。このオブジェクトには、Firebase Storage オブジェクトに示されるメタデータの Key-Value ペアが含まれます。これらのプロパティを read または write リクエストの際に調べることで、データの整合性を確認することができます。

write リクエスト(アップロード、メタデータの更新、削除など)では、現在リクエストパスに存在しているファイルのファイル メタデータを含む resource オブジェクトに加え、書き込みが許可された場合に書き込まれるファイル メタデータのサブセットを含む request.resource オブジェクトを使用することもできます。この 2 つの値を使用してデータの整合性を確認したり、ファイルのタイプやサイズといったアプリケーションの制約を適用したりできます。

resource オブジェクトのプロパティの完全なリストは次のとおりです。

プロパティ 説明
name 文字列 オブジェクトのフルネームです。
bucket 文字列 このオブジェクトが置かれているバケットの名前です。
generation 整数 このオブジェクトの GCS オブジェクト生成です。
metageneration 整数 このオブジェクトの GCS オブジェクト メタ生成です。
size 整数 オブジェクトのサイズです(バイト単位)。
timeCreated タイムスタンプ オブジェクトの作成時刻を示すタイムスタンプです。
updated タイムスタンプ オブジェクトの最終更新時刻を示すタイムスタンプです。
md5Hash 文字列 オブジェクトの MD5 ハッシュです。
crc32c 文字列 オブジェクトの crc32c ハッシュです。
etag 文字列 このオブジェクトに関連付けられた etag です。
contentDisposition 文字列 このオブジェクトに関連付けられたコンテンツの配置です。
contentEncoding 文字列 このオブジェクトに関連付けられたコンテンツ エンコーディングです。
contentLanguage 文字列 このオブジェクトに関連付けられたコンテンツ言語です。
contentType 文字列 このオブジェクトに関連付けられたコンテンツ タイプです。
metadata マップ<文字列, 文字列> デベロッパーがカスタム メタデータで指定した、追加の Key-Value ペアです。

request.resourcegenerationmetagenerationetagtimeCreatedupdated を除いて、上記のすべてを含みます。

これらのプロパティの詳細なドキュメントは、Firebase Storage セキュリティ ルール API リファレンスから入手できます。

次のようにすべてをまとめて、画像ストレージ ソリューションのルールの完全な例を作成することができます。

service firebase.storage {
 match /b/<your-firebase-storage-bucket>/o {
   match /images {
     // Cascade read to any image type at any path
     match /{allImages=**} {
       allow read;
     }

     // Allow write files to the path "images/*", subject to the constraints:
     // 1) File is less than 5MB
     // 2) Content type is an image
     // 3) Uploaded content type matches existing content type
     // 4) File name (stored in imageId wildcard variable) is less than 32 characters
     match /{imageId} {
       allow write: if request.resource.size < 5 * 1024 * 1024
                    && request.resource.contentType.matches('image/.*')
                    && request.resource.contentType == resource.contentType
                    && imageId.size() < 32
     }
   }
 }
}

次は、ユーザー セキュリティのセクションで、ユーザーのファイル アクセス権ごとに Firebase Authentication を個別に統合しましょう。

フィードバックを送信...