async def channelperms(self, ctx): """Gets bot permissions for the current channel.""" chan_perms = ctx.channel.permissions_for(ctx.guild.me) req_perms = ctx.bot.req_perms perms_compare = chan_perms >= req_perms core_dir = ctx.bot.core_dir data_dir = os.path.join(core_dir, '..', 'data') data_file = 'permissions.json' msg = "Channel Permissions: {}\n".format(chan_perms.value) msg += "Met Minimum Permissions: {}\n\n".format(str(perms_compare)) with open(os.path.join(data_dir, data_file), "r") as perm_json: perm_dict = json.load(perm_json) for perm, bitshift in perm_dict.items(): if bool((req_perms.value >> bitshift) & 1): if bool((chan_perms.value >> bitshift) & 1): msg += ":white_small_square: {}\n".format(perm) else: msg += ":black_small_square: {}\n".format(perm) try: if chan_perms.embed_links: embed = utils.make_embed(msg_type='info', title='Channel Permissions', content=msg) await ctx.send(embed=embed) else: await ctx.send(msg) except discord.errors.Forbidden: embed = utils.make_embed(msg_type='info', title='Channel Permissions', content=msg) await ctx.author.send(embed=embed)
async def _prefix(self, ctx, *, new_prefix: str = None): """Get and set server prefix. Use the argument 'reset' to reset the guild prefix to default. """ if not ctx.guild: if new_prefix: embed = utils.make_embed(msg_type='error', title="Prefix cannot be set in DMs.") return await ctx.send(embed=embed) embed = utils.make_embed(msg_type='info', title="Prefix is {}".format(prefix)) return await ctx.send(embed=embed) if not new_prefix: guild_prefix = ctx.bot.prefixes.get(ctx.guild.id) prefix = guild_prefix or ctx.bot.default_prefix embed = utils.make_embed(msg_type='info', title="Prefix is {}".format(prefix)) return await ctx.send(embed=embed) if await checks.check_is_admin(ctx): await db.execute_sql( "INSERT OR REPLACE INTO prefixes(guild_id, prefix)" "VALUES(?, ?)", (ctx.guild.id, new_prefix)) ctx.bot.prefixes[ctx.guild.id] = new_prefix embed = utils.make_embed( msg_type='info', title="Prefix set to {}".format(new_prefix)) return await ctx.send(embed=embed) embed = utils.make_embed(msg_type='error', title="Prefix can only be set by admins.") return await ctx.send(embed=embed)
async def load(self, ctx, ext): """Load or reload an extension.""" bot = ctx.bot ext_folder = "extensions" ext_dir = os.path.join(os.path.dirname(__file__), "..", ext_folder) ext_files = [name for _, name, _ in pkgutil.iter_modules([ext_dir])] if ext in ext_files: ext_name = ("firetail.extensions." + ext) was_loaded = ext_name in bot.extensions try: bot.unload_extension(ext_name) bot.load_extension(ext_name) if was_loaded: msg = ext + ' extension reloaded.' else: msg = ext + ' extension loaded.' embed = utils.make_embed(msg_type='success', title=msg) await ctx.send(embed=embed) except Exception as e: # logger.critical('Error loading ext: {} - {}: {}'.format( # str(ext), type(e).__name__, e)) embed = utils.make_embed( msg_type='error', title='Error when loading ' + str(ext), content='{}: {}'.format(type(e).__name__, e)) await ctx.send(embed=embed) else: embed = utils.make_embed(msg_type='error', title=ext + ' extension not found.') await ctx.send(embed=embed)
async def _prefix(self, ctx, *, new_prefix: str = None): """Get and set server prefix. Use the argument 'reset' to reset the guild prefix to default. """ bot = ctx.bot default_prefix = bot.default_prefix if ctx.guild: if new_prefix: await bot.data.guild(ctx.guild.id).prefix(new_prefix) if new_prefix.lower() == 'reset': new_prefix = bot.default_prefix embed = utils.make_embed( msg_type='success', title="Prefix set to {}".format(new_prefix)) await ctx.send(embed=embed) else: guild_prefix = await bot.data.guild(ctx.guild).prefix() prefix = guild_prefix if guild_prefix else default_prefix if len(prefix) > 1: prefix = ', '.join(default_prefix) else: prefix = prefix[0] embed = utils.make_embed(msg_type='info', title="Prefix is {}".format(prefix)) await ctx.send(embed=embed) else: if len(default_prefix) > 1: prefix = ', '.join(default_prefix) else: prefix = default_prefix[0] embed = utils.make_embed(msg_type='info', title="Prefix is {}".format(prefix)) await ctx.send(embed=embed)
async def unload(self, ctx, ext): """Unload an extension.""" bot = ctx.bot ext_name = ("firetail.extensions." + ext) if ext_name in bot.extensions: bot.unload_extension(ext_name) embed = utils.make_embed(msg_type='success', title=ext + ' extension unloaded.') await ctx.send(embed=embed) else: embed = utils.make_embed(msg_type='error', title=ext + ' extension not loaded.') await ctx.send(embed=embed)
async def reload_em(self, ctx): """Reload Extension Manager.""" bot = ctx.bot try: bot.unload_extension('firetail.core.extension_manager') bot.load_extension('firetail.core.extension_manager') embed = utils.make_embed(msg_type='success', title='Extension Manager reloaded.') await ctx.send(embed=embed) except Exception as e: msg = "{}: {}".format(type(e).__name__, e) embed = utils.make_embed(msg_type='error', title='Error loading Extension Manager', content=msg) await ctx.send(embed=embed)
async def _nickname(self, ctx, *, nickname: str): """Sets bot nickname""" try: await ctx.guild.me.edit(nick=nickname) except discord.Forbidden: embed = utils.make_embed( msg_type='success', title="Failed to set nickname", content=("I'm missing permissions to change my nickname. " "Use **{}get guildperms** to check permissions." "").format(ctx.prefix)) await ctx.send() else: embed = utils.make_embed(msg_type='success', title="Nickname set.") await ctx.send(embed=embed)
async def reload_core(self, ctx): """Reload Core Commands.""" bot = ctx.bot try: bot.unload_extension('firetail.core.commands') bot.load_extension('firetail.core.commands') embed = utils.make_embed(msg_type='success', title='Core Commands reloaded.') await ctx.send(embed=embed) except Exception as e: msg = f"{type(e).__name__}: {e}" embed = utils.make_embed(msg_type='error', title='Error loading Core Commands', content=msg) await ctx.send(embed=embed)
async def reload_dm(self, ctx): """Reload Data Manager.""" bot = ctx.bot try: bot.unload_extension('firetail.data_manager') bot.load_extension('firetail.data_manager') embed = utils.make_embed(msg_type='success', title='Data Manager reloaded.') await ctx.send(embed=embed) except Exception as e: msg = f"{type(e).__name__}: {e}" embed = utils.make_embed(msg_type='error', title='Error loading Data Manager', content=msg) await ctx.send(embed=embed)
async def _username(self, ctx, *, username: str): """Sets bot username""" try: await ctx.bot.user.edit(username=username) except discord.HTTPException: embed = utils.make_embed( msg_type='error', title="Failed to change name", content=("Remember that you can only do it up to 2 times an " "hour. Use nicknames if you need frequent changes. " "**{}set nickname**").format(ctx.prefix)) await ctx.send(embed=embed) else: embed = utils.make_embed(msg_type='success', title="Username set.") await ctx.send(embed=embed)
async def post_operation(self, operation, very_soon): if very_soon: title = 'Fleet Starting In Less Than 5 Minutes' elif very_soon is None: title = 'New Fleet Posted' else: title = 'Fleet Starting In Less Than 30 Minutes' doctrine = 'N/A' if len(operation['Doctrines']) > 0: doctrine = operation['Doctrines'] embed = make_embed( title=title, title_url='https://fleet-up.com/Operation#{}'.format( operation['Id'])) embed.set_footer(icon_url=self.bot.user.avatar_url, text="Provided Via Firetail Bot & Fleet-Up") embed.set_thumbnail( url="https://fleet-up.com/Content/Images/logo_title.png") embed.add_field( name="Fleet Information", value='Fleet Name: {}\nFleet Time: {} EVE\nPlanned Doctrines: {}\n' 'Form-Up Location: {} {}\nOrganizer: {}\n\nDetails: {}'.format( operation['Subject'], operation['StartString'], doctrine, operation['Location'], operation['LocationInfo'], operation['Organizer'], operation['Details'])) dest = self.bot.get_channel(int(self.config.fleetUp['channel_id'])) await dest.send(embed=embed)
async def _status(self, ctx): """Shows the current status of TQ.""" # Spam Check global status, player_count self.logger.info('EveStatus - {} requested server info.'.format( str(ctx.message.author))) data = await ctx.bot.esi_data.server_info() try: if data.get('start_time'): status = 'Online' player_count = data.get('players') except Exception: status = 'Offline' player_count = 'N/A' embed = make_embed(guild=ctx.guild) embed.set_footer(icon_url=ctx.bot.user.avatar_url, text="Provided Via Firetail Bot") embed.set_thumbnail( url="https://image.eveonline.com/Alliance/434243723_64.png") embed.add_field(name="Status", value="Server State:\nPlayer Count:", inline=True) embed.add_field(name="-", value="{}\n{}".format(status, player_count), inline=True) dest = ctx.author if ctx.bot.config.dm_only else ctx await dest.send(embed=embed) if ctx.bot.config.delete_commands: await ctx.message.delete()
async def report_upcoming(self, ctx, system_data, fight_type, defender_name): constellation_data = await self.bot.esi_data.constellation_info( system_data['constellation_id']) constellation_name = constellation_data['name'] region_id = constellation_data['region_id'] region_data = await self.bot.esi_data.region_info(region_id) region_name = region_data['name'] zkill_link = "https://zkillboard.com/system/{}".format( system_data['system_id']) dotlan_link = "http://evemaps.dotlan.net/system/{}".format( system_data['name'].replace(' ', '_')) constellation_dotlan = "http://evemaps.dotlan.net/map/{}/{}".format( region_name.replace(' ', '_'), constellation_name.replace(' ', '_')) title = 'Upcoming Sov Battle In: {}'.format(system_data['name']) embed = make_embed( msg_type='info', title=title, title_url=dotlan_link, content= '[ZKill]({}) / [{}]({}) / [Constellation: {}]({})\nDo this command again once ' 'the battle has begun to receive live updates.'.format( zkill_link, system_data['name'], dotlan_link, constellation_name, constellation_dotlan)) embed.set_footer(icon_url=ctx.bot.user.avatar_url, text="Provided Via firetail Bot") embed.add_field(name="Upcoming Sov Battle", value='Defender:\nFight Type:') embed.add_field(name="-", value='{}\n{}'.format(defender_name, fight_type), inline=True) await ctx.channel.send(embed=embed)
async def report_ended(self, system_data, tracked_fight_type, winner, channel_id): fight_type_raw = tracked_fight_type fight_type = fight_type_raw.replace('_', ' ').title() constellation_data = await self.bot.esi_data.constellation_info( system_data['constellation_id']) constellation_name = constellation_data['name'] region_id = constellation_data['region_id'] region_data = await self.bot.esi_data.region_info(region_id) region_name = region_data['name'] zkill_link = f"https://zkillboard.com/system/{system_data['system_id']}" dotlan_link = f"http://evemaps.dotlan.net/system/{system_data['name'].replace(' ', '_')}" constellation_dotlan = f"http://evemaps.dotlan.net/map/{region_name}/{constellation_name}".replace( ' ', '_') title = f"Sov Battle In {system_data['name']} has ended." embed = make_embed( msg_type='info', title=title, title_url=dotlan_link, content= (f"[ZKill]({zkill_link}) / " f"[{system_data['name']}]({dotlan_link}) / " f"[Constellation: {constellation_name}]({constellation_dotlan})\n\n" f"The {fight_type} fight has ended with the {winner} claiming victory." ), inline=False) channel = self.bot.get_channel(channel_id) try: await channel.send(embed=embed) except Exception: return None
async def report_upcoming(self, ctx, system_data, fight_type, defender_name): constellation_data = await self.bot.esi_data.constellation_info( system_data['constellation_id']) constellation_name = constellation_data['name'] region_id = constellation_data['region_id'] region_data = await self.bot.esi_data.region_info(region_id) region_name = region_data['name'] zkill_link = f"https://zkillboard.com/system/{system_data['system_id']}" dotlan_link = f"http://evemaps.dotlan.net/system/{system_data['name'].replace(' ', '_')}" constellation_dotlan = f"http://evemaps.dotlan.net/map/{region_name}/{constellation_name}".replace( ' ', '_') title = f"Upcoming Sov Battle In: {system_data['name']}" embed = make_embed( msg_type='info', title=title, title_url=dotlan_link, content= (f"[ZKill]({zkill_link}) / " f"[{system_data['name']}]({dotlan_link}) / " f"[Constellation: {constellation_name}]({constellation_dotlan})\n" f"Do this command again once the battle has begun to receive live updates." )) embed.add_field( name="Upcoming Sov Battle", value=f'Defender: {defender_name}\nFight Type: {fight_type}', inline=False) await ctx.channel.send(embed=embed)
async def list(self, ctx): """List all available extensions and their loaded status.""" ext_folder = "extensions" ext_dir = os.path.join(os.path.dirname(__file__), "..", ext_folder) ext_files = [name for _, name, _ in pkgutil.iter_modules([ext_dir])] loaded_ext = [] count_loaded = 0 count_ext = 0 msg = "" for ext in ctx.bot.extensions: loaded_ext.append(ext) for ext in ext_files: count_ext += 1 ext_name = ("firetail.extensions." + ext) is_loaded = ext_name in loaded_ext status = ":black_small_square:" if is_loaded: count_loaded += 1 status = ":white_small_square:" msg += "{0} {1}\n".format(status, ext) count_msg = "{} of {} extensions loaded.\n\n".format( count_loaded, count_ext) embed = utils.make_embed(msg_type='info', title='Available Extensions', content=count_msg + msg) await ctx.send(embed=embed)
async def charinfo(self, ctx, *, characters: str): """ Shows you information about unicode characters. Only up to 25 characters at a time. """ if len(characters) > 25: return await ctx.send(f'Too many characters ({len(characters)}/25)' ) charlist = [] rawlist = [] for char in characters: digit = f'{ord(char):x}' name = f"[{unicodedata.name(char, '')}](http://www.fileformat.info/info/unicode/char/{digit})" u_code = f'\\U{digit:>08}' if len(str(digit)) <= 4: u_code = f'\\u{digit:>04}' charlist.append(f'`{u_code.ljust(10)}`: {name} - {char}') rawlist.append(u_code) embed = utils.make_embed(msg_type='info', title='Character Info', content='\n'.join(charlist)) if len(characters) > 1: embed.add_field(name='Raw', value=f"`{''.join(rawlist)}`", inline=False) await ctx.send(embed=embed)
async def charinfo(self, ctx, *, characters: str): """Shows you information about unicode characters. Only up to 25 characters at a time. """ if len(characters) > 25: return await ctx.send( 'Too many characters ({}/25)'.format(len(characters))) charlist = [] rawlist = [] for char in characters: digit = '{0:x}'.format(ord(char)) url = "http://www.fileformat.info/info/unicode/char/{}".format( digit) name = "[{}]({})".format(unicodedata.name(char, ''), url) u_code = '\\U{0:>08}'.format(digit) if len(str(digit)) <= 4: u_code = '\\u{0:>04}'.format(digit) charlist.append( ' '.join(['`{}`:'.format(u_code.ljust(10)), name, '-', char])) rawlist.append(u_code) embed = utils.make_embed( msg_type='info', title='Character Info', content='\n'.join(charlist)) if len(characters) > 1: embed.add_field( name='Raw', value="`{}`".format(''.join(rawlist)), inline=False) await ctx.send(embed=embed)
async def showext(self, ctx): """Show raw extension list.""" bot = ctx.bot embed = utils.make_embed(msg_type='info', title='Raw Extension List', content='\n'.join(bot.extensions)) await ctx.send(embed=embed)
async def _sessions_resumed(self, ctx): """Gets the number of websocket reconnections.""" r_c = ctx.bot.resumed_count embed = utils.make_embed( msg_type='info', title="Connections Resumed: {}".format(r_c)) await ctx.send(embed=embed)
async def _ping(self, ctx): """Gets the discord server response time.""" msg = "{0:.2f} ms".format(ctx.bot.ws.latency * 1000) embed = utils.make_embed( msg_type='info', title='Bot Latency: {}'.format(msg)) await ctx.send(embed=embed)
async def _rpg_top(self, ctx): """Get the top RPG players""" sql = ''' SELECT * FROM eve_rpg_players WHERE `player_id` = (?) ''' values = (ctx.message.author.id,) result = await db.select_var(sql, values) sql = ''' SELECT * FROM eve_rpg_players ORDER BY `level` DESC LIMIT 10 ''' top_levels = await db.select(sql) top_levels_array = [] for levels in top_levels: top_levels_user = self.bot.get_user(int(levels[2])) top_levels_array.append('{} - Level {}'.format(top_levels_user.display_name, levels[5])) levels_list = '\n'.join(top_levels_array) sql = ''' SELECT * FROM eve_rpg_players ORDER BY `kills` DESC LIMIT 10 ''' top_killers = await db.select(sql) top_killers_array = [] for killers in top_killers: top_killer_user = self.bot.get_user(int(killers[2])) top_killers_array.append('{} - {} Kills'.format(top_killer_user.display_name, killers[3])) killers_list = '\n'.join(top_killers_array) if result is None: return await ctx.author.send('**Error** - No player found. You must be part of the game to view this') else: embed = make_embed(guild=ctx.guild) embed.set_footer(icon_url=ctx.bot.user.avatar_url, text="Provided Via Firetail Bot") embed.add_field(name="Level Leaderboard", value=levels_list, inline=False) embed.add_field(name="Kills Leaderboard", value=killers_list, inline=False) await ctx.channel.send(embed=embed)
async def report_ended(self, system_data, tracked_fight_type, winner, channel_id): fight_type_raw = tracked_fight_type fight_type = fight_type_raw.replace('_', ' ').title() constellation_data = await self.bot.esi_data.constellation_info( system_data['constellation_id']) constellation_name = constellation_data['name'] region_id = constellation_data['region_id'] region_data = await self.bot.esi_data.region_info(region_id) region_name = region_data['name'] zkill_link = "https://zkillboard.com/system/{}".format( system_data['system_id']) dotlan_link = "http://evemaps.dotlan.net/system/{}".format( system_data['name'].replace(' ', '_')) constellation_dotlan = "http://evemaps.dotlan.net/map/{}/{}".format( region_name.replace(' ', '_'), constellation_name.replace(' ', '_')) title = 'Sov Battle In {} has ended.'.format(system_data['name']) embed = make_embed( msg_type='info', title=title, title_url=dotlan_link, content= '[ZKill]({}) / [{}]({}) / [Constellation: {}]({})\n\nThe {} fight has ended with' ' the {} claiming victory.'.format(zkill_link, system_data['name'], dotlan_link, constellation_name, constellation_dotlan, fight_type, winner)) embed.set_footer(icon_url=self.bot.user.avatar_url, text="Provided Via firetail Bot") channel = self.bot.get_channel(channel_id) try: await channel.send(embed=embed) except: return None
async def status(self, ctx, *, status: str): """Sets bot status Available statuses: online idle dnd """ statuses = { "online": discord.Status.online, "idle": discord.Status.idle, "dnd": discord.Status.dnd, "invisible": discord.Status.invisible } game = ctx.me.game try: status = statuses[status.lower()] except KeyError: await ctx.bot.send_cmd_help(ctx) else: await ctx.bot.change_presence(status=status, game=game) embed = utils.make_embed( msg_type='success', title="Status changed to {}.".format(status)) await ctx.send(embed=embed)
async def _rpg_stats(self, ctx): """Get your RPG Stats""" sql = ''' SELECT * FROM eve_rpg_players WHERE `player_id` = (?) ''' values = (ctx.message.author.id,) result = await db.select_var(sql, values) sql = ''' SELECT * FROM eve_rpg_players ORDER BY `level` DESC LIMIT 1 ''' top_level = await db.select(sql) top_level_user = self.bot.get_user(int(top_level[0][2])) sql = ''' SELECT * FROM eve_rpg_players ORDER BY `kills` DESC LIMIT 1 ''' top_killer = await db.select(sql) top_killer_user = self.bot.get_user(int(top_killer[0][2])) if result is None: return await ctx.author.send('**Error** - No player found.') else: ship_attack, ship_defense, ship_maneuverability, ship_tracking = await self.ship_attributes(result) item_attack, item_defense, item_maneuverability, item_tracking = await self.item_attributes(result) ship_stats = ' {}/{}/{}/{}'.format(ship_attack, ship_defense, ship_maneuverability, ship_tracking) item_stats = ' {}/{}/{}/{}'.format(item_attack, item_defense, item_maneuverability, item_tracking) embed = make_embed(guild=ctx.guild) embed.set_footer(icon_url=ctx.bot.user.avatar_url, text="Provided Via Firetail Bot") embed.add_field(name="Stats", value='\n Level: {}\nXP: {}/100\nShip : {}\nAttack/Defense/Maneuverability/Tracking: {}\n' 'Items: {}\nItem Bonuses (Already applied to ship): {}\nKills: {}\nLosses: {}'.format( result[0][5], result[0][6], result[0][7], ship_stats, result[0][8], item_stats, result[0][3], result[0][4])) embed.add_field(name="Top Players", value='\n Top Level: {} (Level {})\nMost Kills: {} ({} Kills)'.format( top_level_user.display_name, top_level[0][5], top_killer_user.display_name, top_killer[0][3]), inline=False) await ctx.channel.send(embed=embed)
async def _game(self, ctx, *, game: str): """Sets bot game status""" status = ctx.me.status game = discord.Game(name=game) await ctx.bot.change_presence(status=status, game=game) embed = utils.make_embed(msg_type='success', title='Game set.') await ctx.send(embed=embed)
async def _break(self, ctx): """Simulates a sudden disconnection.""" embed = utils.make_embed(msg_type='warning', title='Faking a crash...') try: await ctx.send(embed=embed) except discord.HTTPException: pass await ctx.bot.logout()
async def purge(self, ctx, msg_number: int = 10): """Delete a number of messages from the channel. Default is 10. Max 100.""" if msg_number > 100: embed = utils.make_embed( msg_type='info', title="ERROR", content="No more than 100 messages can be purged at a time.", guild=ctx.guild) await ctx.send(embed=embed) return deleted = await ctx.channel.purge(limit=msg_number) embed = utils.make_embed() result_msg = await ctx.send('Deleted {} message{}'.format( len(deleted), "s" if len(deleted) > 1 else "")) await asyncio.sleep(3) await result_msg.delete()
async def _restart(self, ctx): """Restarts the bot""" embed = utils.make_embed(title='Restarting.', msg_colour='red', icon="https://i.imgur.com/uBYS8DR.png") try: await ctx.send(embed=embed) except discord.HTTPException: pass await ctx.bot.shutdown(restart=True)
async def _shutdown(self, ctx): """Shuts down the bot""" embed = utils.make_embed(title='Shutting down.', msg_colour='red', icon="https://i.imgur.com/uBYS8DR.png") try: await ctx.send(embed=embed) except discord.HTTPException: pass await ctx.bot.shutdown()