scurrypy 0.1.0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of scurrypy might be problematic. Click here for more details.
- discord/__init__.py +9 -0
- discord/client.py +312 -0
- discord/dispatch/__init__.py +1 -0
- discord/dispatch/command_dispatcher.py +156 -0
- discord/dispatch/event_dispatcher.py +85 -0
- discord/dispatch/prefix_dispatcher.py +53 -0
- discord/error.py +63 -0
- discord/events/__init__.py +33 -0
- discord/events/channel_events.py +52 -0
- discord/events/guild_events.py +38 -0
- discord/events/hello_event.py +9 -0
- discord/events/interaction_events.py +145 -0
- discord/events/message_events.py +43 -0
- discord/events/reaction_events.py +99 -0
- discord/events/ready_event.py +30 -0
- discord/gateway.py +175 -0
- discord/http.py +292 -0
- discord/intents.py +87 -0
- discord/logger.py +147 -0
- discord/model.py +88 -0
- discord/models/__init__.py +8 -0
- discord/models/application.py +37 -0
- discord/models/emoji.py +34 -0
- discord/models/guild.py +35 -0
- discord/models/integration.py +23 -0
- discord/models/member.py +27 -0
- discord/models/role.py +53 -0
- discord/models/user.py +15 -0
- discord/parts/__init__.py +28 -0
- discord/parts/action_row.py +258 -0
- discord/parts/attachment.py +18 -0
- discord/parts/channel.py +20 -0
- discord/parts/command.py +102 -0
- discord/parts/component_types.py +5 -0
- discord/parts/components_v2.py +270 -0
- discord/parts/embed.py +154 -0
- discord/parts/message.py +179 -0
- discord/parts/modal.py +21 -0
- discord/parts/role.py +39 -0
- discord/resources/__init__.py +10 -0
- discord/resources/application.py +94 -0
- discord/resources/bot_emojis.py +49 -0
- discord/resources/channel.py +192 -0
- discord/resources/guild.py +265 -0
- discord/resources/interaction.py +155 -0
- discord/resources/message.py +223 -0
- discord/resources/user.py +111 -0
- scurrypy-0.1.0.dist-info/METADATA +8 -0
- scurrypy-0.1.0.dist-info/RECORD +52 -0
- scurrypy-0.1.0.dist-info/WHEEL +5 -0
- scurrypy-0.1.0.dist-info/licenses/LICENSE +5 -0
- scurrypy-0.1.0.dist-info/top_level.txt +1 -0
|
@@ -0,0 +1,155 @@
|
|
|
1
|
+
from dataclasses import dataclass
|
|
2
|
+
from typing import Optional, Unpack
|
|
3
|
+
|
|
4
|
+
from ..http import HTTPClient
|
|
5
|
+
from ..model import DataModel
|
|
6
|
+
|
|
7
|
+
from ..parts.modal import ModalBuilder
|
|
8
|
+
from ..parts.message import *
|
|
9
|
+
from ..parts.embed import *
|
|
10
|
+
from ..parts.component_types import *
|
|
11
|
+
|
|
12
|
+
from ..models.guild import GuildModel
|
|
13
|
+
from ..models.member import MemberModel
|
|
14
|
+
|
|
15
|
+
from .channel import Channel
|
|
16
|
+
|
|
17
|
+
class InteractionDataTypes:
|
|
18
|
+
"""Interaction data types constants."""
|
|
19
|
+
|
|
20
|
+
SLASH_COMMAND = 1
|
|
21
|
+
"""The interaction is a slash command."""
|
|
22
|
+
|
|
23
|
+
USER_COMMAND = 2
|
|
24
|
+
"""The interaction is attached to a user."""
|
|
25
|
+
|
|
26
|
+
MESSAGE_COMMAND = 3
|
|
27
|
+
"""The interaction is attached to a message."""
|
|
28
|
+
|
|
29
|
+
class InteractionCallbackTypes:
|
|
30
|
+
"""Interaction callback types constants."""
|
|
31
|
+
|
|
32
|
+
PONG = 1
|
|
33
|
+
"""Acknowledge a Ping."""
|
|
34
|
+
|
|
35
|
+
CHANNEL_MESSAGE_WITH_SOURCE = 4
|
|
36
|
+
"""Respond to an interaction with a message."""
|
|
37
|
+
|
|
38
|
+
DEFERRED_CHANNEL_MESSAGE_WITH_SOURCE = 5
|
|
39
|
+
"""Acknowledge an interaction and edit a response later. User sees a loading state."""
|
|
40
|
+
|
|
41
|
+
DEFERRED_UPDATE_MESSAGE = 6
|
|
42
|
+
"""Acknowledge an interaction and edit the original message later.
|
|
43
|
+
The user does NOT see a loading state. (Components only)
|
|
44
|
+
"""
|
|
45
|
+
|
|
46
|
+
UPDATE_MESSAGE = 7
|
|
47
|
+
"""Edit the message in which the component was attached."""
|
|
48
|
+
|
|
49
|
+
APPLICATION_COMMAND_AUTOCOMPLETE_RESULT = 8
|
|
50
|
+
"""Respond to an autocomplete interaction with suggested choices."""
|
|
51
|
+
|
|
52
|
+
MODAL = 9
|
|
53
|
+
"""Respond to an interaction with a popup modal (not available for MODAL_SUBMIT and PING interactions)."""
|
|
54
|
+
|
|
55
|
+
LAUNCH_ACTIVITY = 12
|
|
56
|
+
"""Launch an activity associated with the app (Activities must be enabled)."""
|
|
57
|
+
|
|
58
|
+
@dataclass
|
|
59
|
+
class Interaction(DataModel):
|
|
60
|
+
"""Represents a Discord Interaction object."""
|
|
61
|
+
|
|
62
|
+
id: int
|
|
63
|
+
"""ID of the interaction."""
|
|
64
|
+
|
|
65
|
+
token: str
|
|
66
|
+
"""Continuation token for responding to the interaction."""
|
|
67
|
+
|
|
68
|
+
_http: HTTPClient
|
|
69
|
+
"""HTTP session for requests."""
|
|
70
|
+
|
|
71
|
+
type: int
|
|
72
|
+
"""Type of interaction."""
|
|
73
|
+
|
|
74
|
+
channel_id: int
|
|
75
|
+
"""ID of the channel where the interaction was sent."""
|
|
76
|
+
|
|
77
|
+
application_id: int
|
|
78
|
+
"""ID of the application that owns the interaction."""
|
|
79
|
+
|
|
80
|
+
app_permissions: int
|
|
81
|
+
"""Bitwise set of permissions pertaining to the location of the interaction."""
|
|
82
|
+
|
|
83
|
+
member: MemberModel = None # guild member invoking the interaction
|
|
84
|
+
"""Guild member invoking the interaction."""
|
|
85
|
+
|
|
86
|
+
locale: str = None
|
|
87
|
+
"""Invoking user's locale."""
|
|
88
|
+
|
|
89
|
+
guild_locale: str = None
|
|
90
|
+
"""Locale of the guild the interaction was invoked (if invoked in a guild)."""
|
|
91
|
+
|
|
92
|
+
guild_id: Optional[int] = None
|
|
93
|
+
"""ID of guild the interaction was invoked (if invoked in a guild)."""
|
|
94
|
+
|
|
95
|
+
guild: Optional[GuildModel] = None
|
|
96
|
+
"""Partial guild object of the guild the interaction was invoked (if invoked in a guild)."""
|
|
97
|
+
|
|
98
|
+
channel: Optional[Channel] = None
|
|
99
|
+
"""Partial channel object the interaction was invoked."""
|
|
100
|
+
|
|
101
|
+
async def respond(self, message: str | MessageBuilder, **flags: Unpack[MessageFlagParams]):
|
|
102
|
+
"""Create a message in response to an interaction.
|
|
103
|
+
|
|
104
|
+
Args:
|
|
105
|
+
message (str | MessageBuilder): content as a string or from MessageBuilder
|
|
106
|
+
"""
|
|
107
|
+
if isinstance(message, str):
|
|
108
|
+
message = MessageBuilder(content=message).set_flags(**flags)
|
|
109
|
+
|
|
110
|
+
content = {
|
|
111
|
+
'type': InteractionCallbackTypes.CHANNEL_MESSAGE_WITH_SOURCE,
|
|
112
|
+
'data': message._to_dict()
|
|
113
|
+
}
|
|
114
|
+
|
|
115
|
+
await self._http.request(
|
|
116
|
+
'POST',
|
|
117
|
+
f'/interactions/{self.id}/{self.token}/callback',
|
|
118
|
+
content,
|
|
119
|
+
files=[fp.path for fp in message.attachments])
|
|
120
|
+
|
|
121
|
+
async def update(self, message: str | MessageBuilder, **flags: Unpack[MessageFlagParams]):
|
|
122
|
+
"""Update a message in response to an interaction.
|
|
123
|
+
|
|
124
|
+
Args:
|
|
125
|
+
message (str | MessageBuilder): content as a string or from MessageBuilder
|
|
126
|
+
"""
|
|
127
|
+
if isinstance(message, str):
|
|
128
|
+
message = MessageBuilder(content=message).set_flags(**flags)
|
|
129
|
+
|
|
130
|
+
content = {
|
|
131
|
+
'type': InteractionCallbackTypes.UPDATE_MESSAGE,
|
|
132
|
+
'data': message._to_dict()
|
|
133
|
+
}
|
|
134
|
+
|
|
135
|
+
await self._http.request(
|
|
136
|
+
'POST',
|
|
137
|
+
f'/interactions/{self.id}/{self.token}/callback',
|
|
138
|
+
content,
|
|
139
|
+
files=[fp.path for fp in message.attachments])
|
|
140
|
+
|
|
141
|
+
async def respond_modal(self, modal: ModalBuilder):
|
|
142
|
+
"""Create a modal in response to an interaction.
|
|
143
|
+
|
|
144
|
+
Args:
|
|
145
|
+
modal (ModalBuilder): modal data
|
|
146
|
+
"""
|
|
147
|
+
content = {
|
|
148
|
+
'type': InteractionCallbackTypes.MODAL,
|
|
149
|
+
'data': modal._to_dict()
|
|
150
|
+
}
|
|
151
|
+
|
|
152
|
+
await self._http.request(
|
|
153
|
+
'POST',
|
|
154
|
+
f'/interactions/{self.id}/{self.token}/callback',
|
|
155
|
+
content)
|
|
@@ -0,0 +1,223 @@
|
|
|
1
|
+
from dataclasses import dataclass
|
|
2
|
+
from typing import Optional
|
|
3
|
+
|
|
4
|
+
from ..http import HTTPClient
|
|
5
|
+
from ..model import DataModel
|
|
6
|
+
|
|
7
|
+
from ..models.user import UserModel
|
|
8
|
+
from ..models.emoji import EmojiModel
|
|
9
|
+
from ..parts.message import MessageBuilder
|
|
10
|
+
|
|
11
|
+
@dataclass
|
|
12
|
+
class Message(DataModel):
|
|
13
|
+
"""A Discord message."""
|
|
14
|
+
|
|
15
|
+
id: int
|
|
16
|
+
"""ID of the message"""
|
|
17
|
+
|
|
18
|
+
channel_id: int
|
|
19
|
+
"""Channel ID of the message."""
|
|
20
|
+
|
|
21
|
+
_http: HTTPClient
|
|
22
|
+
"""HTTP session for requests."""
|
|
23
|
+
|
|
24
|
+
author: UserModel = None
|
|
25
|
+
"""User data of author of the message."""
|
|
26
|
+
|
|
27
|
+
content: str = None
|
|
28
|
+
"""Content of the message."""
|
|
29
|
+
|
|
30
|
+
pinned: bool = None
|
|
31
|
+
"""If the message is pinned."""
|
|
32
|
+
|
|
33
|
+
type: int = None
|
|
34
|
+
"""Type of message."""
|
|
35
|
+
|
|
36
|
+
webhook_id: Optional[int] = None
|
|
37
|
+
"""ID of the webhook if the message is a webhook."""
|
|
38
|
+
|
|
39
|
+
def _update(self, data: dict):
|
|
40
|
+
"""Update this message in place."""
|
|
41
|
+
self.__dict__.update(Message.from_dict(data, self._http).__dict__)
|
|
42
|
+
|
|
43
|
+
async def fetch(self):
|
|
44
|
+
"""Fetches the message data based on the given channel id and message id.
|
|
45
|
+
|
|
46
|
+
Returns:
|
|
47
|
+
(Message): the message object
|
|
48
|
+
"""
|
|
49
|
+
data = await self._http.request('GET', f"/channels/{self.channel_id}/messages/{self.id}")
|
|
50
|
+
|
|
51
|
+
return Message.from_dict(data, self._http)
|
|
52
|
+
|
|
53
|
+
async def send(self, message: str | MessageBuilder):
|
|
54
|
+
"""Sends a new message to the current channel.
|
|
55
|
+
|
|
56
|
+
Permissions:
|
|
57
|
+
* SEND_MESSAGES → required to senf your own messages
|
|
58
|
+
|
|
59
|
+
Args:
|
|
60
|
+
message (str | MessageBuilder): can be just text or the MessageBuilder for dynamic messages
|
|
61
|
+
|
|
62
|
+
Returns:
|
|
63
|
+
(Message): the new Message object with all fields populated
|
|
64
|
+
"""
|
|
65
|
+
if isinstance(message, str):
|
|
66
|
+
message = MessageBuilder(content=message)
|
|
67
|
+
|
|
68
|
+
data = await self._http.request(
|
|
69
|
+
"POST",
|
|
70
|
+
f"/channels/{self.channel_id}/messages",
|
|
71
|
+
message._to_dict(),
|
|
72
|
+
files=[fp.path for fp in message.attachments] if message.attachments else None
|
|
73
|
+
)
|
|
74
|
+
return Message.from_dict(data, self._http)
|
|
75
|
+
|
|
76
|
+
async def edit(self, message: str | MessageBuilder):
|
|
77
|
+
"""Edits this message.
|
|
78
|
+
|
|
79
|
+
Permissions:
|
|
80
|
+
* MANAGE_MESSAGES → ONLY if editing another user's message
|
|
81
|
+
|
|
82
|
+
Args:
|
|
83
|
+
message (str | MessageBuilder): can be just text or the MessageBuilder for dynamic messages
|
|
84
|
+
"""
|
|
85
|
+
if isinstance(message, str):
|
|
86
|
+
message = MessageBuilder(content=message)
|
|
87
|
+
|
|
88
|
+
data = await self._http.request(
|
|
89
|
+
"PATCH",
|
|
90
|
+
f"/channels/{self.channel_id}/messages/{self.id}",
|
|
91
|
+
message._to_dict(),
|
|
92
|
+
files=[fp.path for fp in message.attachments] if message.attachments else None)
|
|
93
|
+
|
|
94
|
+
self._update(data)
|
|
95
|
+
|
|
96
|
+
async def reply(self, message: str | MessageBuilder):
|
|
97
|
+
"""Reply to this message with a new message.
|
|
98
|
+
|
|
99
|
+
Permissions:
|
|
100
|
+
* SEND_MESSAGES → required to send the message
|
|
101
|
+
|
|
102
|
+
Args:
|
|
103
|
+
message (str | MessageBuilder): the new message
|
|
104
|
+
"""
|
|
105
|
+
if isinstance(message, str):
|
|
106
|
+
message = MessageBuilder(content=message)
|
|
107
|
+
|
|
108
|
+
message = message._set_reference(self.id, self.channel_id)
|
|
109
|
+
|
|
110
|
+
await self._http.request(
|
|
111
|
+
'POST',
|
|
112
|
+
f"/channels/{self.channel_id}/messages",
|
|
113
|
+
message._to_dict(),
|
|
114
|
+
files=[fp.path for fp in message.attachments] if message.attachments else None)
|
|
115
|
+
|
|
116
|
+
async def crosspost(self):
|
|
117
|
+
"""Crosspost this message in an Annoucement channel to all following channels.
|
|
118
|
+
|
|
119
|
+
Permissions:
|
|
120
|
+
* SEND_MESSAGES → required to publish your own messages
|
|
121
|
+
* MANAGE_MESSAGES → required to publish messages from others
|
|
122
|
+
|
|
123
|
+
Returns:
|
|
124
|
+
(Message): the published (crossposted) message
|
|
125
|
+
"""
|
|
126
|
+
data = await self._http.request('POST', f'/channels/{self.channel_id}/messages/{self.id}/crosspost')
|
|
127
|
+
|
|
128
|
+
return Message.from_dict(data, self._http)
|
|
129
|
+
|
|
130
|
+
async def delete(self):
|
|
131
|
+
"""Deletes this message."""
|
|
132
|
+
await self._http.request("DELETE", f"/channels/{self.channel_id}/messages/{self.id}")
|
|
133
|
+
|
|
134
|
+
async def add_reaction(self, emoji: EmojiModel | str):
|
|
135
|
+
"""Add a reaction from this message.
|
|
136
|
+
|
|
137
|
+
Permissions:
|
|
138
|
+
* READ_MESSAGE_HISTORY → required to view message
|
|
139
|
+
* ADD_REACTIONS → required to create reaction
|
|
140
|
+
|
|
141
|
+
Args:
|
|
142
|
+
emoji (EmojiModel | str): the standard emoji (str) or custom emoji (EmojiModel)
|
|
143
|
+
"""
|
|
144
|
+
if isinstance(emoji, str):
|
|
145
|
+
emoji = EmojiModel(emoji)
|
|
146
|
+
|
|
147
|
+
await self._http.request(
|
|
148
|
+
"PUT",
|
|
149
|
+
f"/channels/{self.channel_id}/messages/{self.id}/reactions/{emoji.api_code}/@me")
|
|
150
|
+
|
|
151
|
+
async def remove_reaction(self, emoji: EmojiModel | str):
|
|
152
|
+
"""Remove the bot's reaction from this message.
|
|
153
|
+
|
|
154
|
+
Args:
|
|
155
|
+
emoji (EmojiModel | str): the standard emoji (str) or custom emoji (EmojiModel)
|
|
156
|
+
"""
|
|
157
|
+
if isinstance(emoji, str):
|
|
158
|
+
emoji = EmojiModel(emoji)
|
|
159
|
+
|
|
160
|
+
await self._http.request(
|
|
161
|
+
"DELETE",
|
|
162
|
+
f"/channels/{self.channel_id}/messages/{self.id}/reactions/{emoji.api_code}/@me")
|
|
163
|
+
|
|
164
|
+
async def remove_user_reaction(self, emoji: EmojiModel | str, user_id: int):
|
|
165
|
+
"""Remove a specific user's reaction from this message.
|
|
166
|
+
|
|
167
|
+
Permissions:
|
|
168
|
+
* MANAGE_MESSAGES → required to remove another user's reaction
|
|
169
|
+
|
|
170
|
+
Args:
|
|
171
|
+
emoji (EmojiModel | str): the standard emoji (str) or custom emoji (EmojiModel)
|
|
172
|
+
user_id (int): user's ID
|
|
173
|
+
"""
|
|
174
|
+
if isinstance(emoji, str):
|
|
175
|
+
emoji = EmojiModel(emoji)
|
|
176
|
+
|
|
177
|
+
await self._http.request(
|
|
178
|
+
"DELETE",
|
|
179
|
+
f"/channels/{self.channel_id}/messages/{self.id}/reactions/{emoji.api_code}/{user_id}")
|
|
180
|
+
|
|
181
|
+
async def remove_all_reactions(self):
|
|
182
|
+
"""Clear all reactions from this message.
|
|
183
|
+
|
|
184
|
+
Permissions:
|
|
185
|
+
* MANAGE_MESSAGES → required to remove all reaction
|
|
186
|
+
"""
|
|
187
|
+
await self._http.request(
|
|
188
|
+
"DELETE",
|
|
189
|
+
f"/channels/{self.channel_id}/messages/{self.id}/reactions")
|
|
190
|
+
|
|
191
|
+
async def pin(self):
|
|
192
|
+
"""Pin this message to its channel's pins."""
|
|
193
|
+
await self._http.request('PUT', f'/channels/{self.channel_id}/messages/pins/{self.id}')
|
|
194
|
+
|
|
195
|
+
async def unpin(self):
|
|
196
|
+
"""Unpin this message from its channel's pins."""
|
|
197
|
+
await self._http.request('DELETE', f'/channels/{self.channel_id}/messages/pins/{self.id}')
|
|
198
|
+
|
|
199
|
+
def _has_prefix(self, prefix: str):
|
|
200
|
+
"""Utility function. Checks if this message starts with the given prefix.
|
|
201
|
+
|
|
202
|
+
Args:
|
|
203
|
+
prefix (str): the prefix
|
|
204
|
+
|
|
205
|
+
Returns:
|
|
206
|
+
(bool): whether the message starts with the prefix
|
|
207
|
+
"""
|
|
208
|
+
if not self.content:
|
|
209
|
+
return False
|
|
210
|
+
return self.content.lower().startswith(prefix.lower())
|
|
211
|
+
|
|
212
|
+
def _extract_args(self, prefix: str):
|
|
213
|
+
"""Utility function. Extracts the args from this message's content.
|
|
214
|
+
|
|
215
|
+
Args:
|
|
216
|
+
prefix (str): the prefix
|
|
217
|
+
|
|
218
|
+
Returns:
|
|
219
|
+
(list[str] | None): list of args or None if no content
|
|
220
|
+
"""
|
|
221
|
+
if not self.content:
|
|
222
|
+
return
|
|
223
|
+
return self.content[len(prefix):].strip().lower().split()
|
|
@@ -0,0 +1,111 @@
|
|
|
1
|
+
from dataclasses import dataclass
|
|
2
|
+
from typing import Optional, TypedDict, Unpack
|
|
3
|
+
|
|
4
|
+
from ..http import HTTPClient
|
|
5
|
+
from ..model import DataModel
|
|
6
|
+
|
|
7
|
+
from ..models.guild import GuildModel
|
|
8
|
+
from ..models.member import MemberModel
|
|
9
|
+
|
|
10
|
+
class FetchUserGuildsParams(TypedDict, total=False):
|
|
11
|
+
before: int
|
|
12
|
+
"""Get guilds before this guild ID."""
|
|
13
|
+
|
|
14
|
+
after: int
|
|
15
|
+
"""Get guilds after this guild ID."""
|
|
16
|
+
|
|
17
|
+
limit: int
|
|
18
|
+
"""Max number of guilds to return. Range 1 - 200. Default 200."""
|
|
19
|
+
|
|
20
|
+
with_counts: bool
|
|
21
|
+
"""Include approximate member and presence count."""
|
|
22
|
+
|
|
23
|
+
@dataclass
|
|
24
|
+
class User(DataModel):
|
|
25
|
+
"""A Discord user."""
|
|
26
|
+
|
|
27
|
+
id: int
|
|
28
|
+
"""ID of the user."""
|
|
29
|
+
|
|
30
|
+
_http: HTTPClient
|
|
31
|
+
"""HTTP session for requests."""
|
|
32
|
+
|
|
33
|
+
username: str = None
|
|
34
|
+
"""Username of the user."""
|
|
35
|
+
|
|
36
|
+
discriminator: str = None
|
|
37
|
+
"""Discriminator of the user (#XXXX)"""
|
|
38
|
+
|
|
39
|
+
global_name: str = None
|
|
40
|
+
"""Global name of the user."""
|
|
41
|
+
|
|
42
|
+
avatar: str = None
|
|
43
|
+
"""Image hash of the user's avatar."""
|
|
44
|
+
|
|
45
|
+
bot: Optional[bool] = None
|
|
46
|
+
"""If the user is a bot."""
|
|
47
|
+
|
|
48
|
+
system: Optional[bool] = None
|
|
49
|
+
"""If the user belongs to an OAuth2 application."""
|
|
50
|
+
|
|
51
|
+
mfa_enabled: Optional[bool] = None
|
|
52
|
+
"""Whether the user has two factor enabled."""
|
|
53
|
+
|
|
54
|
+
banner: Optional[str] = None
|
|
55
|
+
"""Image hash of the user's banner."""
|
|
56
|
+
|
|
57
|
+
accent_color: Optional[int] = None
|
|
58
|
+
"""Color of user's banner represented as an integer."""
|
|
59
|
+
|
|
60
|
+
locale: Optional[str] = None
|
|
61
|
+
"""Chosen language option of the user."""
|
|
62
|
+
|
|
63
|
+
async def fetch(self):
|
|
64
|
+
"""Fetch this user by ID.
|
|
65
|
+
!!! note
|
|
66
|
+
Fetch includes both /users/@me AND /users/{user.id}!
|
|
67
|
+
|
|
68
|
+
Returns:
|
|
69
|
+
(User): the User object
|
|
70
|
+
"""
|
|
71
|
+
data = await self._http.request('GET', f'/users/{self.id}')
|
|
72
|
+
|
|
73
|
+
return User.from_dict(data, self._http)
|
|
74
|
+
|
|
75
|
+
async def fetch_guilds(self, **kwargs: Unpack[FetchUserGuildsParams]):
|
|
76
|
+
"""Fetch this user's guilds.
|
|
77
|
+
!!! warning "Important"
|
|
78
|
+
Requires the OAuth2 guilds scope!
|
|
79
|
+
|
|
80
|
+
Args:
|
|
81
|
+
kwargs: Field-specific data
|
|
82
|
+
!!! note
|
|
83
|
+
If no kwargs are provided, default to 200 guilds limit.
|
|
84
|
+
|
|
85
|
+
Returns:
|
|
86
|
+
(list[GuildModel]): each guild's data
|
|
87
|
+
"""
|
|
88
|
+
params = {
|
|
89
|
+
'limit': 200,
|
|
90
|
+
'with_counts': False,
|
|
91
|
+
**kwargs
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
data = await self._http.request('GET', '/users/@me/guilds', params=params)
|
|
95
|
+
|
|
96
|
+
return [GuildModel.from_dict(guild) for guild in data]
|
|
97
|
+
|
|
98
|
+
async def fetch_guild_member(self, guild_id: int):
|
|
99
|
+
"""Fetch this user's guild member data.
|
|
100
|
+
!!! warning "Important"
|
|
101
|
+
Requires the OAuth2 guilds.members.read scope!
|
|
102
|
+
|
|
103
|
+
Args:
|
|
104
|
+
guild_id (int): id of guild to fetch data from
|
|
105
|
+
|
|
106
|
+
Returns:
|
|
107
|
+
(MemberModel): member data from guild
|
|
108
|
+
"""
|
|
109
|
+
data = await self._http.request('GET', f'/users/@me/{guild_id}/member')
|
|
110
|
+
|
|
111
|
+
return MemberModel.from_dict(data)
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
discord/__init__.py,sha256=2mkaOJP7-7iT_aSkrstLuq10QykiDa3Y2vvl-wD9r1c,185
|
|
2
|
+
discord/client.py,sha256=kLwVFjUkl4qQWSj6hsxUk4F_6FDbW462roeHgRXxfW4,11986
|
|
3
|
+
discord/error.py,sha256=AlislRTna554cM6KC0KrwKugzYDYtx_9C8_3QFe4XDc,2070
|
|
4
|
+
discord/gateway.py,sha256=H_WaUrpK8rl3rGlT3qNexpru7R6O6Y6GQPkQcDt_KX8,6555
|
|
5
|
+
discord/http.py,sha256=cGFhGEeNebf1sgSUB4Xfnlj00twWLFi9AwO85gAAUDA,10955
|
|
6
|
+
discord/intents.py,sha256=Lf2fogFFDqilZeKJv7tcUgKmMW3D7ykK4bBNi-zDzYA,2866
|
|
7
|
+
discord/logger.py,sha256=GBcvldIrSBnwNSgus-oa1NsYV8hU7f8_4J4VX_GmkxA,4700
|
|
8
|
+
discord/model.py,sha256=Fr0PO_8UCgEep_Dk9eVtHmgzrlxkdsEYeuiS3EYK4hY,3015
|
|
9
|
+
discord/dispatch/__init__.py,sha256=m7ixrbNhOV9QRORXPw6LSwxofQMAvLmPFBweBZu9ACc,20
|
|
10
|
+
discord/dispatch/command_dispatcher.py,sha256=jOfO6GEQvp0muY3iE9otucsyBE36-xhMcZKMwHGnstU,5543
|
|
11
|
+
discord/dispatch/event_dispatcher.py,sha256=CX-7htyG7Gi9KobFIZJYHx78km3BT0M8gymZEVCi9LM,2902
|
|
12
|
+
discord/dispatch/prefix_dispatcher.py,sha256=IV2xKqCVaz-PGvg9etgqqUpMWQgvRnYEk6eURt4UqQc,1894
|
|
13
|
+
discord/events/__init__.py,sha256=BcmwAj84-nzMZEkip-V903jD0ZCKqhySzlAx5wDwJoo,630
|
|
14
|
+
discord/events/channel_events.py,sha256=lkBzNI-gKNgIPfIrOJhx-zjbK5v4bErEUurWp9L-VWw,1369
|
|
15
|
+
discord/events/guild_events.py,sha256=4rDPbldG4kjsBmSuRasDoXc-2cYmjdJOP5PTAdEbRw8,1008
|
|
16
|
+
discord/events/hello_event.py,sha256=O8Ketu_N943cnGaFkGsAHfWhgKXFQCYCqSD3EqdsXjA,225
|
|
17
|
+
discord/events/interaction_events.py,sha256=5hlYOsV1ROiRXISAGCKcZo8vfk6oqiZcNzzZjSteiag,4361
|
|
18
|
+
discord/events/message_events.py,sha256=M5xdaJH1zRzdZk0oN0Jykaeu9k09EjgZjeiIT_EkL1A,1475
|
|
19
|
+
discord/events/reaction_events.py,sha256=xx7GD-fqakhJmS-X-HbuAUg9pg6Gqo_KRtLTdPJu7UE,2643
|
|
20
|
+
discord/events/ready_event.py,sha256=iDuCTegyrN05FdYVPY0hsfJn1NABslkzsa_b2WxrRu0,792
|
|
21
|
+
discord/models/__init__.py,sha256=T6C5C8RdkEPurA_zQas5riq3nrThMaSWl9Yasha0xXc,216
|
|
22
|
+
discord/models/application.py,sha256=2sXtRysUc2TJ40FjdcrWgosmwMrp_h3ybddubQMixKM,924
|
|
23
|
+
discord/models/emoji.py,sha256=6iz1DhWj_eTUj2KHmwMewjB3AdEBm68EmIZp2WFFCQg,932
|
|
24
|
+
discord/models/guild.py,sha256=aXUByOUUIGt9d2qIGC6_X_vh0Nyib8Iqj5ZElBeNV_I,819
|
|
25
|
+
discord/models/integration.py,sha256=V29RO2925mQbVXPAMt665cML3m8mJACYmdJLWwbbUyE,612
|
|
26
|
+
discord/models/member.py,sha256=pkI-NVRMb3hUBkxI26FSYZxzx2mRNGXOeWWCw3BGGsY,705
|
|
27
|
+
discord/models/role.py,sha256=erlERmK-IZz4YzSNY-XLNvCc-Z5PoVlClxPOX67dQJg,1169
|
|
28
|
+
discord/models/user.py,sha256=lgG6GoU_7L68oHt6PGTzTkU1vrbsclRQzGjKzsLBeKA,298
|
|
29
|
+
discord/parts/__init__.py,sha256=dxrdklnWRHYIbPi6KBvUcJTWky8oTHRyMQbh58_2cmA,511
|
|
30
|
+
discord/parts/action_row.py,sha256=D0oUJu_0yfLojqFbKyxfiFFOv9RcFFN11nVt5_y70mk,8266
|
|
31
|
+
discord/parts/attachment.py,sha256=fhWpb5e0JKfbibcEc0EOiNrzqSSAUEL87NEhRmB1H34,388
|
|
32
|
+
discord/parts/channel.py,sha256=2wmEjmRqUpORzL3CFp2rugMxrpSm_LxxvlcrmWIH4r4,584
|
|
33
|
+
discord/parts/command.py,sha256=CPyPO_T5ULp7j7syF9z2LztP3SF6KyX89sodz2c40Aw,2924
|
|
34
|
+
discord/parts/component_types.py,sha256=qr1R0jzXpE_h9Xv4P5DyYRSuhxS0Qnm9aag-JKrJvBA,131
|
|
35
|
+
discord/parts/components_v2.py,sha256=53cQm4FmxXHAA7PmDcDIO4bergX-BaUB3bZVWej-U9s,8660
|
|
36
|
+
discord/parts/embed.py,sha256=_PV-lEAKn-MiXyyLa2s8JKHEplA8J9dDO80NPdZtmLk,3986
|
|
37
|
+
discord/parts/message.py,sha256=egCWGUxcTqbgzz_-dxZOV1WQZpuzd6tq9uFiZH40s1Y,5499
|
|
38
|
+
discord/parts/modal.py,sha256=EX6J9Mh5dAQBOZqYKzSE7SFsKLfM_B1BhcJamjBNkZw,554
|
|
39
|
+
discord/parts/role.py,sha256=cK96UdgT-kU0gY5C_1LZXPrYg144x2RDmGjT28so57A,920
|
|
40
|
+
discord/resources/__init__.py,sha256=ubRaTXEy4dNJhqO8JXf-xBoJjPt9zKs1GZHY8Um2_mk,282
|
|
41
|
+
discord/resources/application.py,sha256=vYMTli_FSbC7venMepsJ9bkzdEQVkKYpnxCJ9K2XDho,2765
|
|
42
|
+
discord/resources/bot_emojis.py,sha256=RvGCSOBkjS39P2aab0FzYUOTzBOiHX99RLrJZzAYNiU,1701
|
|
43
|
+
discord/resources/channel.py,sha256=-boYdVYW0v0oaV5X1SIhfdbKn0RDFF_HJo83dreVTm0,5943
|
|
44
|
+
discord/resources/guild.py,sha256=Unld1lWY3XynmRHU2FCi3-LA9VNp2thMI2BlILUTTxk,8183
|
|
45
|
+
discord/resources/interaction.py,sha256=8z91X49KSknaT1syBfLr0SHRgAxaQ-8lbhkb3LU21fg,4911
|
|
46
|
+
discord/resources/message.py,sha256=RtvcCRx0lwW-mHPl3aNYoEvGffrvtpLsQ2fVWckywVI,7527
|
|
47
|
+
discord/resources/user.py,sha256=vk89TnCVi-6ZgbDs_TZTCXrx_NfFS5Q9Wi_itYoaoyg,3085
|
|
48
|
+
scurrypy-0.1.0.dist-info/licenses/LICENSE,sha256=NtspfRMAlryd1Eev4BYi9EFbKhvdmlCJJ2-ADUoEBoI,426
|
|
49
|
+
scurrypy-0.1.0.dist-info/METADATA,sha256=uRHnWjovcV97VB7PQrhVDFUotTd53CGoAY9IVEmv0Ww,186
|
|
50
|
+
scurrypy-0.1.0.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
|
|
51
|
+
scurrypy-0.1.0.dist-info/top_level.txt,sha256=fJkrNbR-_8ubMBUcDEJBcfkpECrvSEmMrNKgvLlQFoM,8
|
|
52
|
+
scurrypy-0.1.0.dist-info/RECORD,,
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
Copyright (c) 2025 Furmissile. All rights reserved.
|
|
2
|
+
|
|
3
|
+
Derivative works are not permitted -- the source code is made available for educational and reference purposes only, and is not exempt from licensing.
|
|
4
|
+
This software is provided on an "as-is" basis and the author is not responsible for any liability that may come from misuse.
|
|
5
|
+
No commercial profit may be drawn off of derivatives of this software project for any reason.
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
discord
|