You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何利用Firebase实时数据库规则按UID限制巡检员读写对应案件

问题:Firebase实时数据库规则实现巡检员按UID匹配案件权限

数据库数据结构

https://dev-xxx-xxxx-xxx-xxx.firebaseio.com/
    ↓idCase
    ↓IdLoans
    -NREvs1K2xaCcjP37ALm
    →LoanNumber: "0001"
    →InspectorName: "John"
    →PropertyAddress: "F-32 Maa St." 
    →Property Condition: "No Data"
        →Property Occupancy: "No Data"

    -NRIs9ibnlVVhI2QtfGt
    →LoanNumber: "0002"
    →InspectorName: "'Jane"
    →PropertyAddress: "D-12 Doo St." 
    →Property Condition: "No Data"
        →Property Occupancy: "No Data"

    -NRJEhrCJAY-QoQFn0wX
    →LoanNumber: "0003"
    →InspectorName: "'Joah"
    →PropertyAddress: "Y-20 Saa St." 
    →Property Condition: "No Data"
        →Property Occupancy: "No Data"

    -NT-HB1Z3cUDG7jvvx2c
    →LoanNumber: "0004"
    →InspectorName: "John"
    →PropertyAddress: "F-34 Maa St." 
    →Property Condition: "No Data"
        →Property Occupancy: "No Data"

尝试的无效规则

{
  "rules": {
    "idCase": {
      "IdLoans": {
        ".read": "auth != null && (auth.uid === 'z6Iy8yZFZ1Mf6ZsbfgnF1GlFYtN2' && query.orderByChild === 'InspectorName' && query.equalTo === 'John' || auth.uid === 'tMfqfdh6B8hRBrZKT0fjRblUyO13' && query.orderByChild === 'InspectorName' && query.equalTo === 'Joah' || auth.uid === 'ynn3RTNQ7CQ6ENIRaXy55AvvFb73' && query.orderByChild === 'InspectorName' && query.equalTo === 'Jane')",
        ".write":  "auth != null && (auth.uid === 'z6Iy8yZFZ1Mf6ZsbfgnF1GlFYtN2' && query.orderByChild === 'InspectorName' && query.equalTo === 'John' || auth.uid === 'tMfqfdh6B8hRBrZKT0fjRblUyO13' && query.orderByChild === 'InspectorName' && query.equalTo === 'Joah' || auth.uid === 'ynn3RTNQ7CQ6ENIRaXy55AvvFb73' && query.orderByChild === 'InspectorName' && query.equalTo === 'Jane')"
      }
    }
  }
}

解决方案

原规则问题分析

  1. 硬编码UID与巡检员姓名的对应关系,新增或修改用户必须更新规则,扩展性差
  2. 写规则错误依赖query条件,写操作无需查询参数,应直接验证新数据的InspectorName
  3. 数据中Jane和Joah字段值带多余单引号('Jane'、'Joah'),与规则中的字符串不匹配,导致权限验证失败

方案1:使用用户自定义Claims(推荐)

通过Firebase Auth自定义Claims关联用户UID和巡检员姓名,无需硬编码规则:

  1. 为每个用户设置自定义Claims(使用Firebase CLI):
firebase auth:set-custom-claims z6Iy8yZFZ1Mf6ZsbfgnF1GlFYtN2 '{"inspectorName": "John"}'
firebase auth:set-custom-claims tMfqfdh6B8hRBrZKT0fjRblUyO13 '{"inspectorName": "Joah"}'
firebase auth:set-custom-claims ynn3RTNQ7CQ6ENIRaXy55AvvFb73 '{"inspectorName": "Jane"}'

注意:数据中'Jane'和'Joah'的单引号需删除,保持与Claims中字符串一致

  1. 编写数据库规则:
{
  "rules": {
    "idCase": {
      "IdLoans": {
        // 读权限:用户需登录,且查询必须按InspectorName筛选并匹配自身Claims中的姓名
        ".read": "auth != null && query.orderByChild === 'InspectorName' && query.equalTo === auth.token.inspectorName",
        // 写权限:用户需登录,且新数据的InspectorName必须匹配自身Claims中的姓名
        ".write": "auth != null && newData.child('InspectorName').val() === auth.token.inspectorName"
      }
    }
  }
}

方案2:使用用户映射节点(适合无法使用Claims的场景)

在数据库中新增节点存储UID与巡检员姓名的映射,规则通过该节点验证权限:

  1. 添加userInspectorMap节点:
{
  "userInspectorMap": {
    "z6Iy8yZFZ1Mf6ZsbfgnF1GlFYtN2": "John",
    "tMfqfdh6B8hRBrZKT0fjRblUyO13": "Joah",
    "ynn3RTNQ7CQ6ENIRaXy55AvvFb73": "Jane"
  }
}
  1. 编写数据库规则:
{
  "rules": {
    // 禁止普通用户访问映射节点,仅管理员可修改
    "userInspectorMap": {
      ".read": false,
      ".write": false
    },
    "idCase": {
      "IdLoans": {
        ".read": "auth != null && query.orderByChild === 'InspectorName' && query.equalTo === root.child('userInspectorMap').child(auth.uid).val()",
        ".write": "auth != null && newData.child('InspectorName').val() === root.child('userInspectorMap').child(auth.uid).val()"
      }
    }
  }
}

内容的提问来源于stack exchange,提问作者Samuel Garcia Agosto

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.24 16:22:50