Korol_Kotov
@Korol_Kotov
Человек

Как сделать кулдаун на команду discord.py?

Я пытаюсь сделать кулдаун на команду с помощью asyncio.sleep(time) и базы данных json:
@commands.command()
	async def work(self, ctx):
		with open('Databases/economy.json','r') as f:
			money = json.load(f)

		with open('Databases/queue.json','r') as f:
			queue = json.load(f)

		if not str(ctx.guild.id) in queue:
			queue[str(ctx.guild.id)] = {}
			queue[str(ctx.guild.id)]["Work"] = {}
			queue[str(ctx.guild.id)]["Rob"] = {}

			with open('Databases/queue.json','w') as f:
			    json.dump(queue, f, indent=4)

		if not str(ctx.author.id) in money[str(ctx.guild.id)]["Users"]:
			money[str(ctx.guild.id)]["Banks"][str(ctx.author.id)] = 0
			money[str(ctx.guild.id)]["Users"][str(ctx.author.id)] = 0
			
			with open('Databases/queue.json','w') as f:
			    json.dump(queue, f, indent=4)

		if not str(ctx.author.id) in queue[str(ctx.guild.id)]["Work"]:
			NotQueueWork = discord.Embed(description = f'**{ctx.author.mention}, вы поработали и получили `{money[str(ctx.guild.id)]["Settings"]["WorkMoney"]}` {money[str(ctx.guild.id)]["Settings"]["EconomyEmoji"]}!**', color = 0xd6ff8f)
			NotQueueWork.set_author(name = f'Работа', icon_url = self.client.user.avatar_url)

			await ctx.send(embed = NotQueueWork)

			money[str(ctx.guild.id)]["Users"][str(ctx.author.id)] += money[str(ctx.guild.id)]["Settings"]["WorkMoney"]

			with open('Databases/economy.json','w') as f:
			    json.dump(money, f, indent=4)
			    
			needMoney = int(money[str(ctx.guild.id)]["Settings"]["WorkTime"])
			
			timestamp = datetime.timestamp(datetime.now(timezone.utc))
			
			nowdate = int(timestamp) + 10800 + needMoney
			
			nowtimestamp = datetime.fromtimestamp(nowdate, timezone.utc)

			queue[str(ctx.guild.id)]["Work"][str(ctx.author.id)] = {}
			queue[str(ctx.guild.id)]["Work"][str(ctx.author.id)]["WorkGG"] = str(nowtimestamp.strftime("%Y.%m.%d %H:%M:%S"))

			with open('Databases/queue.json','w') as f:
			    json.dump(queue, f, indent=4)

			await wait(needMoney)

			del queue[str(ctx.guild.id)]["Work"][str(ctx.author.id)]

			with open('Databases/queue.json','w') as f:
			    json.dump(queue, f, indent=4)
			
		if str(ctx.author.id) in queue[str(ctx.guild.id)]["Work"]:   
		    InQueueWork = discord.Embed(description = f'**{ctx.author.mention}, вы устали, приходите в `{queue[str(ctx.guild.id)]["Work"][str(ctx.author.id)]["WorkGG"]}` по МСК!**', color = 0xff0303)
		    InQueueWork.set_author(name = f'Работа', icon_url = self.client.user.avatar_url)
		    
		    return await ctx.send(embed = InQueueWork)

Но, такая ситуация:
У меня стоит кулдаун 3 часа, я пишу команду, получаю монеты и жду 3 часа. Проходит 4 часа, я пишу команду, но оно пишет: вы устали, приходите в 16:35:36. У меня время 17:35:36
Жду еще, но результат тот же, тоесть кулдаун не работает.
Я пытался сделать его через @cooldown.cooldown(rate, per, type)
Но, тут тоже возникает проблемка:
Я хочу сделать, чтобы он брал время которое установлено в базе данных и устанавливал его в per кулдауна, но у меня ничего не выходит.
Помогите, подскажите как сделать хороший кулдаун? Если что-то нужно, уточняйте.
  • Вопрос задан
  • 63 просмотра
Решения вопроса 1
SoreMix
@SoreMix Куратор тега Python
yellow
В коде не разбирался, быстро глянул, но по-моему вы очень его перегрузили. Если вы хотите делать проверку руками, то не знаю зачем ждать через sleep и тд.

Вызывается ваша команда work, происходит выдача человеку денег. Записывается таймстамп выдачи в в ваш json файл. Тут уже от нужды зависит, можете записывать только время последней выдачи, можно время последней выдачи + время, когда в следующий раз нужно будет выдать и тд. Допустим, для примера будет только одно поле - время последнего выполнения команды в виде таймстампа. Далее вы просто берете время последнего выполнения и складываете его с вашей задержкой для команды (в секундах, естественно), и если получившееся число меньше текущего таймстампа - выполняете команду.

def work():
    with open('users.json', 'r', encoding='utf-8') as f:
        users = json.load(f)

    if ctx.author.id not in users:
        users[ctx.author.id] = {'last_work_time': 0}

    current_timestamp = int(time.time())
    work_cooldown = 60*60 # допустим задержка 1 час

    last_work_time = users[ctx.author.id]['last_work_time']

    if last_work_time + work_cooldown <= current_timestamp or last_work_time == 0:
        send_message('Ваша оплата: xxx')
        users[ctx.author.id]['last_work_time'] = current_timestamp

        with open('users.json', 'w', encoding='utf-8') as f:
            json.dump(users, f)
Ответ написан
Пригласить эксперта
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Войти через центр авторизации
Похожие вопросы