Decrypt initial message after joining new DM

Suppose that Alice logs in using Element. Before this change, when Bob
would send a DM to Alice through Pantalaimon, Alice would not be able to
decrypt Bob's initial message. Instead, she would see "Unable to
decrypt: The sender's device has not sent us the keys for this message."
and Pantalaimon's olmsessions table would have no associated records.
Any future messages would be visible however. On the other hand, when
Alice (using Element) is the one to send the first DM to Bob, he can
decrypt the initial message.

For Pantalaimon to execute /keys/claim, get_missing_sessions must return
the invitee's device (and log "Missing session for device"). If
Pantalaimon calls this method too soon, then self.device_store will not
have the device. To populate self.device_store before Pantalaimon calls
get_missing_sessions, it must execute /keys/query (and invoke
_handle_key_query) earlier, during the /createRoom request. Pantalaimon
does execute the /keys/query request during a sync after the server
finishes creating the DM (and logs "Adding new device to the device
store for user"), but only after checking unsuccessfully for the device
in self.device_store.

After this change, Pantalaimon executes /keys/claim, there is one record
in olmsessions, and Alice can decrypt Bob's initial message.
This commit is contained in:
Igor Artemenko 2023-01-12 16:26:24 +00:00
parent b5a419e488
commit 313a5d528c
No known key found for this signature in database
GPG Key ID: E993592DCB6C45E9
2 changed files with 23 additions and 0 deletions

View File

@ -793,6 +793,27 @@ class ProxyDaemon:
body=await response.read(),
)
async def createRoom(self, request):
try:
content = await request.json()
except (JSONDecodeError, ContentTypeError):
return self._not_json
invite = content.get("invite", ())
if invite:
access_token = self.get_access_token(request)
if not access_token:
return self._missing_token
client = await self._find_client(access_token)
if not client:
return self._unknown_token
client.users_for_key_query.update(invite)
return await self.forward_to_web(request)
async def messages(self, request):
access_token = self.get_access_token(request)

View File

@ -71,6 +71,8 @@ async def init(data_dir, server_conf, send_queue, recv_queue):
web.post("/_matrix/client/v3/login", proxy.login),
web.get("/_matrix/client/r0/sync", proxy.sync),
web.get("/_matrix/client/v3/sync", proxy.sync),
web.post("/_matrix/client/r0/createRoom", proxy.createRoom),
web.post("/_matrix/client/v3/createRoom", proxy.createRoom),
web.get("/_matrix/client/r0/rooms/{room_id}/messages", proxy.messages),
web.get("/_matrix/client/v3/rooms/{room_id}/messages", proxy.messages),
web.put(