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

Implement MSC2326 (label based filtering) #6301

Merged
merged 16 commits into from
Nov 1, 2019
Merged
2 changes: 1 addition & 1 deletion changelog.d/6301.feature
Original file line number Diff line number Diff line change
@@ -1 +1 @@
Implement label-based filtering.
Implement label-based filtering on `/sync` and `/messages` ([MSC2326](https://github.com/matrix-org/matrix-doc/pull/2326)).
6 changes: 5 additions & 1 deletion synapse/api/constants.py
Original file line number Diff line number Diff line change
Expand Up @@ -140,4 +140,8 @@ class LimitBlockingTypes(object):
HS_DISABLED = "hs_disabled"


LabelsField = "org.matrix.labels"
class EventContentFields(object):
"""Fields found in events' content, regardless of type."""

# Labels for the event, cf https://github.com/matrix-org/matrix-doc/pull/2326
Labels = "org.matrix.labels"
babolivier marked this conversation as resolved.
Show resolved Hide resolved
6 changes: 4 additions & 2 deletions synapse/api/filtering.py
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@

from twisted.internet import defer

from synapse.api.constants import LabelsField
from synapse.api.constants import EventContentFields
from synapse.api.errors import SynapseError
from synapse.storage.presence import UserPresenceState
from synapse.types import RoomID, UserID
Expand Down Expand Up @@ -67,6 +67,8 @@
"contains_url": {"type": "boolean"},
"lazy_load_members": {"type": "boolean"},
"include_redundant_members": {"type": "boolean"},
# Include or exclude events with the provided labels.
# cf https://github.com/matrix-org/matrix-doc/pull/2326
"org.matrix.labels": {"type": "array", "items": {"type": "string"}},
babolivier marked this conversation as resolved.
Show resolved Hide resolved
"org.matrix.not_labels": {"type": "array", "items": {"type": "string"}},
},
Expand Down Expand Up @@ -307,7 +309,7 @@ def check(self, event):
content = event.get("content", {})
# check if there is a string url field in the content for filtering purposes
contains_url = isinstance(content.get("url"), text_type)
labels = content.get(LabelsField, [])
labels = content.get(EventContentFields.Labels, [])

return self.check_fields(room_id, sender, ev_type, labels, contains_url)

Expand Down
3 changes: 3 additions & 0 deletions synapse/rest/client/versions.py
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,9 @@ def on_GET(self, request):
"m.require_identity_server": False,
# as per MSC2290
"m.separate_add_and_bind": True,
# Implements support for label-based filtering as described in
# MSC2326.
"org.matrix.label_based_filtering": True,
},
},
)
Expand Down
12 changes: 10 additions & 2 deletions synapse/storage/data_stores/main/events.py
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@
from twisted.internet import defer

import synapse.metrics
from synapse.api.constants import EventTypes, LabelsField
from synapse.api.constants import EventContentFields, EventTypes
from synapse.api.errors import SynapseError
from synapse.events import EventBase # noqa: F401
from synapse.events.snapshot import EventContext # noqa: F401
Expand Down Expand Up @@ -1491,7 +1491,7 @@ def _update_metadata_tables_txn(
self._handle_event_relations(txn, event)

# Store the labels for this event.
labels = event.content.get(LabelsField)
labels = event.content.get(EventContentFields.Labels)
if labels:
self.insert_labels_for_event_txn(txn, event.event_id, labels)

Expand Down Expand Up @@ -2483,6 +2483,14 @@ def get_all_updated_current_state_deltas_txn(txn):
)

def insert_labels_for_event_txn(self, txn, event_id, labels):
babolivier marked this conversation as resolved.
Show resolved Hide resolved
"""Store the mapping between an event's ID and its labels, with one row per
(event_id, label) tuple.

Args:
txn (LoggingTransaction): The transaction to execute.
event_id (str): The event's ID.
labels (list[str]): A list of text labels.
"""
return self._simple_insert_many_txn(
txn=txn,
table="event_labels",
Expand Down
10 changes: 5 additions & 5 deletions tests/api/test_filtering.py
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@

from twisted.internet import defer

from synapse.api.constants import LabelsField
from synapse.api.constants import EventContentFields
from synapse.api.errors import SynapseError
from synapse.api.filtering import Filter
from synapse.events import FrozenEvent
Expand Down Expand Up @@ -329,7 +329,7 @@ def test_filter_labels(self):
sender="@foo:bar",
type="m.room.message",
room_id="!secretbase:unknown",
content={LabelsField: ["#fun"]},
content={EventContentFields.Labels: ["#fun"]},
)

self.assertTrue(Filter(definition).check(event))
Expand All @@ -338,7 +338,7 @@ def test_filter_labels(self):
sender="@foo:bar",
type="m.room.message",
room_id="!secretbase:unknown",
content={LabelsField: ["#notfun"]},
content={EventContentFields.Labels: ["#notfun"]},
)

self.assertFalse(Filter(definition).check(event))
Expand All @@ -349,7 +349,7 @@ def test_filter_not_labels(self):
sender="@foo:bar",
type="m.room.message",
room_id="!secretbase:unknown",
content={LabelsField: ["#fun"]},
content={EventContentFields.Labels: ["#fun"]},
)

self.assertFalse(Filter(definition).check(event))
Expand All @@ -358,7 +358,7 @@ def test_filter_not_labels(self):
sender="@foo:bar",
type="m.room.message",
room_id="!secretbase:unknown",
content={LabelsField: ["#notfun"]},
content={EventContentFields.Labels: ["#notfun"]},
)

self.assertTrue(Filter(definition).check(event))
Expand Down
10 changes: 5 additions & 5 deletions tests/rest/client/v1/test_rooms.py
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@
from twisted.internet import defer

import synapse.rest.admin
from synapse.api.constants import EventTypes, LabelsField, Membership
from synapse.api.constants import EventContentFields, EventTypes, Membership
from synapse.rest.client.v1 import login, profile, room

from tests import unittest
Expand Down Expand Up @@ -860,7 +860,7 @@ def _test_filter_labels(self, message_filter):
content={
"msgtype": "m.text",
"body": "with right label",
LabelsField: ["#fun"],
EventContentFields.Labels: ["#fun"],
},
)

Expand All @@ -876,7 +876,7 @@ def _test_filter_labels(self, message_filter):
content={
"msgtype": "m.text",
"body": "with wrong label",
LabelsField: ["#work"],
EventContentFields.Labels: ["#work"],
},
)

Expand All @@ -886,7 +886,7 @@ def _test_filter_labels(self, message_filter):
content={
"msgtype": "m.text",
"body": "with two wrong labels",
LabelsField: ["#work", "#notfun"],
EventContentFields.Labels: ["#work", "#notfun"],
},
)

Expand All @@ -896,7 +896,7 @@ def _test_filter_labels(self, message_filter):
content={
"msgtype": "m.text",
"body": "with right label",
LabelsField: ["#fun"],
EventContentFields.Labels: ["#fun"],
},
)

Expand Down
10 changes: 5 additions & 5 deletions tests/rest/client/v2_alpha/test_sync.py
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@
from mock import Mock

import synapse.rest.admin
from synapse.api.constants import EventTypes, LabelsField
from synapse.api.constants import EventContentFields, EventTypes
from synapse.rest.client.v1 import login, room
from synapse.rest.client.v2_alpha import sync

Expand Down Expand Up @@ -157,7 +157,7 @@ def _test_sync_filter_labels(self, sync_filter):
content={
"msgtype": "m.text",
"body": "with right label",
LabelsField: ["#fun"],
EventContentFields.Labels: ["#fun"],
},
tok=tok,
)
Expand All @@ -175,7 +175,7 @@ def _test_sync_filter_labels(self, sync_filter):
content={
"msgtype": "m.text",
"body": "with wrong label",
LabelsField: ["#work"],
EventContentFields.Labels: ["#work"],
},
tok=tok,
)
Expand All @@ -186,7 +186,7 @@ def _test_sync_filter_labels(self, sync_filter):
content={
"msgtype": "m.text",
"body": "with two wrong labels",
LabelsField: ["#work", "#notfun"],
EventContentFields.Labels: ["#work", "#notfun"],
},
tok=tok,
)
Expand All @@ -197,7 +197,7 @@ def _test_sync_filter_labels(self, sync_filter):
content={
"msgtype": "m.text",
"body": "with right label",
LabelsField: ["#fun"],
EventContentFields.Labels: ["#fun"],
},
tok=tok,
)
Expand Down