Skip to content
Advertisement

Triggering method from within a loop with Python and Pycord

I’m playing around with Pycord and trying to send a message to a channel X for each element in an array.

The following class will throw a TypeError: MyClient.on_ready() missing 1 required positional argument: 'message' indicating that MyClient.on_ready() needs 2 arguments, one for self, one for message, but every example on how to pass arguments to class methods were only sending the argument.

class MyClient(discord.Client):
    def __init__(self, *args, **kwargs):
        super().__init__(*args, **kwargs)
    
    async def on_ready(self, message):
        channel = self.get_channel(123)  # Your channel ID goes here
        await channel.send(message)

client = MyClient()

for comment in comments:   
    if  comment['data']['parent_id'].startswith("t1") and comment['data']['name'] not in comments_json:
        wop = comment['data']['permalink']
        client.on_ready(wop)
        client.run("xxx")   

What am I missing?

EDIT: Added changes from comment, now error message reads as follow:

coroutine 'MyClient.on_ready' was never awaited
  client.on_ready(wop)
RuntimeWarning: Enable tracemalloc to get the object allocation traceback
Ignoring exception in on_ready
Traceback (most recent call last):
  File "C:Python310libsite-packagesdiscordclient.py", line 352, in _run_event
    await coro(*args, **kwargs)
TypeError: MyClient.on_ready() missing 1 required positional argument: 'message'

Advertisement

Answer

The error you got is because on_ready doesn’t take any arguments

Maybe something like this is what you are looking for, gets an channel object and sends an array (also subclassed just like the code you send)

import discord
import os
import asyncio
from typing import Iterable, Optional, Any


class MyClient(discord.Client):

    # > trying to send a message to a channel X for each element in an array.
    def __init__(
        self,
        channel_to_send: int,
        array: Iterable,
        *,
        loop: Optional[asyncio.AbstractEventLoop] = None,
        **options: Any
    ):
        self.channel_to_send = channel_to_send
        self.array = array
        super().__init__(loop=loop, **options)

    async def on_ready(self):
        channel_ = await self.fetch_channel(self.channel_to_send)
        for element in self.array:
            await channel_.send(element)


channel_id = 917803321929134133 # Replace this with that of yours 
array = ["foo", "bar", "this", "is", "working"] # Replace this with that of yours

client = MyClient(channel_id, array)
client.run(os.getenv("DISCORD_TOKEN"))

Result : result

User contributions licensed under: CC BY-SA
4 People found this is helpful
Advertisement