Firestore Security Rules breaking with update rule
Firebase Support confirms that there is a bug related to the evaluation of request.writeFields.size()
. No estimate was given of when it will be fixed.
The existence of the bug can be demonstrated with the following rules:
service cloud.firestore {
match /databases/{database}/documents {
match /cities/{city} {
// This should always evaluate to true, but does not.
allow create: if (request.writeFields.size() == 1) || (request.writeFields.size() != 1);
allow update: if true;
}
}
}
Although the create
rule should always evaluate to true, an attempt to create a city fails with Permission Denied. It seems that the problem with request.writeFields
affects not only the rule in which it appears, but also other rules for the path. For the rules shown above, an attempt to update an existing city also fails with Permission Denied.
Firestore rules: will a general write rule override the more granular update/delete/create rules?
I would not think of any rules as "overriding" other rules. The only thing you need to know is this: if any rule allows access for a read or write operation, then no other rule can later deny that access.
So, if you have a write rule that allows write access in some situation, it doesn't matter what any other rule says about that situation.
I suggest reading further into that page of documentation that you linked in the section about overlapping match statements.
Firestore security rules: update document security rule
Keep in mind that request.resource.data
always contains all of the fields in the document, after the update would succeed. This includes all existing fields in the document.
The update in situation works because the new contents of the document satisfy all the conditions.
Ths update in the second situation doesn't work because it's failing all of the checks for fields that don't already exist in the document, and are also not being provided in the update. If you want this second situation to work, you're going to have to code the rules so that the missing fields are not actually required with specific types like they are now.
Firestore rules - Allow only update certain field of a document
It looks like there is a really helpful MapDiff type that might be able to simplify your rules. Sample code from the docs:
// Compare two Map objects and return whether the key "a" has been
// affected; that is, key "a" was added or removed, or its value was updated.
request.resource.data.diff(resource.data).affectedKeys().hasOnly(["a"]);
https://firebase.google.com/docs/reference/rules/rules.MapDiff
Firestore Security Rules - how to prevent modification of a certain field
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
Firebase Firestore, can you have multiple update rules for a collection
it lists multiple update rules and I wondered, is this allowed?
Yes, you can have multiple rules for a particular access method.
Would Firebase then skip that rule and move onto the next one to see if it applies?
No rules are skipped. If you have multiple rules, it will compute the logical OR of each one. So, if any of the rules allows update, then that access is granted.
that the condition
request.resource.data.name == resource.data.name
can't possible be true if the name property
Not necessarily. If the document had a name
field prior to the update, it will have that value here. request.resource.data
contains the entire contents of the new document being written, not just the fields that were specified in the update. But if the field doesn't already exist, and you don't provide one in the update, then the rules will reject the update.
Related Topics
Swift Package Manager with Resources Compile Errors
Swift: Ambiguous Reference to Member 'Map'
Swiftui Tabview Gives an Error Message During Add/Delete the Element of Coredata
Alamofireimage How to Clean Memory and Cache
Swift:Program for Addition of 2 Numbers Using Closure
Problem Creating and Writing a Subdirectory in Swift 5
Sending Variables with a Segue
How to Use Dispatchgroup/Gcd to Execute Functions Sequentially in Swift
How to Create an Operator to Implement Error Chaining
Getting Pixel Format from Cgimage
Swift Check If Value Is of Type Array (Of Any Type)
Accessing Struct from One Class to Another
Swift Decodable, Endpoint Returns Completely Different Types
Unexpectedly Found Nil While Unwrapping an Optional Value While Reading from Ds with Fromcstring
Initializer for Conditional Binding Must Have Optional Type, Not '[String:Any]'
Swift 2 Unrecognized Selector in Tapgesture