diff --git a/docs/differences.md b/docs/differences.md new file mode 100644 index 0000000..dfd1b74 --- /dev/null +++ b/docs/differences.md @@ -0,0 +1,16 @@ +# API Differences + +## Request Guild Members + +### In regards to ID serialization + +Request Guild Members does not follow the same logic Discord does when +invalid IDs are given on the `user_ids` field. + +Instead of returning them as non-string numbers, **they're returned as-is.** + +This should not cause any problems to well-formed requests. + +### Assumptions on business logic + +When using `user_ids`, Litecord will ignore the given `query` in the payload. diff --git a/litecord/gateway/websocket.py b/litecord/gateway/websocket.py index d68f2d6..6b2e0db 100644 --- a/litecord/gateway/websocket.py +++ b/litecord/gateway/websocket.py @@ -32,7 +32,7 @@ from litecord.auth import raw_token_check from litecord.enums import RelationshipType, ChannelType from litecord.schemas import validate, GW_STATUS_UPDATE from litecord.utils import ( - task_wrapper, yield_chunks + task_wrapper, yield_chunks, maybe_int ) from litecord.permissions import get_permissions @@ -770,11 +770,12 @@ class GatewayWebsocket: if not exists: return - # limit user_ids to 1000 possible members - user_ids = user_ids[:1000] + # limit user_ids to 1000 possible members, and try your best + # to convert them to ints, giving the same user id if it fails. + # this is checked later on to fill the not_found array + user_ids = [maybe_int(uid) for uid in user_ids[:1000]] - # assumption: requesting user_ids means - # we don't do query. + # ASSUMPTION: requesting user_ids means we don't do query. if user_ids: members = await self.storage.get_member_multi(guild_id, user_ids) mids = [m['user']['id'] for m in members] diff --git a/litecord/utils.py b/litecord/utils.py index 6018ba9..fcc192d 100644 --- a/litecord/utils.py +++ b/litecord/utils.py @@ -19,7 +19,7 @@ along with this program. If not, see . import asyncio import json -from typing import Any, Iterable, Optional, Sequence, List, Dict +from typing import Any, Iterable, Optional, Sequence, List, Dict, Union from logbook import Logger from quart.json import JSONEncoder @@ -214,3 +214,12 @@ async def search_result_from_list(rows: List) -> Dict[str, Any]: 'messages': res, 'analytics_id': '', } + + +def maybe_int(val: Any) -> Union[int, Any]: + """Try to convert a given value to an integer. Returns the same value + if it is not.""" + try: + return int(val) + except (ValueError, TypeError): + return val