Skip to content
Advertisement

Why I can’t send messages in a @tasks.loop in discord.py?

I have a problem: I can’t send message in a @tasks.loop() function.

When I try to get the channel object with self.client.get_channel(channlid), it return me a Nonetype variable.

My code :

import nextcord
from nextcord.ext import commands
from nextcord.ext import tasks
from datetime import date, datetime

channlid = 934533675083792465
global channel
def setup(client):
    client.add_cog(Blagues(client))

class Blagues(commands.Cog):
    def __init__(self, client):
        self.client = client
        self.index = 0
        self.blaguedujour.start()
    
    @tasks.loop(seconds=1)
    async def blaguedujour(self):
        channel = self.client.get_channel(channlid)
        channel.send("a")


    
    @commands.command()
    async def test(self, ctx):
        await ctx.send("test")

my error:

PS C:Usersbaron_btjit4i> & C:/Users/baron_btjit4i/AppData/Local/Programs/Python/Python39/python.exe c:/Users/baron_btjit4i/Desktop/Autrebot/main.py
Unhandled exception in internal background task 'blaguedujour'.
Traceback (most recent call last):
  File "C:Usersbaron_btjit4iAppDataLocalProgramsPythonPython39libsite-packagesnextcordexttasks__init__.py", line 168, in _loop
    await self.coro(*args, **kwargs)
  File "c:Usersbaron_btjit4iDesktopAutrebotCogsblagues.py", line 20, in blaguedujour
    channel.send("a")
AttributeError: 'NoneType' object has no attribute 'send'

Can you help me ?

Advertisement

Answer

Problem

You’re calling client.get_channel before the client is ready. So, the client cannot find the channel you’re looking for, and channel becomes None.

This happens because you are starting blaguedujour in the initialization of your Blagues class.

Solution

Explanation

Instead of starting the task in __init__, you should start in when the client is ready, in on_ready. This can be accomplished by adding a commands.Cog.listener() in your Blagues cog.

Code

class Blagues(commands.Cog):
    def __init__(self, client):
        self.client = client
        self.index = 0
    
    @tasks.loop(seconds=1)
    async def blaguedujour(self):
        channel = self.client.get_channel(channlid)
        channel.send("a")

    @commands.Cog.listener()
    async def on_ready():
        self.blaguedujour.start()

    
    @commands.command()
    async def test(self, ctx):
        await ctx.send("test")

Aside

channel.send() is a coroutine: it must be awaited. Use await channel.send("a") instead.

Advertisement