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

Commit bb4b118

Browse files
authored
Add missing type hints to handlers and fix a Spam Checker type hint. (#9896)
The user_may_create_room_alias method on spam checkers declared the room_alias parameter as a str when in reality it is passed a RoomAlias object.
1 parent 0085dc5 commit bb4b118

File tree

8 files changed

+82
-54
lines changed

8 files changed

+82
-54
lines changed

changelog.d/9896.bugfix

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
Correct the type hint for the `user_may_create_room_alias` method of spam checkers. It is provided a `RoomAlias`, not a `str`.

changelog.d/9896.misc

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
Add type hints to the `synapse.handlers` module.

synapse/events/spamcheck.py

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@
2020
from synapse.rest.media.v1._base import FileInfo
2121
from synapse.rest.media.v1.media_storage import ReadableFileWrapper
2222
from synapse.spam_checker_api import RegistrationBehaviour
23+
from synapse.types import RoomAlias
2324
from synapse.util.async_helpers import maybe_awaitable
2425

2526
if TYPE_CHECKING:
@@ -113,7 +114,9 @@ async def user_may_create_room(self, userid: str) -> bool:
113114

114115
return True
115116

116-
async def user_may_create_room_alias(self, userid: str, room_alias: str) -> bool:
117+
async def user_may_create_room_alias(
118+
self, userid: str, room_alias: RoomAlias
119+
) -> bool:
117120
"""Checks if a given user may create a room alias
118121
119122
If this method returns false, the association request will be rejected.

synapse/handlers/directory.py

Lines changed: 33 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,7 @@
1414

1515
import logging
1616
import string
17-
from typing import Iterable, List, Optional
17+
from typing import TYPE_CHECKING, Iterable, List, Optional
1818

1919
from synapse.api.constants import MAX_ALIAS_LENGTH, EventTypes
2020
from synapse.api.errors import (
@@ -27,15 +27,19 @@
2727
SynapseError,
2828
)
2929
from synapse.appservice import ApplicationService
30-
from synapse.types import Requester, RoomAlias, UserID, get_domain_from_id
30+
from synapse.storage.databases.main.directory import RoomAliasMapping
31+
from synapse.types import JsonDict, Requester, RoomAlias, UserID, get_domain_from_id
3132

3233
from ._base import BaseHandler
3334

35+
if TYPE_CHECKING:
36+
from synapse.server import HomeServer
37+
3438
logger = logging.getLogger(__name__)
3539

3640

3741
class DirectoryHandler(BaseHandler):
38-
def __init__(self, hs):
42+
def __init__(self, hs: "HomeServer"):
3943
super().__init__(hs)
4044

4145
self.state = hs.get_state_handler()
@@ -60,7 +64,7 @@ async def _create_association(
6064
room_id: str,
6165
servers: Optional[Iterable[str]] = None,
6266
creator: Optional[str] = None,
63-
):
67+
) -> None:
6468
# general association creation for both human users and app services
6569

6670
for wchar in string.whitespace:
@@ -104,8 +108,9 @@ async def create_association(
104108
"""
105109

106110
user_id = requester.user.to_string()
111+
room_alias_str = room_alias.to_string()
107112

108-
if len(room_alias.to_string()) > MAX_ALIAS_LENGTH:
113+
if len(room_alias_str) > MAX_ALIAS_LENGTH:
109114
raise SynapseError(
110115
400,
111116
"Can't create aliases longer than %s characters" % MAX_ALIAS_LENGTH,
@@ -114,7 +119,7 @@ async def create_association(
114119

115120
service = requester.app_service
116121
if service:
117-
if not service.is_interested_in_alias(room_alias.to_string()):
122+
if not service.is_interested_in_alias(room_alias_str):
118123
raise SynapseError(
119124
400,
120125
"This application service has not reserved this kind of alias.",
@@ -138,7 +143,7 @@ async def create_association(
138143
raise AuthError(403, "This user is not permitted to create this alias")
139144

140145
if not self.config.is_alias_creation_allowed(
141-
user_id, room_id, room_alias.to_string()
146+
user_id, room_id, room_alias_str
142147
):
143148
# Lets just return a generic message, as there may be all sorts of
144149
# reasons why we said no. TODO: Allow configurable error messages
@@ -211,7 +216,7 @@ async def delete_association(
211216

212217
async def delete_appservice_association(
213218
self, service: ApplicationService, room_alias: RoomAlias
214-
):
219+
) -> None:
215220
if not service.is_interested_in_alias(room_alias.to_string()):
216221
raise SynapseError(
217222
400,
@@ -220,25 +225,27 @@ async def delete_appservice_association(
220225
)
221226
await self._delete_association(room_alias)
222227

223-
async def _delete_association(self, room_alias: RoomAlias):
228+
async def _delete_association(self, room_alias: RoomAlias) -> str:
224229
if not self.hs.is_mine(room_alias):
225230
raise SynapseError(400, "Room alias must be local")
226231

227232
room_id = await self.store.delete_room_alias(room_alias)
228233

229234
return room_id
230235

231-
async def get_association(self, room_alias: RoomAlias):
236+
async def get_association(self, room_alias: RoomAlias) -> JsonDict:
232237
room_id = None
233238
if self.hs.is_mine(room_alias):
234-
result = await self.get_association_from_room_alias(room_alias)
239+
result = await self.get_association_from_room_alias(
240+
room_alias
241+
) # type: Optional[RoomAliasMapping]
235242

236243
if result:
237244
room_id = result.room_id
238245
servers = result.servers
239246
else:
240247
try:
241-
result = await self.federation.make_query(
248+
fed_result = await self.federation.make_query(
242249
destination=room_alias.domain,
243250
query_type="directory",
244251
args={"room_alias": room_alias.to_string()},
@@ -248,13 +255,13 @@ async def get_association(self, room_alias: RoomAlias):
248255
except CodeMessageException as e:
249256
logging.warning("Error retrieving alias")
250257
if e.code == 404:
251-
result = None
258+
fed_result = None
252259
else:
253260
raise
254261

255-
if result and "room_id" in result and "servers" in result:
256-
room_id = result["room_id"]
257-
servers = result["servers"]
262+
if fed_result and "room_id" in fed_result and "servers" in fed_result:
263+
room_id = fed_result["room_id"]
264+
servers = fed_result["servers"]
258265

259266
if not room_id:
260267
raise SynapseError(
@@ -275,7 +282,7 @@ async def get_association(self, room_alias: RoomAlias):
275282

276283
return {"room_id": room_id, "servers": servers}
277284

278-
async def on_directory_query(self, args):
285+
async def on_directory_query(self, args: JsonDict) -> JsonDict:
279286
room_alias = RoomAlias.from_string(args["room_alias"])
280287
if not self.hs.is_mine(room_alias):
281288
raise SynapseError(400, "Room Alias is not hosted on this homeserver")
@@ -293,7 +300,7 @@ async def on_directory_query(self, args):
293300

294301
async def _update_canonical_alias(
295302
self, requester: Requester, user_id: str, room_id: str, room_alias: RoomAlias
296-
):
303+
) -> None:
297304
"""
298305
Send an updated canonical alias event if the removed alias was set as
299306
the canonical alias or listed in the alt_aliases field.
@@ -344,7 +351,9 @@ async def _update_canonical_alias(
344351
ratelimit=False,
345352
)
346353

347-
async def get_association_from_room_alias(self, room_alias: RoomAlias):
354+
async def get_association_from_room_alias(
355+
self, room_alias: RoomAlias
356+
) -> Optional[RoomAliasMapping]:
348357
result = await self.store.get_association_from_room_alias(room_alias)
349358
if not result:
350359
# Query AS to see if it exists
@@ -372,7 +381,7 @@ def can_modify_alias(self, alias: RoomAlias, user_id: Optional[str] = None) -> b
372381
# either no interested services, or no service with an exclusive lock
373382
return True
374383

375-
async def _user_can_delete_alias(self, alias: RoomAlias, user_id: str):
384+
async def _user_can_delete_alias(self, alias: RoomAlias, user_id: str) -> bool:
376385
"""Determine whether a user can delete an alias.
377386
378387
One of the following must be true:
@@ -394,14 +403,13 @@ async def _user_can_delete_alias(self, alias: RoomAlias, user_id: str):
394403
if not room_id:
395404
return False
396405

397-
res = await self.auth.check_can_change_room_list(
406+
return await self.auth.check_can_change_room_list(
398407
room_id, UserID.from_string(user_id)
399408
)
400-
return res
401409

402410
async def edit_published_room_list(
403411
self, requester: Requester, room_id: str, visibility: str
404-
):
412+
) -> None:
405413
"""Edit the entry of the room in the published room list.
406414
407415
requester
@@ -469,7 +477,7 @@ async def edit_published_room_list(
469477

470478
async def edit_published_appservice_room_list(
471479
self, appservice_id: str, network_id: str, room_id: str, visibility: str
472-
):
480+
) -> None:
473481
"""Add or remove a room from the appservice/network specific public
474482
room list.
475483
@@ -499,5 +507,4 @@ async def get_aliases_for_room(
499507
room_id, requester.user.to_string()
500508
)
501509

502-
aliases = await self.store.get_aliases_for_room(room_id)
503-
return aliases
510+
return await self.store.get_aliases_for_room(room_id)

synapse/handlers/identity.py

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@
1717
"""Utilities for interacting with Identity Servers"""
1818
import logging
1919
import urllib.parse
20-
from typing import Awaitable, Callable, Dict, List, Optional, Tuple
20+
from typing import TYPE_CHECKING, Awaitable, Callable, Dict, List, Optional, Tuple
2121

2222
from synapse.api.errors import (
2323
CodeMessageException,
@@ -41,13 +41,16 @@
4141

4242
from ._base import BaseHandler
4343

44+
if TYPE_CHECKING:
45+
from synapse.server import HomeServer
46+
4447
logger = logging.getLogger(__name__)
4548

4649
id_server_scheme = "https://"
4750

4851

4952
class IdentityHandler(BaseHandler):
50-
def __init__(self, hs):
53+
def __init__(self, hs: "HomeServer"):
5154
super().__init__(hs)
5255

5356
# An HTTP client for contacting trusted URLs.
@@ -80,7 +83,7 @@ async def ratelimit_request_token_requests(
8083
request: SynapseRequest,
8184
medium: str,
8285
address: str,
83-
):
86+
) -> None:
8487
"""Used to ratelimit requests to `/requestToken` by IP and address.
8588
8689
Args:

synapse/handlers/message.py

Lines changed: 17 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,7 @@
1515
# limitations under the License.
1616
import logging
1717
import random
18-
from typing import TYPE_CHECKING, Dict, List, Optional, Tuple
18+
from typing import TYPE_CHECKING, Any, Dict, List, Mapping, Optional, Tuple
1919

2020
from canonicaljson import encode_canonical_json
2121

@@ -66,7 +66,7 @@
6666
class MessageHandler:
6767
"""Contains some read only APIs to get state about a room"""
6868

69-
def __init__(self, hs):
69+
def __init__(self, hs: "HomeServer"):
7070
self.auth = hs.get_auth()
7171
self.clock = hs.get_clock()
7272
self.state = hs.get_state_handler()
@@ -91,7 +91,7 @@ async def get_room_data(
9191
room_id: str,
9292
event_type: str,
9393
state_key: str,
94-
) -> dict:
94+
) -> Optional[EventBase]:
9595
"""Get data from a room.
9696
9797
Args:
@@ -115,6 +115,10 @@ async def get_room_data(
115115
data = await self.state.get_current_state(room_id, event_type, state_key)
116116
elif membership == Membership.LEAVE:
117117
key = (event_type, state_key)
118+
# If the membership is not JOIN, then the event ID should exist.
119+
assert (
120+
membership_event_id is not None
121+
), "check_user_in_room_or_world_readable returned invalid data"
118122
room_state = await self.state_store.get_state_for_events(
119123
[membership_event_id], StateFilter.from_types([key])
120124
)
@@ -186,10 +190,12 @@ async def get_state_events(
186190

187191
event = last_events[0]
188192
if visible_events:
189-
room_state = await self.state_store.get_state_for_events(
193+
room_state_events = await self.state_store.get_state_for_events(
190194
[event.event_id], state_filter=state_filter
191195
)
192-
room_state = room_state[event.event_id]
196+
room_state = room_state_events[
197+
event.event_id
198+
] # type: Mapping[Any, EventBase]
193199
else:
194200
raise AuthError(
195201
403,
@@ -210,10 +216,14 @@ async def get_state_events(
210216
)
211217
room_state = await self.store.get_events(state_ids.values())
212218
elif membership == Membership.LEAVE:
213-
room_state = await self.state_store.get_state_for_events(
219+
# If the membership is not JOIN, then the event ID should exist.
220+
assert (
221+
membership_event_id is not None
222+
), "check_user_in_room_or_world_readable returned invalid data"
223+
room_state_events = await self.state_store.get_state_for_events(
214224
[membership_event_id], state_filter=state_filter
215225
)
216-
room_state = room_state[membership_event_id]
226+
room_state = room_state_events[membership_event_id]
217227

218228
now = self.clock.time_msec()
219229
events = await self._event_serializer.serialize_events(

synapse/handlers/room_member.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1044,7 +1044,7 @@ async def _is_server_notice_room(self, room_id: str) -> bool:
10441044

10451045

10461046
class RoomMemberMasterHandler(RoomMemberHandler):
1047-
def __init__(self, hs):
1047+
def __init__(self, hs: "HomeServer"):
10481048
super().__init__(hs)
10491049

10501050
self.distributor = hs.get_distributor()

0 commit comments

Comments
 (0)