So i have a Discord Bot that is written in Python & Discord.py, now my question is, is it possible to do something like that:
Server_ID = 'TheServerID'
if ServerID = Server_ID:
leave
The most efficient way is to only check this if you're joining a guild right now, this is done with the discord.on_guild_join(guild) Reference. Then it's just checking the id and leaving if the id matches.
#client.event
async def on_guild_join(guild):
bad_id = 12345
if guild.id == bad_id:
await guild.leave()
In order to get the server id you have ctx.guild.id which is of type int, then you can compare it to any other int you want.
And if you want the bot to leave the serveur, you have to use guild.leave() which is a coroutine, so make sure to put await.
You code should looks like this:
server_id = <the id you want to compare>
if ctx.guild.id == server_id:
await ctx.guild.leave()
Make sure you put this code into an asynchronous function that would be maybe an event or a command.
If you have troubles to deal with discord.py, please refere to the documentation.
Related
So I'm creating a bot that can change the perms of roles. and to start I wanted to code a thing that allows me see and check what role has been mentioned. I want the identification to be open to all roles not just one because later on I want to be able to change the perms of multiple roles at once.
#client.event
async def on_message(message):
if message == client.user:
return
if message.channel.name in ['general']:
if message.content.lower().startswith('!rc'):
role = str(message.role.id)
await message.channel.send (f'{message.role.mention}')
return
So far I have tried doing this where I create a .startswith for the initial command then I create a "role" variable that I then use to mention that role but this doesn't work, can someone help/point me in the right direction in getting this?
Don't use on_message event for these type of commands because you would need to put a bunch of code to solve this problem with that event. Use the below code which helps to solve your problem in an easy manner
#client.command()
async def role(ctx,role:discord.Role):
if ctx.channel.name=="general":
await ctx.send(role.mention)
I want my bot to display some information about a user when they leave. Here's my code:
#client.event
async def on_member_remove(member):
channel = client.get_channel(810613415185350666)
mention = []
for role in member.roles:
if role.name != "#everyone":
mention.append(role.mention)
b = ", ".join(mention)
await channel.send(f"{member} has left the server. Roles: {b}")
Now when the event is triggered, it tells me that they've left (as expected). However, it does not show any roles even though they had several. I would assume this is because they are no longer in the server, which means they technically don't have any roles.
How would I fix this?
on the doc the return is member, but i think that when the member left the server the argument of on_member_remove from memberbecome user so it doesn't haves roles. So if that is correct you need to save in file/database the roles of the members at every on_members_update
MY BAD! This code works fine, but the user that was leaving simply didn't have any roles to display... I'm an idiot, sorry about that. Have a good day :)
(Would delete this question if it'd let me)
I have been trying to get this to work for about an hour now, but my dumb brain cannot figure it out. basically i want to get my bot to set it's own nickname when someone says (prefix)name (namechangeto)
#client.command(aliases=["nick", "name"])
async def nickname(ctx, name="Bot"):
user = guild.me()
await user.edit(nick=name)
any help appreciated
(also sorry for bad formatting, and i know this code probably makes some people cringe lol im sorry)
For me the problem in your code is that your variable guild is not defined, so you have to use ctx.guild to get the good guild. Besides that, discord.Guild.me is not a function (callable with ()) but an attribute, you just have to use guild.me.
So you can try to make :
user = ctx.guild.me
await user.edit(nick=name)
In addition to that, it's not really the problem but an advice, you can use async def nickname(ctx, *, name="Bot"): instead of async def nickname(ctx, name="Bot"): to allow user to set a nickname with spaces in it.
So your final code for me is that :
#client.command(aliases=["nick", "name"])
async def nickname(ctx, *, name="Bot"):
user = ctx.guild.me
await user.edit(nick=name)
Have a nice day!
Baptiste
I want my Discord bot to send a certain message, For example: "Hello" when he joins a new server. The bot should search for the top channel to write to and then send the message there.
i saw this, but this isn't helpful to me
async def on_guild_join(guild):
general = find(lambda x: x.name == 'general', guild.text_channels)
if general and general.permissions_for(guild.me).send_messages:
await general.send('Hello {}!'.format(guild.name))```
The code you used is actually very helpful, as it contains all of the building blocks you need:
The on_guild_join event
The list of all channels in order from top to bottom (according to the official reference). If you want to get the "top channel" you can therefore just use guild.text_channels[0]
checking the permissions of said channel
async def on_guild_join(guild):
general = guild.text_channels[0]
if general and general.permissions_for(guild.me).send_messages:
await general.send('Hello {}!'.format(guild.name))
else:
# raise an error
Now one problem you might encounter is the fact that if the top channel is something like an announcement channel, you might not have permissions to message in it. So logically you would want to try the next channel and if that doesn't work, the next etc. You can do this in a normal for loop:
async def on_guild_join(guild):
for general in guild.text_channels:
if general and general.permissions_for(guild.me).send_messages:
await general.send('Hello {}!'.format(guild.name))
return
print('I could not send a message in any channel!')
So in actuality, the piece of code you said was "not useful" was actually the key to doing the thing you want. Next time please be concise and say what of it is not useful instead of just saying "This whole thing is not useful because it does not do the thing I want".
I would like to grab user input from the user when they enter a certain command and store the input into a variable (but not the command) so that I can do things with it.
As an example, when the user types "!id 500", I want the bot to type "500" in the channel. I have tried just using message.content but it doesn't work properly because the bot spams it indefinitely, plus it shows the command as well.
#client.event
async def on_message(message):
if message.content.startswith("!id"):
await client.send_message(message.channel, message.content)
Sorry if this is a silly question, but any help would mean a lot.
If you want the bot to just send the message of the user without the command part ("!id") you'll have to specify which part of the string you want to send back. Since strings are really just lists of characters you can specify what part of the string you want by asking for an index.
For example:
"This is an example"[1]
returns "h".
In your case you just want to get rid of the beginning part of the string which can be done like so:
#client.event
async def on_message(message):
if message.content.startswith("!id"):
await client.send_message(message.channel, message.content[3:])
this works because it sends the string back starting with the 4th index place (indexes start at 0 so really [3] is starting at the fourth value)
This also applies if you just want to save the user's message as a variable as you can just do this:
userInput = message.content[3:]
You read more about string manipulation at the python docs.
I would use commands extension - https://github.com/Rapptz/discord.py/blob/async/examples/basic_bot.py
Then make a command like,
#bot.command(pass_context=True)
async def id(ctx, number : int):
await bot.say(number)
The reason your bot spams the text is because your bot is saying the command, which it follow. You need to block your bot from counting your output as a command. You could block it by:
if message.author.bot: return.
This will return None if the author is a bot. Or, you could just block your bot's own id. You won't need to do this if you actually get your command to work correctly, but you should still add it. Second of all, the way I separate the command and arguments is
cmd = message.content.split()[0].lower()[1:]
args = message.content.split()[1:]
With these variables, you could do
#client.event
async def on_message(message):
if message.content.startswith('!'):
if message.author.bot: return # Blocks bots from using commands.
cmd = message.content.split()[0].lower()[1:]
args = message.content.split()[1:]
if command == "id":
await client.send_message(message.channel, ' '.join(args)