Reputation: 1016
I'm looking into being able to manage user sessions - e.g. revoke tokens for bad actors and not let them to access data immediately (instead of after an hour/token lifetime).
In the guides it mentions being able to do comparisons vs stored "revoke time" in Security Rules. But it only mentions Firebase Realtime Database.
Save the refresh token revocation timestamp. This is needed to track ID token revocation via Firebase rules. This allows for efficient checks within the database.
{
"rules": {
"users": {
"$user_id": {
".read": "$user_id === auth.uid && auth.token.auth_time > (root.child('metadata').child(auth.uid).child('revokeTime').val() || 0)",
".write": "$user_id === auth.uid && auth.token.auth_time > (root.child('metadata').child(auth.uid).child('revokeTime').val() || 0)"
}
}
}
}
The key here is auth.token.auth_time
I tried to use this in Firestore Security Rules but it doesn't seem to be available.
Is this not possible in Firestore?
Upvotes: 0
Views: 500
Reputation: 1016
Sebe had you were correct in needing to put request
before request.auth.token.auth_time
.
Even though its not shown in the documentation it seems to be there.
I had to create my own document during AuthOnCreate
for each user when they first sign up so that there were fields for revoke_time
(the designated key I made up, you can choose your own).
Then I stored these for each user in a revoked_tokens
collection and could compare against in security rules.
function notRevoked() {
return request.auth.token.auth_time > get(/databases/$(db)/documents/revoked_tokens/$(currentUser().uid)).data.revoke_time;
}
Firestore seems to be different that RTDB because you can't just use a default value of || 0
. You actually need to have a value in the Firestore to compare against. I think this is because Firestore get() functions return null
.
non-null
rules.firestore.Resource
the document, ornull
if it does not exist.
So if the document doesn't exist and you try to drill down into the get().data.someKey
it will just error out and blow up your Security Rule. It would be like trying to do null.data.someKey
Upvotes: 1
Reputation: 1310
Maybe this works, in Firestore you have to set these rules on collections or documents.
service cloud.firestore {
match /databases/{database}/documents {
match /collection/{documentId} {
allow read, write: if request.auth.uid != null && request.auth.token.auth_time > (root.child('metadata').child(auth.uid).child('revokeTime').val() || 0);
}
}
}
I will try it myself if i find the time.
Upvotes: 2