简体   繁体   中英

Discord.py bot returning multiple messages

Hi O'm having a problem with this simple little python discord bot module. Whenever I use command, it seems to be returning 4 or 5 responses even though it's coded to only return one. I'm I overlooking something, Is there a simple fix for this?

Here is the code I'm working with

import discord
import os
import logging as log
from datetime import datetime,timedelta
from discord.ext import commands
from discord import Forbidden, HTTPException

from .utils.dataIO import dataIO
from .utils import checks


import asyncio

class lurkout:
"""
add roles to new members after x amount of time
"""

def __init__(self, bot):
    self.bot = bot

@commands.command(pass_context=True, no_pm=True)
@checks.is_owner()
async def huntlurkers(self, ctx, *_):
    """Look for lurkers"""

    serverid = '465536300452151298'
    server = self.bot.get_server(serverid)

    for member in server.members:
        lurker_role = discord.utils.get(member.server.roles, name="Lurker")
        if lurker_role not in member.roles:
            await self.bot.say("No lurkers seen within the last 3 days.")
        else:
            await self.check_roles(serverid, member)
            await self.bot.say("Success! You have manually added the Lurker role to those who haven't received a members role in 3 days.")
            return


@commands.command(pass_context=True, no_pm=True)
@checks.is_owner()
async def kicklurkers(self, ctx, *_):
    """Mass kick lurkers"""

    serverid = '465536300452151298'
    server = self.bot.get_server(serverid)

    for member in server.members:
        lurker_role = discord.utils.get(member.server.roles, name="Lurker")
        if lurker_role not in member.roles:
            await self.bot.send_message("There are no lurkers to kick.")
        else:
            if lurker_role in member.roles:
                await self.check_lurkers(serverid, member)
                await self.bot.send_message("Kicked some lurkers :D.")
                return


async def check_roles(self, serverid, member: discord.Member, *_):

    serverid = '465536300452151298'
    server = self.bot.get_server(serverid)
    lurker_role = discord.utils.get(member.server.roles, name="Lurker")
    members_role = discord.utils.get(member.server.roles, name="Members")

    for member in server.members:
         if member.joined_at + timedelta(days=3) <= datetime.today():
            if members_role not in member.roles:    
                try:
                    await self.bot.add_roles(member, lurker_role)
                    log.info("[SUCCESS] Changing role of "+str(member)+" succeeded")
                except (Forbidden, HTTPException) as e:
                    log.info("[FAILURE] Changing role of "+str(member)+" failed")


async def check_lurkers(self, serverid, member: discord.Member, *_):

    serverid = '465536300452151298'
    server = self.bot.get_server(serverid)
    lurker_role = discord.utils.get(member.server.roles, name="Lurker")
    members_role = discord.utils.get(member.server.roles, name="Members")

    for member in list(self.bot.get_all_members()):
         if member.joined_at + timedelta(days=0) <= datetime.today():
            if lurker_role in member.roles:    
                try:
                    await self.bot.kick(member)
                    log.info("[SUCCESS] Changing role of "+str(member)+" succeeded")
                except (Forbidden, HTTPException) as e:
                    log.info("[FAILURE] Changing role of "+str(member)+" failed")


async def check_day(self):
    tomorrow = datetime.now()+timedelta(days=1)
    midnight = datetime(year=tomorrow.year, month=tomorrow.month, 
                    day=tomorrow.day, hour=0, minute=0, second=0)

    await asyncio.sleep((midnight - datetime.now()).seconds)
    print("About to start")
    while self is self.bot.get_cog("check_roles"):

        await self.autoaddrole_update()

        await asyncio.sleep(86400) # Wait 24 hours



def setup(bot):
    q = lurkout(bot)
    loop = asyncio.get_event_loop()
    loop.create_task(q.check_day())
    bot.add_cog(q)

The issue persists with the async def huntlurkers(self, ctx, *_): and async def kicklurkers(self, ctx, *_): commands and the await statements return about 4 times.

Edit:

Here is the edit I have attempted to put in to my code the issue I get is local variable 'member' referenced before assignment

@commands.command(pass_context=True, no_pm=True)
@checks.is_owner()
async def kicklurkers(self, ctx, *_):
    """Mass kick lurkers"""

    serverid = '465536300452151298'
    server = self.bot.get_server(serverid) # This could probably be ctx.message.server
    lurker_role = discord.utils.get(server.roles, name="Lurker")
    member_role = discord.utils.get(server.roles, name="Members")
    any_lurkers = False
    if member_role not in member.roles:
        for member in server.members:
            if lurker_role in member.roles:
                if member.joined_at + timedelta(days=3) <= datetime.today():
                    await self.bot.kick(member)
                    any_lurkers=True
            if any_lurkers:
                await self.bot.say("Kicked all lurkers!")
            else:
                await self.bot.say("No lurkers to kick!")

Your commands loop over the members of a server. For each member , if they are not a lurker you send a message. If they are a lurker, you do something with that member, then stop processing. From the messages you're sending, it seems that you instead want to process all the users, then print one of the two messages depending on whether or not you discover any lurkers.

@commands.command(pass_context=True, no_pm=True)
@checks.is_owner()
async def kicklurkers(self, ctx, *_):
    """Mass kick lurkers"""

    serverid = '465536300452151298'
    server = self.bot.get_server(serverid) # This could probably be ctx.message.server
    lurker_role = discord.utils.get(server.roles, name="Lurker")
    member_role = discord.utils.get(server.roles, name="Members")
    any_lurkers = False
    for member in server.members:
        if member_role not in member.roles and lurker_role in member.roles:
            if member.joined_at + timedelta(days=3) <= datetime.today():
                await self.bot.kick(member)
                any_lurkers=True
    if any_lurkers:
        await self.bot.say("Kicked all lurkers!")
    else:
        await self.bot.say("No lurkers to kick!")

I don't understand what your check_lurkers coroutine is trying to accomplish. Is it to check if a specific Member is a lurker, to kick all the lurkers from a server, or to change their roles?

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