def METHOD_NAME(
    self, *, user=None, traits=None, world, permission=Permission.ROOM_VIEW
):
    from .auth import RoomGrant, WorldGrant
    traits = traits or user.traits
    if world.has_permission_implicit(traits=traits, permissions=[permission]):
        # User has the permission globally, nothing to do
        return self.all()
    # Get all roles that grant view access
    roles = [
        role
        for role, permissions in [*world.roles.items(), *SYSTEM_ROLES.items()]
        if permission.value in permissions
    ]
    if not roles:  # pragma: no cover
        # No role grants access, impossible
        return self.none()
    if user:
        sq_user_has_room_grant = RoomGrant.objects.filter(
            user=user, world=world, room_id=OuterRef("pk"), role__in=roles
        )
        sq_user_has_world_grant = WorldGrant.objects.filter(
            user=user, world=world, role__in=roles
        )
        qs = self.annotate(
            user_has_room_grant=Exists(sq_user_has_room_grant),
            user_has_world_grant=Exists(sq_user_has_world_grant),
        )
        requirements = Q(user_has_room_grant=True) | Q(user_has_world_grant=True)
    else:
        qs = self
        requirements = Q()
    # Implicit role grants, i.e. grants given by trait_grants values on the room itself
    # We calculate this entirely in SQL for performance reasons. This is a little more complicated
    # since trait_grants can contain AND and OR restrictions.
    # For example, if we know from above the "moderator" role would grant the required permission, we need to
    # check the trait_grants["moderator"] value of the room, which always is an array. All values inside the
    # array are connected as AND restrictions. However, the value may either be strings (user must have that trait)
    # or arrays (user must have one of the traits -- OR). We therefore need to do In-SQL type checks.
    # In case it is an empty array, everyone is permitted. When our user has traits, this is automatically ensured
    # by the ALL() statement, but when traits=[] we need to do a special case check since "IN ()" is not valid SQL
    for i, role in enumerate(roles):
        if traits:
            qs = qs.annotate(
                **{
                    f"has_role_{i}": RawSQL(
                        f"""(
                        trait_grants ? %s AND
                        trait_grants->%s IS NOT NULL AND
                        TRUE = ALL(
                            SELECT (
                                CASE jsonb_typeof(d{i}.elem)
                                    WHEN 'array' THEN EXISTS(SELECT 1 FROM jsonb_array_elements(d{i}.elem) e{i}(elem) WHERE e{i}.elem#>>'{"{}"}' IN %s )
                                    ELSE d{i}.elem#>>'{"{}"}' IN %s
                                END
                            ) FROM jsonb_array_elements( trait_grants->%s ) AS d{i}(elem)
                        )
                    )""",
                        (
                            role,  # ? check
                            role,  # IS NOT NULL check
                            tuple(traits),  # IN check
                            tuple(traits),  # IN check
                            role,  # jsonb_array_elements
                        ),
                    )
                }
            )
        else:
            qs = qs.annotate(
                **{
                    f"has_role_{i}": RawSQL(
                        """(
                            trait_grants ? %s AND
                            trait_grants->%s IS NOT NULL AND
                            jsonb_array_length(trait_grants->%s) = 0
                        )""",
                        (
                            role,  # ? check
                            role,  # IS NOT NULL check
                            role,  # jsonb_array_length
                        ),
                    )
                }
            )
        requirements |= Q(**{f"has_role_{i}": True})
    qs = qs.filter(
        requirements,
        world=world,
    )
    return qs