问题
Let's assume we have a Firestore collection called todos, where each todo will look something like this:
{
name: "Buy milk",
completed: false,
user: "eYtGDHdfgSERewfqwEFfweE" // some user's uid
}
Now, I want to prevent modification of the user field during updates (in other words - make this field read-only).
Believe me, I've done my research. My update rule looks like this:
allow update: if request.auth.uid == resource.data.user
//&& !request.writeFields.hasAny(["user"]);
//&& !(request.writeFields.hasAny(["user"]));
//&& !request.resource.data.keys().hasAny(["user"]);
//&& !('user' in request.resource.data);
//&& ('user' in request.resource.data) == false;
//&& !('user' in request.writeFields);
None of the above (commented out) work. They all result in an error: Error: Missing or insufficient permissions..
But...
It gets even more interesting! Because if we compare some of the above rules for positive outcome (aka true) they will work!
For example, this one works perfectly (assuming we include user field in our request):
allow update: if request.resource.data.keys().hasAny(["user"]) == true;
BUT this one doesn't work (assuming we do NOT include the user field in the request):
allow update: if request.resource.data.keys().hasAny(["user"]) == false;
Can anyone explain me what is going on here? Is it possible this is actually a bug in Firestore?
回答1:
At "Writing conditions for Cloud Firestore Security Rules" section "Data validation" example #2
service cloud.firestore {
match /databases/{database}/documents {
// Make sure all cities have a positive population and
// the name is not changed
match /cities/{city} {
allow update: if request.resource.data.population > 0
&& request.resource.data.name == resource.data.name;
}
}
}
So request.resource.data.user == resource.data.user should work for you? CMIIW
Ref: https://firebase.google.com/docs/firestore/security/rules-conditions#data_validation
来源:https://stackoverflow.com/questions/52343935/firestore-security-rules-how-to-prevent-modification-of-a-certain-field