安全規則語言

Firebase 安全規則利用支持各種複雜性和粒度的靈活、強大的自定義語言。您可以將規則設為對您的應用有意義的具體或一般規則。實時數據庫規則使用類似於 JSON 結構中的 JavaScript 的語法。 Cloud Firestore 和 Cloud Storage 規則使用基於通用表達式語言 (CEL)的語言,該語言以 CEL 為基礎,具有matchallow支持有條件授予訪問權限的語句。

但是,因為這些是自定義語言,所以存在學習曲線。隨著您深入了解更複雜的規則,使用本指南可以更好地理解規則語言。

選擇產品以了解有關其規則的更多信息。

基本結構

雲防火牆

Cloud Firestore 和 Cloud Storage 中的 Firebase 安全規則使用以下結構和語法:

service <<name>> {
  // Match the resource path.
  match <<path>> {
    // Allow the request if the following conditions are true.
    allow <<methods>> : if <<condition>>
  }
}

在構建規則時,理解以下關鍵概念很重要:

  • 請求:allow語句中調用的一個或多個方法。這些是您允許運行的方法。標準方法是: getlistcreateupdatedeleteread便利方法可以在指定的數據庫或存儲路徑上實現廣泛的write訪問。
  • 路徑:數據庫或存儲位置,表示為 URI 路徑。
  • 規則: allow語句,其中包含一個條件,如果請求的計算結果為 true,則允許請求。

下面更詳細地描述這些概念中的每一個。

雲儲存

Cloud Firestore 和 Cloud Storage 中的 Firebase 安全規則使用以下結構和語法:

service <<name>> {
  // Match the resource path.
  match <<path>> {
    // Allow the request if the following conditions are true.
    allow <<methods>> : if <<condition>>
  }
}

在構建規則時,理解以下關鍵概念很重要:

  • 請求:allow語句中調用的一個或多個方法。這些是您允許運行的方法。標準方法是: getlistcreateupdatedeleteread便利方法可以在指定的數據庫或存儲路徑上實現廣泛的write訪問。
  • 路徑:數據庫或存儲位置,表示為 URI 路徑。
  • 規則: allow語句,其中包含一個條件,如果請求的計算結果為 true,則允許請求。

下面更詳細地描述這些概念中的每一個。

實時數據庫

在實時數據庫中,Firebase 安全規則由 JSON 文檔中包含的類似 JavaScript 的表達式組成。

它們使用以下語法:

{
  "rules": {
    "<<path>>": {
    // Allow the request if the condition for each method is true.
      ".read": <<condition>>,
      ".write": <<condition>>,
      ".validate": <<condition>>
    }
  }
}

該規則包含三個基本要素:

  • 路徑:數據庫位置。這反映了您的數據庫的 JSON 結構。
  • 請求:這些是規則用於授予訪問權限的方法。 readwrite規則授予廣泛的讀取和寫入訪問權限,而validate規則充當輔助驗證以根據傳入或現有數據授予訪問權限。
  • 條件:如果計算結果為真,則允許請求的條件。

規則構造

雲防火牆

Cloud Firestore 和 Cloud Storage 中規則的基本元素如下:

  • service聲明:聲明規則適用的 Firebase 產品。
  • match塊:定義應用規則的數據庫或存儲桶中的路徑。
  • allow語句:提供授予訪問權限的條件,按方法區分。支持的方法包括: getlistcreateupdatedelete ,以及方便的方法readwrite
  • 可選function聲明:提供組合和包裝條件以跨多個規則使用的能力。

service包含一個或多個match塊,其中包含提供允許訪問請求的條件的allow語句。 requestresource變量可用於規則條件。 Firebase 安全規則語言還支持function聲明。

語法版本

syntax語句指示用於編寫源代碼的 Firebase 規則語言的版本。該語言的最新版本是v2

rules_version = '2';
service cloud.firestore {
...
}

如果未提供rules_version語句,您的規則將使用v1引擎進行評估。

服務

service聲明定義了您的規則適用於哪個 Firebase 產品或服務。每個源文件只能包含一個service聲明。

雲防火牆

service cloud.firestore {
 // Your 'match' blocks with their corresponding 'allow' statements and
 // optional 'function' declarations are contained here
}

雲儲存

service firebase.storage {
  // Your 'match' blocks with their corresponding 'allow' statements and
  // optional 'function' declarations are contained here
}

如果您使用 Firebase CLI 為 Cloud Firestore 和 Cloud Storage 定義規則,則必須將它們保存在單獨的文件中。

比賽

match塊聲明與請求操作的路徑(傳入request.path )匹配的path模式。 match的主體必須有一個或多個嵌套的match塊、 allow語句或function聲明。嵌套match塊中的路徑相對於父match塊中的路徑。

path模式是一個類似目錄的名稱,可能包含變量或通配符。 path模式允許單路徑段和多路徑段匹配。 path中綁定的任何變量在match範圍或聲明path的任何嵌套範圍內都是可見的。

path模式的匹配可能是部分的或完整的:

  • 部分匹配: path模式是request.path的前綴匹配。
  • 完全匹配: path模式匹配整個request.path

完全匹配時,塊內的規則將被評估。當進行部分匹配時,將測試嵌套match規則以查看是否有任何嵌套path完成匹配。

評估每個完整match中的規則以確定是否允許該請求。如果任何匹配的規則授予訪問權限,則允許該請求。如果沒有匹配的規則授予訪問權限,則該請求被拒絕。

// Given request.path == /example/hello/nested/path the following
// declarations indicate whether they are a partial or complete match and
// the value of any variables visible within the scope.
service firebase.storage {
  // Partial match.
  match /example/{singleSegment} {   // `singleSegment` == 'hello'
    allow write;                     // Write rule not evaluated.
    // Complete match.
    match /nested/path {             // `singleSegment` visible in scope.
      allow read;                    // Read rule is evaluated.
    }
  }
  // Complete match.
  match /example/{multiSegment=**} { // `multiSegment` == /hello/nested/path
    allow read;                      // Read rule is evaluated.
  }
}

如上例所示, path聲明支持以下變量:

  • 單段通配符:通配符變量通過用花括號括起來在路徑中聲明: {variable} 。此變量可在match語句中作為string訪問。
  • 遞歸通配符:遞歸或多段通配符匹配路徑上或路徑下的多個路徑段。此通配符與您設置的位置下方的所有路徑匹配。您可以通過在段變量的末尾添加=**字符串來聲明它: {variable=**} 。此變量可在match語句中作為path對象訪問。

允許

match塊包含一個或多個allow語句。這些是你的實際規則。您可以將allow規則應用於一種或多種方法。 allow語句中的條件必須評估為 true,Cloud Firestore 或 Cloud Storage 才能授予任何傳入請求。您還可以編寫不帶條件的allow語句,例如, allow read 。但是,如果allow語句不包含條件,它總是允許對該方法的請求。

如果滿足該方法的任何allow規則,則允許該請求。此外,如果更廣泛的規則授予訪問權限,則規則會授予訪問權限並忽略可能限制訪問權限的任何更細化的規則。

考慮以下示例,其中任何用戶都可以讀取或刪除他們自己的任何文件。如果請求寫入的用戶擁有文件並且文件是 PNG,則更精細的規則僅允許寫入。用戶可以刪除子路徑中的任何文件——即使它們不是 PNG——因為之前的規則允許這樣做。

service firebase.storage {
  // Allow the requestor to read or delete any resource on a path under the
  // user directory.
  match /users/{userId}/{anyUserFile=**} {
    allow read, delete: if request.auth != null && request.auth.uid == userId;
  }

  // Allow the requestor to create or update their own images.
  // When 'request.method' == 'delete' this rule and the one matching
  // any path under the user directory would both match and the `delete`
  // would be permitted.

  match /users/{userId}/images/{imageId} {
    // Whether to permit the request depends on the logical OR of all
    // matched rules. This means that even if this rule did not explicitly
    // allow the 'delete' the earlier rule would have.
    allow write: if request.auth != null && request.auth.uid == userId && imageId.matches('*.png');
  }
}

方法

每個allow語句都包含一個方法,該方法授予對相同方法的傳入請求的訪問權限。

方法請求類型
方便的方法
read任何類型的讀取請求
write任何類型的寫請求
標準方法
get讀取單個文檔或文件的請求
list查詢和集合的讀取請求
create編寫新文檔或文件
update寫入現有數據庫文檔或更新文件元數據
delete刪除數據

您不能在同一match塊中重疊讀取方法或在同一path聲明中重疊寫入方法。

例如,以下規則將失敗:

service bad.example {
  match /rules/with/overlapping/methods {
    // This rule allows reads to all authenticated users
    allow read: if request.auth != null;

    match another/subpath {
      // This secondary, more specific read rule causes an error
      allow get: if request.auth != null && request.auth.uid == "me";
      // Overlapping write methods in the same path cause an error as well
      allow write: if request.auth != null;
      allow create: if request.auth != null && request.auth.uid == "me";
    }
  }
}

功能

隨著您的安全規則變得越來越複雜,您可能希望將條件集包裝在可以在整個規則集中重用的函數中。安全規則支持自定義函數。自定義函數的語法有點像 JavaScript,但安全規則函數是用特定領域的語言編寫的,有一些重要的限制:

  • 函數只能包含一個return語句。它們不能包含任何額外的邏輯。例如,它們不能執行循環或調用外部服務。
  • 函數可以從定義它們的範圍內自動訪問函數和變量。例如,在service cloud.firestore範圍內定義的函數可以訪問resource變量和內置函數,例如get()exists()
  • 函數可以調用其他函數,但不能遞歸。總調用堆棧深度限制為 20。
  • 在規則版本v2中,函數可以使用let關鍵字定義變量。函數最多可以有 10 個 let 綁定,但必須以 return 語句結尾。

函數使用function關鍵字定義,並接受零個或多個參數。例如,您可能希望將上述示例中使用的兩種類型的條件組合成一個函數:

service cloud.firestore {
  match /databases/{database}/documents {
    // True if the user is signed in or the requested data is 'public'
    function signedInOrPublic() {
      return request.auth.uid != null || resource.data.visibility == 'public';
    }

    match /cities/{city} {
      allow read, write: if signedInOrPublic();
    }

    match /users/{user} {
      allow read, write: if signedInOrPublic();
    }
  }
}

這是一個顯示函數參數和 let 分配的示例。 let 賦值語句必須用分號隔開。

function isAuthorOrAdmin(userId, article) {
  let isAuthor = article.author == userId;
  let isAdmin = exists(/databases/$(database)/documents/admins/$(userId));
  return isAuthor || isAdmin;
}

請注意isAdmin分配如何強制查找 admins 集合。對於不需要不必要查找的惰性求值,利用&& (AND) 和||的短路特性。 (OR) 比較僅在isAuthor顯示為真(對於&&比較)或假(對於||比較)時才調用第二個函數。

function isAdmin(userId) {
  return exists(/databases/$(database)/documents/admins/$(userId));
}
function isAuthorOrAdmin(userId, article) {
  let isAuthor = article.author == userId;
  // `||` is short-circuiting; isAdmin called only if isAuthor == false.
  return isAuthor || isAdmin(userId);
}

隨著規則復雜性的增加,在安全規則中使用函數會使它們更易於維護。

雲儲存

Cloud Firestore 和 Cloud Storage 中規則的基本元素如下:

  • service聲明:聲明規則適用的 Firebase 產品。
  • match塊:定義應用規則的數據庫或存儲桶中的路徑。
  • allow語句:提供授予訪問權限的條件,按方法區分。支持的方法包括: getlistcreateupdatedelete ,以及方便的方法readwrite
  • 可選function聲明:提供組合和包裝條件以跨多個規則使用的能力。

service包含一個或多個match塊,其中包含提供允許訪問請求的條件的allow語句。 requestresource變量可用於規則條件。 Firebase 安全規則語言還支持function聲明。

語法版本

syntax語句指示用於編寫源代碼的 Firebase 規則語言的版本。該語言的最新版本是v2

rules_version = '2';
service cloud.firestore {
...
}

如果未提供rules_version語句,您的規則將使用v1引擎進行評估。

服務

service聲明定義了您的規則適用於哪個 Firebase 產品或服務。每個源文件只能包含一個service聲明。

雲防火牆

service cloud.firestore {
 // Your 'match' blocks with their corresponding 'allow' statements and
 // optional 'function' declarations are contained here
}

雲儲存

service firebase.storage {
  // Your 'match' blocks with their corresponding 'allow' statements and
  // optional 'function' declarations are contained here
}

如果您使用 Firebase CLI 為 Cloud Firestore 和 Cloud Storage 定義規則,則必須將它們保存在單獨的文件中。

比賽

match塊聲明與請求操作的路徑(傳入request.path )匹配的path模式。 match的主體必須有一個或多個嵌套的match塊、 allow語句或function聲明。嵌套match塊中的路徑相對於父match塊中的路徑。

path模式是一個類似目錄的名稱,可能包含變量或通配符。 path模式允許單路徑段和多路徑段匹配。 path中綁定的任何變量在match範圍或聲明path的任何嵌套範圍內都是可見的。

path模式的匹配可能是部分的或完整的:

  • 部分匹配: path模式是request.path的前綴匹配。
  • 完全匹配: path模式匹配整個request.path

完全匹配時,塊內的規則將被評估。當進行部分匹配時,將測試嵌套match規則以查看是否有任何嵌套path完成匹配。

評估每個完整match中的規則以確定是否允許該請求。如果任何匹配的規則授予訪問權限,則允許該請求。如果沒有匹配的規則授予訪問權限,則該請求被拒絕。

// Given request.path == /example/hello/nested/path the following
// declarations indicate whether they are a partial or complete match and
// the value of any variables visible within the scope.
service firebase.storage {
  // Partial match.
  match /example/{singleSegment} {   // `singleSegment` == 'hello'
    allow write;                     // Write rule not evaluated.
    // Complete match.
    match /nested/path {             // `singleSegment` visible in scope.
      allow read;                    // Read rule is evaluated.
    }
  }
  // Complete match.
  match /example/{multiSegment=**} { // `multiSegment` == /hello/nested/path
    allow read;                      // Read rule is evaluated.
  }
}

如上例所示, path聲明支持以下變量:

  • 單段通配符:通配符變量通過用花括號括起來在路徑中聲明: {variable} 。此變量可在match語句中作為string訪問。
  • 遞歸通配符:遞歸或多段通配符匹配路徑上或路徑下的多個路徑段。此通配符與您設置的位置下方的所有路徑匹配。您可以通過在段變量的末尾添加=**字符串來聲明它: {variable=**} 。此變量可在match語句中作為path對象訪問。

允許

match塊包含一個或多個allow語句。這些是你的實際規則。您可以將allow規則應用於一種或多種方法。 allow語句中的條件必須評估為 true,Cloud Firestore 或 Cloud Storage 才能授予任何傳入請求。您還可以編寫不帶條件的allow語句,例如, allow read 。但是,如果allow語句不包含條件,它總是允許對該方法的請求。

如果滿足該方法的任何allow規則,則允許該請求。此外,如果更廣泛的規則授予訪問權限,則規則會授予訪問權限並忽略可能限制訪問權限的任何更細化的規則。

考慮以下示例,其中任何用戶都可以讀取或刪除他們自己的任何文件。如果請求寫入的用戶擁有文件並且文件是 PNG,則更精細的規則僅允許寫入。用戶可以刪除子路徑中的任何文件——即使它們不是 PNG——因為之前的規則允許這樣做。

service firebase.storage {
  // Allow the requestor to read or delete any resource on a path under the
  // user directory.
  match /users/{userId}/{anyUserFile=**} {
    allow read, delete: if request.auth != null && request.auth.uid == userId;
  }

  // Allow the requestor to create or update their own images.
  // When 'request.method' == 'delete' this rule and the one matching
  // any path under the user directory would both match and the `delete`
  // would be permitted.

  match /users/{userId}/images/{imageId} {
    // Whether to permit the request depends on the logical OR of all
    // matched rules. This means that even if this rule did not explicitly
    // allow the 'delete' the earlier rule would have.
    allow write: if request.auth != null && request.auth.uid == userId && imageId.matches('*.png');
  }
}

方法

每個allow語句都包含一個方法,該方法授予對相同方法的傳入請求的訪問權限。

方法請求類型
方便的方法
read任何類型的讀取請求
write任何類型的寫請求
標準方法
get讀取單個文檔或文件的請求
list查詢和集合的讀取請求
create編寫新文檔或文件
update寫入現有數據庫文檔或更新文件元數據
delete刪除數據

您不能在同一match塊中重疊讀取方法或在同一path聲明中重疊寫入方法。

例如,以下規則將失敗:

service bad.example {
  match /rules/with/overlapping/methods {
    // This rule allows reads to all authenticated users
    allow read: if request.auth != null;

    match another/subpath {
      // This secondary, more specific read rule causes an error
      allow get: if request.auth != null && request.auth.uid == "me";
      // Overlapping write methods in the same path cause an error as well
      allow write: if request.auth != null;
      allow create: if request.auth != null && request.auth.uid == "me";
    }
  }
}

功能

隨著您的安全規則變得越來越複雜,您可能希望將條件集包裝在可以在整個規則集中重用的函數中。安全規則支持自定義函數。自定義函數的語法有點像 JavaScript,但安全規則函數是用特定領域的語言編寫的,有一些重要的限制:

  • 函數只能包含一個return語句。它們不能包含任何額外的邏輯。例如,它們不能執行循環或調用外部服務。
  • 函數可以從定義它們的範圍內自動訪問函數和變量。例如,在service cloud.firestore範圍內定義的函數可以訪問resource變量和內置函數,例如get()exists()
  • 函數可以調用其他函數,但不能遞歸。總調用堆棧深度限制為 20。
  • 在規則版本v2中,函數可以使用let關鍵字定義變量。函數最多可以有 10 個 let 綁定,但必須以 return 語句結尾。

函數使用function關鍵字定義,並接受零個或多個參數。例如,您可能希望將上述示例中使用的兩種類型的條件組合成一個函數:

service cloud.firestore {
  match /databases/{database}/documents {
    // True if the user is signed in or the requested data is 'public'
    function signedInOrPublic() {
      return request.auth.uid != null || resource.data.visibility == 'public';
    }

    match /cities/{city} {
      allow read, write: if signedInOrPublic();
    }

    match /users/{user} {
      allow read, write: if signedInOrPublic();
    }
  }
}

這是一個顯示函數參數和 let 分配的示例。 let 賦值語句必須用分號隔開。

function isAuthorOrAdmin(userId, article) {
  let isAuthor = article.author == userId;
  let isAdmin = exists(/databases/$(database)/documents/admins/$(userId));
  return isAuthor || isAdmin;
}

請注意isAdmin分配如何強制查找 admins 集合。對於不需要不必要查找的惰性求值,利用&& (AND) 和||的短路特性。 (OR) 比較僅在isAuthor顯示為真(對於&&比較)或假(對於||比較)時才調用第二個函數。

function isAdmin(userId) {
  return exists(/databases/$(database)/documents/admins/$(userId));
}
function isAuthorOrAdmin(userId, article) {
  let isAuthor = article.author == userId;
  // `||` is short-circuiting; isAdmin called only if isAuthor == false.
  return isAuthor || isAdmin(userId);
}

隨著規則復雜性的增加,在安全規則中使用函數會使它們更易於維護。

實時數據庫

如上所述,實時數據庫規則包括三個基本元素:作為數據庫 JSON 結構鏡像的數據庫位置、請求類型和授予訪問權限的條件。

數據庫位置

您的規則結構應遵循您存儲在數據庫中的數據結構。例如,在帶有消息列表的聊天應用程序中,您可能擁有如下所示的數據:

  {
    "messages": {
      "message0": {
        "content": "Hello",
        "timestamp": 1405704370369
      },
      "message1": {
        "content": "Goodbye",
        "timestamp": 1405704395231
      },
      ...
    }
  }

您的規則應該反映該結構。例如:

  {
    "rules": {
      "messages": {
        "$message": {
          // only messages from the last ten minutes can be read
          ".read": "data.child('timestamp').val() > (now - 600000)",

          // new messages must have a string content and a number timestamp
          ".validate": "newData.hasChildren(['content', 'timestamp']) &&
                        newData.child('content').isString() &&
                        newData.child('timestamp').isNumber()"
        }
      }
    }
  }

如上例所示,實時數據庫規則支持$location變量來匹配路徑段。使用路徑段前面的$前綴將您的規則與路徑上的任何子節點相匹配。

  {
    "rules": {
      "rooms": {
        // This rule applies to any child of /rooms/, the key for each room id
        // is stored inside $room_id variable for reference
        "$room_id": {
          "topic": {
            // The room's topic can be changed if the room id has "public" in it
            ".write": "$room_id.contains('public')"
          }
        }
      }
    }
  }

您還可以將$variable與常量路徑名並行使用。

  {
    "rules": {
      "widget": {
        // a widget can have a title or color attribute
        "title": { ".validate": true },
        "color": { ".validate": true },

        // but no other child paths are allowed
        // in this case, $other means any key excluding "title" and "color"
        "$other": { ".validate": false }
      }
    }
  }

方法

在實時數據庫中,存在三種類型的規則。其中兩種規則類型—— read ——適用write傳入請求的方法。 validate規則類型強制執行數據結構並驗證數據的格式和內容。規則在驗證.write規則授予訪問權限後運行.validate規則。

規則類型
。讀描述是否以及何時允許用戶讀取數據。
。寫描述是否以及何時允許寫入數據。
。證實定義格式正確的值的外觀、是否具有子屬性以及數據類型。

默認情況下,如果沒有規則允許,則拒絕訪問路徑。

建築條件

雲防火牆

條件是一個布爾表達式,用於確定是否應允許或拒絕特定操作。 requestresource變量為這些條件提供上下文。

request變量

request變量包括以下字段和對應的信息:

request.auth

包含來自 Firebase 身份驗證的身份驗證憑據的 JSON Web 令牌 (JWT)。 auth令牌包含一組標準聲明和您通過 Firebase 身份驗證創建的任何自定義聲明。詳細了解Firebase 安全規則和身份驗證

request.method

request.method可以是任何標準方法或自定義方法。便利方法readwrite還存在以簡化分別適用於所有隻讀或所有隻寫標準方法的寫入規則。

request.params

request.params包括與request.resource無關的任何可能對評估有用的數據。實際上,對於所有標準方法,此映射應該為空,並且應該包含自定義方法的非資源數據。服務必須注意不要重命名或修改任何作為參數呈現的鍵和值的類型。

request.path

request.path是目標resource的路徑。路徑是相對於服務的。包含非 url 安全字符(如/ )的路徑段是 url 編碼的。

resource變量

resource是服務中的當前值,表示為鍵值對的映射。在條件內引用resource將導致最多從服務讀取一次值。此查找將計入資源的任何服務相關配額。對於get請求, resource將僅計入拒絕時的配額。

運算符和運算符優先級

使用下表作為 Cloud Firestore 和 Cloud Storage 規則中運算符及其相應優先級的參考。

給定任意表達式ab 、字段f和索引i

操作員描述關聯性
a[i] a() af索引、調用、字段訪問左到右
!a -a一元否定右到左
a/ba%ba*b乘法運算符左到右
a+b ab加法運算符左到右
a>ba>=ba關係運算符左到右
a in b存在於列表或地圖中左到右
a is type類型比較,其中type可以是 bool、int、float、number、string、list、map、timestamp、duration、path 或 latlng左到右
a==ba!=b比較運算符左到右
a && b條件與左到右
a || b條件或左到右
a ? true_value : false_value三元表達式左到右

雲儲存

條件是一個布爾表達式,用於確定是否應允許或拒絕特定操作。 requestresource變量為這些條件提供上下文。

request變量

request變量包括以下字段和對應的信息:

request.auth

包含來自 Firebase 身份驗證的身份驗證憑據的 JSON Web 令牌 (JWT)。 auth令牌包含一組標準聲明和您通過 Firebase 身份驗證創建的任何自定義聲明。詳細了解Firebase 安全規則和身份驗證

request.method

request.method可以是任何標準方法或自定義方法。便利方法readwrite還存在以簡化分別適用於所有隻讀或所有隻寫標準方法的寫入規則。

request.params

request.params包括與request.resource無關的任何可能對評估有用的數據。實際上,對於所有標準方法,此映射應該為空,並且應該包含自定義方法的非資源數據。服務必須注意不要重命名或修改任何作為參數呈現的鍵和值的類型。

request.path

request.path是目標resource的路徑。路徑是相對於服務的。包含非 url 安全字符(如/ )的路徑段是 url 編碼的。

resource變量

resource是服務中的當前值,表示為鍵值對的映射。在條件內引用resource將導致最多從服務讀取一次值。此查找將計入資源的任何服務相關配額。對於get請求, resource將僅計入拒絕時的配額。

運算符和運算符優先級

使用下表作為 Cloud Firestore 和 Cloud Storage 規則中運算符及其相應優先級的參考。

給定任意表達式ab 、字段f和索引i

操作員描述關聯性
a[i] a() af索引、調用、字段訪問左到右
!a -a一元否定右到左
a/ba%ba*b乘法運算符左到右
a+b ab加法運算符左到右
a>ba>=ba關係運算符左到右
a in b存在於列表或地圖中左到右
a is type類型比較,其中type可以是 bool、int、float、number、string、list、map、timestamp、duration、path 或 latlng左到右
a==ba!=b比較運算符左到右
a && b條件與左到右
a || b條件或左到右
a ? true_value : false_value三元表達式左到右

實時數據庫

條件是一個布爾表達式,用於確定是否應允許或拒絕特定操作。您可以通過以下方式在實時數據庫規則中定義這些條件。

預定義變量

在規則定義中可以訪問許多有用的預定義變量。以下是每個的簡要摘要:

預定義變量
現在自 Linux 紀元以來的當前時間(以毫秒為單位)。這對於驗證使用 SDK 的 firebase.database.ServerValue.TIMESTAMP 創建的時間戳特別有效。
一個RuleDataSnapshot ,表示在嘗試操作之前存在的 Firebase 數據庫中的根路徑。
新數據一個RuleDataSnapshot ,表示嘗試操作後將存在的數據。它包括正在寫入的新數據和現有數據。
數據表示嘗試操作之前存在的數據的RuleDataSnapshot
$變量用於表示 id 和動態子鍵的通配符路徑。
授權表示經過身份驗證的用戶的令牌有效負載。

這些變量可以在規則中的任何地方使用。例如,下面的安全規則確保寫入/foo/節點的數據必須是少於 100 個字符的字符串:

{
  "rules": {
    "foo": {
      // /foo is readable by the world
      ".read": true,

      // /foo is writable by the world
      ".write": true,

      // data written to /foo must be a string less than 100 characters
      ".validate": "newData.isString() && newData.val().length < 100"
    }
  }
}

基於數據的規則

數據庫中的任何數據都可以在您的規則中使用。使用預定義變量rootdatanewData ,您可以訪問在寫入事件之前或之後存在的任何路徑。

考慮這個例子,它允許寫入操作,只要/allow_writes/節點的值為true ,父節點沒有設置readOnly標誌,並且新寫入的數據中有一個名為foo的子節點:

".write": "root.child('allow_writes').val() === true &&
          !data.parent().child('readOnly').exists() &&
          newData.child('foo').exists()"

基於查詢的規則

儘管您不能將規則用作過濾器,但您可以通過在規則中使用查詢參數來限制對數據子集的訪問。使用query.規則中的表達式以根據查詢參數授予讀取或寫入訪問權限。

例如,以下基於查詢的規則使用基於用戶的安全規則和基於查詢的規則來限制對購物baskets集合中數據的訪問,僅限活動用戶擁有的購物籃:

"baskets": {
  ".read": "auth.uid != null &&
            query.orderByChild == 'owner' &&
            query.equalTo == auth.uid" // restrict basket access to owner of basket
}

以下查詢(包括規則中的查詢參數)將成功:

db.ref("baskets").orderByChild("owner")
                 .equalTo(auth.currentUser.uid)
                 .on("value", cb)                 // Would succeed

但是,不包含規則中參數的查詢將失敗並出現PermissionDenied錯誤:

db.ref("baskets").on("value", cb)                 // Would fail with PermissionDenied

您還可以使用基於查詢的規則來限制客戶端通過讀取操作下載的數據量。

例如,以下規則將讀取權限限制為僅查詢的前 1000 個結果,按優先級排序:

messages: {
  ".read": "query.orderByKey &&
            query.limitToFirst <= 1000"
}

// Example queries:

db.ref("messages").on("value", cb)                // Would fail with PermissionDenied

db.ref("messages").limitToFirst(1000)
                  .on("value", cb)                // Would succeed (default order by key)

以下query.表達式在實時數據庫規則中可用。

基於查詢的規則表達式
表達類型描述
query.orderByKey
query.orderByPriority
query.orderByValue
布爾值True 對於按鍵、優先級或值排序的查詢。否則為假。
query.orderByChild細繩
空值
使用字符串表示子節點的相對路徑。例如, query.orderByChild == "address/zip" 。如果查詢不是按子節點排序的,則此值為空。
查詢.startAt
查詢.endAt
查詢.equalTo
細繩
數字
布爾值
空值
檢索執行查詢的邊界,如果沒有邊界集,則返回 null。
query.limitToFirst
query.limitToLast
數字
空值
檢索執行查詢的限制,如果沒有設置限制,則返回 null。

運營商

實時數據庫規則支持許多可用於組合條件語句中的變量的運算符。請參閱參考文檔中的完整運算符列表。

創造條件

您的實際條件將根據您要授予的訪問權限而有所不同。規則有意提供了極大的靈活性,因此您的應用程序的規則最終可以像您需要的那樣簡單或複雜。

有關創建簡單的生產就緒規則的一些指導,請參閱基本安全規則