Skip to content

Commit d1cbd88

Browse files
committed
feat: add methods to interact with http methods
1 parent fa99dd3 commit d1cbd88

File tree

1 file changed

+50
-0
lines changed

1 file changed

+50
-0
lines changed

interactions/models/discord/message.py

Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
import asyncio
22
import base64
33
import re
4+
from collections import namedtuple
45
from dataclasses import dataclass
56
from typing import (
67
TYPE_CHECKING,
@@ -29,6 +30,7 @@
2930
from interactions.models.discord.emoji import process_emoji_req_format
3031
from interactions.models.discord.file import UPLOADABLE_TYPE
3132
from interactions.models.discord.poll import Poll
33+
from interactions.models.misc.iterator import AsyncIterator
3234

3335
from .base import DiscordObject
3436
from .enums import (
@@ -68,6 +70,32 @@
6870

6971
channel_mention = re.compile(r"<#(?P<id>[0-9]{17,})>")
7072

73+
class PollAnswerVotersIterator(AsyncIterator):
74+
def __init__(self, message: "Message", answer_id: int, limit: int = 25, after: Snowflake_Type | None = None) -> None:
75+
self.message: "Message" = message
76+
self.answer_id = answer_id
77+
self.after: Snowflake_Type | None = after
78+
self._more: bool = True
79+
super().__init__(limit)
80+
81+
async def fetch(self) -> list["models.User"]:
82+
if not self.last:
83+
self.last = namedtuple("temp", "id")
84+
self.last.id = self.after
85+
86+
rcv = await self.message._client.http.get_answer_voters(
87+
self.message._channel_id,
88+
self.message.id,
89+
self.answer_id,
90+
limit=self.get_limit,
91+
after=to_snowflake(self.last.id) if self.last.id else None,
92+
)
93+
if not rcv:
94+
raise asyncio.QueueEmpty
95+
96+
users = [self.message._client.cache.place_user_data(user_data) for user_data in rcv["users"]]
97+
return users
98+
7199

72100
@attrs.define(eq=False, order=False, hash=False, kw_only=True)
73101
class Attachment(DiscordObject):
@@ -361,6 +389,8 @@ class Message(BaseMessage):
361389
"""Data showing the source of a crosspost, channel follow add, pin, or reply message"""
362390
flags: MessageFlags = attrs.field(repr=False, default=MessageFlags.NONE, converter=MessageFlags)
363391
"""Message flags combined as a bitfield"""
392+
poll: Optional[Poll] = attrs.field(repr=False, default=None, converter=optional_c(Poll.from_dict))
393+
"""A poll."""
364394
interaction: Optional["MessageInteraction"] = attrs.field(repr=False, default=None)
365395
"""Sent if the message is a response to an Interaction"""
366396
components: Optional[List["models.ActionRow"]] = attrs.field(repr=False, default=None)
@@ -593,6 +623,18 @@ def proto_url(self) -> str:
593623
"""A URL like `jump_url` that uses protocols."""
594624
return f"discord://-/channels/{self._guild_id or '@me'}/{self._channel_id}/{self.id}"
595625

626+
def answer_voters(self, answer_id: int, limit: int = 0, before: Snowflake_Type | None = None) -> PollAnswerVotersIterator:
627+
"""
628+
An async iterator for getting the voters for an answer in the poll this message has.
629+
630+
Args:
631+
answer_id: The answer to get voters for
632+
after: Get messages after this user ID
633+
limit: The max number of users to return (default 25, max 100)
634+
635+
"""
636+
return PollAnswerVotersIterator(self, answer_id, limit, before)
637+
596638
async def edit(
597639
self,
598640
*,
@@ -848,6 +890,14 @@ async def publish(self) -> None:
848890
"""
849891
await self._client.http.crosspost_message(self._channel_id, self.id)
850892

893+
async def end_poll(self) -> "Message":
894+
"""
895+
Ends the poll in this message.
896+
"""
897+
message_data = await self._client.http.end_poll(self._channel_id, self.id)
898+
if message_data:
899+
return self._client.cache.place_message_data(message_data)
900+
851901

852902
def process_allowed_mentions(allowed_mentions: Optional[Union[AllowedMentions, dict]]) -> Optional[dict]:
853903
"""

0 commit comments

Comments
 (0)