diff --git a/synapse/appservice/__init__.py b/synapse/appservice/__init__.py
index d5a7a5ce2f..c0d35132fe 100644
--- a/synapse/appservice/__init__.py
+++ b/synapse/appservice/__init__.py
@@ -186,8 +186,13 @@ class ApplicationService(object):
@cachedInlineCallbacks(num_args=1, cache_context=True)
def _matches_user_in_member_list(self, room_id, store, cache_context):
+
+ def invalidate_only_when_as_users_change(room_id, member):
+ if self.is_interested_in_user(member):
+ cache_context.invalidate(room_id)
+
member_list = yield store.get_users_in_room(
- room_id, on_invalidate=cache_context.invalidate
+ room_id, on_invalidate=invalidate_only_when_as_users_change
)
# check joined member events
diff --git a/synapse/storage/events.py b/synapse/storage/events.py
index f3d65f4338..14768e4bfb 100644
--- a/synapse/storage/events.py
+++ b/synapse/storage/events.py
@@ -793,6 +793,13 @@ class EventsStore(EventsWorkerStore):
self._invalidate_cache_and_stream(
txn, self.get_rooms_for_user_with_stream_ordering, (member,)
)
+ # we call this once for each member to allow AS workers to
+ # only invalidate their caches when AS members change.
+ # other folks naively using a cached get_users_in_rooms will
+ # just get prodded multiple times and can ignore the member key.
+ self._invalidate_cache_and_stream(
+ txn, self.get_users_in_room, (room_id, member)
+ )
for host in set(get_domain_from_id(u) for u in members_changed):
self._invalidate_cache_and_stream(
@@ -803,10 +810,6 @@ class EventsStore(EventsWorkerStore):
)
self._invalidate_cache_and_stream(
- txn, self.get_users_in_room, (room_id,)
- )
-
- self._invalidate_cache_and_stream(
txn, self.get_current_state_ids, (room_id,)
)
|