async def update_options(self, updated_fields=None): logger.info(f"Updating command fields: {updated_fields}") await self.role_processor.update_choices(updated_fields) await self.group_processor.update_choices(updated_fields) if db_utils.is_updated(updated_fields, "group"): group_choices = self.group_processor.choices group_commands = [self.group_info, self.group_delete, self.role_snapshot_all] for command in group_commands: command.options[0]["choices"] = group_choices self.role_snapshot_role.options[1]["choices"] = group_choices if self._sider_group is None: self._sider_group = await RoleGroup.get_or_none(name="Sider") if db_utils.is_updated(updated_fields, "role"): crews = [await Role.get_or_none(name=role) for role in (utils.stream_crew_role, utils.update_crew_role, utils.bot_crew_role)] crews = [create_choice(name=role.name, value=role.id) for role in crews if role is not None] self.crew_join.options[0]["choices"] = crews self.crew_leave.options[0]["choices"] = crews self.has_crews = bool(crews) if self._sider_group is not None: sider_choices = [create_choice(name=role.name, value=role.id) for role in await Role.filter(group=self._sider_group)][:24] sider_choices.insert(0, create_choice(name="Noside", value=-1)) self.side_join.options[0]["choices"] = sider_choices await self.bot.slash.sync_all_commands()
class Help(commands.Cog): def __init__(self, bot): self.bot = bot # --- SLASH COMMANDS --- # @cog_ext.cog_slash(name='help', description='Detailed list of bot commands!', guild_ids=guild_ids, options=[ create_option(name='module', description='Choose category!', required=True, option_type=3, choices=[ create_choice( name='Administration', value='admin'), create_choice(name='Info', value='info'), create_choice(name='Market', value='market') ]) ]) async def _help(self, ctx: SlashContext, module: str): if module == 'admin': embed = discord.Embed(title='Administration', description=' ', colour=discord.Colour.blurple()) embed.set_author(name='Commands List', icon_url=BOT_AVATAR) embed.add_field(name=';prune __Amount__', value='Removes the amount of messages specified', inline=False) embed.add_field(name=';mute __@user / user ID__', value='Mutes the specified user', inline=False) embed.add_field(name=';unmute __@user / user ID__', value='Unmutes the specified user', inline=False) embed.set_footer( text='User IDs can be found by turning on "Developer Mode"') elif module == 'info': embed = discord.Embed(title='Info', description=' ', colour=discord.Colour.blurple()) embed.set_author(name='Commands List', icon_url=BOT_AVATAR) embed.add_field(name=';ping', value='pong!', inline=False) elif module == 'market': embed = discord.Embed(title='Market', description=' ', colour=discord.Colour.blurple()) embed.set_author(name='Commands List', icon_url=BOT_AVATAR) embed.add_field(name=';coin __1-100__ or ;coin __name__', value='Displays Name / Current Price', inline=False) embed.add_field(name=';top __1-100__', value='Displays the top # coins', inline=False) await ctx.send(embeds=[embed])
def update_options(self): choices = [ create_choice(name=check.capitalize(), value=check) for check in self.checks.keys() ] choices = [create_choice(name="All", value="all")] + choices + \ [create_choice(name="None (stats and info only)", value="none")] self.check_member.options[1]["choices"] = choices self.check_server.options[0]["choices"] = choices
async def starboard_autocomplete(self, ctx: AutoCompleteContext): if ctx.name != "starboard": return guild_data = await self.bot.mongo.get_guild_data(ctx.guild_id) starboard_data = guild_data.starboard if not starboard_data: return if starboard_data.blacklist is None: return if ctx.focused_option == "channel": channel_ids = starboard_data.blacklist.get("channels") if not channel_ids: return channels: List[TextChannel] = [ ctx.guild.get_channel(channel_id) for channel_id in channel_ids ] choices = [ create_choice(name=channel.name, value=str(channel.id)) for channel in channels if channel.name.startswith(ctx.user_input) ][:25] elif ctx.focused_option == "member": member_ids = starboard_data.blacklist.get("members") if not member_ids: return members: List[Member] = [ ctx.guild.get_member(member_id) for member_id in member_ids ] choices = [ create_choice(name=member.display_name, value=str(member.id)) for member in members if member.display_name.startswith(ctx.user_input) ][:25] elif ctx.focused_option == "role": role_ids = starboard_data.blacklist.get("roles") if not role_ids: return roles: List[Role] = [ ctx.guild.get_role(role_id) for role_id in role_ids ] choices = [ create_choice(name=role.name, value=str(role.id)) for role in roles if role.name.startswith(ctx.user_input) ][:25] await ctx.populate(choices)
async def playlist_autocomplete(self, ctx: AutoCompleteContext): choices = None if ctx.name not in ["music", "global"]: return guild_data = await self.bot.mongo.get_guild_data(ctx.guild_id) global_data = await self.bot.mongo.get_global_data() if ctx.focused_option == "playlist": user_guild_data = await guild_data.get_user(ctx.author_id) user_global_data = await global_data.get_user(ctx.author_id) all_playlists = user_guild_data.music_playlists | user_global_data.music_playlists playlists = [ playlist for playlist in all_playlists if playlist.startswith(ctx.user_input) ] choices = [ create_choice(name=playlist, value=playlist) for playlist in playlists ] elif ctx.focused_option == "name": user_guild_data = await guild_data.get_user(ctx.author_id) user_global_data = await global_data.get_user(ctx.author_id) if not user_guild_data.music_playlists and not user_global_data.music_playlists: return input_playlist = ctx.options["playlist"] all_playlists = user_guild_data.music_playlists | user_global_data.music_playlists tracks_list = all_playlists.get(input_playlist) choices = [ create_choice(name=track, value=track) for track in tracks_list if track.startswith(ctx.user_input) ] elif ctx.focused_option == "member_playlist": member_data = await guild_data.get_user(int(ctx.options["member"])) playlists = [ playlist for playlist in member_data.music_playlists if playlist.startswith(ctx.user_input) ] choices = [ create_choice(name=playlist, value=playlist) for playlist in playlists ] if choices: await ctx.populate(choices)
def get_programme_choices(): return list( create_choice( name=f'{programmes[programme_id].uni_name} {programmes[programme_id].display_name}', value=programme_id ) for programme_id in programmes )
async def load_emotes(self): files = multi_glob(*(abs_join("emotes", f"*{ext}") for ext in image_exts)) self.emotes = { os.path.splitext(os.path.split(filename)[1])[0].replace( "_", " ").strip().lower(): filename for filename in files } self.emote_pick.options[0]["choices"] = [ create_choice(name=key, value=key) for key in self.emotes.keys() ][:25] if self.emotes: self.generate_thumbnail_image() self.has_thumbnail = True else: if os.path.exists(self.emotes_thumbnail): os.remove(self.emotes_thumbnail) self.has_thumbnail = False logger.debug(f"Loaded emotes: {self.emotes}") if not self._first_ready: await self.bot.slash.sync_all_commands()
async def loadplugin(ctx, plugin: str): '''Allows you to add any number of available plugins to the current instance of bot''' potentialplugins = getPluginList() loaded = [] alreadyLoaded = [] notLoaded = [] if plugin in potentialplugins: if plugin not in loadConfig(['plugins'])[0]: await ctx.send('Loading **{}**. Please have patience, this may take a while...'.format(plugin)) config['plugins'].append(plugin) #probably should make a setter for this bot.load_extension('plugins.{}'.format(plugin)) print('\tLoaded extension: {}'.format(plugin)) loadedPlugins.append(create_choice(plugin, plugin)) for i in range(len(unloadedPlugins)): if unloadedPlugins[i]['value'] == plugin: unloadedPlugins.pop(i) break loaded.append(plugin) else: alreadyLoaded.append(plugin) else: notLoaded.append(plugin) await savestate(ctx, True) returnString = '' if len(loaded) > 0: returnString += '**Loaded:** ' + ', '.join(loaded) + '\n' if len(alreadyLoaded) > 0: returnString += '**Not Loaded (already loaded):** ' + ', '.join(alreadyLoaded) + '\n' if len(notLoaded) > 0: returnString += '**Not Loaded (plugin does not exist):** ' + ', '.join(notLoaded) + '\n' await ctx.send(returnString) await refreshPlugins()
async def unloadplugin(ctx, plugin: str): '''Allows you to remove any number of available plugins to the current instance of bot''' potentialplugins = getPluginList() unloaded = [] alreadyUnloaded = [] notUnloaded = [] if plugin in potentialplugins: if plugin in loadConfig(['plugins'])[0]: config['plugins'].remove(plugin) #this is terrible and naive bot.unload_extension('plugins.{}'.format(plugin)) print('\tUnloaded extension: {}'.format(plugin)) unloadedPlugins.append(create_choice(plugin, plugin)) for i in range(len(loadedPlugins)): if loadedPlugins[i]['value'] == plugin: loadedPlugins.pop(i) break unloaded.append(plugin) else: alreadyUnloaded.append(plugin) else: notUnloaded.append(plugin) await savestate(ctx, True) returnString = '' if len(unloaded) > 0: returnString += '**Unloaded:** ' + ', '.join(unloaded) + '\n' if len(alreadyUnloaded) > 0: returnString += '**Not Unloaded (already unloaded):** ' + ', '.join(alreadyUnloaded) + '\n' if len(notUnloaded) > 0: returnString += '**Not Unloaded (plugin does not exist):** ' + ', '.join(notUnloaded) + '\n' await ctx.send(returnString) await refreshPlugins()
class DeleteRankCommand(commands.Cog): def __init__(self, bot): self.bot = bot @slash( name='deleterank', description= 'Delete your ranking number and the corresponding offer date (if it exists) from the bot', options=[ create_option(name='programme', description='Study programme', option_type=command_option_type.STRING, required=True, choices=programmes_helper.get_programme_choices() + [create_choice(name='All programmes', value='all')]), create_option(name='year', description='Year of application', option_type=command_option_type.INTEGER, required=True, choices=programmes_helper.get_year_choices()) ]) async def deleterank(self, ctx: SlashContext, programme: str, year: int): user = ctx.author if programme == 'all': programme = None async with (await self.bot.get_db_conn()).acquire() as connection: ranks = ranks_service.RanksService(connection) await ranks.delete_rank(str(user.id), programme, year) await ctx.send(user.mention + ' Rank deleted.')
async def add_commands(self, slash: SlashCommand): base_command = self.configuration.get("command_prefix", "") + "randovania-faq" for game in enum_lib.iterate_enum(RandovaniaGame): faq_entries = list(game.data.faq) if not faq_entries: continue def _shorten(n: str) -> str: if len(n) > 100: return n[:97] + "..." return n slash.add_subcommand( functools.partial(self.faq_game_command, game=game), base_command, name=game.value, description=f"Prints the answer to a FAQ for {game.long_name}.", options=[ manage_commands.create_option( "question", "Which question to answer?", option_type=SlashCommandOptionType.STRING, required=True, choices=[ manage_commands.create_choice( f"question_{question_id}", _shorten(question)) for question_id, (question, answer) in enumerate(faq_entries) ]) ], )
async def register_my_tickets_command(bot, cmd) -> None: """Dirty hack to register options on fly for my_tickets command""" lotteries = await Lottery.all().order_by("-created_at").limit(10) try: # force sync_commands to detect new changes and sync slash commands with Discord del bot.slash.subcommands["sweepstake"]["tickets"] except KeyError: pass bot.slash.add_subcommand( cmd=cmd, base="sweepstake", name="tickets", description="My tickets", guild_ids=config.GUILD_IDS, options=[ create_option( name="name", description="choose sweepstake", option_type=3, required=True, choices=[create_choice(name=_.name, value=_.name) for _ in lotteries], ) ], ) return None
class SlashCourse(commands.Cog): def __init__(self, bot): self.bot = bot @cog_ext.cog_slash( name="course", description="Displays information about a course.", options=[ create_option( name="course", description="The course code.", option_type=3, required=True, ), create_option( name="school", description="The school the course is at.", option_type=3, required=False, choices=[ create_choice(name="Queens University", value="queens"), create_choice(name="University of Waterloo", value="waterloo"), create_choice(name="University of Toronto", value="uoft"), ], ), ], ) async def _course(self, ctx, course, school=None): """/course""" if " " in course: course = course.split(" ") course = f"{course[0].upper()}-{course[1]}" else: final = "" if "-" not in course: dash = False for i in course: if i.isnumeric() and not dash: final += "-" + i.upper() dash = True else: final += i.upper() course = final await call_course(ctx, self.bot, course, school)
def get_choices(self): choices = [] for i in range(len(self._games)): choices.append( create_choice( name=self._games[i]["name"], value=self._games[i]["name"], )) if len(self._games) < 1: choices.append(create_choice( name="Inválido", value="Invalid", )) return choices
class ListPermissions(commands.Cog): """List Permissions for a specified user/role""" def __init__(self, bot): self.bot = bot self.emoji = bot.emoji_list self.paginator = pagination.LinePaginator(prefix="", suffix="") @cog_ext.cog_subcommand( base="permissions", name="get", description="Get the permissions of a role or user", base_default_permission=True, options=[ manage_commands.create_option( name="scope", description="Do you want guild perms, or channel overrides", required=True, option_type=4, choices=[ manage_commands.create_choice(value=1, name="guild"), manage_commands.create_choice(value=2, name="channel"), ], ), manage_commands.create_option( name="target", description="The user or role you want to get perms for", required=True, option_type=9), ], ) async def get_permissions(self, ctx: SlashContext, **kwargs): mention = int(kwargs.get("target")) if user := ctx.guild.get_member(mention): if kwargs.get("scope") == 1: return await self.perms_guild(ctx, user) return await self.perms_channel(ctx, user) elif role := ctx.guild.get_role(mention): if kwargs.get("scope") == 1: return await self.perms_guild(ctx, role) return await self.perms_channel(ctx, role)
async def add_commands(self, slash: SlashCommand): slash.add_slash_command( self.database_command, name=self.configuration.get("command_prefix", "") + "database-inspect", description= "Consult the Randovania's logic database for one specific room.", guild_ids=None, options=[ manage_commands.create_option( "game", "The game's database to check.", option_type=SlashCommandOptionType.STRING, required=True, choices=[ manage_commands.create_choice(game.value, game.long_name) for game in enum_lib.iterate_enum(RandovaniaGame) ]) ], ) def add_id(custom_id: str, call, **kwargs): self._on_database_component_listener[ custom_id] = functools.partial(call, **kwargs) for game in enum_lib.iterate_enum(RandovaniaGame): db = default_database.game_description_for(game) world_options = await create_split_worlds(db) self._split_worlds[game] = world_options add_id(f"{game.value}_world", self.on_database_world_selected, game=game) add_id(f"back_to_{game.value}", self.on_database_back_to_game, game=game) for i, split_world in enumerate(world_options): add_id(f"{game.value}_world_{i}", self.on_database_area_selected, game=game, split_world=split_world, world_id=i) for j, area in enumerate(split_world.areas): add_id(f"{game.value}_world_{i}_area_{j}", self.on_area_node_selection, game=game, area=area) slash.add_component_callback( self.on_database_component, components=list(self._on_database_component_listener.keys()), use_callback_name=False, )
async def tag_autocomplete(self, ctx: AutoCompleteContext): if ctx.name != "tag" and ctx.focused_option != "tag_name": return choices = [] guild_data = await self.bot.mongo.get_guild_data(ctx.guild_id) tags = guild_data.tags choices = [ create_choice(name=tag.name, value=tag.name) for tag in tags if tag.name.startswith(ctx.user_input) ][:25] await ctx.populate(choices)
def deck_slash_options(): """ Returns the slash command options for decks. :return: """ return [ create_option(name="code", description=lang.locale('deck_code_desc'), option_type=4, required=True), create_option(name="type", description=lang.locale('deck_type_desc'), option_type=3, required=False, choices=[ create_choice(name=lang.locale('public_deck'), value="decklist"), create_choice(name=lang.locale('private_deck'), value="deck"), ]), ]
async def level_autocomplete(self, ctx: AutoCompleteContext): if self.bot.get_transformed_command_name(ctx) != "levels": return choices = [] if ctx.focused_option in ["current_level", "remove"]: guild_data = await self.bot.mongo.get_guild_data(ctx.guild_id) roles_by_level = guild_data.roles_by_level choices = [ create_choice(name=level, value=int(level)) for level in roles_by_level ] if choices: await ctx.populate(choices)
async def command_autocomplete(self, ctx: AutoCompleteContext): if self.bot.get_transformed_command_name(ctx) != "command": return guild_data = await self.bot.mongo.get_guild_data(ctx.guild_id) disabled_commands = guild_data.configuration.disabled_commands choices = [ create_choice(name=command_name, value=command_name) for command_name in disabled_commands if command_name.startswith(ctx.user_input) ][:25] await ctx.populate(choices)
def timing_slash_options(): """ Returns the slash command options for Game's Framework. :return: """ return [ create_option(name="timing", description=lang.locale('timings_type_desc'), option_type=3, required=True, choices=[ create_choice(name=lang.locale('mythos_phase'), value="M"), create_choice( name=lang.locale('investigation_phase'), value="I"), create_choice(name=lang.locale('enemy_phase'), value="E"), create_choice(name=lang.locale('upkeep_phase'), value="U"), create_choice(name=lang.locale('skill_test'), value="S"), ]) ]
async def updateTemplates(self): choices = [] for i in self.manager.get_all_templates(): choices.append( manage_commands.create_choice(i, self.getTemplateName(i))) self.slash.commands['version'].options = [ manage_commands.create_option( "version", "The game version to set the juggler to.", 3, True, choices=choices) ] await self.slash.sync_all_commands()
class Games(commands.Cog): def __init__(self, bot): self.bot = bot self.economy = self.bot.get_cog("Economy") self.econ_manager = self.economy.manager @cog_ext.cog_slash( name="slots", description="Slot machine minigame", guild_ids=[336950154189864961], options=[ create_option(name="amount", description= "How many e฿UX you would like to put into each spin", option_type=SlashCommandOptionType.INTEGER, choices=[ create_choice(10, "฿10"), create_choice(50, "฿50"), create_choice(100, "฿100"), create_choice(1000, "฿1,000"), create_choice(10000, "฿10,000"), create_choice(100000, "฿100,000") ], required=False) ]) async def slots(self, ctx: SlashContext, amount: int): slots = SlotMachine(ctx, self.bot, amount) await slots.play() @commands.command(name="connect4", aliases=["c4"]) async def connect4(self, ctx, target: discord.User, wager: int = 0): players = [target, ctx.message.author] game = ConnectFour(ctx, self.bot, players, wager) await game.play() @commands.command("blackjack") async def blackjack(self, ctx, minimum: int = 10): if minimum >= 10: blackjack = BlackJack(ctx, self.bot, minimum) await blackjack.play() else: await ctx.reply("Minimum bet must be at least 10") def get_card_string(self, name): for card in self.bot.playing_cards: if card.name == name: return return None
def general_card_slash_options(): """ Returns the slash command options for general cards. :return: """ return [ create_option(name="name", description=lang.locale('name_description'), option_type=3, required=True), create_option(name="type", description=lang.locale('card_type_desc'), option_type=3, required=False, choices=[ create_choice(name=lang.locale('scenario'), value="S"), create_choice(name=lang.locale('act'), value="A"), create_choice(name=lang.locale('agenda'), value="P"), create_choice(name=lang.locale('treachery'), value="T"), create_choice(name=lang.locale('enemy'), value="E"), create_choice(name=lang.locale('location'), value="L"), create_choice(name=lang.locale('player_cards'), value="J"), create_choice(name=lang.locale('mythos'), value="M"), ]), create_option(name="sub", description=lang.locale('sub_description'), option_type=3, required=False), create_option(name="pack", description=lang.locale('pack_description'), option_type=3, required=False), ]
async def note_autocomplete(self, ctx: AutoCompleteContext): if not self.bot.get_transformed_command_name(ctx).startswith("note"): return if ctx.focused_option != "name": return global_data = await self.bot.mongo.get_global_data() guild_data = await self.bot.mongo.get_guild_data(ctx.guild_id) user_guild_data = await guild_data.get_user(ctx.author_id) user_global_data = await global_data.get_user(ctx.author_id) if not user_guild_data.notes and not user_global_data.notes: return choices = [ create_choice( name=f"{count}. | {note['created_at']} | {note['name']}", value=note["name"], ) for count, note in enumerate( user_guild_data.notes + user_global_data.notes, start=1) if ctx.user_input in f"{count}. {note['created_at']} | {note['name']}" ][:25] await ctx.populate(choices)
class Utilitys(commands.Cog): def __init__(self, bot): self.bot = bot @cog_ext.cog_slash( name='info', description='shows info on a user', guild_ids=[740531414008856596], options=[ manage_commands.create_option( name="user", description="the user you want to see the info of", option_type=6, required=False) ]) async def info(self, ctx, member: discord.Member = None): member = member if member != None else ctx.author embed = discord.Embed( title='User Info', description='do `hb: info` to get info about you') embed.add_field(name='Name:', value=member.name) embed.add_field(name='Discriminator:', value=member.discriminator) embed.add_field(name='ID:', value=member.id) embed.add_field(name='Bot?', value=member.bot) embed.add_field(name='Booster?', value=is_booster(member)) await ctx.send(embed=embed) @cog_ext.cog_slash( name='userinfo', description='shows info on a user', guild_ids=[740531414008856596], options=[ manage_commands.create_option( name="user", description="the user you want to see the info of", option_type=6, required=True) ]) async def userinfo(self, ctx, user: discord.User): embed = discord.Embed(title='User Info', ) embed.add_field(name='Name:', value=user.name) embed.add_field(name='Discriminator:', value=user.discriminator) embed.add_field(name='ID:', value=user.id) embed.add_field(name='Bot?', value=user.bot) await ctx.send(embed=embed) @cog_ext.cog_slash(name='botinfo', description='shows info about this bot', guild_ids=[740531414008856596]) async def botinfo(self, ctx): embed = discord.Embed( title='henos bot', description='use `hb: help` for a list of the commands') embed.add_field(name='Name:', value=self.bot.user.name) embed.add_field(name='Discriminator:', value=self.bot.user.discriminator) embed.add_field(name='ID:', value=self.bot.user.id) embed.add_field(name='Owner:', value='henos') embed.add_field(name='Ping:', value=f'{round(self.bot.latency * 1000)} ms') embed.add_field(name='Invite:', value='http://tiny.cc/henosbot') embed.add_field(name='Servers:', value=len(self.bot.guilds)) embed.add_field(name='Members:', value=len(self.bot.users)) embed.add_field(name='Prefixs:', value='hb: , hb:') await ctx.send(embed=embed) @cog_ext.cog_slash(name='serverinfo', description='shows info on a server', guild_ids=[740531414008856596]) async def guildinfo(self, ctx): embed = discord.Embed(title='Server Info') embed.add_field(name='Name:', value=ctx.guild.name) embed.add_field(name='ID:', value=ctx.guild.id) embed.add_field(name='Channels:', value=len(ctx.guild.channels)) embed.add_field(name='Members:', value=len(ctx.guild.members)) embed.add_field(name='Boosts:', value=len(ctx.guild.premium_subscribers)) embed.add_field(name='Owner:', value=ctx.guild.owner.mention) welcome_msgs = await db.ignored(ctx.guild, 'welcome_msgs') lvl_msgs = await db.ignored(ctx.guild, 'lvl_msgs') embed.add_field(name='Interaction disabled?', value=f'Welcome: {welcome_msgs}, Level: {lvl_msgs}') await ctx.send(embed=embed) @cog_ext.cog_slash( name='disableinteraction', description='disables interaction in a server', guild_ids=[740531414008856596], options=[ manage_commands.create_option( name="type", description="the type of thing u want to disable", option_type=3, required=True) ]) @commands.has_permissions(manage_guild=True) async def disableinteraction(self, ctx, type): await db.guild_set(ctx.guild, type, False) await ctx.send(f'Guild {ctx.guild.name} has disabled {type} messages.') @cog_ext.cog_slash( name='enableinteraction', description='enables interaction in a server', guild_ids=[740531414008856596], options=[ manage_commands.create_option( name="type", description="the type of thing u want to enable", option_type=3, required=True, choices=[ manage_commands.create_choice(name='level', value='lvl'), manage_commands.create_choice(name='welcome', value='welcome') ]) ]) @commands.has_permissions(manage_guild=True) async def enableinteraction(self, ctx, type): await db.guild_set(ctx.guild, type, True) await ctx.send(f'Guild {ctx.guild.name} has enabled {type} messages.') @commands.command() @commands.is_owner() async def text(self, ctx, user: discord.User, *, message): msg = await user.send('Incoming text message from my owner...') await msg.edit(content=f'Message: {message}') await ctx.send('Message sent successfully') @cog_ext.cog_slash(name='roles', description='shows all the roles in a server', guild_ids=[740531414008856596]) @commands.guild_only() async def roles(self, ctx): allroles = "" for num, role in enumerate(sorted(ctx.guild.roles, reverse=True), start=1): allroles += f"[{str(num).zfill(2)}] {role.id}\t{role.name}\t[ Users: {len(role.members)} ]\r\n" data = BytesIO(allroles.encode('utf-8')) await ctx.send(content=f"Roles in **{ctx.guild.name}**", file=discord.File(data, filename=f"{timetext('Roles')}")) @cog_ext.cog_slash(name='joinedat', description='show when a user joined ur server', guild_ids=[740531414008856596], options=[ manage_commands.create_option( name='user', description='the user to see the `joinedat` of', option_type=6, required=False) ]) @commands.guild_only() async def joinedat(self, ctx, user: discord.Member = None): user = user or ctx.author embed = discord.Embed() embed.set_thumbnail(url=user.avatar_url) embed.description = f'**{user}** joined **{ctx.guild.name}**\n{date(user.joined_at)}' await ctx.send(embed=embed) @cog_ext.cog_slash(name='mods', description='shows the mods that are currently online', guild_ids=[740531414008856596]) @commands.guild_only() async def mods(self, ctx): message = "" all_status = { "online": { "users": [], "emoji": "🟢" }, "idle": { "users": [], "emoji": "🟡" }, "dnd": { "users": [], "emoji": "🔴" }, "offline": { "users": [], "emoji": "⚫" } } for user in ctx.guild.members: user_perm = ctx.channel.permissions_for(user) if user_perm.kick_members or user_perm.ban_members: if not user.bot: all_status[str(user.status)]["users"].append(f"**{user}**") for g in all_status: if all_status[g]["users"]: message += f"{all_status[g]['emoji']} {', '.join(all_status[g]['users'])}\n" await ctx.send(f"Mods in **{ctx.guild.name}**\n{message}")
import discord from discord.ext import commands import requests from discord_slash import cog_ext, SlashContext from main import test_guilds, make_error_embed from discord_slash.utils.manage_commands import create_option, create_choice options = [ create_option(name="species", description="Select a species.", option_type=3, required=True, choices=[ create_choice(name="cat", value="cat"), create_choice(name="dog", value="dog"), create_choice(name="panda", value="panda"), create_choice(name="koala", value="koala") ]) ] class AnimalFact(commands.Cog): def __init__(self, client): self.client = client @cog_ext.cog_subcommand( base="animal", name="fact", options=options, #guild_ids=test_guilds )
class Greetings(utils.AutoLogCog, utils.StartupCog): """Simple greetings and welcome commands""" activity_time_format = "%H:%M %d.%m.%Y" def __init__(self, bot): utils.StartupCog.__init__(self) utils.AutoLogCog.__init__(self, logger) self.bot = bot self.activity_file_path = utils.abs_join("last_activity") self._last_greeted_member = None self._started_at = None self._last_active_at = None async def on_startup(self): logger.info(f"Logged in as {self.bot.user}") guilds_list = [ f"[{g.name}: {g.member_count} members]" for g in self.bot.guilds ] logger.info(f"Current servers: {', '.join(guilds_list)}") last_activity = self.get_file_activity_time() self._started_at = datetime.utcnow() self._last_active_at = datetime.utcnow() self.update_activity_time_loop.start() # Don't send greetings if last activity was less than a 3 hours ago if last_activity is None or (self._last_active_at - last_activity > timedelta(hours=3)): await self.send_home_channels_message( "Hello hello! I'm back online and ready to work!") @tasks.loop(hours=1) async def update_activity_time_loop(self): self._last_active_at = datetime.utcnow() self.update_file_activity_time() @commands.Cog.listener() async def on_member_join(self, member: discord.Member): if member.bot: return channels = await self.bot.get_cog("Channels").get_welcome_channels( member.guild) if not channels: return message = await self.get_welcome_message(member) if not message: logger.info("Member greeting is disabled") return for greeting_channel in channels: if utils.can_bot_respond(greeting_channel): await greeting_channel.send( message, allowed_mentions=discord.AllowedMentions.none()) logger.info(f"Greeted new guild member {member}") def get_file_activity_time(self) -> Optional[datetime]: try: with open(self.activity_file_path, 'r') as startup_time_file: return datetime.strptime(startup_time_file.read(), self.activity_time_format) except (ValueError, OSError): return None def update_file_activity_time(self): """writes to the startup file current _started_at file""" last_activity = self._last_active_at.strftime( self.activity_time_format) with open(self.activity_file_path, 'w') as activity_time_file: activity_time_file.write(last_activity) logger.info(f"Updated last activity time file: {last_activity}") @cog_ext.cog_subcommand(base="home", name="notify", options=[ create_option( name="message", description="Message to send", option_type=str, required=False, ), create_option( name="attachment_link", description="Link to attachment to send", option_type=str, required=False, ) ], guild_ids=guild_ids) @has_bot_perms() async def home_channel_notify(self, ctx: SlashContext, message="", attachment_link=None): """Sends message with the attachment to the home channels of the guilds from the bot""" if not message and not attachment_link: await ctx.send("Can't send an empty message", hidden=True) return await ctx.defer() file = None name = "" if attachment_link is not None: async with aiohttp.ClientSession() as session: async with session.get(attachment_link) as response: if response.ok: file = await response.read() name = Path(urlparse(attachment_link).path).name await self.send_home_channels_message(message, file, name) await ctx.send("Notification sent") logger.important( f"{self.format_caller(ctx)} sent global notification {message} with attachment {attachment_link}" ) @cog_ext.cog_subcommand(base="home", name="where", guild_ids=guild_ids) async def home_channel_where(self, ctx: SlashContext): """Shows where current home of the bot in this server is.""" current_homes = await self.bot.get_cog("Channels").get_home_channels( ctx.guild) if current_homes: if len(current_homes) == 1: await ctx.send( f"My home channel is {current_homes[0].mention}", hidden=True) else: current_homes = ", ".join( [channel.mention for channel in current_homes]) await ctx.send(f"My home channels are {current_homes}", hidden=True) else: await ctx.send("I'm homeless T_T", hidden=True) async def send_home_channels_message(self, message: str, attachment=None, attachment_name=""): channels = await self.bot.get_cog("Channels").get_home_channels() for channel in channels: if channel.guild not in self.bot.guilds: continue file = discord.File( io.BytesIO(attachment), attachment_name) if attachment is not None else None await channel.send(message, file=file) def get_start_time(self) -> datetime: return self._started_at def get_last_activity_time(self) -> datetime: return self._last_active_at def get_greeting(self, member): greetings = \ ["Hi, {}!", "Hello, {}~", "Yo, {}!", "Sup, {}", "{}! Good to see you!", "The Skybox waited for you, {}!", "Greetings, {} =)", "/-//- /--/ {}.", "Oh! Hello there, you must be {}.", "G'day, {}!", "Howdy, {}", "Arigato, {}-san", "Hoi, {}", ] message = random.choice(greetings).format(member.display_name) if self._last_greeted_member is not None and self._last_greeted_member.id == member.id: message = f"{message}\nThis feels oddly familiar..." self._last_greeted_member = member return message @staticmethod def get_member_welcome_message(member: discord.Member) -> str: """Returns personal part of the welcome message""" greetings = \ ["Welcome, {}!", "Glad to see you here, {}!", "Welcome here, {}!", "{} just joined, welcome!", "Welcome, {}. We're not Discord, we demand pizza!", "Hello, {}. Have a good time here!", ] # Discord mobile client have a bug where it shows mention as @invalid-user # What exactly triggers that is beyond my understanding right now, so I just put back the display name for now return random.choice(greetings).format(member.display_name) @staticmethod async def get_welcome_message(member: discord.Member) -> Optional[str]: """Returns full welcome message for specific server and person""" guild_greeting = await GuildGreetings.get_or_none( guild_id=member.guild.id) if not guild_greeting: return None member_greeting = Greetings.get_member_welcome_message(member) return "\n".join([ member_greeting, guild_greeting.greeting_text ]) if guild_greeting.greeting_text else member_greeting @staticmethod async def set_guild_greeting_text(guild: discord.Guild, greeting_text: Optional[str]): (greeting, _) = await GuildGreetings.get_or_create(guild_id=guild.id) greeting.greeting_text = greeting_text await greeting.save() @staticmethod async def delete_welcome_message(guild: discord.Guild): greeting = await GuildGreetings.get_or_none(guild_id=guild.id) if greeting: await greeting.delete() @cog_ext.cog_subcommand( base="greeting", name="set", description= "Enables welcome message and sets server specific part of the this message", options=[ create_option( name="message", description="Server specific part of the welcome message", option_type=str, required=False, ), create_option( name="template_link", description= "Link to the message, which text should be used as a welcome message", option_type=str, required=False, ), ], guild_ids=guild_ids) @has_server_perms() async def set_greeting(self, ctx: SlashContext, message: str = "", template_link: Optional[str] = None): await ctx.defer(hidden=True) if not message and template_link: message = await utils.get_message_from_link( self.bot, template_link) message = message.content await self.set_guild_greeting_text(ctx.guild, message) message = f"'{message}'" if message else message logger.db( f"{ctx.author} set greeting for guild {ctx.guild} to {message}") await ctx.send( f"Successfully set message to personal greeting {'and ' + message if message else 'only'}", hidden=True) @cog_ext.cog_subcommand( base="greeting", name="delete", description="Disables welcome message for new people", guild_ids=guild_ids) @has_server_perms() async def delete_greeting(self, ctx: SlashContext): await ctx.defer(hidden=True) await self.delete_welcome_message(ctx.guild) logger.db(f"{ctx.author} deleted greeting for guild {ctx.guild}'") await ctx.send( f"Successfully deleted welcome message! Bot won't send welcome message when new people joins", hidden=True) @cog_ext.cog_subcommand( base="greeting", name="greet", description="Sends greeting for you or specific person", options=[ create_option( name="member", description="Person to greet", option_type=discord.Member, required=False, ), create_option( name="hidden", description= "If enabled, it'll be only you who see the greeting", option_type=bool, required=False, ), ], guild_ids=guild_ids) async def greet(self, ctx: SlashContext, member: discord.Member = None, hidden: bool = False): member = member or ctx.author message = await self.get_welcome_message(member) if not message: await ctx.send("Welcome message is disabled for the server", hidden=True) return await ctx.send(message, hidden=hidden, allowed_mentions=discord.AllowedMentions.none()) @cog_ext.cog_subcommand(base="greeting", name="list", description="Lists all greetings in database", guild_ids=guild_ids) @has_bot_perms() async def list_greetings(self, ctx: SlashContext): await ctx.defer(hidden=True) async for greeting in GuildGreetings.all(): guild = self.bot.get_guild(greeting.guild_id) message = "\n".join([ f"'{guild.name if guild else 'ID ' + str(greeting.guild_id)}' greeting:", greeting.greeting_text if greeting.greeting_text else "Personal greeting only", ]) await ctx.send(content=message, hidden=True) @cog_ext.cog_slash(options=[ create_option( name="member", description="Member who bot should greet", option_type=discord.Member, required=False, ) ], guild_ids=guild_ids) async def hello(self, ctx: SlashContext, member: discord.Member = None): """Says hello to you or mentioned member.""" if member and not isinstance(member, discord.Member): raise commands.BadArgument( f"Failed to get member '{member}' info!") if not utils.can_bot_respond(ctx.channel): raise commands.BadArgument( f"I can't send messages to this channel" ) # This will be shown as hidden response, so we can do that member = member or ctx.author await ctx.send(self.get_greeting(member)) async def get_activity_code(self, voice, application_id): url = f"https://discord.com/api/v8/channels/{voice.channel.id}/invites" api_json = { "max_age": 86400, "max_uses": 0, "target_application_id": f"{application_id}", "target_type": 2, "temporary": False, "validate": None } headers = { "Authorization": f"Bot {self.bot.token}", "Content-Type": "application/json" } async with aiohttp.ClientSession() as session: async with session.post(url, json=api_json, headers=headers) as response: data = await response.json() code = data["code"] return code @staticmethod async def get_application_icon(application_id): async with aiohttp.ClientSession() as session: api_url = f"https://discord.com/api/v9/applications/{application_id}/rpc" async with session.get(api_url) as response: data = await response.json() icon_code = data["icon"] icon_url = f"https://cdn.discordapp.com/app-icons/{application_id}/{icon_code}.png" return icon_url @cog_ext.cog_slash(name="activity", options=[ create_option(name="type", description="Type of activity", option_type=str, required=True, choices=[ create_choice(name=name, value=name) for name in activities.keys() ]) ], connector={"type": "activity_type"}, guild_ids=guild_ids) async def start_activity(self, ctx: SlashContext, activity_type): """Creates an activity invite for voice channel you are in""" if not ctx.author.voice: await ctx.send( hidden=True, content= "You need to be in a voice channel to start an activity!") return await ctx.defer() voice = ctx.author.voice application_id = activities[activity_type] code = await self.get_activity_code(voice, application_id) invite = f"https://discord.gg/{code}" icon = await self.get_application_icon(application_id) embed = discord.Embed(title="New voice channel activity started!", colour=utils.embed_color) embed.set_author(name=activity_type, icon_url=icon, url=invite) embed.set_thumbnail(url=icon) embed.description = f"**{activity_type}** activity just started in {voice.channel.mention}\n" \ f"[Click this link and join!]({invite})\n" \ f"This invite will expire after 1 day!" await ctx.send(embed=embed)
class Schedule(commands.Cog): def __init__(self, bot): self.bot = bot self.max_left_arrow = "⏮" self.left_arrow = "◀" self.max_right_arrow = "⏭" self.right_arrow = "▶" @staticmethod async def _is_played(ctx: Union[commands.Context, SlashContext]) -> None: async with aiohttp.ClientSession() as session: async with session.get("https://radio17.pl/api/stream/stats/extended") as response: json_resp = await response.json() embed = discord.Embed(title="Obecnie gramy:") is_played = f'{json_resp["current"]["artist"]} - {json_resp["current"]["title"]}' embed.add_field(name=is_played, value="https://radio17.pl") await ctx.send(embed=embed) @staticmethod async def _will_play(ctx: Union[commands.Context, SlashContext]) -> None: async with aiohttp.ClientSession() as session: async with session.get("https://radio17.pl/api/stream/stats/extended") as response: embed = discord.Embed(title="Za chwilę będziemy grać:") json_resp = await response.json() if json_resp["next"] is not None: will_play = f'{json_resp["next"]["artist"]} - {json_resp["next"]["title"]}' embed.add_field(name=will_play, value="https://radio17.pl") else: embed.add_field(name="No nie wiem co będzie grane.", value="https://radio17.pl") await ctx.send(embed=embed) async def _schedule(self, ctx: Union[commands.Context, SlashContext], day: str) -> None: async with aiohttp.ClientSession() as session: async with session.get("https://radio17.pl/api/schedule") as response: json_resp = await response.json() # "strony" embeda, kazda z nich odpowiada jednej audycji pages = [] # szczegolny przypadek jesli uzytkownik chce skrocona ramowke if day.lower() == "short": short_embed = discord.Embed(title="Dziś jeszcze gramy:") # tylko dla danego dnia tygodnia sprawdza co jest grane, datetime.datetime.today().weekday() # zwraca dzien tygodnia jako numer print(json_resp) for broadcast in json_resp[week_days[datetime.datetime.today().weekday()]]: # broadcast["end_hour"][:2] bierze pierwsze dwie cyfry z godziny podanej w formacie hh:mm:ss if int(broadcast["end_hour"][:2]) > datetime.datetime.today().hour: short_embed.add_field(name=broadcast["title"], value=f'{broadcast["start_hour"]} - {broadcast["end_hour"]}', inline=False) await ctx.send(embed=short_embed) return # sprawdza czy dzien tygodnia podany przez uzytkownika jest poprawny if day.lower() not in week_days: await ctx.send("Wpisz poprawny dzień tygodnia w języku angielskim!") return # dla kazdej audycji tworzy jedna "strone" embeda for broadcast in json_resp[day]: embed = discord.Embed(title=broadcast["title"]) embed.add_field(name="Nazwa audycji:", value=broadcast["title"], inline=False) embed.add_field(name="Od - do:", value=f'{broadcast["start_hour"]} - {broadcast["end_hour"]}', inline=False) if broadcast["description"] is not None: embed.add_field(name="Opis:", value=broadcast["description"], inline=False) embed.set_image(url=broadcast["player_image"]) pages.append(embed) # wysyla pierwsza strone embeda message = await ctx.send(embed=pages[0]) # dodaje kolejno reakcje pod embedem sluzace do przesuwania stron await message.add_reaction(self.max_left_arrow) await message.add_reaction(self.left_arrow) await message.add_reaction(self.right_arrow) await message.add_reaction(self.max_right_arrow) # funkcja sprawdzajaca czy reakcja dodana pod embedem jest od autora komendy def check(reaction, user): return user == ctx.author i = 0 reaction = None while True: # reakcja do powrotu do pierwszej strony emebda if str(reaction) == self.max_left_arrow: i = 0 await message.edit(embed=pages[i]) # reakcja cofa embed o jedna strone elif str(reaction) == self.left_arrow: if i > 0: i -= 1 await message.edit(embed=pages[i]) # reakcja przenosi na kolejna strone mebeda elif str(reaction) == self.right_arrow: if i < len(pages) - 1: i += 1 await message.edit(embed=pages[i]) # reakcja przenosi do ostatniej strony embeda elif str(reaction) == self.max_right_arrow: i = len(pages) - 1 await message.edit(embed=pages[i]) try: # sprawdza czy autor dodal reakcje pod wiadomoscia reaction, user = await self.bot.wait_for("reaction_add", timeout=30.0, check=check) # usuwa dodana reakcje pod wiadomoscia, by mozna bylo dodac kolejna await message.remove_reaction(reaction, user) except: break # usuwa reakcje po uplywie 30s await message.clear_reactions() @commands.command( brief="Co jest grane?", help="Bot informuje o obecnie granym utworze.", name="cjg" ) @commands.cooldown(1, 60, commands.BucketType.user) async def is_played(self, ctx: commands.Context) -> None: await self._is_played(ctx) return @cog_ext.cog_slash( name="cjg", description="Informuje co obecnie jest grane w radiu." ) async def is_played_slash(self, ctx: SlashContext) -> None: await self._is_played(ctx) return @commands.command( brief="Co będzie grane?", help="Bot informuje jaki utwór będzie grany następnie.", name="cbg" ) @commands.cooldown(1, 60, commands.BucketType.user) async def will_play(self, ctx: commands.Context) -> None: await self._will_play(ctx) return @cog_ext.cog_slash( name="cbg", description="Informuje co będzie grane za chwilę w radiu." ) async def will_play_slash(self, ctx: SlashContext) -> None: await self._will_play(ctx) return @commands.command( brief="Wysyła ramówkę na dany dzień.", help="Przyjmuje dni tygodnia po angielsku i wysyła ramówkę na zadany dzień. Podaje godzinę rozpoczęcia i " "zakończenia audycji oraz jej krótki opis. " ) @commands.cooldown(1, 60, commands.BucketType.user) async def schedule(self, ctx: commands.Context, day: str) -> None: await self._schedule(ctx, day) return @cog_ext.cog_slash( name="schedule", description="Wysyła ramówkę na dany dzień.", # tworzy opcje do wyboru w wypadku slash command options=[ create_option( name="day", description="Wybierz dzień tygodnia", option_type=3, required=True, choices=[ create_choice( name="Krótsza wersja ramówki", value="short" ), create_choice( name="Poniedziałek", value="monday" ), create_choice( name="Wtorek", value="tuesday" ), create_choice( name="Środa", value="wednesday" ), create_choice( name="Czwartek", value="thursday" ), create_choice( name="Piątek", value="friday", ), create_choice( name="Sobota", value="saturday" ), create_choice( name="Niedziela", value="sunday" ) ] ) ] ) async def schedule_slash(self, ctx: SlashContext, day: str) -> None: if ctx.guild is None: await ctx.send("Komenda nie działa w wiadomości prywatnej!") return await self._schedule(ctx, day) return
class Market(commands.Cog): def __init__(self, bot): self.bot = bot # --- SLASH COMMANDS --- # @cog_ext.cog_subcommand( base='market', name='coin', description='Displays cryptocoin info from CoinMarketCap', guild_ids=guild_ids, options=[ create_option( name='module', description=' ', required=True, option_type=3, choices=[ create_choice( name='rank', value='rank' ), create_choice( name='name', value='name' ) ] ) ] ) async def _market_coin(self, ctx: SlashContext, module: str): # Variables emoji_list = ['◀', '▶'] # Database cur.execute('SELECT * FROM coin_info ORDER BY coin_rank asc') rows = cur.fetchall() if module == 'rank': embed = discord.Embed( title='Please enter a rank from 1-100', description=' ', colour=discord.Colour.blurple() ) await ctx.send(embeds=[embed], delete_after=5.0) try: msg = await self.bot.wait_for('message', timeout=5.0) except asyncio.exceptions.TimeoutError: embed = discord.Embed( title=f'{ctx.author} failed to send a message within the allotted time', description=' ', colour=discord.Colour.red() ) await ctx.send(embeds=[embed], delete_after=5.0) try: coin_number = int(msg.content) await msg.delete() # Deletes message sent by user for x in rows: # ID: x[0] || Name: x[1] || Symbol: x[2] || Price: x[3] || Rank: x[4] || Change: x[5] || Logo: x[6] if x[4] == coin_number: current_page = x[4] embed = discord.Embed( title=f'${str(x[3])}', description=' ', colour=discord.Colour.blurple() ) embed.set_author( name=f'{x[4]}. {x[1]} / {x[2]}', icon_url=x[6] ) embed.add_field( name='24h %', value=f'{x[5]:.2f}%', inline=False) embed.set_footer(text="") message = await ctx.send(embed=embed) if current_page <= 1: # Adds / Removes emoji if it passes threshold await message.add_reaction(emoji_list[1]) elif current_page >= 100: await message.add_reaction(emoji_list[0]) else: for emoji in emoji_list: await message.add_reaction(emoji) check = reaction_check(message=message, author=ctx.author, emoji=(emoji_list[0], emoji_list[1])) while True: # Continues to run for 10 seconds until user does not click the emojis try: reaction, user = await self.bot.wait_for('reaction_add', timeout=10.0, check=check) if reaction.emoji == emoji_list[0]: # Left page await message.delete() # Deletes embed before sending a new one current_page = current_page - 1 if current_page <= 0: current_page = 1 embed = get_left_coin(1) else: embed = get_left_coin(current_page) message = await ctx.send(embed=embed) if current_page <= 1: # Adds / Removes emoji if it passes threshold await message.add_reaction(emoji_list[1]) elif current_page >= 100: await message.add_reaction(emoji_list[0]) else: for emoji in emoji_list: await message.add_reaction(emoji) check = reaction_check(message=message, author=ctx.author, emoji=(emoji_list[0], emoji_list[1])) elif reaction.emoji == emoji_list[1]: # Right page await message.delete() # Deletes embed before sending a new one current_page = current_page + 1 if current_page >= 100: current_page = 100 embed = get_right_coin(100) else: embed = get_right_coin(current_page) message = await ctx.send(embed=embed) if current_page <= 1: # Adds / Removes emoji if it passes threshold await message.add_reaction(emoji_list[1]) elif current_page >= 100: await message.add_reaction(emoji_list[0]) else: for emoji in emoji_list: await message.add_reaction(emoji) check = reaction_check(message=message, author=ctx.author, emoji=(emoji_list[0], emoji_list[1])) except TimeoutError: print('Timeout') except ValueError: await msg.delete() # Deletes message sent by user embed = discord.Embed( title=f'Input is not a rank: {msg.content}', description=' ', colour=discord.Colour.red() ) await ctx.send(embeds=[embed], delete_after=5.0) elif module == 'name': embed = discord.Embed( title='Please enter a name', description=' ', colour=discord.Colour.blurple() ) await ctx.send(embeds=[embed], delete_after=5.0) try: msg = await self.bot.wait_for('message', timeout=5.0) except asyncio.exceptions.TimeoutError: embed = discord.Embed( title=f'{ctx.author} failed to send a message within the allotted time', description=' ', colour=discord.Colour.red() ) await ctx.send(embeds=[embed], delete_after=5.0) try: coin_name = msg.content.lower() await msg.delete() # Deletes message sent by user for x in rows: # ID: x[0] || Name: x[1] || Symbol: x[2] || Price: x[3] || Rank: x[4] || Change: x[5] || Logo: x[6] if x[1].lower() == coin_name: current_page = x[4] embed = discord.Embed( title=f'${str(x[3])}', description=' ', colour=discord.Colour.blurple() ) embed.set_author( name=f'{x[4]}. {x[1]} / {x[2]}', icon_url=x[6] ) embed.add_field( name='24h %', value=f'{x[5]:.2f}%', inline=False) embed.set_footer(text="") message = await ctx.send(embed=embed) if current_page <= 1: # Adds / Removes emoji if it passes threshold await message.add_reaction(emoji_list[1]) elif current_page >= 100: await message.add_reaction(emoji_list[0]) else: for emoji in emoji_list: await message.add_reaction(emoji) check = reaction_check(message=message, author=ctx.author, emoji=(emoji_list[0], emoji_list[1])) while True: # Continues to run for 10 seconds until user does not click the emojis try: reaction, user = await self.bot.wait_for('reaction_add', timeout=10.0, check=check) if reaction.emoji == emoji_list[0]: # Left page await message.delete() # Deletes embed before sending a new one current_page = current_page - 1 if current_page <= 0: current_page = 1 embed = get_left_coin(1) else: embed = get_left_coin(current_page) message = await ctx.send(embed=embed) if current_page <= 1: # Adds / Removes emoji if it passes threshold await message.add_reaction(emoji_list[1]) elif current_page >= 100: await message.add_reaction(emoji_list[0]) else: for emoji in emoji_list: await message.add_reaction(emoji) check = reaction_check(message=message, author=ctx.author, emoji=(emoji_list[0], emoji_list[1])) elif reaction.emoji == emoji_list[1]: # Right page await message.delete() # Deletes embed before sending a new one current_page = current_page + 1 if current_page >= 100: current_page = 100 embed = get_right_coin(100) else: embed = get_right_coin(current_page) message = await ctx.send(embed=embed) if current_page <= 1: # Adds / Removes emoji if it passes threshold await message.add_reaction(emoji_list[1]) elif current_page >= 100: await message.add_reaction(emoji_list[0]) else: for emoji in emoji_list: await message.add_reaction(emoji) check = reaction_check(message=message, author=ctx.author, emoji=(emoji_list[0], emoji_list[1])) except TimeoutError: print('Timeout') except ValueError: await msg.delete() # Deletes message sent by user embed = discord.Embed( title=f'Input is not a name: {msg.content}', description=' ', colour=discord.Colour.red() ) await ctx.send(embeds=[embed], delete_after= 5.0) @cog_ext.cog_subcommand( base='market', name='top', description='Displays the top # coins from 1-100', guild_ids=guild_ids ) async def _market_top(self, ctx: SlashContext, *, rank): # Variables emoji_list = ['◀', '▶'] # Database cur.execute('SELECT * FROM coin_info ORDER BY coin_rank asc') # 1,2,3...,100 rows = cur.fetchall() try: rank = int(rank) if rank < 11: min = 1 max = 10 else: min = rank - 10 max = rank if max > 100: max = 100 embed = discord.Embed( title=' ', description=' ', colour=discord.Colour.blurple() ) # ID: x[0] || Name: x[1] || Symbol: x[2] || Price: x[3] || Rank: x[4] || Change: x[5] || Logo: x[6] for x in rows: if min <= x[4] <= max: embed.set_author(name=f'Top {max} Crypto Coins', icon_url=BOT_AVATAR) embed.add_field( name=f'{x[4]}. {x[1]} / {x[2]}', value=f'${x[3]}', inline=False) embed.set_footer(text="") message = await ctx.send(embed=embed) if rank <= 10: # Adds / Removes emoji if it passes threshold await message.add_reaction(emoji_list[1]) elif rank >= 100: await message.add_reaction(emoji_list[0]) else: for emoji in emoji_list: await message.add_reaction(emoji) check = reaction_check(message=message, author=ctx.author, emoji=(emoji_list[0], emoji_list[1])) current_page = max while True: try: reaction, user = await self.bot.wait_for('reaction_add', timeout=10.0, check=check) if reaction.emoji == emoji_list[0]: # Left page await message.delete() # Deletes embed before sending a new one current_page = current_page - 10 if current_page <= 0: current_page = 10 embed = get_left_10_coins(10) else: embed = get_left_10_coins(current_page) message = await ctx.send(embed=embed) if current_page <= 10: # Adds / Removes emoji if it passes threshold await message.add_reaction(emoji_list[1]) elif current_page >= 100: await message.add_reaction(emoji_list[0]) else: for emoji in emoji_list: await message.add_reaction(emoji) check = reaction_check(message=message, author=ctx.author, emoji=(emoji_list[0], emoji_list[1])) elif reaction.emoji == emoji_list[1]: # Right page await message.delete() # Deletes embed before sending a new one current_page = current_page + 10 if current_page >= 100: current_page = 100 embed = get_right_10_coins(100) else: embed = get_right_10_coins(current_page) message = await ctx.send(embed=embed) if current_page <= 1: # Adds / Removes emoji if it passes threshold await message.add_reaction(emoji_list[1]) elif current_page >= 100: await message.add_reaction(emoji_list[0]) else: for emoji in emoji_list: await message.add_reaction(emoji) check = reaction_check(message=message, author=ctx.author, emoji=(emoji_list[0], emoji_list[1])) except TimeoutError: print('Timeout') except ValueError: embed = discord.Embed( title=f'Input is not a rank: {rank}', description=' ', colour=discord.Colour.red() ) await ctx.send(embeds=[embed], delete_after=5.0)