discord.py: if ctx.author = guild.roles - discord.py

I am creating a command that allows specific users to block everyone.
I don't know how to write the if to make sure that if the author of the command is of that role he can read it (I'm doing this because I would like to impose different limits on certain roles).
At the same time I would like the user who executes the command to be given a user permission where he can write (this command is useful for my server when it is necessary to make important and immediate speeches.)
How could I do?
Error:
Traceback (most recent call last):
File "C:\Users\PC GIUSEPPE\PycharmProjects\untitled\venv\lib\site-packages\discord\ext\commands\bot.py", line 892, in invoke
await ctx.command.invoke(ctx)
File "C:\Users\PC GIUSEPPE\PycharmProjects\untitled\venv\lib\site-packages\discord\ext\commands\core.py", line 797, in invoke
await injected(*ctx.args, **ctx.kwargs)
File "C:\Users\PC GIUSEPPE\PycharmProjects\untitled\venv\lib\site-packages\discord\ext\commands\core.py", line 92, in wrapped
raise CommandInvokeError(exc) from exc
discord.ext.commands.errors.CommandInvokeError: Command raised an exception: NameError: name 'Guild' is not defined
Code:
#client.command(aleases=["Templock","TEMPLOCK","tl","Tl","TL"])
#commands.has_any_role('Moderatori', 'Triumvirato', 'Co-Triumvirato')
async def templock(ctx, seconds = 0, *,arg="Motivo non specificato"):
channel_ability_mention = ctx.channel.mention
channel_ability_name = ctx.channel.name
embed = discord.Embed(
color=0xa61022
)
if not seconds:
embed.set_author(
name="Per favore specifica il tempo!",
icon_url="https://cdn.discordapp.com/attachments/640563710104043530/730639329453670420/DuscePeppe_FRIULI.png"
)
await ctx.send(embed=embed, delete_after=10.0)
return
if ctx.author == Guild.roles(name='Triumvirato'):
if seconds > 600:
embed.set_author(
name="Hai superato il limite stabilito per i Triumviri!",
icon_url="https://cdn.discordapp.com/attachments/640563710104043530/730639329453670420/DuscePeppe_FRIULI.png"
)
await ctx.send(embed=embed, delete_after=10.0)
return
embed = discord.Embed(
color=0x03c03c
)

First, you didn't defined Guild, if you want the server the command was invoked, you need to replace Guild.roles to ctx.guild.roles.
Then, the way you get the triumvirato role is wrong, you can get it by id or by name this way:
#by id
triumvirato = discord.utils.get(ctx.guild.roles, id=role_id)
#by name
triumvirato = discord.utils.get(ctx.guild.roles, name="Triumvirato")
Finally, ctx.author is a Member object, not a Role object, so your if statement will never be True. To make it work, you'll have to replace this line:
if ctx.author == Guild.roles(name='Triumvirato'):
To this:
if triumvirato in ctx.author.roles:

Related

Discord.py onmessage role allocation issue

I've been trying to work this out but can't work out what i'm doing wrong, the method worked fine to delete and display the message but when I tried to get it to allocate a role at the same time I broke it
#bot.event
async def on_message(msg):
for badword in file:
if badword in msg.content.lower():
role = discord.utils.get(msg.guild.roles, name="Muted")
await msg.author.add_roles(role)
await msg.delete()
await msg.channel.send(f'{msg.author.mention}! That was a bad word! You have been muted!')
await bot.process_commands(msg)
I presume i'm missing something simple?
This is the error i'm getting:
Ignoring exception in on_message
Traceback (most recent call last):
File "/opt/virtualenvs/python3/lib/python3.8/site-packages/discord/client.py", line 343, in _run_event
await coro(*args, **kwargs)
File "main.py", line 283, in on_message
await msg.author.add_roles(role)
File "/opt/virtualenvs/python3/lib/python3.8/site-packages/discord/member.py", line 676, in add_roles
await req(guild_id, user_id, role.id, reason=reason)
AttributeError: 'NoneType' object has no attribute 'id'
Also the above is making my other bot.commands repeat indefinitely. So now when I use the random quote command it never stops til I shut off the bot:
#wisdom function
#bot.command(help="Wisdom function",
brief="Get a random wise quote")
async def wisdom(ctx):
responses = open('quotes.txt').read().splitlines()
random.seed(a=None)
response = random.choice(responses)
await ctx.send(f'Hey {ctx.message.author.mention} here is your wisdom:')
await ctx.send(response)
await req(guild_id, user_id, role.id, reason=reason)
^^^^^^^
AttributeError: 'NoneType' object has no attribute 'id'
The problem here is discord.utils.get cannot find a role called Muted, so it returns a NoneType. When you are trying to assign the role, you are essentially doing msg.author.add_roles(None). Maybe try making sure that the role exists, or referencing it by ID instead of Name.
Edit: You should also (in your quote function) send the quote in the same message as the first. (By using \n as a line-break)
Edit 2: You should use a with block to readlines from your file, because with what you have now, the file never closes. Also, read() returns a string, you cannot do readlines() off of the string. Instead do readlines() off of the file object.
Edit 3: You are processing commands for every badword in file (why it runs forever)
Refer to #Frederick Reynolds post about your errors in reading the textfile. I can point out a few things as well, however. For your on_message function, you never check if the message is from your own bot itself, which triggers the repetition of the function. To avoid this, add if msg.author == bot.user: return at the beginning of this function. Secondly, role = discord.utils.get(msg.guild.roles, name="Muted") is not able to find the Muted role for some reason, which is why it sets the value of role to None. This is why, when you call await msg.author.add_roles(role), you're basically doing await msg.author.add_roles(None). Lastly, your indentation is wrong, as you are awaiting bot.process_comands(msg) for every badword in file. Here's the fixed code for the function
#bot.event
async def on_message(msg):
if msg.author == bot.user:
return
for badword in file:
if badword in msg.content.lower():
role = discord.utils.get(msg.guild.roles, name="Muted")
await msg.author.add_roles(role)
await msg.delete()
await msg.channel.send(f'{msg.author.mention}! That was a bad word! You have been muted!')
await bot.process_commands(msg)

how to make bot assign roles when given command

i am trying to make the bot give the 'mall' role and remove the 'study hall' role. However, it keeps returning the error
Ignoring exception in on_message
Traceback (most recent call last):
File "C:\Users\frost\AppData\Local\Programs\Python\Python38-32\lib\site-packages\discord\client.py", line 333, in _run_event
await coro(*args, **kwargs)
File "D:\GalaxyConflux Master\gcclient.py", line 89, in on_message
role.id = 798193741403127818
AttributeError: 'str' object has no attribute 'id'
the code that is running is this
#client.event
async def on_message(message):
if message.content.startswith(gccmd.cmd_prfx + 'mall'):
role = 'Mall'
role.id = 798193741403127818
await message.author.add_roles(role.id)
i have tried many different approaches but each result in a similar error.
I had it just go off of the role = 'Mall' part but that did not work either.
How can I convert the role id into an actual id?
Thanks so much!
~Glimmer
here's an example peice that shows you how to add a role and remove one.
#client.command()
async def mall(ctx):
# if prefix is '-' you'd type: -mall
await user.remove_roles(#ROLE_ID)
await user.add_roles(#ROLE_ID)
await ctx.send("Mall role added!")
#client.command()
async def home(ctx):
# if prefix is '-' you'd type: -home
await user.remove_roles(#ROLE_ID)
await user.add_roles(#ROLE_ID)
await ctx.send("Home role added!")
If you want to remove multiple roles, you'd have to just add all of the roles there you want to remove, then add the one's you want.
For example, if you are heading to the mall from your house, it removes every role including the house role and adds the mall one.

I am getting a name error in my coding any one know why?

#bot.command()
#commands.has_guild_permissions(mute_members=True)
async def mute(ctx, member: discord.Member, *, Reason=None):
await Member.add_roles(get_role)
await get_role('751096892867477594')
await ctx.send(f'User {member} Has been muted')
So I am coding a mute command in discord.py and that is the code for it, but when I run the bot and try and mute my test account I get this error:
Ignoring exception in command mute:
Traceback (most recent call last):
File "C:\Users\Robin\AppData\Roaming\Python\Python37\sitepackages\discord\ext\commands\core.py", line 85, in wrapped
ret = await coro(*args, **kwargs)
File "C:\Users\Robin\Desktop\discord bot in python\bot.py", line 85, in mute
await Member.add_roles(get_role)
NameError: name ‘Member’ is not defined
The above exception was the direct cause of the following exception:
Traceback (most recent call last):
File "C:\Users\Robin\AppData\Roaming\Python\Python37\site-packages\discord\ext\commands\bot.py", line 903, in invoke
await ctx.command. invoke (ctx)
File "C:\Users\Robin\AppData\Roaming\Python\Python37\site-packages\discord\ext\commands\core.py", line 855, in invoke
await injected(“ctx.args, “*ctx.kwargs)
File "C:\Users\Robin\AppData\Roaming\Python\Python37\site-packages\discord\ext\commands\core.py", line 94, in wrapped
raise CommandInvokeError(exc) from exc
discord.ext.commands.errors.CommandInvokeError: Command raised an exception: NameError: name ‘Member’ is not defined
Member in line 4 is supposed to be lowercase like you passed it in your parameters. Also to get a role use get and role ids are supposed to be int which you passed as a str. The following code will work for you, just change id to your muted role's id.
#bot.command()
#commands.has_guild_permissions(mute_members=True)
async def mute(ctx, member: discord.Member, *, reason=None):
muted_role = discord.utils.get(ctx.guild.roles, id=750678725544247329)
await member.add_roles(muted_role, reason=reason)
await ctx.send(f'User {member} Has been muted')
You have multiple errors:
In Member.add_roles(...), Member has to be in lower case.
You need to get the role before adding it to your user.
The way you use get_role() is wrong → The role id must be an integer, not a string / Writing get_role() wont work since it's a Guild class method.
Your code should look like this:
#bot.command()
#commands.has_guild_permissions(mute_members=True)
async def mute(ctx, member: discord.Member, *, Reason=None):
role = ctx.guild.get_role(751096892867477594)
await member.add_roles(role)
await ctx.send(f'User {member.mention} Has been muted')

discord.py I can't run server-info command

I recently program with discord.py and after several searches I still can't find a way to implement this command (it also leads me to have problems with other commands that request information from the server) and therefore I need help if you can.
In this case I want to create a command that gives me the server information.
Traceback (most recent call last):
File "C:\Users\PC GIUSEPPE\PycharmProjects\untitled\venv\lib\site-packages\discord\ext\commands\bot.py", line 892, in invoke
await ctx.command.invoke(ctx)
File "C:\Users\PC GIUSEPPE\PycharmProjects\untitled\venv\lib\site-packages\discord\ext\commands\core.py", line 797, in invoke
await injected(*ctx.args, **ctx.kwargs)
File "C:\Users\PC GIUSEPPE\PycharmProjects\untitled\venv\lib\site-packages\discord\ext\commands\core.py", line 92, in wrapped
raise CommandInvokeError(exc) from exc
discord.ext.commands.errors.CommandInvokeError: Command raised an exception: NameError: name 'server' is not defined
Code:
#client.command(aliases=["serverinfo","Server_info","Serverinfo","SERVERINFO","si","Si","SI"])
#commands.has_any_role('Moderatori', 'Triumvirato', 'Co-Triumvirato', 'Senatori', '690956686147453048')
async def ServerInfo(ctx):
author = ctx.author.name
name_server = server.name
create_server = server.create
owner_server = server.owner.name
embed = discord.Embed(
title="Informazioni del server",
description=f'Tutte le informazioni generali del nostro server {name_server}',
color=0x003399
)
embed.set_thumbnail(url='')
embed.set_footer(text=f'Richiesto da: {author}')
embed.add_field(
name='Server creato il:',
value='f{create_server}',
)
embed.add_field(
name='Owner Attuale del server:',
value='f{create_server}',
)
embed.add_field(
name='Server creato il:',
value=f'{create_server}',
)
embed.add_field(
name='Server creato il:',
value=f'{owner_server}',
)
You didn't defined server in your code, that's why you have this error.
Server was the old discord.py reference for the discord server the bot is in. Now, you'll have to use Guild like so:
#client.command()
async def ServerInfo(ctx):
author = ctx.author.name
guild = ctx.guild
name = guild.name
create_server = server.created_at
owner_server = server.owner.name
(...)
You could also create a dictionnary of those informations:
#client.command()
async def ServerInfo(ctx):
author = ctx.author.name
guild = ctx.guild
infos = {
'name': guild.name
'owner': guild.owner.name
'created_at': guild.created_at
}
(...)
In case you don't really know the difference between discord.py (before v1.0) and discord.py#rewrite (after v1.0), here's a summary link.

Betting, Required arguement missing?

Im starting a new bot, which I hope can eventually start to allow users to bet. Im having trouble finalising this command as it allows the bot to run but when use the ?Coinflip command it says:
Ignoring exception in command coinflip:
Traceback (most recent call last):
File
"C:\Users\sambe\AppData\Local\Programs\Python\Python36\lib\site-packages\discord\ext\commands\bot.py",
line 859, in invoke
await ctx.command.invoke(ctx) File "C:\Users\sambe\AppData\Local\Programs\Python\Python36\lib\site-packages\discord\ext\commands\core.py",
line 718, in invoke
await self.prepare(ctx) File "C:\Users\sambe\AppData\Local\Programs\Python\Python36\lib\site-packages\discord\ext\commands\core.py",
line 682, in prepare
await self._parse_arguments(ctx) File "C:\Users\sambe\AppData\Local\Programs\Python\Python36\lib\site-packages\discord\ext\commands\core.py",
line 596, in _parse_arguments
transformed = await self.transform(ctx, param) File "C:\Users\sambe\AppData\Local\Programs\Python\Python36\lib\site-packages\discord\ext\commands\core.py",
line 442, in transform
raise MissingRequiredArgument(param) discord.ext.commands.errors.MissingRequiredArgument: guess is a
required argument that is missing.
This is the command I am using:
#bot.command(pass_context=True)
async def coinflip(ctx, guess: str, amount: float):
guesses = ('heads', 'tails')
guess = guess.lower()
if guess not in guesses:
await bot.say("Invalid guess.")
return
author = ctx.message.author
balance = get_dollars(author)
if balance < amount:
await bot.say("You don't have that much money. Your balance is ${balance:.2f}")
return
result = random.sample(guesses)
if result == guess:
await bot.say("You won!")
add_dollars(author, amount)
else:
await bot.say("You lost!")
remove_dollars(author, amount)
Id like it to give a coinflip command which gives off random numbers.
Although it just ignores the command.
This error means that you aren't passing enough arguments while using this command. You are propably sending ?coinflip instead of ?coinflip heads 12.

Resources