Google cloud firestore Firestore安全规则:如何约束使用get(<;document_path>;)的查询?
因此,我有一个查询(失败)。它是这样写的:“作为我的用户,我可以为一个组织列出我所参与的所有业务” 以及保护它的安全规则(要点): 基本上,它会在用户文档中查找用户的角色(该文档由该企业拥有)。这种类型的规则(使用Google cloud firestore Firestore安全规则:如何约束使用get(<;document_path>;)的查询?,google-cloud-firestore,firebase-security,Google Cloud Firestore,Firebase Security,因此,我有一个查询(失败)。它是这样写的:“作为我的用户,我可以为一个组织列出我所参与的所有业务” 以及保护它的安全规则(要点): 基本上,它会在用户文档中查找用户的角色(该文档由该企业拥有)。这种类型的规则(使用get()运算符)适用于{businessId}的子集合(例如,查询订单),但不适用于尝试列出业务的查询 现在我知道,organizationUid是一个有效的约束,但通过阅读,我可以理解为什么Firestore不能在不读取大量数据的情况下验证此声明 问题是,那么我该如何解决这个问题呢
get()
运算符)适用于{businessId}
的子集合(例如,查询订单
),但不适用于尝试列出业务的查询
现在我知道,organizationUid
是一个有效的约束,但通过阅读,我可以理解为什么Firestore不能在不读取大量数据的情况下验证此声明
问题是,那么我该如何解决这个问题呢?Firestore如何正确验证子集合的约束?安全规则不能满足您的要求,因为它需要为查询匹配的每个文档读取另一个文档。由于路径中存在变量(
businessId
),因此规则无法提前知道这些文档将是什么。如果此查询将在业务集合中生成数百万个文档,您可以看到从/businesss/$(businessId)/users/$(request.auth.uid)读取每个匹配的文档以确定是否应允许拒绝整个查询是多么困难(对您来说代价高昂)
规则必须以极快的速度运行,以便按照Firestore需要的方式进行扩展。规则不能被过滤的限制是可伸缩性要求的一部分。这也是为什么每次规则评估时使用get()
读取10个文档的总限制
从规则的角度来看,除了在每个集合的规则范围内执行多个查询,并在客户端应用程序中合并结果之外,这里没有其他解决方法
fs
.collection('businesses')
.where('organizationUid', isEqualTo: 'some-organization-id')
.get();
match /businesses/{businessId} {
function isStaffOrHigher() {
return get(/databases/$(database)/documents/businesses/$(businessId)/users/$(request.auth.uid)).data.role >= 50;
}
allow read: if isStaffOrHigher();
match /orders/{orderId} {
allow read, write: if isStaffOrHigher();
}
match /users/{userId} {
allow read: if request.auth.uid == userId || isStaffOrHigher();
}
}