Firestore security rule to see if a user is in a 'set' of groups?

81 views
Skip to first unread message

Kevin Burton

unread,
Jun 6, 2019, 11:43:53 PM6/6/19
to Firebase Google Group
Rules are easy for things like 'is admin' or role === 'Readers' 

However, for group based security it's harder if not impossible.

I have a user and that user is a member of a set of groups

Then I have a document and that document is readable by anyone in its own set of groups.

Is this model possible? I don't think it is... If there were set theoretic code then this would be straight forward.  Even loops.  But now I don't think I can see if there's overlap.

One HACK could be via regex... I haven't tried this but I could compile one of the maps into a OR regexp and see if it matches 


Scott Fortmann-Roe

unread,
Jun 7, 2019, 10:55:55 AM6/7/19
to fireba...@googlegroups.com
My app required a similar security model. Given the current lack of a looping or map functionality in rules, I couldn't find any way to implement it for the general case.

I ended up restricting the maximum number of groups a user could be in (to 5 in my case). Then just copying and pasting the logic to check one each of the group allowed number of groups (e.g. allow read: if hasAccess(request.auth.token.groups[0]) ||  hasAccess(request.auth.token.groups[1])  ||  hasAccess(request.auth.token.groups[2])  ||  hasAccess(request.auth.token.groups[3])  ||  hasAccess(request.auth.token.groups[4])).

This is not great but is workable if you can limit the number of groups.

--
You received this message because you are subscribed to the Google Groups "Firebase Google Group" group.
To unsubscribe from this group and stop receiving emails from it, send an email to firebase-tal...@googlegroups.com.
To post to this group, send email to fireba...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/firebase-talk/dde86f5d-df53-4704-af3c-59cb620a39f2%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

Sam Stern

unread,
Jun 7, 2019, 12:45:25 PM6/7/19
to Firebase Google Group
Thanks Kevin and Scott for the discussion.  Kevin would you mind writing an example of your "dream" security rules here?  That would help inform the internal discussion about improving this situation.

- Sam

Kato Richardson

unread,
Jun 7, 2019, 12:56:47 PM6/7/19
to Firebase Google Group
Hi Kevin,

I've looked over role based doc sharing extensively. I'm trying to accumulate enough material to put together a codelab on the topic. So the one-liner is that as long as you avoid inheritance (i.e. group A inherits all members of group B) then things are okay. If you do go with inheritance, you definitely want to disallow circular dependencies (unless you'd like to try and recreate my 1K lines of still buggy code and accompanying 2K lines of unit tests).

Here's a quick summary of the approaches with some links to relevant rules and the pseudo-code is here.

Simple doc sharing

This will list of authorized users attached directly to each doc as an array. No groups.

image.png

Doc sharing with simple groups

Simple groups are also not terrible as long as we leave out inheritance. This works by using a Function to reverse map members of a group into an array for each user, and then the security rule just compares the two arrays.
image.png

Doc sharing with group inheritance

Things get quite a bit more complex when dealing with inheritance. The gist of it is something like the diagram below. Of course, the real work is the functions code that sorts out what happens when you add members to a group or change the inherited group structure, and that's far too complex to cover here.
My goal is to write some sort of pluggable code to help with these in the future, but I can't commit to any timetable and won't be providing updates on this thread.

image.png




On Fri, Jun 7, 2019 at 7:55 AM Scott Fortmann-Roe <sco...@gmail.com> wrote:

For more options, visit https://groups.google.com/d/optout.


--

Kato Richardson | Developer Programs Eng | kato...@google.com | 775-235-8398

Kevin Burton

unread,
Jun 7, 2019, 2:05:36 PM6/7/19
to Firebase Google Group

Thanks. I had to dive in to find the functions supported on list and saw that it supports hasAny.

This would work well for me.  We were thinking of the same schema above where we resolve group membership and then see if the uid of the user is a member via hasAny.


Myles McNamara

unread,
Jun 7, 2019, 7:44:15 PM6/7/19
to Firebase Google Group
So my solution was a bit different, since i'm using "roles" and "permissions" but maybe you could use the same process for groups.  

Basically what I did was to use custom claims on user auth, but instead of setting specific claims on the auth, I set the key to "group" and then the value to the ID of the group document the user is assigned to.  Then in rules just pull that value from the DB to determine permissions or other groups to check.  Of course this would have to be tweaked based on your setup, but i found using custom claims the easiest to set reference to permissions/role without having to make a db call from rule checking and firebase functions

Kevin Burton

unread,
Jun 10, 2019, 10:55:18 AM6/10/19
to Firebase Google Group
Thanks.  The problem I had with custom claims is that they're limited to 1k.  

Even if you could use raw 64 bit (8 byte) group IDs you're still limited to ~125 groups max per user.

But maybe you could do a hybrid. It's probably rare that any user has > 125 group subscriptions so you could store them in a custom claim for 90% of people but maybe do a 'get' for everyone else?
Reply all
Reply to author
Forward
0 new messages