简体   繁体   中英

Command cooldown in discord.py

I want commands for my discord bot to have cooldowns. I've tried other methods, but none of them seemed to work for what I have.

@client.event
async def on_message(message):
  if message.content == 'shear sheep':
    await message.channel.send('you sheared your sheep, gaining 1 wool.')
    #cooldown?

It will be better if you use @bot.command , not event . Then, you must just put @commands.cooldown(1, {seconds off cooldown}, commands.BucketType.user) below @bot.command

Example:

@bot.command
@commands.cooldown(1, 15, commands.BucketType.user)
async def shearsheep(ctx):
    await ctx.send('you sheared your sheep, gaining 1 wool.')

Then, you can make an error handler, that will send a message, when you try to use a command, but it will be on cooldown, for example:

@bot.event
async def on_command_error(ctx, error):
    if isinstance(error, commands.CommandOnCooldown):
        await ctx.send('This command is on cooldown, you can use it in {round(error.retry_after, 2)}')

I think it's the easiest method.

I would suggest using a variable to track weather the command has been used or before the cooldown.

import time
cooldown = True

@client.event
async def on_message(message):
    global cooldown
    if message.content == 'shear sheep' and cooldown:
        cooldown = False
        await message.channel.send('you sheared your sheep, gaining 1 wool.')
        time.sleep(1)
        cooldown = True

This will add a cooldown for all users, if you want to add a cooldown for each user, use a table to check weather if an individual user has used the command.

import time
cooldown = []

@client.event
async def on_message(message):
    global cooldown
    if message.content == 'shear sheep' and cooldown.count(message.author.id) == 0:
        cooldown.append(message.author.id)
        await message.channel.send('you sheared your sheep, gaining 1 wool.')
        time.sleep(1)
        cooldown.remove(message.author.id)

Since you're interfacing with on_message for cooldowns, you would need to create a custom cooldown mapping using commands.CooldownMapping.from_cooldown() (NOTE: THIS IS NOT COVERED IN THE DOCS, THIS IS WHAT WAS GIVEN BY RAPPTZ), get the bucket with the method get_bucket(message) and pass your message object into message, then use update_rate_limit() on the bucket to check if you're rate-limited or not(returns a bool). However, this system is not reliable at all since it will trigger the cooldown for normal messages as well. Using commands is much easier since it is fully documented but with the downside of not being able to use in on_message.

Both systems have downsides to them, but using commands ultimately is more documented and powerful

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM