def _intersect_expanded_scopes(scopes_a, scopes_b, db=None):
    """Intersect two sets of scopes by comparing their permissions

    Arguments:
      scopes_a, scopes_b: sets of expanded scopes
      db (optional): db connection for resolving group membership

    Returns:
      intersection: set of expanded scopes as intersection of the arguments

    If db is given, group membership will be accounted for in intersections,
    Otherwise, it can result in lower than intended permissions,
          (i.e. users!group=x & users!user=y will be empty, even if user y is in group x.)
    """
    scopes_a = frozenset(scopes_a)
    scopes_b = frozenset(scopes_b)

    # cached lookups for group membership of users and servers
    @lru_cache
    def groups_for_user(username):
        """Get set of group names for a given username"""
        # if we need a group lookup, the result is not cacheable
        nonlocal needs_db
        needs_db = True
        group_query = (
            db.query(orm.Group.name)
            .join(orm.User.groups)
            .filter(orm.User.name == username)
        )
        return {row[0] for row in group_query}

    @lru_cache
    def groups_for_server(server):
        """Get set of group names for a given server"""
        username, _, servername = server.partition("/")
        return groups_for_user(username)

    parsed_scopes_a = parse_scopes(scopes_a)
    parsed_scopes_b = parse_scopes(scopes_b)

    # track whether we need a db lookup (for groups)
    # because we can't cache the intersection if we do
    # if there are no group filters, this is cacheable
    needs_db = False

    common_bases = parsed_scopes_a.keys() & parsed_scopes_b.keys()

    common_filters = {}
    warned = False
    for base in common_bases:
        filters_a = parsed_scopes_a[base]
        filters_b = parsed_scopes_b[base]
        if filters_a == Scope.ALL:
            common_filters[base] = filters_b
        elif filters_b == Scope.ALL:
            common_filters[base] = filters_a
        else:
            common_entities = filters_a.keys() & filters_b.keys()
            all_entities = filters_a.keys() | filters_b.keys()

            # if we don't have a db session, we can't check group membership
            # warn *if* there are non-overlapping user= and group= filters that we can't check
            if (
                db is None
                and not warned
                and 'group' in all_entities
                and ('user' in all_entities or 'server' in all_entities)
            ):
                # this could resolve wrong if there's a user or server only on one side and a group only on the other
                # check both directions: A has group X not in B group list AND B has user Y not in A user list
                for a, b in [(filters_a, filters_b), (filters_b, filters_a)]:
                    for b_key in ('user', 'server'):
                        if (
                            not warned
                            and "group" in a
                            and b_key in b
                            and a["group"].difference(b.get("group", []))
                            and b[b_key].difference(a.get(b_key, []))
                        ):
                            warnings.warn(
                                f"{base}[!{b_key}={b[b_key]}, !group={a['group']}] combinations of filters present,"
                                " without db access. Intersection between not considered."
                                " May result in lower than intended permissions.",
                                UserWarning,
                            )
                            warned = True
                            needs_db = True

            common_filters[base] = {
                entity: filters_a[entity] & filters_b[entity]
                for entity in common_entities
            }

            # resolve hierarchies (group/user/server) in both directions
            common_servers = initial_common_servers = common_filters[base].get(
                "server", frozenset()
            )
            common_users = initial_common_users = common_filters[base].get(
                "user", frozenset()
            )

            for a, b in [(filters_a, filters_b), (filters_b, filters_a)]:
                if 'server' in a and b.get('server') != a['server']:
                    # skip already-added servers (includes overlapping servers)
                    servers = a['server'].difference(common_servers)

                    # resolve user/server hierarchy
                    if servers and 'user' in b:
                        for server in servers:
                            username, _, servername = server.partition("/")
                            if username in b['user']:
                                common_servers = common_servers | {server}

                    # resolve group/server hierarchy if db available
                    servers = servers.difference(common_servers)
                    if db is not None and servers and 'group' in b:
                        needs_db = True
                        for server in servers:
                            server_groups = groups_for_server(server)
                            if server_groups & b['group']:
                                common_servers = common_servers | {server}

                # resolve group/user hierarchy if db available and user sets aren't identical
                if (
                    db is not None
                    and 'user' in a
                    and 'group' in b
                    and b.get('user') != a['user']
                ):
                    # skip already-added users (includes overlapping users)
                    users = a['user'].difference(common_users)
                    for username in users:
                        groups = groups_for_user(username)
                        if groups & b["group"]:
                            common_users = common_users | {username}

            # add server filter if it's non-empty
            # and it changed
            if common_servers and common_servers != initial_common_servers:
                common_filters[base]["server"] = common_servers

            # add user filter if it's non-empty
            # and it changed
            if common_users and common_users != initial_common_users:
                common_filters[base]["user"] = common_users

    intersection = unparse_scopes(common_filters)
    if needs_db:
        # return intersection, but don't cache it if it needed db lookups
        return DoNotCache(intersection)

    return intersection
Intersect two sets of scopes by comparing their permissions

Arguments:
scopes_a, scopes_b: sets of expanded scopes
db (optional): db connection for resolving group membership

Returns:
intersection: set of expanded scopes as intersection of the arguments

If db is given, group membership will be accounted for in intersections,
Otherwise, it can result in lower than intended permissions,
(i.e. users!group=x & users!user=y will be empty, even if user y is in group x.)
jupyterhub/scopes.py