In my bot made with pyrogram, I wrote a code that asks the user to answer the messages after 60 seconds with asyncio sleep, but if too many people trigger this code, my bot does not receive any command until any of these waiting processes are over, how can I solve this problem?
My code:
from pyrogram import Client, filters
from pyrogram.types import Message
import asyncio
app = Client("my_account", bot_token="", api_id=0, api_hash="")
#app.on_message(filters.command("hello"))
async def hello(_, message: Message):
await message.reply_text("Hello!")
#app.on_message(filters.text)
async def answer(_, message: Message):
await asyncio.sleep(60)
await message.reply_text("Heyy!")
app.run()
Related
I followed a tutorial to make add a basic music function to a discord bot, but it doesnt respond to any commands. I get the "henlo frens i is alieving" message as to indicate that the bot is ready, and there are no errors showing up. But then when i try to use the ping command i get no response, and nothing shows up in the terminal unlike the other bots i've written.
from plznodie import plznodie
from discord.ext import commands
import music
import time
#vars
cogs=[music]
intents = discord.Intents()
intents.all()
client = commands.Bot(command_prefix = "!" , intents=intents)
intents.members = True
activvv = discord.Game("you guys complain")
#config
for i in range(len(cogs)):
cogs[i].setup(client)
#client.event
async def on_ready ():
await client.change_presence(status = discord.Status.online, activity = activvv)
print("Henlo frens i is alieving")
#client.command()
async def ping(ctx):
before = time.monotonic()
message = await ctx.send("Pong!")
ping = (time.monotonic() - before) * 1000
await message.edit(content=f"Pong! `{int(ping)}ms`")
client.run("TOKEN")```
Don't change_presence (or make API calls) in on_ready within your Bot or Client.
Discord has a high chance to completely disconnect you during the READY or GUILD_CREATE events (1006 close code) and there is nothing you can do to prevent it.
Instead set the activity and status kwargs in the constructor of these Classes.
bot = commands.Bot(command_prefix="!", activity=..., status=...)
As noted in the docs, on_ready is also triggered multiple times, not just once.
I can further confirm this because running your code snippet (without on_ready defined) on my machine actually worked :
to process commands you need to add on_message function
#client.event
async def on_message(msg):
await client.process_commands(msg)
So this is part of my code, I can provide the entire thing if needed.
Previously my bot is all well when using this pretty standard status looping (the first bit). But since I tried the second version I started to receive
socket.send() raised exception.
And now running the bot makes all async commands unusable. Despite the commands are all correctly sent, nothing returns, and even the console doesn't show any errors for some reason... Does anyone understand why including client.change_presence(...) under on_ready() doesn't seem to work and why it conflicts with any other previously working commands?
status = cycle(['Vice-Captain of The Perkers', 'At your service...', 'AHIHIP Forever', 'Hey there!']) #Status update
#tasks.loop(seconds=7.5)
async def change_status():
await client.change_presence(activity=discord.Game(next(status)))
#client.event
async def on_ready():
change_status.start()
print("#G11 - The Perkers Vice-Captain Little Green reporting.")
time.sleep(0.75)
print("What can I help with, sir?")```
import discord
import time
import datetime
import random
import math
import pytz
import dns
import os
import pymongo
from pymongo import MongoClient
from discord.ext import commands,tasks
from itertools import cycle
from discord.utils import get
from typing import List
client = commands.Bot(command_prefix='lg')
#tasks.loop(seconds=5)
async def status_change():
while True:
await client.wait_until_ready()
await client.change_presence(status=discord.Status.idle, activity=discord.Game(name='Vice-Captain of The Perkers'))
time.sleep(10)
await client.change_presence(status=discord.Status.do_not_disturb, activity=discord.Game(name='At your service...'))
time.sleep(10)
await client.change_presence(status=discord.Status.online, activity=discord.Game(name='AHIHIP Forever!'))
time.sleep(10)
#client.event
async def on_ready():
print("#G11 - The Perkers Vice-Captain Little Green reporting.")
time.sleep(0.75)
print("What can I help with, sir?")
time.sleep(3)
client.loop.create_task(status_change())
#client.command()
async def hallo(ctx):
await ctx.send('Hi!')
client.run('Token')
Main goal:
Send a message to a channel every Wednesday at 08:00
This is my current code:
import schedule
import time
import discord
import asyncio
from discord.ext import commands, tasks
from discord.ext.tasks import loop
client = discord.Client()
# IMPORTANT
channel =
botToken = ""
async def sendloop():
while True:
schedule.run_pending()
await asyncio.sleep(1)
#client.event
async def on_ready():
general_channel = client.get_channel(channel)
print('ready')
schedule.every(2).seconds.do(lambda:loop.create_task(general_channel.send('TEST')))
client.run(botToken)
So far, there are no errors, just stuck on "ready". I am a beginner using VS Code.
I wouldn't recommend using scheduler, since discord the extension task which can do the same as what you are trying to implement in your code:
from discord.ext import commands, tasks
ch = id_channel
client = commands.Bot(command_prefix='.')
TOKEN = "Token"
#every week at this time, you can change this to seconds=2
#to replicate what you have been testing
#tasks.loop(hours=168)
async def every_wednesday():
message_channel = client.get_channel(ch)
await message_channel.send("Your message")
#every_wednesday.before_loop
async def before():
await client.wait_until_ready()
every_wednesday.start()
client.run(TOKEN)
If you were to run this code on the time you want it to be repeated, it will accomplish what you want. Another approach is checking on the before() function to check if it is the right time to run if you don't want to wait and run the code on the day you want this to run.
But if you really want to use the schedule module, this post my help you: Discord.py Time Schedule
I am trying to set up a schedule to run a subroutine. I am trying to use the subroutine example to send a message to a discord channel when the schedule is triggered. At first I attempted to try and just send the message but got an error. I then tried looking into how to solve this and have tried different ways using asyncio all of which have not worked.
If anyone is able to give me any pointers on how I could do this then it would be much appreciated.
import discord
import asyncio
import time
import schedule # pip install schedule
client = discord.Client()
#client.event
async def on_ready():
print("Connected!")
async def example(message):
await client.get_channel(CHANNEL ID).send(message)
client.run(SECRET KEY)
def scheduledEvent():
loop = asyncio.get_event_loop()
loop.run_until_complete(example("Test Message"))
loop.close()
schedule.every().minute.do(scheduledEvent)
while True:
schedule.run_pending()
time.sleep(1)
You can't run your blocking schedule code in the same thread as your asynchronous event loop (your current code won't even try to schedule tasks until the bot has already disconnected). Instead, you should use the built in tasks extension which allows you to schedule tasks.
import discord
from discord.ext import tasks, commands
CHANNEL_ID = 1234
TOKEN = 'abc'
client = discord.Client()
#client.event
async def on_ready():
print("Connected!")
#tasks.loop(minutes=1)
async def example():
await client.get_channel(CHANNEL_ID).send("Test Message")
#example.before_loop
async def before_example():
await client.wait_until_ready()
example.start()
clinet.run(TOKEN)
I am writing a discord bot with discord.py.
I wrote an initial version but I decided it all needed reorganizing so I moved code to different files.
The code is all the same as it was before but now when I boot up the bot, the bot detects no messages being sent in any server unless the message came from the bot itself.
The main code that handles the client is:
import discord
import time
from command_list import *
from resource_functions import grab_setting_from_category
print("Main initialized")
client = discord.Client()
token = "BOT TOKEN"
prefix = "!"
#client.event
async def on_ready():
print("*** BOT IS READY ***")
async def server_count_loop():
while True:
servers = client.servers
await client.change_presence(
game=discord.Game(name=" in {0} Servers".format(str(len(servers)))))
time.sleep(10)
for server in client.servers:
for channel in server.channels:
if channel.name == "general":
await client.send_message(channel, content="Bot Online")
await server_count_loop()
#client.event
async def on_message(message):
print("Message detected from {0} as '{1}'".format(message.author, message.content))
if not message.author.bot:
global prefix
prefix = grab_setting_from_category(message.server.id, "server", "prefix")
if message.content.startswith(prefix):
for i in range(0,len(commands)):
key = list(commands.keys())[i]
table = list(commands.values())[i]
if message.content.startswith(prefix+key):
table["function"](message, commands)
client.run(token)
In the code there's the print(...) at the start of the on_message function which I am using as a basic way to let me know if the bot is detecting messages. The print statement prints whenever the bot sends a message in on_ready but no messages from other users on Discord are triggering the function.
Don't use:
time.sleep(...)
Instead, use:
await asyncio.sleep(...)
time.sleep is a blocking call, it blocks the asyncio loop to continue to run. That is why you need to have an asynchronous .sleep(...) method.