Skip to content

Expose MSC4354 Sticky Events over MSC4186 (Simplified) Sliding Sync.#19591

Merged
reivilibre merged 29 commits into
developfrom
rei/sticky_events_sliding_sync
Jun 23, 2026
Merged

Expose MSC4354 Sticky Events over MSC4186 (Simplified) Sliding Sync.#19591
reivilibre merged 29 commits into
developfrom
rei/sticky_events_sliding_sync

Conversation

@reivilibre

@reivilibre reivilibre commented Mar 20, 2026

Copy link
Copy Markdown
Contributor

Follows: #19487
Part of: MSC4354 whose experimental feature tracking issue is #19409

This PR implements the Sliding Sync (MSC4186) extension described in MSC4354, allowing sliding sync clients
to receive sticky events in a reliable way.

The logic is much the same as for oldschool sync (implementation in #19487),
although in the sliding sync extension, the client can choose their own limit
and must control their own pagination through an extra token in the extension request/response bodies.

EDIT: Note this PR does not yet send down existing sticky events in the room when the room has been newly-joined.
This newly-discovered gap is tracked at #19662 and will be addressed for both current sync and MSC4186 SSS soon.


This pull request is commit-by-commit review friendly.

  1. Add gather_optional_coroutines/7 overload

  2. Add fields for sticky events sliding sync extension

  3. Add explicit Absent utility type

  4. Implement sliding sync extension for sticky events

  5. Add sliding sync extension test

  6. drive-by docstring tweak on ordering

@reivilibre reivilibre changed the title Expose [MSC4354 Sticky Events](https://github.com/matrix-org/matrix-spec-proposals/pull/4354) over [MSC4186 (Simplified) Sliding Sync](https://github.com/matrix-org/matrix-spec-proposals/pull/4186). Expose MSC4354 Sticky Events over MSC4186 (Simplified) Sliding Sync. Mar 20, 2026
Comment thread synapse/util/sentinel.py Outdated
Comment thread synapse/handlers/sliding_sync/extensions.py Outdated
@reivilibre reivilibre force-pushed the rei/sticky_events_sliding_sync branch 4 times, most recently from 360c60b to adb3191 Compare March 20, 2026 16:20
Comment thread pyproject.toml Outdated
@reivilibre reivilibre force-pushed the rei/sticky_events_sliding_sync branch from 97efd43 to 6883dcd Compare March 20, 2026 17:24
@reivilibre reivilibre marked this pull request as ready for review March 20, 2026 17:25
@reivilibre reivilibre requested a review from a team as a code owner March 20, 2026 17:25
Comment thread synapse/handlers/sliding_sync/extensions.py Outdated
Signed-off-by: Olivier 'reivilibre <oliverw@matrix.org>
Fixes
builtins.NotImplementedError: Cannot check isinstance when validating
from json, use a JsonOrPython validator instead.
This reverts commit 6883dcd.

EPEL 10 only had 2.9.2 so try to work around issue without updating
builtins.NotImplementedError: Cannot check isinstance when validating
from json, use a JsonOrPython validator instead.
@reivilibre reivilibre force-pushed the rei/sticky_events_sliding_sync branch from 6883dcd to c5c1b01 Compare April 7, 2026 16:14
@reivilibre reivilibre requested review from a team and erikjohnston and removed request for erikjohnston April 7, 2026 17:44
Comment thread synapse/types/__init__.py Outdated
Comment thread synapse/types/__init__.py
Comment thread synapse/types/__init__.py
Comment thread synapse/types/__init__.py Outdated
Comment thread synapse/util/sentinel.py Outdated
Comment on lines +1008 to +1020
since_token = sticky_events_request.since or SlidingSyncStickyEventsToken(
sticky_events_stream_id=0
)
(
sticky_events_to_id,
room_to_event_ids,
) = await self.store.get_sticky_events_in_rooms(
all_interested_room_ids,
from_id=since_token.sticky_events_stream_id,
to_id=to_token.sticky_events_key,
now=now,
limit=min(sticky_events_request.limit, StickyEvent.MAX_EVENTS_IN_SYNC),
)

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

The Sticky Events extension having it's own pagination inside Sliding Sync seems like a smell to me.

Related discussion: matrix-org/matrix-spec-proposals#4354 (comment)

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

I can't find the linked discussion (GH deep links not working atm) but I trust that it captures the essence of the smell enough?

I broadly agree; in fact I'd go so far as to say that sliding sync is missing a high-level steward who sets the strategy for pagination. I have opened matrix-org/matrix-spec#2378 to describe this but not sure how to 'anchor' this down anywhere or find the right outcome for it.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Thanks for creating the issue. Given the to_device extension already uses this pattern, I guess we can opt to use it as well. Holding on to the hope that we don't settle.

I'm not really convinced it's the way to go. It's basically introducing it's own pagination behavior compared to the normal part of the Sliding Sync response. For the normal Sliding Sync response, the "No pagination" pattern is just to return all of the latest unseen data and if there is too much data (they've been offline too long and the homeserver deems it will take too many resources to compile their response, or the response is too large), reset the connection (M_UNKNOWN_POS) which tells the client to start over. I think that last detail should be added to matrix-org/matrix-spec#2378

And my general thoughts for sticky events is summarized in matrix-org/matrix-spec-proposals#4354 (comment) which was resolved for some reason 😠

Comment thread synapse/types/rest/client/__init__.py
Comment thread synapse/types/rest/client/__init__.py
Comment thread tests/rest/client/sliding_sync/test_extension_sticky_events.py
Comment thread tests/rest/client/sliding_sync/test_extension_sticky_events.py
@reivilibre reivilibre force-pushed the rei/sticky_events_sliding_sync branch from f5b8de3 to aa20913 Compare June 15, 2026 13:14
Comment thread synapse/types/rest/client/__init__.py Outdated
Comment thread synapse/handlers/sliding_sync/extensions.py Outdated
Comment thread tests/rest/client/sliding_sync/test_extension_sticky_events.py
Comment on lines +1008 to +1020
since_token = sticky_events_request.since or SlidingSyncStickyEventsToken(
sticky_events_stream_id=0
)
(
sticky_events_to_id,
room_to_event_ids,
) = await self.store.get_sticky_events_in_rooms(
all_interested_room_ids,
from_id=since_token.sticky_events_stream_id,
to_id=to_token.sticky_events_key,
now=now,
limit=min(sticky_events_request.limit, StickyEvent.MAX_EVENTS_IN_SYNC),
)

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Thanks for creating the issue. Given the to_device extension already uses this pattern, I guess we can opt to use it as well. Holding on to the hope that we don't settle.

I'm not really convinced it's the way to go. It's basically introducing it's own pagination behavior compared to the normal part of the Sliding Sync response. For the normal Sliding Sync response, the "No pagination" pattern is just to return all of the latest unseen data and if there is too much data (they've been offline too long and the homeserver deems it will take too many resources to compile their response, or the response is too large), reset the connection (M_UNKNOWN_POS) which tells the client to start over. I think that last detail should be added to matrix-org/matrix-spec#2378

And my general thoughts for sticky events is summarized in matrix-org/matrix-spec-proposals#4354 (comment) which was resolved for some reason 😠

Comment thread synapse/types/rest/client/__init__.py
Comment thread synapse/handlers/sliding_sync/extensions.py Outdated
Comment thread tests/rest/client/sliding_sync/test_extension_sticky_events.py Outdated
@reivilibre reivilibre enabled auto-merge (squash) June 22, 2026 16:16
@reivilibre reivilibre merged commit 16fe5fb into develop Jun 23, 2026
178 of 186 checks passed
@reivilibre reivilibre deleted the rei/sticky_events_sliding_sync branch June 23, 2026 13:04
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants