Skip to content
This repository has been archived by the owner on Apr 26, 2024. It is now read-only.

Correct field name for stripped state events when knocking. knock_state_events -> knock_room_state #14102

Merged
merged 4 commits into from
Oct 12, 2022
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions changelog.d/14102.bugfix
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Fix a bug introduced in Synapse v1.37.0 in which an incorrect key name was used for sending and receiving room metadata when knocking on a room.
2 changes: 1 addition & 1 deletion synapse/federation/federation_client.py
Original file line number Diff line number Diff line change
@@ -1294,7 +1294,7 @@ async def _do_send_leave(self, destination: str, pdu: EventBase) -> JsonDict:
return resp[1]

async def send_knock(self, destinations: List[str], pdu: EventBase) -> JsonDict:
"""Attempts to send a knock event to given a list of servers. Iterates
"""Attempts to send a knock event to a given list of servers. Iterates
through the list until one attempt succeeds.

Doing so will cause the remote server to add the event to the graph,
9 changes: 8 additions & 1 deletion synapse/federation/federation_server.py
Original file line number Diff line number Diff line change
@@ -824,7 +824,14 @@ async def on_send_knock_request(
context, self._room_prejoin_state_types
)
)
return {"knock_state_events": stripped_room_state}
return {
"knock_room_state": stripped_room_state,
# Since v1.37, Synapse incorrectly used "knock_state_events" for this field.
# Thus, we also populate a 'knock_state_events' with the same content to
# support old instances.
# See https://github.com/matrix-org/synapse/issues/14088.
"knock_state_events": stripped_room_state,
}

async def _on_send_membership_event(
self, origin: str, content: JsonDict, membership_type: str, room_id: str
20 changes: 16 additions & 4 deletions synapse/handlers/federation.py
Original file line number Diff line number Diff line change
@@ -781,15 +781,27 @@ async def do_knock(

# Send the signed event back to the room, and potentially receive some
# further information about the room in the form of partial state events
stripped_room_state = await self.federation_client.send_knock(
target_hosts, event
)
knock_response = await self.federation_client.send_knock(target_hosts, event)

# Store any stripped room state events in the "unsigned" key of the event.
# This is a bit of a hack and is cribbing off of invites. Basically we
# store the room state here and retrieve it again when this event appears
# in the invitee's sync stream. It is stripped out for all other local users.
event.unsigned["knock_room_state"] = stripped_room_state["knock_state_events"]
stripped_room_state = (
knock_response.get("knock_room_state")
# Since v1.37, Synapse incorrectly used "knock_state_events" for this field.
# Thus, we also check for a 'knock_state_events' to support old instances.
# See https://github.com/matrix-org/synapse/issues/14088.
or knock_response.get("knock_state_events")
)

if stripped_room_state is None:
raise KeyError(
"Missing 'knock_room_state' (or legacy 'knock_state_events') field in "
"send_knock response"
)
Comment on lines +799 to +802
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think a different exception type would be more appropriate (and user-friendly) here. But I'm inclined not to change things too much in this PR.

The earlier code would have also raised a KeyError in the case the field was not present.


event.unsigned["knock_room_state"] = stripped_room_state

context = EventContext.for_outlier(self._storage_controllers)
stream_id = await self._federation_event_handler.persist_events_and_notify(