Browse Source

Move some event auth checks out to a different method (#13065)

* Add auth events to events used in tests

* Move some event auth checks out to a different method

Some of the event auth checks apply to an event's auth_events, rather than the
state at the event - which means they can play no part in state
resolution. Move them out to a separate method.

* Rename check_auth_rules_for_event

Now it only checks the state-dependent auth rules, it needs a better name.
tags/v1.62.0rc1
Richard van der Hoff 2 years ago
committed by GitHub
parent
commit
8ecf6be1e1
No known key found for this signature in database GPG Key ID: 4AEE18F83AFDEB23
7 changed files with 219 additions and 98 deletions
  1. +1
    -0
      changelog.d/13065.misc
  2. +79
    -29
      synapse/event_auth.py
  3. +6
    -2
      synapse/handlers/event_auth.py
  4. +17
    -10
      synapse/handlers/federation_event.py
  5. +2
    -2
      synapse/state/v1.py
  6. +1
    -1
      synapse/state/v2.py
  7. +113
    -54
      tests/test_event_auth.py

+ 1
- 0
changelog.d/13065.misc View File

@@ -0,0 +1 @@
Avoid rechecking event auth rules which are independent of room state.

+ 79
- 29
synapse/event_auth.py View File

@@ -15,11 +15,12 @@

import logging
import typing
from typing import Any, Dict, Iterable, List, Optional, Set, Tuple, Union
from typing import Any, Collection, Dict, Iterable, List, Optional, Set, Tuple, Union

from canonicaljson import encode_canonical_json
from signedjson.key import decode_verify_key_bytes
from signedjson.sign import SignatureVerifyException, verify_signed_json
from typing_extensions import Protocol
from unpaddedbase64 import decode_base64

from synapse.api.constants import (
@@ -35,7 +36,8 @@ from synapse.api.room_versions import (
EventFormatVersions,
RoomVersion,
)
from synapse.types import StateMap, UserID, get_domain_from_id
from synapse.storage.databases.main.events_worker import EventRedactBehaviour
from synapse.types import MutableStateMap, StateMap, UserID, get_domain_from_id

if typing.TYPE_CHECKING:
# conditional imports to avoid import cycle
@@ -45,6 +47,17 @@ if typing.TYPE_CHECKING:
logger = logging.getLogger(__name__)


class _EventSourceStore(Protocol):
async def get_events(
self,
event_ids: Collection[str],
redact_behaviour: EventRedactBehaviour,
get_prev_content: bool = False,
allow_rejected: bool = False,
) -> Dict[str, "EventBase"]:
...


def validate_event_for_room_version(event: "EventBase") -> None:
"""Ensure that the event complies with the limits, and has the right signatures

@@ -112,47 +125,52 @@ def validate_event_for_room_version(event: "EventBase") -> None:
raise AuthError(403, "Event not signed by authorising server")


def check_auth_rules_for_event(
async def check_state_independent_auth_rules(
store: _EventSourceStore,
event: "EventBase",
auth_events: Iterable["EventBase"],
) -> None:
"""Check that an event complies with the auth rules

Checks whether an event passes the auth rules with a given set of state events

Assumes that we have already checked that the event is the right shape (it has
enough signatures, has a room ID, etc). In other words:

- it's fine for use in state resolution, when we have already decided whether to
accept the event or not, and are now trying to decide whether it should make it
into the room state
"""Check that an event complies with auth rules that are independent of room state

- when we're doing the initial event auth, it is only suitable in combination with
a bunch of other tests.
Runs through the first few auth rules, which are independent of room state. (Which
means that we only need to them once for each received event)

Args:
store: the datastore; used to fetch the auth events for validation
event: the event being checked.
auth_events: the room state to check the events against.

Raises:
AuthError if the checks fail
"""
# We need to ensure that the auth events are actually for the same room, to
# stop people from using powers they've been granted in other rooms for
# example.
#
# Arguably we don't need to do this when we're just doing state res, as presumably
# the state res algorithm isn't silly enough to give us events from different rooms.
# Still, it's easier to do it anyway.
# Check the auth events.
auth_events = await store.get_events(
event.auth_event_ids(),
redact_behaviour=EventRedactBehaviour.as_is,
allow_rejected=True,
)
room_id = event.room_id
for auth_event in auth_events:
auth_dict: MutableStateMap[str] = {}
for auth_event_id in event.auth_event_ids():
auth_event = auth_events.get(auth_event_id)

# we should have all the auth events by now, so if we do not, that suggests
# a synapse programming error
if auth_event is None:
raise RuntimeError(
f"Event {event.event_id} has unknown auth event {auth_event_id}"
)

# We need to ensure that the auth events are actually for the same room, to
# stop people from using powers they've been granted in other rooms for
# example.
if auth_event.room_id != room_id:
raise AuthError(
403,
"During auth for event %s in room %s, found event %s in the state "
"which is in room %s"
% (event.event_id, room_id, auth_event.event_id, auth_event.room_id),
% (event.event_id, room_id, auth_event_id, auth_event.room_id),
)

# We also need to check that the auth event itself is not rejected.
if auth_event.rejected_reason:
raise AuthError(
403,
@@ -160,6 +178,8 @@ def check_auth_rules_for_event(
% (event.event_id, auth_event.event_id),
)

auth_dict[(auth_event.type, auth_event.state_key)] = auth_event_id

# Implementation of https://matrix.org/docs/spec/rooms/v1#authorization-rules
#
# 1. If type is m.room.create:
@@ -181,16 +201,46 @@ def check_auth_rules_for_event(
"room appears to have unsupported version %s" % (room_version_prop,),
)

logger.debug("Allowing! %s", event)
return

auth_dict = {(e.type, e.state_key): e for e in auth_events}

# 3. If event does not have a m.room.create in its auth_events, reject.
creation_event = auth_dict.get((EventTypes.Create, ""), None)
if not creation_event:
raise AuthError(403, "No create event in auth events")


def check_state_dependent_auth_rules(
event: "EventBase",
auth_events: Iterable["EventBase"],
) -> None:
"""Check that an event complies with auth rules that depend on room state

Runs through the parts of the auth rules that check an event against bits of room
state.

Note:

- it's fine for use in state resolution, when we have already decided whether to
accept the event or not, and are now trying to decide whether it should make it
into the room state

- when we're doing the initial event auth, it is only suitable in combination with
a bunch of other tests (including, but not limited to, check_state_independent_auth_rules).

Args:
event: the event being checked.
auth_events: the room state to check the events against.

Raises:
AuthError if the checks fail
"""
# there are no state-dependent auth rules for create events.
if event.type == EventTypes.Create:
logger.debug("Allowing! %s", event)
return

auth_dict = {(e.type, e.state_key): e for e in auth_events}

# additional check for m.federate
creating_domain = get_domain_from_id(event.room_id)
originating_domain = get_domain_from_id(event.sender)


+ 6
- 2
synapse/handlers/event_auth.py View File

@@ -23,7 +23,10 @@ from synapse.api.constants import (
)
from synapse.api.errors import AuthError, Codes, SynapseError
from synapse.api.room_versions import RoomVersion
from synapse.event_auth import check_auth_rules_for_event
from synapse.event_auth import (
check_state_dependent_auth_rules,
check_state_independent_auth_rules,
)
from synapse.events import EventBase
from synapse.events.builder import EventBuilder
from synapse.events.snapshot import EventContext
@@ -52,9 +55,10 @@ class EventAuthHandler:
context: EventContext,
) -> None:
"""Check an event passes the auth rules at its own auth events"""
await check_state_independent_auth_rules(self._store, event)
auth_event_ids = event.auth_event_ids()
auth_events_by_id = await self._store.get_events(auth_event_ids)
check_auth_rules_for_event(event, auth_events_by_id.values())
check_state_dependent_auth_rules(event, auth_events_by_id.values())

def compute_auth_events(
self,


+ 17
- 10
synapse/handlers/federation_event.py View File

@@ -50,7 +50,8 @@ from synapse.api.errors import (
from synapse.api.room_versions import KNOWN_ROOM_VERSIONS, RoomVersion, RoomVersions
from synapse.event_auth import (
auth_types_for_event,
check_auth_rules_for_event,
check_state_dependent_auth_rules,
check_state_independent_auth_rules,
validate_event_for_room_version,
)
from synapse.events import EventBase
@@ -1430,7 +1431,9 @@ class FederationEventHandler:
allow_rejected=True,
)

def prep(event: EventBase) -> Optional[Tuple[EventBase, EventContext]]:
events_and_contexts_to_persist: List[Tuple[EventBase, EventContext]] = []

async def prep(event: EventBase) -> None:
with nested_logging_context(suffix=event.event_id):
auth = []
for auth_event_id in event.auth_event_ids():
@@ -1444,7 +1447,7 @@ class FederationEventHandler:
event,
auth_event_id,
)
return None
return
auth.append(ae)

# we're not bothering about room state, so flag the event as an outlier.
@@ -1453,17 +1456,20 @@ class FederationEventHandler:
context = EventContext.for_outlier(self._storage_controllers)
try:
validate_event_for_room_version(event)
check_auth_rules_for_event(event, auth)
await check_state_independent_auth_rules(self._store, event)
check_state_dependent_auth_rules(event, auth)
except AuthError as e:
logger.warning("Rejecting %r because %s", event, e)
context.rejected = RejectedReason.AUTH_ERROR

return event, context
events_and_contexts_to_persist.append((event, context))

for event in fetched_events:
await prep(event)

events_to_persist = (x for x in (prep(event) for event in fetched_events) if x)
await self.persist_events_and_notify(
room_id,
tuple(events_to_persist),
events_and_contexts_to_persist,
# Mark these events backfilled as they're historic events that will
# eventually be backfilled. For example, missing events we fetch
# during backfill should be marked as backfilled as well.
@@ -1515,7 +1521,8 @@ class FederationEventHandler:

# ... and check that the event passes auth at those auth events.
try:
check_auth_rules_for_event(event, claimed_auth_events)
await check_state_independent_auth_rules(self._store, event)
check_state_dependent_auth_rules(event, claimed_auth_events)
except AuthError as e:
logger.warning(
"While checking auth of %r against auth_events: %s", event, e
@@ -1563,7 +1570,7 @@ class FederationEventHandler:
auth_events_for_auth = calculated_auth_event_map

try:
check_auth_rules_for_event(event, auth_events_for_auth.values())
check_state_dependent_auth_rules(event, auth_events_for_auth.values())
except AuthError as e:
logger.warning("Failed auth resolution for %r because %s", event, e)
context.rejected = RejectedReason.AUTH_ERROR
@@ -1663,7 +1670,7 @@ class FederationEventHandler:
)

try:
check_auth_rules_for_event(event, current_auth_events)
check_state_dependent_auth_rules(event, current_auth_events)
except AuthError as e:
logger.warning(
"Soft-failing %r (from %s) because %s",


+ 2
- 2
synapse/state/v1.py View File

@@ -330,7 +330,7 @@ def _resolve_auth_events(
auth_events[(prev_event.type, prev_event.state_key)] = prev_event
try:
# The signatures have already been checked at this point
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
event,
auth_events.values(),
)
@@ -347,7 +347,7 @@ def _resolve_normal_events(
for event in _ordered_events(events):
try:
# The signatures have already been checked at this point
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
event,
auth_events.values(),
)


+ 1
- 1
synapse/state/v2.py View File

@@ -573,7 +573,7 @@ async def _iterative_auth_checks(
auth_events[key] = event_map[ev_id]

try:
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
event,
auth_events.values(),
)


+ 113
- 54
tests/test_event_auth.py View File

@@ -1,4 +1,4 @@
# Copyright 2018 New Vector Ltd
# Copyright 2018-2022 The Matrix.org Foundation C.I.C.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
@@ -13,7 +13,7 @@
# limitations under the License.

import unittest
from typing import Optional
from typing import Collection, Dict, Iterable, List, Optional

from parameterized import parameterized

@@ -22,8 +22,41 @@ from synapse.api.constants import EventContentFields
from synapse.api.errors import AuthError
from synapse.api.room_versions import EventFormatVersions, RoomVersion, RoomVersions
from synapse.events import EventBase, make_event_from_dict
from synapse.storage.databases.main.events_worker import EventRedactBehaviour
from synapse.types import JsonDict, get_domain_from_id

from tests.test_utils import get_awaitable_result


class _StubEventSourceStore:
"""A stub implementation of the EventSourceStore"""

def __init__(self):
self._store: Dict[str, EventBase] = {}

def add_event(self, event: EventBase):
self._store[event.event_id] = event

def add_events(self, events: Iterable[EventBase]):
for event in events:
self._store[event.event_id] = event

async def get_events(
self,
event_ids: Collection[str],
redact_behaviour: EventRedactBehaviour,
get_prev_content: bool = False,
allow_rejected: bool = False,
) -> Dict[str, EventBase]:
assert allow_rejected
assert not get_prev_content
assert redact_behaviour == EventRedactBehaviour.as_is
results = {}
for e in event_ids:
if e in self._store:
results[e] = self._store[e]
return results


class EventAuthTestCase(unittest.TestCase):
def test_rejected_auth_events(self):
@@ -36,11 +69,15 @@ class EventAuthTestCase(unittest.TestCase):
_join_event(RoomVersions.V9, creator),
]

event_store = _StubEventSourceStore()
event_store.add_events(auth_events)

# creator should be able to send state
event_auth.check_auth_rules_for_event(
_random_state_event(RoomVersions.V9, creator),
auth_events,
event = _random_state_event(RoomVersions.V9, creator, auth_events)
get_awaitable_result(
event_auth.check_state_independent_auth_rules(event_store, event)
)
event_auth.check_state_dependent_auth_rules(event, auth_events)

# ... but a rejected join_rules event should cause it to be rejected
rejected_join_rules = _join_rules_event(
@@ -50,23 +87,27 @@ class EventAuthTestCase(unittest.TestCase):
)
rejected_join_rules.rejected_reason = "stinky"
auth_events.append(rejected_join_rules)
event_store.add_event(rejected_join_rules)

self.assertRaises(
AuthError,
event_auth.check_auth_rules_for_event,
_random_state_event(RoomVersions.V9, creator),
auth_events,
)
with self.assertRaises(AuthError):
get_awaitable_result(
event_auth.check_state_independent_auth_rules(
event_store,
_random_state_event(RoomVersions.V9, creator),
)
)

# ... even if there is *also* a good join rules
auth_events.append(_join_rules_event(RoomVersions.V9, creator, "public"))
event_store.add_event(rejected_join_rules)

self.assertRaises(
AuthError,
event_auth.check_auth_rules_for_event,
_random_state_event(RoomVersions.V9, creator),
auth_events,
)
with self.assertRaises(AuthError):
get_awaitable_result(
event_auth.check_state_independent_auth_rules(
event_store,
_random_state_event(RoomVersions.V9, creator),
)
)

def test_random_users_cannot_send_state_before_first_pl(self):
"""
@@ -82,7 +123,7 @@ class EventAuthTestCase(unittest.TestCase):
]

# creator should be able to send state
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_random_state_event(RoomVersions.V1, creator),
auth_events,
)
@@ -90,7 +131,7 @@ class EventAuthTestCase(unittest.TestCase):
# joiner should not be able to send state
self.assertRaises(
AuthError,
event_auth.check_auth_rules_for_event,
event_auth.check_state_dependent_auth_rules,
_random_state_event(RoomVersions.V1, joiner),
auth_events,
)
@@ -119,13 +160,13 @@ class EventAuthTestCase(unittest.TestCase):
# pleb should not be able to send state
self.assertRaises(
AuthError,
event_auth.check_auth_rules_for_event,
event_auth.check_state_dependent_auth_rules,
_random_state_event(RoomVersions.V1, pleb),
auth_events,
),

# king should be able to send state
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_random_state_event(RoomVersions.V1, king),
auth_events,
)
@@ -140,27 +181,27 @@ class EventAuthTestCase(unittest.TestCase):
]

# creator should be able to send aliases
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_alias_event(RoomVersions.V1, creator),
auth_events,
)

# Reject an event with no state key.
with self.assertRaises(AuthError):
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_alias_event(RoomVersions.V1, creator, state_key=""),
auth_events,
)

# If the domain of the sender does not match the state key, reject.
with self.assertRaises(AuthError):
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_alias_event(RoomVersions.V1, creator, state_key="test.com"),
auth_events,
)

# Note that the member does *not* need to be in the room.
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_alias_event(RoomVersions.V1, other),
auth_events,
)
@@ -175,24 +216,24 @@ class EventAuthTestCase(unittest.TestCase):
]

# creator should be able to send aliases
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_alias_event(RoomVersions.V6, creator),
auth_events,
)

# No particular checks are done on the state key.
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_alias_event(RoomVersions.V6, creator, state_key=""),
auth_events,
)
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_alias_event(RoomVersions.V6, creator, state_key="test.com"),
auth_events,
)

# Per standard auth rules, the member must be in the room.
with self.assertRaises(AuthError):
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_alias_event(RoomVersions.V6, other),
auth_events,
)
@@ -220,12 +261,12 @@ class EventAuthTestCase(unittest.TestCase):

# on room V1, pleb should be able to modify the notifications power level.
if allow_modification:
event_auth.check_auth_rules_for_event(pl_event, auth_events)
event_auth.check_state_dependent_auth_rules(pl_event, auth_events)

else:
# But an MSC2209 room rejects this change.
with self.assertRaises(AuthError):
event_auth.check_auth_rules_for_event(pl_event, auth_events)
event_auth.check_state_dependent_auth_rules(pl_event, auth_events)

def test_join_rules_public(self):
"""
@@ -243,14 +284,14 @@ class EventAuthTestCase(unittest.TestCase):
}

# Check join.
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_join_event(RoomVersions.V6, pleb),
auth_events.values(),
)

# A user cannot be force-joined to a room.
with self.assertRaises(AuthError):
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_member_event(RoomVersions.V6, pleb, "join", sender=creator),
auth_events.values(),
)
@@ -260,7 +301,7 @@ class EventAuthTestCase(unittest.TestCase):
RoomVersions.V6, pleb, "ban"
)
with self.assertRaises(AuthError):
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_join_event(RoomVersions.V6, pleb),
auth_events.values(),
)
@@ -269,7 +310,7 @@ class EventAuthTestCase(unittest.TestCase):
auth_events[("m.room.member", pleb)] = _member_event(
RoomVersions.V6, pleb, "leave"
)
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_join_event(RoomVersions.V6, pleb),
auth_events.values(),
)
@@ -278,7 +319,7 @@ class EventAuthTestCase(unittest.TestCase):
auth_events[("m.room.member", pleb)] = _member_event(
RoomVersions.V6, pleb, "join"
)
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_join_event(RoomVersions.V6, pleb),
auth_events.values(),
)
@@ -287,7 +328,7 @@ class EventAuthTestCase(unittest.TestCase):
auth_events[("m.room.member", pleb)] = _member_event(
RoomVersions.V6, pleb, "invite", sender=creator
)
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_join_event(RoomVersions.V6, pleb),
auth_events.values(),
)
@@ -309,14 +350,14 @@ class EventAuthTestCase(unittest.TestCase):

# A join without an invite is rejected.
with self.assertRaises(AuthError):
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_join_event(RoomVersions.V6, pleb),
auth_events.values(),
)

# A user cannot be force-joined to a room.
with self.assertRaises(AuthError):
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_member_event(RoomVersions.V6, pleb, "join", sender=creator),
auth_events.values(),
)
@@ -326,7 +367,7 @@ class EventAuthTestCase(unittest.TestCase):
RoomVersions.V6, pleb, "ban"
)
with self.assertRaises(AuthError):
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_join_event(RoomVersions.V6, pleb),
auth_events.values(),
)
@@ -336,7 +377,7 @@ class EventAuthTestCase(unittest.TestCase):
RoomVersions.V6, pleb, "leave"
)
with self.assertRaises(AuthError):
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_join_event(RoomVersions.V6, pleb),
auth_events.values(),
)
@@ -345,7 +386,7 @@ class EventAuthTestCase(unittest.TestCase):
auth_events[("m.room.member", pleb)] = _member_event(
RoomVersions.V6, pleb, "join"
)
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_join_event(RoomVersions.V6, pleb),
auth_events.values(),
)
@@ -354,7 +395,7 @@ class EventAuthTestCase(unittest.TestCase):
auth_events[("m.room.member", pleb)] = _member_event(
RoomVersions.V6, pleb, "invite", sender=creator
)
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_join_event(RoomVersions.V6, pleb),
auth_events.values(),
)
@@ -376,7 +417,7 @@ class EventAuthTestCase(unittest.TestCase):
}

with self.assertRaises(AuthError):
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_join_event(RoomVersions.V6, pleb),
auth_events.values(),
)
@@ -413,7 +454,7 @@ class EventAuthTestCase(unittest.TestCase):
EventContentFields.AUTHORISING_USER: "@creator:example.com"
},
)
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
authorised_join_event,
auth_events.values(),
)
@@ -429,7 +470,7 @@ class EventAuthTestCase(unittest.TestCase):
pl_auth_events[("m.room.member", "@inviter:foo.test")] = _join_event(
RoomVersions.V8, "@inviter:foo.test"
)
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_join_event(
RoomVersions.V8,
pleb,
@@ -442,7 +483,7 @@ class EventAuthTestCase(unittest.TestCase):

# A join which is missing an authorised server is rejected.
with self.assertRaises(AuthError):
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_join_event(RoomVersions.V8, pleb),
auth_events.values(),
)
@@ -455,7 +496,7 @@ class EventAuthTestCase(unittest.TestCase):
{"invite": 100, "users": {"@other:example.com": 150}},
)
with self.assertRaises(AuthError):
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_join_event(
RoomVersions.V8,
pleb,
@@ -469,7 +510,7 @@ class EventAuthTestCase(unittest.TestCase):
# A user cannot be force-joined to a room. (This uses an event which
# *would* be valid, but is sent be a different user.)
with self.assertRaises(AuthError):
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_member_event(
RoomVersions.V8,
pleb,
@@ -487,7 +528,7 @@ class EventAuthTestCase(unittest.TestCase):
RoomVersions.V8, pleb, "ban"
)
with self.assertRaises(AuthError):
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
authorised_join_event,
auth_events.values(),
)
@@ -496,7 +537,7 @@ class EventAuthTestCase(unittest.TestCase):
auth_events[("m.room.member", pleb)] = _member_event(
RoomVersions.V8, pleb, "leave"
)
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
authorised_join_event,
auth_events.values(),
)
@@ -506,7 +547,7 @@ class EventAuthTestCase(unittest.TestCase):
auth_events[("m.room.member", pleb)] = _member_event(
RoomVersions.V8, pleb, "join"
)
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_join_event(RoomVersions.V8, pleb),
auth_events.values(),
)
@@ -516,7 +557,7 @@ class EventAuthTestCase(unittest.TestCase):
auth_events[("m.room.member", pleb)] = _member_event(
RoomVersions.V8, pleb, "invite", sender=creator
)
event_auth.check_auth_rules_for_event(
event_auth.check_state_dependent_auth_rules(
_join_event(RoomVersions.V8, pleb),
auth_events.values(),
)
@@ -539,6 +580,7 @@ def _create_event(
"state_key": "",
"sender": user_id,
"content": {"creator": user_id},
"auth_events": [],
},
room_version=room_version,
)
@@ -559,6 +601,7 @@ def _member_event(
"sender": sender or user_id,
"state_key": user_id,
"content": {"membership": membership, **(additional_content or {})},
"auth_events": [],
"prev_events": [],
},
room_version=room_version,
@@ -609,7 +652,22 @@ def _alias_event(room_version: RoomVersion, sender: str, **kwargs) -> EventBase:
return make_event_from_dict(data, room_version=room_version)


def _random_state_event(room_version: RoomVersion, sender: str) -> EventBase:
def _build_auth_dict_for_room_version(
room_version: RoomVersion, auth_events: Iterable[EventBase]
) -> List:
if room_version.event_format == EventFormatVersions.V1:
return [(e.event_id, "not_used") for e in auth_events]
else:
return [e.event_id for e in auth_events]


def _random_state_event(
room_version: RoomVersion,
sender: str,
auth_events: Optional[Iterable[EventBase]] = None,
) -> EventBase:
if auth_events is None:
auth_events = []
return make_event_from_dict(
{
"room_id": TEST_ROOM_ID,
@@ -618,6 +676,7 @@ def _random_state_event(room_version: RoomVersion, sender: str) -> EventBase:
"sender": sender,
"state_key": "",
"content": {"membership": "join"},
"auth_events": _build_auth_dict_for_room_version(room_version, auth_events),
},
room_version=room_version,
)


Loading…
Cancel
Save