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

Commit c3e4edb

Browse files
authored
Stabilize the threads API. (#14175)
Stabilize the threads API (MSC3856) by supporting (only) the v1 path for the endpoint. This also marks the API as safe for workers since it is a read-only API.
1 parent 9ff4155 commit c3e4edb

File tree

7 files changed

+35
-29
lines changed

7 files changed

+35
-29
lines changed

changelog.d/13394.feature

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1 +1 @@
1-
Experimental support for [MSC3856](https://github.com/matrix-org/matrix-spec-proposals/pull/3856): threads list API.
1+
Support for [MSC3856](https://github.com/matrix-org/matrix-spec-proposals/pull/3856): threads list API.

changelog.d/14175.feature

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
Support for [MSC3856](https://github.com/matrix-org/matrix-spec-proposals/pull/3856): threads list API.

docker/configure_workers_and_start.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -118,6 +118,7 @@
118118
"^/_matrix/client/(api/v1|r0|v3|unstable)/rooms/.*/state$",
119119
"^/_matrix/client/v1/rooms/.*/hierarchy$",
120120
"^/_matrix/client/(v1|unstable)/rooms/.*/relations/",
121+
"^/_matrix/client/v1/rooms/.*/threads$",
121122
"^/_matrix/client/(api/v1|r0|v3|unstable)/login$",
122123
"^/_matrix/client/(api/v1|r0|v3|unstable)/account/3pid$",
123124
"^/_matrix/client/(api/v1|r0|v3|unstable)/account/whoami$",

docs/workers.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -204,6 +204,7 @@ information.
204204
^/_matrix/client/(api/v1|r0|v3|unstable)/rooms/.*/state$
205205
^/_matrix/client/v1/rooms/.*/hierarchy$
206206
^/_matrix/client/(v1|unstable)/rooms/.*/relations/
207+
^/_matrix/client/v1/rooms/.*/threads$
207208
^/_matrix/client/unstable/org.matrix.msc2716/rooms/.*/batch_send$
208209
^/_matrix/client/unstable/im.nheko.summary/rooms/.*/summary$
209210
^/_matrix/client/(r0|v3|unstable)/account/3pid$

synapse/config/experimental.py

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -101,9 +101,6 @@ def read_config(self, config: JsonDict, **kwargs: Any) -> None:
101101
# MSC3848: Introduce errcodes for specific event sending failures
102102
self.msc3848_enabled: bool = experimental.get("msc3848_enabled", False)
103103

104-
# MSC3856: Threads list API
105-
self.msc3856_enabled: bool = experimental.get("msc3856_enabled", False)
106-
107104
# MSC3852: Expose last seen user agent field on /_matrix/client/v3/devices.
108105
self.msc3852_enabled: bool = experimental.get("msc3852_enabled", False)
109106

synapse/rest/client/relations.py

Lines changed: 2 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -82,11 +82,7 @@ async def on_GET(
8282

8383

8484
class ThreadsServlet(RestServlet):
85-
PATTERNS = (
86-
re.compile(
87-
"^/_matrix/client/unstable/org.matrix.msc3856/rooms/(?P<room_id>[^/]*)/threads"
88-
),
89-
)
85+
PATTERNS = (re.compile("^/_matrix/client/v1/rooms/(?P<room_id>[^/]*)/threads"),)
9086

9187
def __init__(self, hs: "HomeServer"):
9288
super().__init__()
@@ -126,5 +122,4 @@ async def on_GET(
126122

127123
def register_servlets(hs: "HomeServer", http_server: HttpServer) -> None:
128124
RelationPaginationServlet(hs).register(http_server)
129-
if hs.config.experimental.msc3856_enabled:
130-
ThreadsServlet(hs).register(http_server)
125+
ThreadsServlet(hs).register(http_server)

tests/rest/client/test_relations.py

Lines changed: 29 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -1710,40 +1710,53 @@ def test_redact_parent_thread(self) -> None:
17101710

17111711

17121712
class ThreadsTestCase(BaseRelationsTestCase):
1713-
@unittest.override_config({"experimental_features": {"msc3856_enabled": True}})
1713+
def _get_threads(self, body: JsonDict) -> List[Tuple[str, str]]:
1714+
return [
1715+
(
1716+
ev["event_id"],
1717+
ev["unsigned"]["m.relations"]["m.thread"]["latest_event"]["event_id"],
1718+
)
1719+
for ev in body["chunk"]
1720+
]
1721+
17141722
def test_threads(self) -> None:
17151723
"""Create threads and ensure the ordering is due to their latest event."""
17161724
# Create 2 threads.
17171725
thread_1 = self.parent_id
17181726
res = self.helper.send(self.room, body="Thread Root!", tok=self.user_token)
17191727
thread_2 = res["event_id"]
17201728

1721-
self._send_relation(RelationTypes.THREAD, "m.room.test")
1722-
self._send_relation(RelationTypes.THREAD, "m.room.test", parent_id=thread_2)
1729+
channel = self._send_relation(RelationTypes.THREAD, "m.room.test")
1730+
reply_1 = channel.json_body["event_id"]
1731+
channel = self._send_relation(
1732+
RelationTypes.THREAD, "m.room.test", parent_id=thread_2
1733+
)
1734+
reply_2 = channel.json_body["event_id"]
17231735

17241736
# Request the threads in the room.
17251737
channel = self.make_request(
17261738
"GET",
1727-
f"/_matrix/client/unstable/org.matrix.msc3856/rooms/{self.room}/threads",
1739+
f"/_matrix/client/v1/rooms/{self.room}/threads",
17281740
access_token=self.user_token,
17291741
)
17301742
self.assertEquals(200, channel.code, channel.json_body)
1731-
thread_roots = [ev["event_id"] for ev in channel.json_body["chunk"]]
1732-
self.assertEqual(thread_roots, [thread_2, thread_1])
1743+
threads = self._get_threads(channel.json_body)
1744+
self.assertEqual(threads, [(thread_2, reply_2), (thread_1, reply_1)])
17331745

17341746
# Update the first thread, the ordering should swap.
1735-
self._send_relation(RelationTypes.THREAD, "m.room.test")
1747+
channel = self._send_relation(RelationTypes.THREAD, "m.room.test")
1748+
reply_3 = channel.json_body["event_id"]
17361749

17371750
channel = self.make_request(
17381751
"GET",
1739-
f"/_matrix/client/unstable/org.matrix.msc3856/rooms/{self.room}/threads",
1752+
f"/_matrix/client/v1/rooms/{self.room}/threads",
17401753
access_token=self.user_token,
17411754
)
17421755
self.assertEquals(200, channel.code, channel.json_body)
1743-
thread_roots = [ev["event_id"] for ev in channel.json_body["chunk"]]
1744-
self.assertEqual(thread_roots, [thread_1, thread_2])
1756+
# Tuple of (thread ID, latest event ID) for each thread.
1757+
threads = self._get_threads(channel.json_body)
1758+
self.assertEqual(threads, [(thread_1, reply_3), (thread_2, reply_2)])
17451759

1746-
@unittest.override_config({"experimental_features": {"msc3856_enabled": True}})
17471760
def test_pagination(self) -> None:
17481761
"""Create threads and paginate through them."""
17491762
# Create 2 threads.
@@ -1757,7 +1770,7 @@ def test_pagination(self) -> None:
17571770
# Request the threads in the room.
17581771
channel = self.make_request(
17591772
"GET",
1760-
f"/_matrix/client/unstable/org.matrix.msc3856/rooms/{self.room}/threads?limit=1",
1773+
f"/_matrix/client/v1/rooms/{self.room}/threads?limit=1",
17611774
access_token=self.user_token,
17621775
)
17631776
self.assertEquals(200, channel.code, channel.json_body)
@@ -1771,7 +1784,7 @@ def test_pagination(self) -> None:
17711784

17721785
channel = self.make_request(
17731786
"GET",
1774-
f"/_matrix/client/unstable/org.matrix.msc3856/rooms/{self.room}/threads?limit=1&from={next_batch}",
1787+
f"/_matrix/client/v1/rooms/{self.room}/threads?limit=1&from={next_batch}",
17751788
access_token=self.user_token,
17761789
)
17771790
self.assertEquals(200, channel.code, channel.json_body)
@@ -1780,7 +1793,6 @@ def test_pagination(self) -> None:
17801793

17811794
self.assertNotIn("next_batch", channel.json_body, channel.json_body)
17821795

1783-
@unittest.override_config({"experimental_features": {"msc3856_enabled": True}})
17841796
def test_include(self) -> None:
17851797
"""Filtering threads to all or participated in should work."""
17861798
# Thread 1 has the user as the root event.
@@ -1807,7 +1819,7 @@ def test_include(self) -> None:
18071819
# All threads in the room.
18081820
channel = self.make_request(
18091821
"GET",
1810-
f"/_matrix/client/unstable/org.matrix.msc3856/rooms/{self.room}/threads",
1822+
f"/_matrix/client/v1/rooms/{self.room}/threads",
18111823
access_token=self.user_token,
18121824
)
18131825
self.assertEquals(200, channel.code, channel.json_body)
@@ -1819,14 +1831,13 @@ def test_include(self) -> None:
18191831
# Only participated threads.
18201832
channel = self.make_request(
18211833
"GET",
1822-
f"/_matrix/client/unstable/org.matrix.msc3856/rooms/{self.room}/threads?include=participated",
1834+
f"/_matrix/client/v1/rooms/{self.room}/threads?include=participated",
18231835
access_token=self.user_token,
18241836
)
18251837
self.assertEquals(200, channel.code, channel.json_body)
18261838
thread_roots = [ev["event_id"] for ev in channel.json_body["chunk"]]
18271839
self.assertEqual(thread_roots, [thread_2, thread_1], channel.json_body)
18281840

1829-
@unittest.override_config({"experimental_features": {"msc3856_enabled": True}})
18301841
def test_ignored_user(self) -> None:
18311842
"""Events from ignored users should be ignored."""
18321843
# Thread 1 has a reply from an ignored user.
@@ -1852,7 +1863,7 @@ def test_ignored_user(self) -> None:
18521863
# Only thread 1 is returned.
18531864
channel = self.make_request(
18541865
"GET",
1855-
f"/_matrix/client/unstable/org.matrix.msc3856/rooms/{self.room}/threads",
1866+
f"/_matrix/client/v1/rooms/{self.room}/threads",
18561867
access_token=self.user_token,
18571868
)
18581869
self.assertEquals(200, channel.code, channel.json_body)

0 commit comments

Comments
 (0)