diff --git a/api/inspirobot.py b/api/inspirobot.py index d47cd36..2be3e42 100644 --- a/api/inspirobot.py +++ b/api/inspirobot.py @@ -1,3 +1,8 @@ +''' +A module that sits between the API and the cog +and provides functions for easy communication +with the inspirobot API +''' import requests from util import logging diff --git a/api/nasa.py b/api/nasa.py index df508e8..e17fb55 100644 --- a/api/nasa.py +++ b/api/nasa.py @@ -1,9 +1,14 @@ +''' +A module that sits between the API and the cog +and provides functions for easy communication +with the NASA API +''' import requests from util import config, logging api_key = config.settings["api_keys"]["nasa"] -def image_of_the_day(): +def image_of_the_day() -> str: url = f"https://api.nasa.gov/planetary/apod?api_key={api_key}" response = requests.get(url) diff --git a/api/steam.py b/api/steam.py index e05cf9a..b72eea6 100644 --- a/api/steam.py +++ b/api/steam.py @@ -1,19 +1,19 @@ +''' +A module that sits between the API and the cog +and provides functions for easy communication +with the Steam API +''' import requests import json -from util import logging +from util import logging, config -# This module acts as an interface between the bot and the Steam API -# The responses of the API are formatted and returned in a standard format - -with open("config.json", "r") as key_file: - json = json.load(key_file) - key = json["api_keys"]["steam"] +key = config.settings["api_keys"]["steam"] # Returns a (hopefully) valid Steam API URL -def assemble_url(interface_name, method_name, version): +def assemble_url(interface_name: str, method_name: str, version: int) -> str: return f"http://api.steampowered.com/{interface_name}/{method_name}/v{version}/?key={key}&format=json" -def get_json_request_response(url : str): +def get_json_request_response(url: str): response = requests.get(url) if not response.ok: @@ -24,7 +24,7 @@ def get_json_request_response(url : str): return json # Finds the SteamID of a user by their Vanity URL -def resolve_vanity_url(vanity_url : str) -> str: +def resolve_vanity_url(vanity_url: str) -> str: url = assemble_url("ISteamUser", "ResolveVanityURL", 1) + f"&vanityurl={vanity_url}" json = get_json_request_response(url) @@ -37,7 +37,7 @@ def resolve_vanity_url(vanity_url : str) -> str: # Gets a users steam level -def get_steam_level(vanity_url : str) -> str: +def get_steam_level(vanity_url: str) -> str: steamid = resolve_vanity_url(vanity_url) if steamid is None: logging.error("Could not resolve Vanity URL") @@ -52,7 +52,7 @@ def get_steam_level(vanity_url : str) -> str: return json["response"]["player_level"] # Gets the percentage of players who have a lower level -def get_steam_level_distribution(level : str) -> str: +def get_steam_level_distribution(level: str) -> str: url = assemble_url("IPlayerService", "GetSteamLevelDistribution", 1) + f"&player_level={level}" json = get_json_request_response(url) diff --git a/bot.py b/bot.py index 1939712..b31d6b5 100644 --- a/bot.py +++ b/bot.py @@ -6,6 +6,7 @@ from util import logging, config # Bot URL https://discordapp.com/api/oauth2/authorize?client_id=657709911337074698&permissions=314432&scope=bot +# The config must be loaded before everything else total = 0 failed = 0 @@ -19,13 +20,12 @@ logging.info("Finished loading configs.") logging.info(f"Total {total}, Failed {failed}\n") - client = commands.Bot(command_prefix=config.settings["prefix"], case_insensitive=True) @client.command() @commands.is_owner() -async def load(ctx, extension): +async def load(ctx : commands.Context, extension : str): try: client.load_extension(f"cogs.{extension}") await ctx.message.add_reaction("👍") @@ -34,7 +34,7 @@ async def load(ctx, extension): @client.command() @commands.is_owner() -async def unload(ctx, extension): +async def unload(ctx : commands.Context, extension : str): try: client.unload_extension(f"cogs.{extension}") await ctx.message.add_reaction("👍") @@ -43,7 +43,7 @@ async def unload(ctx, extension): @client.command() @commands.is_owner() -async def reload(ctx, extension): +async def reload(ctx : commands.Context, extension : str): try: client.reload_extension(f"cogs.{extension}") await ctx.message.add_reaction("👍") @@ -53,6 +53,7 @@ async def reload(ctx, extension): @client.event async def on_ready(): + # Try to load cogs logging.info("--- Loading cogs ---\n") total = 0 diff --git a/cogs/api/inspirobot.py b/cogs/api/inspirobot.py index 06c1984..c533b41 100644 --- a/cogs/api/inspirobot.py +++ b/cogs/api/inspirobot.py @@ -1,3 +1,8 @@ +''' +This is the cog that allows users to +fetch an AI-generated inspirational quote +made by Inspirobot +''' import discord from discord.ext import commands @@ -6,12 +11,12 @@ from util import config class Inspirobot(commands.Cog): - def __init__(self, client): + def __init__(self, client : discord.Client): self.client = client @commands.command(name="Inspirobot", description="Sends a randomly generated inspirational quote", aliases=["inspiration", "inspiro"]) @commands.cooldown(1, 5) - async def inspirobot(self, ctx): + async def inspirobot(self, ctx : commands.Context): image = inspirobot.get_inspirational_quote() if image is None: await ctx.message.add_reaction("⚠️") @@ -20,5 +25,5 @@ class Inspirobot(commands.Cog): embed.set_image(url=image) await ctx.send(embed=embed) -def setup(client): +def setup(client : discord.Client): client.add_cog(Inspirobot(client)) \ No newline at end of file diff --git a/cogs/api/nasa.py b/cogs/api/nasa.py index 3911b1c..4875ef4 100644 --- a/cogs/api/nasa.py +++ b/cogs/api/nasa.py @@ -1,3 +1,7 @@ +''' +This cog is capable of communicating with the +NASA API +''' import discord from discord.ext import commands from api import nasa @@ -5,12 +9,12 @@ from util import config class Nasa(commands.Cog): - def __init__(self, client): + def __init__(self, client: discord.Client): self.client = client @commands.command(name="APOD", description="Posts NASA's picture of the day.") @commands.cooldown(1, 30) - async def apod(self, ctx): + async def apod(self, ctx: commands.Context): url = nasa.image_of_the_day() embed = discord.Embed(title="Astronomy Picture of the day", color=int(config.settings["color"], 16)) embed.set_image(url=url) @@ -18,5 +22,5 @@ class Nasa(commands.Cog): await ctx.send(embed=embed) -def setup(client): +def setup(client: discord.Client): client.add_cog(Nasa(client)) \ No newline at end of file diff --git a/cogs/api/steam.py b/cogs/api/steam.py index b8aee1a..24a301d 100644 --- a/cogs/api/steam.py +++ b/cogs/api/steam.py @@ -1,15 +1,19 @@ +''' +This cog can fetch data from the +Steam WebAPI +''' import discord from discord.ext import commands from api import steam class Steam(commands.Cog): - def __init__(self, client): + def __init__(self, client: discord.Client): self.client = client @commands.command(name="SteamLevel", description="Finds the steam level of a user", usage="SteamLevel ", aliases=["level"]) @commands.cooldown(1, 2) - async def SteamLevel(self, ctx, vanity_url): + async def SteamLevel(self, ctx: commands.Context, vanity_url: str): level = steam.get_steam_level(vanity_url) if level is None: @@ -17,9 +21,7 @@ class Steam(commands.Cog): else: percentile = round(float(steam.get_steam_level_distribution(level)), 2) await ctx.send(f"{vanity_url} is level {level}! This makes him better than {percentile}% of Steam users!") - - -def setup(client): +def setup(client: discord.Client): client.add_cog(Steam(client)) \ No newline at end of file diff --git a/cogs/fun/autoconvert.py b/cogs/fun/autoconvert.py index 7e517b5..bf6bf37 100644 --- a/cogs/fun/autoconvert.py +++ b/cogs/fun/autoconvert.py @@ -1,3 +1,8 @@ +''' +Listens for certain keywords in messages and +then provides conversion charts that might be +useful. +''' import discord from discord.ext import commands from util import logging, checking, config @@ -5,7 +10,7 @@ import re class AutoConvert(commands.Cog): - def __init__(self, client): + def __init__(self, client: discord.Client): self.client = client self.currencies = ['€', '$', '£'] self.currency_conversion = { @@ -33,7 +38,7 @@ class AutoConvert(commands.Cog): return prices - def convert_currency(self, _from, to, value): + def convert_currency(self, _from: str, to: str, value: float) -> float: if _from == '€': conversion_rate = self.currency_conversion[_from + to] elif to == '€': @@ -44,7 +49,7 @@ class AutoConvert(commands.Cog): return round(value * conversion_rate, 2) @commands.Cog.listener() - async def on_message(self, message): + async def on_message(self, message: discord.Message): if message.author.bot: return @@ -63,13 +68,9 @@ class AutoConvert(commands.Cog): currency_string += f"{self.convert_currency(element[1], currency, element[0])}{currency}, " embed.add_field(name=str(element[0])+element[1], value=currency_string[:-2]) - - if not empty: await message.channel.send(embed=embed) - - -def setup(client): +def setup(client: discord.Client): client.add_cog(AutoConvert(client)) \ No newline at end of file diff --git a/cogs/fun/coinflip.py b/cogs/fun/coinflip.py index d18f959..9a510e0 100644 --- a/cogs/fun/coinflip.py +++ b/cogs/fun/coinflip.py @@ -1,18 +1,23 @@ +''' +Flips a coin. +Will probably reworked into a "games" cog to +hold more interactive commands +''' import discord import random from discord.ext import commands class Coinflip(commands.Cog): - def __init__(self, client): + def __init__(self, client: discord.Client): self.client = client @commands.command(name="coinflip", description="Flips a coin and reacts with the result", aliases=["coin", "flip"]) - async def coinflip(self, ctx): + async def coinflip(self, ctx: commands.Context): if random.randint(0, 1) == 0: await ctx.message.add_reaction("🌑") else: await ctx.message.add_reaction("🌕") -def setup(client): +def setup(client: discord.Client): client.add_cog(Coinflip(client)) \ No newline at end of file diff --git a/cogs/fun/reactions.py b/cogs/fun/reactions.py index 349fe45..4764ccb 100644 --- a/cogs/fun/reactions.py +++ b/cogs/fun/reactions.py @@ -1,16 +1,21 @@ +''' +Listens to keywords in messages and +reacts accordingly +''' import discord from discord.ext import commands class Reactions(commands.Cog): - def __init__(self, client): + def __init__(self, client: discord.Client): self.client = client @commands.Cog.listener() - async def on_message(self, message : discord.Message): + async def on_message(self, message: discord.Message): if message.author.bot: return + # Flags if "canada" in message.content.lower(): await message.add_reaction("🇨🇦") @@ -28,9 +33,10 @@ class Reactions(commands.Cog): await message.add_reaction("🇦") await message.add_reaction("🇾") - if "extremejoy" in str(message): - message.add_reaction(664251611765407745) + + if "extremejoy" in message.content.lower(): + await message.add_reaction("<:extremejoy:612424729969819648>") -def setup(client): +def setup(client: discord.Client): client.add_cog(Reactions(client)) \ No newline at end of file diff --git a/util/checking.py b/util/checking.py index 8588a0b..043c7ec 100644 --- a/util/checking.py +++ b/util/checking.py @@ -1,8 +1,13 @@ +''' +This module will provide permission checks +for the command executions. +''' + import discord from discord.ext import commands from util import logging -def is_author_bot(ctx : commands.Context): +def is_author_bot(ctx : commands.Context) -> bool: if ctx.message.author.bot: return False return True \ No newline at end of file diff --git a/util/config.py b/util/config.py index f4db680..6a3de26 100644 --- a/util/config.py +++ b/util/config.py @@ -1,10 +1,15 @@ +''' +This module loads settings. Right now +it can only hold one config file at a time +''' + import json from util import logging filepath = "" settings = {} -def load(file): +def load(file : str) -> bool: global settings filepath = file try: diff --git a/util/logging.py b/util/logging.py index 94612d4..17e9722 100644 --- a/util/logging.py +++ b/util/logging.py @@ -1,10 +1,14 @@ +''' +Provides some simple logging utility +''' import datetime path = "logs/log.txt" cleanup = open(path, "w+") cleanup.close() -def log(msg, log_type, mute): +# Format: [DD.MM.YYYY HH:MM:SS] [] MESSAGE +def log(msg: str, log_type: str, mute: bool): log = f"[{datetime.datetime.now().strftime('%d.%m.%Y %H:%M:%S')}] [{log_type.upper()}] {msg}" log_file = open(path, "a") log_file.write(log + "\n") @@ -12,11 +16,11 @@ def log(msg, log_type, mute): if mute == False: print(log) -def info(msg, mute=False): +def info(msg: str, mute: bool=False): log(msg, "info", mute) -def warning(msg, mute=False): +def warning(msg: str, mute: bool=False): log(msg, "warning", mute) -def error(msg, mute=False): +def error(msg: str, mute: bool=False): log(msg, "error", mute)