Firestore security rule works in simulator but fails in app
我对此Cloud Firestore安全规则有疑问:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 | service cloud.firestore { match /databases/{database}/documents { match /stages/{stageId} { match /collections/{collectionId} { match /pois/{poiId} { allow read; allow write: if request.auth != null || request.method =="update" && request.resource.data.keys() == ["pm"]; } } } } } |
在代码中,我尝试使用值字典更新作为未经身份验证的用户的现有文档的字段
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 | 2018-06-26 12:46:05.476997+0100 app[59292:3472939] 5.3.0 - [Firebase/Firestore][I-FST000001] FSTWriteStream 60c000107230 mutation request: <GCFSWriteRequest 0x60c0006e9e00>: { writes { update { name:"projects/myApp/databases/(default)/documents/stages/dev/collections/ETzbIXBn0Z5FOsCHtHlv/pois/zJELKLTWupuMkYQNb9gl" fields { key:"pm" value { map_value { fields { key:"subLocality" value { string_value:"Albufeira" } } fields { key:"locality" value { string_value:"Albufeira" } } fields { key:"country" value { string_value:"Portugal" } } fields { key:"postalCode" value { string_value:"8200-142" } } fields { key:"adminArea" value { string_value:"Faro" } } fields { key:"timezone" value { string_value:"Europe/Lisbon" } } fields { key:"thoroughfare" value { string_value:"Rua Primeiro de Dezembro" } } fields { key:"name" value { string_value:"Rua Primeiro de Dezembro" } } fields { key:"isoCountryCode" value { string_value:"PT" } } } } } } update_mask { field_paths:"pm" } current_document { exists: true } } stream_token:"\\031\\020hB\\002\\201\\364\\265\\265" } |
此请求因"缺少权限或权限不足"而失败。
当我使用此模拟数据将
1 | {"__name__":"/databases/(default)/documents/stages/dev/collections/ETzbIXBn0Z5FOsCHtHlv/pois/zJELKLTWupuMkYQNb9gl","data":{"pm":{"adminArea":"Germany","testArea":"Munich"}}} |
模拟器允许更新。
在我的代码(Swift项目/ iOS)中,我在现有文档参考上使用
作为参数,我传递了这个数组:
1 | ["pm": ["adminArea":"Faro","name":"Rua Primeiro de Dezembro","postalCode":"8200-142","locality":"Albufeira","subLocality":"Albufeira","isoCountryCode":"PT","timezone":"Europe/Lisbon","thoroughfare":"Rua Primeiro de Dezembro","country":"Portugal"]] |
知道我在做什么错吗?谢谢!
事实证明
1 | request.resource.data.keys() == ["pm"]; |
在部署时没有按预期方式工作(即使它在模拟器中也是如此)。
用
替换
1 | request.writeFields.size() == 1 &&"pm" in request.writeFields; |
帮了我大忙。
模拟规则是迈向实用产品的重要一步(Hello Google:调试规则???),但前提是它们在模拟器中的作用与在实时部署中的作用相同...
您可以重写此
1 | request.resource.data.keys() == ["pm"]; |
with
1 | request.writeFields == ["pm"]; |