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

Fix search 500ing #4122

Merged
merged 2 commits into from
Oct 30, 2018
Merged
Show file tree
Hide file tree
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/4122.bugfix
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Searches that request profile info now no longer fail with a 500.
8 changes: 6 additions & 2 deletions synapse/handlers/search.py
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@
from synapse.api.errors import SynapseError
from synapse.api.filtering import Filter
from synapse.events.utils import serialize_event
from synapse.storage.state import StateFilter
from synapse.visibility import filter_events_for_client

from ._base import BaseHandler
Expand Down Expand Up @@ -324,9 +325,12 @@ def search(self, user, content, batch=None):
else:
last_event_id = event.event_id

state_filter = StateFilter.from_types(
[(EventTypes.Member, sender) for sender in senders]
)

state = yield self.store.get_state_for_event(
last_event_id,
types=[(EventTypes.Member, sender) for sender in senders]
last_event_id, state_filter
)

res["profile_info"] = {
Expand Down
106 changes: 105 additions & 1 deletion tests/rest/client/v1/test_rooms.py
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@
from twisted.internet import defer

from synapse.api.constants import Membership
from synapse.rest.client.v1 import room
from synapse.rest.client.v1 import admin, login, room

from tests import unittest

Expand Down Expand Up @@ -799,3 +799,107 @@ def test_stream_token_is_accepted_for_fwd_pagianation(self):
self.assertEquals(token, channel.json_body['start'])
self.assertTrue("chunk" in channel.json_body)
self.assertTrue("end" in channel.json_body)


class RoomSearchTestCase(unittest.HomeserverTestCase):
servlets = [
admin.register_servlets,
room.register_servlets,
login.register_servlets,
]
user_id = True
hijack_auth = False

def prepare(self, reactor, clock, hs):

# Register the user who does the searching
self.user_id = self.register_user("user", "pass")
self.access_token = self.login("user", "pass")

# Register the user who sends the message
self.other_user_id = self.register_user("otheruser", "pass")
self.other_access_token = self.login("otheruser", "pass")

# Create a room
self.room = self.helper.create_room_as(self.user_id, tok=self.access_token)

# Invite the other person
self.helper.invite(
room=self.room,
src=self.user_id,
tok=self.access_token,
targ=self.other_user_id,
)

# The other user joins
self.helper.join(
room=self.room, user=self.other_user_id, tok=self.other_access_token
)

def test_finds_message(self):
"""
The search functionality will search for content in messages if asked to
do so.
"""
# The other user sends some messages
self.helper.send(self.room, body="Hi!", tok=self.other_access_token)
self.helper.send(self.room, body="There!", tok=self.other_access_token)

request, channel = self.make_request(
"POST",
"/search?access_token=%s" % (self.access_token,),
{
"search_categories": {
"room_events": {"keys": ["content.body"], "search_term": "Hi"}
}
},
)
self.render(request)

# Check we get the results we expect -- one search result, of the sent
# messages
self.assertEqual(channel.code, 200)
results = channel.json_body["search_categories"]["room_events"]
self.assertEqual(results["count"], 1)
self.assertEqual(results["results"][0]["result"]["content"]["body"], "Hi!")

# No context was requested, so we should get none.
self.assertEqual(results["results"][0]["context"], {})

def test_include_context(self):
"""
When event_context includes include_profile, profile information will be
included in the search response.
"""
# The other user sends some messages
self.helper.send(self.room, body="Hi!", tok=self.other_access_token)
self.helper.send(self.room, body="There!", tok=self.other_access_token)

request, channel = self.make_request(
"POST",
"/search?access_token=%s" % (self.access_token,),
{
"search_categories": {
"room_events": {
"keys": ["content.body"],
"search_term": "Hi",
"event_context": {"include_profile": True},
}
}
},
)
self.render(request)

# Check we get the results we expect -- one search result, of the sent
# messages
self.assertEqual(channel.code, 200)
results = channel.json_body["search_categories"]["room_events"]
self.assertEqual(results["count"], 1)
self.assertEqual(results["results"][0]["result"]["content"]["body"], "Hi!")

# We should get context info, like the two users, and the display names.
context = results["results"][0]["context"]
self.assertEqual(len(context["profile_info"].keys()), 2)
self.assertEqual(
context["profile_info"][self.other_user_id]["displayname"], "otheruser"
)