From 75a86a0c9d6857c21e5b9c37f0354ac70730c06c Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Fri, 31 Mar 2023 19:00:25 +0000 Subject: [PATCH 001/184] [pip](deps): Bump better-ipc from 2.0.1 to 2.0.3 (#297) Bumps [better-ipc](https://github.com/MiroslavRosenov/better-ipc) from 2.0.1 to 2.0.3. - [Release notes](https://github.com/MiroslavRosenov/better-ipc/releases) - [Commits](https://github.com/MiroslavRosenov/better-ipc/commits) --- updated-dependencies: - dependency-name: better-ipc dependency-type: direct:production update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 10 +++++----- pyproject.toml | 2 +- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/poetry.lock b/poetry.lock index 6d107d40..0da3fb34 100644 --- a/poetry.lock +++ b/poetry.lock @@ -1,4 +1,4 @@ -# This file is automatically @generated by Poetry 1.4.0 and should not be changed by hand. +# This file is automatically @generated by Poetry and should not be changed by hand. [[package]] name = "aiodns" @@ -343,14 +343,14 @@ files = [ [[package]] name = "better-ipc" -version = "2.0.1" +version = "2.0.3" description = "A high-performance inter-process communication library designed to work with the latest version of discord.py" category = "main" optional = false python-versions = ">=3.8.0" files = [ - {file = "better-ipc-2.0.1.tar.gz", hash = "sha256:eb7f057c74ac9eae4363da9ef85928805bc1c52c65b024eb445284585c1996e9"}, - {file = "better_ipc-2.0.1-py3-none-any.whl", hash = "sha256:419e37dc30d9a8b7989a3fbd79c150c704b36b32345db1ffd5a23b759c867703"}, + {file = "better-ipc-2.0.3.tar.gz", hash = "sha256:000c19f279760e88361d06318b51f970a8bf916a1e45fd35a812570ee317cfc6"}, + {file = "better_ipc-2.0.3-py3-none-any.whl", hash = "sha256:dfb82c2497591d711f05c07b38e0886d6327d678d5e090c33174706c0ff0e5b1"}, ] [package.dependencies] @@ -2629,4 +2629,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "268867ed882e0ca50ec340b1920179b5a8ae7650ec1a46bed8af8f73556d4f4f" +content-hash = "f7034af3d507f874842cf8bd9c24c34f17a9fbeb253ba34af03f2b2ac95b48f5" diff --git a/pyproject.toml b/pyproject.toml index a7fd937c..8d616099 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -15,7 +15,7 @@ asyncpraw = "^7.7.0" uvloop = "^0.17.0" gql = { extras = ["aiohttp"], version = "^3.4.0" } rin-exceptions = "^1.0.3" -better-ipc = "^2.0.1" +better-ipc = "^2.0.3" prisma = "^0.8.2" redis = {extras = ["hiredis"], version = "^4.5.4"} ciso8601 = "^2.3.0" From 9f058693ce6354f271cc417178e087614f905731 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 4 Apr 2023 19:00:16 +0000 Subject: [PATCH 002/184] [pip](deps-dev): Bump pre-commit from 3.2.1 to 3.2.2 (#300) Bumps [pre-commit](https://github.com/pre-commit/pre-commit) from 3.2.1 to 3.2.2. - [Release notes](https://github.com/pre-commit/pre-commit/releases) - [Changelog](https://github.com/pre-commit/pre-commit/blob/main/CHANGELOG.md) - [Commits](https://github.com/pre-commit/pre-commit/compare/v3.2.1...v3.2.2) --- updated-dependencies: - dependency-name: pre-commit dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index 0da3fb34..13f3dc8a 100644 --- a/poetry.lock +++ b/poetry.lock @@ -1729,14 +1729,14 @@ testing = ["pytest", "pytest-benchmark"] [[package]] name = "pre-commit" -version = "3.2.1" +version = "3.2.2" description = "A framework for managing and maintaining multi-language pre-commit hooks." category = "dev" optional = false python-versions = ">=3.8" files = [ - {file = "pre_commit-3.2.1-py2.py3-none-any.whl", hash = "sha256:a06a7fcce7f420047a71213c175714216498b49ebc81fe106f7716ca265f5bb6"}, - {file = "pre_commit-3.2.1.tar.gz", hash = "sha256:b5aee7d75dbba21ee161ba641b01e7ae10c5b91967ebf7b2ab0dfae12d07e1f1"}, + {file = "pre_commit-3.2.2-py2.py3-none-any.whl", hash = "sha256:0b4210aea813fe81144e87c5a291f09ea66f199f367fa1df41b55e1d26e1e2b4"}, + {file = "pre_commit-3.2.2.tar.gz", hash = "sha256:5b808fcbda4afbccf6d6633a56663fed35b6c2bc08096fd3d47ce197ac351d9d"}, ] [package.dependencies] @@ -2629,4 +2629,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "f7034af3d507f874842cf8bd9c24c34f17a9fbeb253ba34af03f2b2ac95b48f5" +content-hash = "bd43cd028ee08cb25b3d5d2e99839df498d9902544137e9ddb9e2b0c3509db2b" diff --git a/pyproject.toml b/pyproject.toml index 8d616099..4aee870f 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -31,7 +31,7 @@ nox-poetry = "^1.0.2" pytest-cov = "^4.0.0" [tool.poetry.group.dev.dependencies] -pre-commit = "^3.2.1" +pre-commit = "^3.2.2" pyinstrument = "^4.4.0" pyright = "^1.1.301" watchfiles = "^0.19.0" From c19b2d5af0c470a429c5ef3287e9f46d5a5c9fa2 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 5 Apr 2023 18:59:17 +0000 Subject: [PATCH 003/184] [pip](deps-dev): Bump pyright from 1.1.301 to 1.1.302 (#301) Bumps [pyright](https://github.com/RobertCraigie/pyright-python) from 1.1.301 to 1.1.302. - [Release notes](https://github.com/RobertCraigie/pyright-python/releases) - [Commits](https://github.com/RobertCraigie/pyright-python/compare/v1.1.301...v1.1.302) --- updated-dependencies: - dependency-name: pyright dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index 13f3dc8a..f45fe7ed 100644 --- a/poetry.lock +++ b/poetry.lock @@ -1997,14 +1997,14 @@ tests = ["hypothesis (>=3.27.0)", "pytest (>=3.2.1,!=3.3.0)"] [[package]] name = "pyright" -version = "1.1.301" +version = "1.1.302" description = "Command line wrapper for pyright" category = "dev" optional = false python-versions = ">=3.7" files = [ - {file = "pyright-1.1.301-py3-none-any.whl", hash = "sha256:ecc3752ba8c866a8041c90becf6be79bd52f4c51f98472e4776cae6d55e12826"}, - {file = "pyright-1.1.301.tar.gz", hash = "sha256:6ac4afc0004dca3a977a4a04a8ba25b5b5aa55f8289550697bfc20e11be0d5f2"}, + {file = "pyright-1.1.302-py3-none-any.whl", hash = "sha256:1929e3126b664b5281dba66a789e8e04358afca48c10994ee0243b8c2a14acdf"}, + {file = "pyright-1.1.302.tar.gz", hash = "sha256:e74a7dfbbb1d754941d015cccea8a6d29b395d8e4cb0e45dcfcaf3b6c6cfd540"}, ] [package.dependencies] @@ -2629,4 +2629,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "bd43cd028ee08cb25b3d5d2e99839df498d9902544137e9ddb9e2b0c3509db2b" +content-hash = "e9d53d21c77412e1d0e00e7846abaabb51815224ded69ddfc82908c60661a379" diff --git a/pyproject.toml b/pyproject.toml index 4aee870f..6289d890 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -33,7 +33,7 @@ pytest-cov = "^4.0.0" [tool.poetry.group.dev.dependencies] pre-commit = "^3.2.2" pyinstrument = "^4.4.0" -pyright = "^1.1.301" +pyright = "^1.1.302" watchfiles = "^0.19.0" jishaku = "^2.5.1" From b7da178d5193afecf6a17902403b7336621dd6b0 Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Wed, 5 Apr 2023 20:16:38 -0700 Subject: [PATCH 004/184] Now we are linting Python 3.8-3.10 --- .github/workflows/lint.yml | 11 ++++++++--- poetry.lock | 31 +++++++++++++++++++++++++++++-- pyproject.toml | 1 + 3 files changed, 38 insertions(+), 5 deletions(-) diff --git a/.github/workflows/lint.yml b/.github/workflows/lint.yml index 53b355ee..9b8167fe 100644 --- a/.github/workflows/lint.yml +++ b/.github/workflows/lint.yml @@ -30,15 +30,20 @@ jobs: --health-timeout 5s --health-retries 5 + strategy: + fail-fast: false + matrix: + version: [3.8, 3.9, '3.10', '3.11'] + steps: - name: Checkout Repository uses: actions/checkout@v3 - - name: Set up Python 3.11 + - name: Set up Python ${{ matrix.version }} id: setup-python uses: actions/setup-python@v4.5.0 with: - python-version: '3.11' + python-version: ${{ matrix.version }} - name: Set up Poetry uses: Gr1N/setup-poetry@v8 @@ -48,7 +53,7 @@ jobs: uses: actions/cache@v3.3.1 with: path: ~/.cache/pypoetry/virtualenvs - key: ${{ runner.os }}-poetry-${{ hashFiles('**/poetry.lock') }} + key: ${{ runner.os }}-poetry-lint-${{ hashFiles('**/poetry.lock') }} - name: Install Poetry Dependencies if: steps.cache-poetry.outputs.cache-hit != 'true' diff --git a/poetry.lock b/poetry.lock index f45fe7ed..f316fbc1 100644 --- a/poetry.lock +++ b/poetry.lock @@ -1,4 +1,4 @@ -# This file is automatically @generated by Poetry and should not be changed by hand. +# This file is automatically @generated by Poetry 1.4.0 and should not be changed by hand. [[package]] name = "aiodns" @@ -2213,6 +2213,33 @@ files = [ {file = "rin_exceptions-1.0.3-py3-none-any.whl", hash = "sha256:7d0e467a313d208589f1340c6225636ae2325e5b0a7be39e0361f1ab0d986fee"}, ] +[[package]] +name = "ruff" +version = "0.0.261" +description = "An extremely fast Python linter, written in Rust." +category = "dev" +optional = false +python-versions = ">=3.7" +files = [ + {file = "ruff-0.0.261-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:6624a966c4a21110cee6780333e2216522a831364896f3d98f13120936eff40a"}, + {file = "ruff-0.0.261-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:2dba68a9e558ab33e6dd5d280af798a2d9d3c80c913ad9c8b8e97d7b287f1cc9"}, + {file = "ruff-0.0.261-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:8dbd0cee5a81b0785dc0feeb2640c1e31abe93f0d77c5233507ac59731a626f1"}, + {file = "ruff-0.0.261-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:581e64fa1518df495ca890a605ee65065101a86db56b6858f848bade69fc6489"}, + {file = "ruff-0.0.261-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:cc970f6ece0b4950e419f0252895ee42e9e8e5689c6494d18f5dc2c6ebb7f798"}, + {file = "ruff-0.0.261-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:8fa98e747e0fe185d65a40b0ea13f55c492f3b5f9a032a1097e82edaddb9e52e"}, + {file = "ruff-0.0.261-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:f268d52a71bf410aa45c232870c17049df322a7d20e871cfe622c9fc784aab7b"}, + {file = "ruff-0.0.261-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:d1293acc64eba16a11109678dc4743df08c207ed2edbeaf38b3e10eb2597321b"}, + {file = "ruff-0.0.261-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:d95596e2f4cafead19a6d1ec0b86f8fda45ba66fe934de3956d71146a87959b3"}, + {file = "ruff-0.0.261-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:4bcec45abdf65c1328a269cf6cc193f7ff85b777fa2865c64cf2c96b80148a2c"}, + {file = "ruff-0.0.261-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:6c5f397ec0af42a434ad4b6f86565027406c5d0d0ebeea0d5b3f90c4bf55bc82"}, + {file = "ruff-0.0.261-py3-none-musllinux_1_2_i686.whl", hash = "sha256:39abd02342cec0c131b2ddcaace08b2eae9700cab3ca7dba64ae5fd4f4881bd0"}, + {file = "ruff-0.0.261-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:aaa4f52a6e513f8daa450dac4859e80390d947052f592f0d8e796baab24df2fc"}, + {file = "ruff-0.0.261-py3-none-win32.whl", hash = "sha256:daff64b4e86e42ce69e6367d63aab9562fc213cd4db0e146859df8abc283dba0"}, + {file = "ruff-0.0.261-py3-none-win_amd64.whl", hash = "sha256:0fbc689c23609edda36169c8708bb91bab111d8f44cb4a88330541757770ab30"}, + {file = "ruff-0.0.261-py3-none-win_arm64.whl", hash = "sha256:d2eddc60ae75fc87f8bb8fd6e8d5339cf884cd6de81e82a50287424309c187ba"}, + {file = "ruff-0.0.261.tar.gz", hash = "sha256:c1c715b0d1e18f9c509d7c411ca61da3543a4aa459325b1b1e52b8301d65c6d2"}, +] + [[package]] name = "setuptools" version = "66.1.1" @@ -2629,4 +2656,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "e9d53d21c77412e1d0e00e7846abaabb51815224ded69ddfc82908c60661a379" +content-hash = "148575131d635a68b673eb1ed81b1fd74e743be3d38a9dfd2656b0566792cb88" diff --git a/pyproject.toml b/pyproject.toml index 6289d890..5ecd7746 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -36,6 +36,7 @@ pyinstrument = "^4.4.0" pyright = "^1.1.302" watchfiles = "^0.19.0" jishaku = "^2.5.1" +ruff = "^0.0.261" [tool.isort] profile = 'black' From dfcac1b9b95f750042d05363eca63bfd4329242d Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Thu, 6 Apr 2023 00:50:47 -0700 Subject: [PATCH 005/184] Implement basic eco cmds + Greedy formatters --- Bot/Cogs/actions.py | 47 +++++++++++++++------- Bot/Cogs/economy.py | 63 ++++++++++++++++++++++++++++++ Bot/Libs/utils/__init__.py | 2 + Bot/Libs/utils/greedy_formatter.py | 9 +++++ Bot/kumikobot.py | 2 +- 5 files changed, 107 insertions(+), 16 deletions(-) create mode 100644 Bot/Cogs/economy.py create mode 100644 Bot/Libs/utils/greedy_formatter.py diff --git a/Bot/Cogs/actions.py b/Bot/Cogs/actions.py index f152afaa..7fb828f7 100644 --- a/Bot/Cogs/actions.py +++ b/Bot/Cogs/actions.py @@ -3,7 +3,8 @@ import orjson from discord import app_commands from discord.ext import commands -from Libs.utils import Embed +from discord.ext.commands import Greedy +from Libs.utils import Embed, formatGreedy class Actions(commands.Cog): @@ -14,78 +15,94 @@ def __init__(self, bot: commands.Bot) -> None: @commands.hybrid_command(name="hug") @app_commands.describe(user="The user to hug") - async def hug(self, ctx: commands.Context, user: discord.Member) -> None: + async def hug(self, ctx: commands.Context, user: Greedy[discord.Member]) -> None: """Hug someone on Discord!""" async with aiohttp.ClientSession() as session: async with session.get("https://nekos.life/api/v2/img/hug") as r: data = await r.json(loads=orjson.loads) - embed = Embed(title=f"{ctx.author.name} hugs {user.name}!") + embed = Embed( + title=f"{ctx.author.name} hugs {formatGreedy([items.name for items in user])}!" + ) embed.set_image(url=data["url"]) await ctx.send(embed=embed) @commands.hybrid_command(name="pat") @app_commands.describe(user="The user to pat") - async def pat(self, ctx: commands.Context, user: discord.Member) -> None: + async def pat(self, ctx: commands.Context, user: Greedy[discord.Member]) -> None: """Give someone a headpat!""" async with aiohttp.ClientSession() as session: async with session.get("https://nekos.life/api/v2/img/pat") as r: data = await r.json(loads=orjson.loads) - embed = Embed(title=f"{ctx.author.name} pats {user.name}!") + embed = Embed( + title=f"{ctx.author.name} pats {formatGreedy([items.name for items in user])}!" + ) embed.set_image(url=data["url"]) await ctx.send(embed=embed) @commands.hybrid_command(name="kiss") @app_commands.describe(user="The user to kiss") - async def kiss(self, ctx: commands.Context, user: discord.Member) -> None: + async def kiss(self, ctx: commands.Context, user: Greedy[discord.Member]) -> None: """Give someone a kiss!""" async with aiohttp.ClientSession() as session: async with session.get("https://nekos.life/api/v2/img/kiss") as r: data = await r.json(loads=orjson.loads) - embed = Embed(title=f"{ctx.author.name} kisses {user.name}!") + embed = Embed( + title=f"{ctx.author.name} kisses {formatGreedy([items.name for items in user])}!" + ) embed.set_image(url=data["url"]) await ctx.send(embed=embed) @commands.hybrid_command(name="cuddle") @app_commands.describe(user="The user to cuddle") - async def cuddle(self, ctx: commands.Context, user: discord.Member) -> None: + async def cuddle(self, ctx: commands.Context, user: Greedy[discord.Member]) -> None: """Cuddle someone on Discord!""" async with aiohttp.ClientSession() as session: async with session.get("https://nekos.life/api/v2/img/cuddle") as r: data = await r.json(loads=orjson.loads) - embed = Embed(title=f"{ctx.author.name} cuddles {user.name}!") + embed = Embed( + title=f"{ctx.author.name} cuddles {formatGreedy([items.name for items in user])}!" + ) embed.set_image(url=data["url"]) await ctx.send(embed=embed) @commands.hybrid_command(name="slap") @app_commands.describe(user="The user to slap") - async def slap(self, ctx: commands.Context, user: discord.Member) -> None: + async def slap(self, ctx: commands.Context, user: Greedy[discord.Member]) -> None: """Slaps someone on Discord!""" async with aiohttp.ClientSession() as session: async with session.get("https://nekos.life/api/v2/img/slap") as r: data = await r.json(loads=orjson.loads) - embed = Embed(title=f"{ctx.author.name} slaps {user.name}!") + embed = Embed( + title=f"{ctx.author.name} slaps {formatGreedy([items.name for items in user])}!" + ) embed.set_image(url=data["url"]) await ctx.send(embed=embed) @commands.hybrid_command(name="tickle") @app_commands.describe(user="The user to tickle") - async def tickles(self, ctx: commands.Context, user: discord.Member) -> None: + async def tickles( + self, ctx: commands.Context, user: Greedy[discord.Member] + ) -> None: """Tickle someone on Discord!""" async with aiohttp.ClientSession() as session: async with session.get("https://nekos.life/api/v2/img/tickle") as r: data = await r.json(loads=orjson.loads) - embed = Embed(title=f"{ctx.author.name} tickles {user.name}!") + embed = Embed( + title=f"{ctx.author.name} tickles {formatGreedy([items.name for items in user])}!" + ) embed.set_image(url=data["url"]) await ctx.send(embed=embed) @commands.hybrid_command(name="poke") @app_commands.describe(user="The user to poke") - async def poke(self, ctx: commands.Context, user: discord.Member) -> None: + async def poke(self, ctx: commands.Context, user: Greedy[discord.Member]) -> None: """Poke someone on Discord!""" async with aiohttp.ClientSession() as session: async with session.get("https://nekos.life/api/v2/img/poke") as r: data = await r.json(loads=orjson.loads) - embed = Embed(title=f"{ctx.author.name} pokes {user.name}!") + embed = Embed( + title=f"{ctx.author.name} pokes {formatGreedy([items.name for items in user])}!" + ) embed.set_image(url=data["url"]) await ctx.send(embed=embed) diff --git a/Bot/Cogs/economy.py b/Bot/Cogs/economy.py new file mode 100644 index 00000000..54583ecc --- /dev/null +++ b/Bot/Cogs/economy.py @@ -0,0 +1,63 @@ +import discord +from discord.ext import commands +from Libs.economy import getUser +from Libs.utils import Embed +from prisma.models import User + + +class Economy(commands.Cog): + """Earn, sell, and interact with Kumiko's economy!""" + + def __init__(self, bot: commands.Bot) -> None: + self.bot = bot + super().__init__() + + @commands.hybrid_group(name="marketplace") + async def eco(self, ctx: commands.Context) -> None: + if ctx.invoked_subcommand is None: + await ctx.send_help(ctx.command) + + @eco.command(name="buy") + async def marketplaceBuy(self, ctx: commands.Context) -> None: + """Buy an item from the marketplace""" + await ctx.send("Buy") + + @commands.hybrid_command(name="register") + async def register(self, ctx: commands.Context) -> discord.Message: + """Create an account for the economy""" + doesUserExist = ( + await User.prisma().count(where={"id": ctx.author.id}, take=1) == 1 + ) + if doesUserExist: + return await ctx.send( + embed=Embed( + title="Already Registered", + description="You already have an account!", + ) + ) + await User.prisma().create(data={"id": ctx.author.id, "name": ctx.author.name}) + return await ctx.send( + embed=Embed( + title="Registered", description="You have successfully registered!" + ) + ) + + @commands.hybrid_command(name="wallet") + async def wallet(self, ctx: commands.Context) -> discord.Message: + """Checks your wallet""" + user = await getUser(ctx.author.id) + if user is None: + return await ctx.send( + embed=Embed( + title="No Wallet", description="You don't have a wallet yet!" + ) + ) + embed = Embed( + title=f"{ctx.author.name}'s Wallet", + description=f"Balance: {user['petals']}", + ) + return await ctx.send(embed=embed) + + +async def setup(bot: commands.Bot) -> None: + await bot.add_cog(Economy(bot)) diff --git a/Bot/Libs/utils/__init__.py b/Bot/Libs/utils/__init__.py index eb42808c..f775c272 100644 --- a/Bot/Libs/utils/__init__.py +++ b/Bot/Libs/utils/__init__.py @@ -1,5 +1,6 @@ from .backoff import backoff from .embeds import Embed, ErrorEmbed +from .greedy_formatter import formatGreedy from .utils import encodeDatetime, parseDatetime, parseSubreddit, parseTimeStr __all__ = [ @@ -10,4 +11,5 @@ "ErrorEmbed", "parseSubreddit", "parseTimeStr", + "formatGreedy", ] diff --git a/Bot/Libs/utils/greedy_formatter.py b/Bot/Libs/utils/greedy_formatter.py new file mode 100644 index 00000000..2c70b2f6 --- /dev/null +++ b/Bot/Libs/utils/greedy_formatter.py @@ -0,0 +1,9 @@ +from typing import List + + +def formatGreedy(list: List[str]) -> str: + if len(list) >= 3: + return f"{', '.join(list[:-1])}, and {list[-1]}" + elif len(list) == 2: + return " and ".join(list) + return "".join(list) diff --git a/Bot/kumikobot.py b/Bot/kumikobot.py index 98a63312..8abff7b5 100644 --- a/Bot/kumikobot.py +++ b/Bot/kumikobot.py @@ -8,7 +8,7 @@ load_dotenv() -KUMIKO_TOKEN = os.environ["KUMIKO_TOKEN"] +KUMIKO_TOKEN = os.environ["DEV_BOT_TOKEN"] DEV_MODE = os.getenv("DEV_MODE") in ("True", "TRUE") intents = discord.Intents.default() intents.message_content = True From b9bb81aa3e4e75573cfac8993c810a1a566f6962 Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Thu, 6 Apr 2023 21:26:50 -0700 Subject: [PATCH 006/184] Invalidate all lint caches --- .github/workflows/lint.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/lint.yml b/.github/workflows/lint.yml index 9b8167fe..59c8b85d 100644 --- a/.github/workflows/lint.yml +++ b/.github/workflows/lint.yml @@ -53,7 +53,7 @@ jobs: uses: actions/cache@v3.3.1 with: path: ~/.cache/pypoetry/virtualenvs - key: ${{ runner.os }}-poetry-lint-${{ hashFiles('**/poetry.lock') }} + key: ${{ runner.os }}-poetry-lint-${{ matrix.version }}-${{ hashFiles('**/poetry.lock') }} - name: Install Poetry Dependencies if: steps.cache-poetry.outputs.cache-hit != 'true' From 40491a00ec93c2351446d131cd239a483b62800a Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Mon, 10 Apr 2023 00:11:29 -0700 Subject: [PATCH 007/184] Now use Starlight's help commands I just give up w/ help commands.... --- Bot/kumikocore.py | 6 +- poetry.lock | 299 +++++++++++++++++++++++++++++++++++++++++++++- pyproject.toml | 1 + 3 files changed, 300 insertions(+), 6 deletions(-) diff --git a/Bot/kumikocore.py b/Bot/kumikocore.py index cfca18fc..801cfc29 100644 --- a/Bot/kumikocore.py +++ b/Bot/kumikocore.py @@ -2,9 +2,9 @@ from pathlib import Path as SyncPath import discord +import starlight from anyio import Path from discord.ext import commands -from Libs.utils.help import KumikoHelp from Libs.utils.redis import redisCheck # Some weird import logic to ensure that watchfiles is there @@ -28,7 +28,9 @@ def __init__( super().__init__( intents=intents, command_prefix=commands.when_mentioned_or(">"), - help_command=KumikoHelp(), + help_command=starlight.MenuHelpCommand( + per_page=5, accent_color=0xFFCCCB, error_color=discord.Color.red() + ), activity=discord.Activity(type=discord.ActivityType.watching, name="/help"), *args, **kwargs, diff --git a/poetry.lock b/poetry.lock index f316fbc1..f17d0a19 100644 --- a/poetry.lock +++ b/poetry.lock @@ -166,6 +166,18 @@ files = [ [package.dependencies] typing_extensions = ">=3.7.2" +[[package]] +name = "alabaster" +version = "0.7.13" +description = "A configurable sidebar-enabled Sphinx theme" +category = "main" +optional = false +python-versions = ">=3.6" +files = [ + {file = "alabaster-0.7.13-py3-none-any.whl", hash = "sha256:1ee19aca801bbabb5ba3f5f258e4422dfa86f82f3e9cefb0859b283cdd7f62a3"}, + {file = "alabaster-0.7.13.tar.gz", hash = "sha256:a27a4a084d5e690e16e01e03ad2b2e552c61a65469419b907243193de1a84ae2"}, +] + [[package]] name = "anyio" version = "3.6.2" @@ -329,6 +341,21 @@ docs = ["furo", "myst-parser", "sphinx", "sphinx-notfound-page", "sphinxcontrib- tests = ["attrs[tests-no-zope]", "zope.interface"] tests-no-zope = ["cloudpickle", "cloudpickle", "hypothesis", "hypothesis", "mypy (>=0.971,<0.990)", "mypy (>=0.971,<0.990)", "pympler", "pympler", "pytest (>=4.3.0)", "pytest (>=4.3.0)", "pytest-mypy-plugins", "pytest-mypy-plugins", "pytest-xdist[psutil]", "pytest-xdist[psutil]"] +[[package]] +name = "babel" +version = "2.12.1" +description = "Internationalization utilities" +category = "main" +optional = false +python-versions = ">=3.7" +files = [ + {file = "Babel-2.12.1-py3-none-any.whl", hash = "sha256:b4246fb7677d3b98f501a39d43396d3cafdc8eadb045f4a31be01863f655c610"}, + {file = "Babel-2.12.1.tar.gz", hash = "sha256:cc2d99999cd01d44420ae725a21c9e3711b3aadc7976d6147f622d8581963455"}, +] + +[package.dependencies] +pytz = {version = ">=2015.7", markers = "python_version < \"3.9\""} + [[package]] name = "backoff" version = "2.2.1" @@ -866,6 +893,18 @@ files = [ {file = "distlib-0.3.6.tar.gz", hash = "sha256:14bad2d9b04d3a36127ac97f30b12a19268f211063d8f8ee4f47108896e11b46"}, ] +[[package]] +name = "docutils" +version = "0.18.1" +description = "Docutils -- Python Documentation Utilities" +category = "main" +optional = false +python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, !=3.4.*" +files = [ + {file = "docutils-0.18.1-py2.py3-none-any.whl", hash = "sha256:23010f129180089fbcd3bc08cfefccb3b890b0050e1ca00c867036e9d161b98c"}, + {file = "docutils-0.18.1.tar.gz", hash = "sha256:679987caf361a7539d76e584cbeddc311e3aee937877c87346f31debc63e9d06"}, +] + [[package]] name = "exceptiongroup" version = "1.1.0" @@ -1268,6 +1307,18 @@ files = [ {file = "idna-3.4.tar.gz", hash = "sha256:814f528e8dead7d329833b91c5faa87d60bf71824cd12a7530b5526063d02cb4"}, ] +[[package]] +name = "imagesize" +version = "1.4.1" +description = "Getting image size from png/jpeg/jpeg2000/gif file" +category = "main" +optional = false +python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*" +files = [ + {file = "imagesize-1.4.1-py2.py3-none-any.whl", hash = "sha256:0d8d18d08f840c19d0ee7ca1fd82490fdc3729b7ac93f49870406ddde8ef8d8b"}, + {file = "imagesize-1.4.1.tar.gz", hash = "sha256:69150444affb9cb0d5cc5a92b3676f0b2fb7cd9ae39e947a5e11a36b4497cd4a"}, +] + [[package]] name = "import-expression" version = "1.1.4" @@ -1290,7 +1341,7 @@ test = ["pytest", "pytest-cov"] name = "importlib-metadata" version = "6.1.0" description = "Read metadata from Python packages" -category = "dev" +category = "main" optional = false python-versions = ">=3.7" files = [ @@ -1687,7 +1738,7 @@ files = [ name = "packaging" version = "22.0" description = "Core utilities for Python packages" -category = "dev" +category = "main" optional = false python-versions = ">=3.7" files = [ @@ -1905,6 +1956,21 @@ typing-extensions = ">=4.2.0" dotenv = ["python-dotenv (>=0.10.4)"] email = ["email-validator (>=1.0.3)"] +[[package]] +name = "pygments" +version = "2.14.0" +description = "Pygments is a syntax highlighting package written in Python." +category = "main" +optional = false +python-versions = ">=3.6" +files = [ + {file = "Pygments-2.14.0-py3-none-any.whl", hash = "sha256:fa7bd7bd2771287c0de303af8bfdfc731f51bd2c6a47ab69d117138893b82717"}, + {file = "Pygments-2.14.0.tar.gz", hash = "sha256:b3ed06a9e8ac9a9aae5a6f5dbe78a8a58655d17b43b93c078f094ddc476ae297"}, +] + +[package.extras] +plugins = ["importlib-metadata"] + [[package]] name = "pyinstrument" version = "4.4.0" @@ -2091,6 +2157,18 @@ files = [ [package.extras] cli = ["click (>=5.0)"] +[[package]] +name = "pytz" +version = "2023.3" +description = "World timezone definitions, modern and historical" +category = "main" +optional = false +python-versions = "*" +files = [ + {file = "pytz-2023.3-py2.py3-none-any.whl", hash = "sha256:a151b3abb88eda1d4e34a9814df37de2a80e301e68ba0fd856fb9b46bfbbbffb"}, + {file = "pytz-2023.3.tar.gz", hash = "sha256:1d8ce29db189191fb55338ee6d0387d82ab59f3d00eac103412d64e0ebd0c588"}, +] + [[package]] name = "pyyaml" version = "6.0" @@ -2281,6 +2359,219 @@ files = [ {file = "sniffio-1.3.0.tar.gz", hash = "sha256:e60305c5e5d314f5389259b7f22aaa33d8f7dee49763119234af3755c55b9101"}, ] +[[package]] +name = "snowballstemmer" +version = "2.2.0" +description = "This package provides 29 stemmers for 28 languages generated from Snowball algorithms." +category = "main" +optional = false +python-versions = "*" +files = [ + {file = "snowballstemmer-2.2.0-py2.py3-none-any.whl", hash = "sha256:c8e1716e83cc398ae16824e5572ae04e0d9fc2c6b985fb0f900f5f0c96ecba1a"}, + {file = "snowballstemmer-2.2.0.tar.gz", hash = "sha256:09b16deb8547d3412ad7b590689584cd0fe25ec8db3be37788be3810cbf19cb1"}, +] + +[[package]] +name = "sphinx" +version = "6.1.3" +description = "Python documentation generator" +category = "main" +optional = false +python-versions = ">=3.8" +files = [ + {file = "Sphinx-6.1.3.tar.gz", hash = "sha256:0dac3b698538ffef41716cf97ba26c1c7788dba73ce6f150c1ff5b4720786dd2"}, + {file = "sphinx-6.1.3-py3-none-any.whl", hash = "sha256:807d1cb3d6be87eb78a381c3e70ebd8d346b9a25f3753e9947e866b2786865fc"}, +] + +[package.dependencies] +alabaster = ">=0.7,<0.8" +babel = ">=2.9" +colorama = {version = ">=0.4.5", markers = "sys_platform == \"win32\""} +docutils = ">=0.18,<0.20" +imagesize = ">=1.3" +importlib-metadata = {version = ">=4.8", markers = "python_version < \"3.10\""} +Jinja2 = ">=3.0" +packaging = ">=21.0" +Pygments = ">=2.13" +requests = ">=2.25.0" +snowballstemmer = ">=2.0" +sphinxcontrib-applehelp = "*" +sphinxcontrib-devhelp = "*" +sphinxcontrib-htmlhelp = ">=2.0.0" +sphinxcontrib-jsmath = "*" +sphinxcontrib-qthelp = "*" +sphinxcontrib-serializinghtml = ">=1.1.5" + +[package.extras] +docs = ["sphinxcontrib-websupport"] +lint = ["docutils-stubs", "flake8 (>=3.5.0)", "flake8-simplify", "isort", "mypy (>=0.990)", "ruff", "sphinx-lint", "types-requests"] +test = ["cython", "html5lib", "pytest (>=4.6)"] + +[[package]] +name = "sphinx-rtd-dark-mode" +version = "1.2.4" +description = "Dark mode for the Sphinx Read the Docs theme." +category = "main" +optional = false +python-versions = ">=3.4" +files = [ + {file = "sphinx_rtd_dark_mode-1.2.4-py3-none-any.whl", hash = "sha256:1d97c1e4f7902fb77ae86adcf72926c3b0e48a300f93eeba49266da5aeed8a29"}, + {file = "sphinx_rtd_dark_mode-1.2.4.tar.gz", hash = "sha256:935bc1f3e62fc76eadd7d2760ac7f48bab907a97e44beda749a48a2706aeed63"}, +] + +[package.dependencies] +sphinx-rtd-theme = "*" + +[[package]] +name = "sphinx-rtd-theme" +version = "1.2.0" +description = "Read the Docs theme for Sphinx" +category = "main" +optional = false +python-versions = "!=3.0.*,!=3.1.*,!=3.2.*,!=3.3.*,!=3.4.*,!=3.5.*,>=2.7" +files = [ + {file = "sphinx_rtd_theme-1.2.0-py2.py3-none-any.whl", hash = "sha256:f823f7e71890abe0ac6aaa6013361ea2696fc8d3e1fa798f463e82bdb77eeff2"}, + {file = "sphinx_rtd_theme-1.2.0.tar.gz", hash = "sha256:a0d8bd1a2ed52e0b338cbe19c4b2eef3c5e7a048769753dac6a9f059c7b641b8"}, +] + +[package.dependencies] +docutils = "<0.19" +sphinx = ">=1.6,<7" +sphinxcontrib-jquery = {version = ">=2.0.0,<3.0.0 || >3.0.0", markers = "python_version > \"3\""} + +[package.extras] +dev = ["bump2version", "sphinxcontrib-httpdomain", "transifex-client", "wheel"] + +[[package]] +name = "sphinxcontrib-applehelp" +version = "1.0.4" +description = "sphinxcontrib-applehelp is a Sphinx extension which outputs Apple help books" +category = "main" +optional = false +python-versions = ">=3.8" +files = [ + {file = "sphinxcontrib-applehelp-1.0.4.tar.gz", hash = "sha256:828f867945bbe39817c210a1abfd1bc4895c8b73fcaade56d45357a348a07d7e"}, + {file = "sphinxcontrib_applehelp-1.0.4-py3-none-any.whl", hash = "sha256:29d341f67fb0f6f586b23ad80e072c8e6ad0b48417db2bde114a4c9746feb228"}, +] + +[package.extras] +lint = ["docutils-stubs", "flake8", "mypy"] +test = ["pytest"] + +[[package]] +name = "sphinxcontrib-devhelp" +version = "1.0.2" +description = "sphinxcontrib-devhelp is a sphinx extension which outputs Devhelp document." +category = "main" +optional = false +python-versions = ">=3.5" +files = [ + {file = "sphinxcontrib-devhelp-1.0.2.tar.gz", hash = "sha256:ff7f1afa7b9642e7060379360a67e9c41e8f3121f2ce9164266f61b9f4b338e4"}, + {file = "sphinxcontrib_devhelp-1.0.2-py2.py3-none-any.whl", hash = "sha256:8165223f9a335cc1af7ffe1ed31d2871f325254c0423bc0c4c7cd1c1e4734a2e"}, +] + +[package.extras] +lint = ["docutils-stubs", "flake8", "mypy"] +test = ["pytest"] + +[[package]] +name = "sphinxcontrib-htmlhelp" +version = "2.0.1" +description = "sphinxcontrib-htmlhelp is a sphinx extension which renders HTML help files" +category = "main" +optional = false +python-versions = ">=3.8" +files = [ + {file = "sphinxcontrib-htmlhelp-2.0.1.tar.gz", hash = "sha256:0cbdd302815330058422b98a113195c9249825d681e18f11e8b1f78a2f11efff"}, + {file = "sphinxcontrib_htmlhelp-2.0.1-py3-none-any.whl", hash = "sha256:c38cb46dccf316c79de6e5515e1770414b797162b23cd3d06e67020e1d2a6903"}, +] + +[package.extras] +lint = ["docutils-stubs", "flake8", "mypy"] +test = ["html5lib", "pytest"] + +[[package]] +name = "sphinxcontrib-jquery" +version = "4.1" +description = "Extension to include jQuery on newer Sphinx releases" +category = "main" +optional = false +python-versions = ">=2.7" +files = [ + {file = "sphinxcontrib-jquery-4.1.tar.gz", hash = "sha256:1620739f04e36a2c779f1a131a2dfd49b2fd07351bf1968ced074365933abc7a"}, + {file = "sphinxcontrib_jquery-4.1-py2.py3-none-any.whl", hash = "sha256:f936030d7d0147dd026a4f2b5a57343d233f1fc7b363f68b3d4f1cb0993878ae"}, +] + +[package.dependencies] +Sphinx = ">=1.8" + +[[package]] +name = "sphinxcontrib-jsmath" +version = "1.0.1" +description = "A sphinx extension which renders display math in HTML via JavaScript" +category = "main" +optional = false +python-versions = ">=3.5" +files = [ + {file = "sphinxcontrib-jsmath-1.0.1.tar.gz", hash = "sha256:a9925e4a4587247ed2191a22df5f6970656cb8ca2bd6284309578f2153e0c4b8"}, + {file = "sphinxcontrib_jsmath-1.0.1-py2.py3-none-any.whl", hash = "sha256:2ec2eaebfb78f3f2078e73666b1415417a116cc848b72e5172e596c871103178"}, +] + +[package.extras] +test = ["flake8", "mypy", "pytest"] + +[[package]] +name = "sphinxcontrib-qthelp" +version = "1.0.3" +description = "sphinxcontrib-qthelp is a sphinx extension which outputs QtHelp document." +category = "main" +optional = false +python-versions = ">=3.5" +files = [ + {file = "sphinxcontrib-qthelp-1.0.3.tar.gz", hash = "sha256:4c33767ee058b70dba89a6fc5c1892c0d57a54be67ddd3e7875a18d14cba5a72"}, + {file = "sphinxcontrib_qthelp-1.0.3-py2.py3-none-any.whl", hash = "sha256:bd9fc24bcb748a8d51fd4ecaade681350aa63009a347a8c14e637895444dfab6"}, +] + +[package.extras] +lint = ["docutils-stubs", "flake8", "mypy"] +test = ["pytest"] + +[[package]] +name = "sphinxcontrib-serializinghtml" +version = "1.1.5" +description = "sphinxcontrib-serializinghtml is a sphinx extension which outputs \"serialized\" HTML files (json and pickle)." +category = "main" +optional = false +python-versions = ">=3.5" +files = [ + {file = "sphinxcontrib-serializinghtml-1.1.5.tar.gz", hash = "sha256:aa5f6de5dfdf809ef505c4895e51ef5c9eac17d0f287933eb49ec495280b6952"}, + {file = "sphinxcontrib_serializinghtml-1.1.5-py2.py3-none-any.whl", hash = "sha256:352a9a00ae864471d3a7ead8d7d79f5fc0b57e8b3f95e9867eb9eb28999b92fd"}, +] + +[package.extras] +lint = ["docutils-stubs", "flake8", "mypy"] +test = ["pytest"] + +[[package]] +name = "starlight-dpy" +version = "0.0.1b3" +description = "A Utility library for discord.py" +category = "main" +optional = false +python-versions = ">=3.8.0" +files = [] +develop = false + +[package.dependencies] +"discord.py" = ">=2.1.0" +sphinx_rtd_dark_mode = ">=1.2.4" + +[package.source] +type = "git" +url = "https://github.com/InterStella0/starlight-dpy" +reference = "3f48f562926125e3fbc277d2338de40c3a5a92fe" +resolved_reference = "3f48f562926125e3fbc277d2338de40c3a5a92fe" + [[package]] name = "tomli" version = "2.0.1" @@ -2641,7 +2932,7 @@ multidict = ">=4.0" name = "zipp" version = "3.15.0" description = "Backport of pathlib-compatible object wrapper for zip files" -category = "dev" +category = "main" optional = false python-versions = ">=3.7" files = [ @@ -2656,4 +2947,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "148575131d635a68b673eb1ed81b1fd74e743be3d38a9dfd2656b0566792cb88" +content-hash = "7e23f8e0a367c9f424c791d2d56212f7c219d06c29f9e231828aef82577a60ed" diff --git a/pyproject.toml b/pyproject.toml index 5ecd7746..d94300c0 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -22,6 +22,7 @@ ciso8601 = "^2.3.0" faust-cchardet = "^2.1.18" discord-py = {extras = ["voice"], version = "^2.2.2"} discord-ext-menus = {git = "https://github.com/Rapptz/discord-ext-menus", rev = "8686b5d1bbc1d3c862292eb436ab630d6e9c9b53"} +starlight-dpy = {git = "https://github.com/InterStella0/starlight-dpy", rev = "3f48f562926125e3fbc277d2338de40c3a5a92fe"} [tool.poetry.group.test.dependencies] pytest = "^7.2.2" From 42e129946be4f7f0fb35c363d619c75d4716e91e Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Mon, 10 Apr 2023 19:02:33 +0000 Subject: [PATCH 008/184] [pip](deps-dev): Bump pytest from 7.2.2 to 7.3.0 (#302) Bumps [pytest](https://github.com/pytest-dev/pytest) from 7.2.2 to 7.3.0. - [Release notes](https://github.com/pytest-dev/pytest/releases) - [Changelog](https://github.com/pytest-dev/pytest/blob/main/CHANGELOG.rst) - [Commits](https://github.com/pytest-dev/pytest/compare/7.2.2...7.3.0) --- updated-dependencies: - dependency-name: pytest dependency-type: direct:development update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 13 ++++++------- pyproject.toml | 2 +- 2 files changed, 7 insertions(+), 8 deletions(-) diff --git a/poetry.lock b/poetry.lock index f17d0a19..f56d112c 100644 --- a/poetry.lock +++ b/poetry.lock @@ -1,4 +1,4 @@ -# This file is automatically @generated by Poetry 1.4.0 and should not be changed by hand. +# This file is automatically @generated by Poetry and should not be changed by hand. [[package]] name = "aiodns" @@ -2082,18 +2082,17 @@ dev = ["twine (>=3.4.1)"] [[package]] name = "pytest" -version = "7.2.2" +version = "7.3.0" description = "pytest: simple powerful testing with Python" category = "dev" optional = false python-versions = ">=3.7" files = [ - {file = "pytest-7.2.2-py3-none-any.whl", hash = "sha256:130328f552dcfac0b1cec75c12e3f005619dc5f874f0a06e8ff7263f0ee6225e"}, - {file = "pytest-7.2.2.tar.gz", hash = "sha256:c99ab0c73aceb050f68929bc93af19ab6db0558791c6a0715723abe9d0ade9d4"}, + {file = "pytest-7.3.0-py3-none-any.whl", hash = "sha256:933051fa1bfbd38a21e73c3960cebdad4cf59483ddba7696c48509727e17f201"}, + {file = "pytest-7.3.0.tar.gz", hash = "sha256:58ecc27ebf0ea643ebfdf7fb1249335da761a00c9f955bcd922349bcb68ee57d"}, ] [package.dependencies] -attrs = ">=19.2.0" colorama = {version = "*", markers = "sys_platform == \"win32\""} exceptiongroup = {version = ">=1.0.0rc8", markers = "python_version < \"3.11\""} iniconfig = "*" @@ -2102,7 +2101,7 @@ pluggy = ">=0.12,<2.0" tomli = {version = ">=1.0.0", markers = "python_version < \"3.11\""} [package.extras] -testing = ["argcomplete", "hypothesis (>=3.56)", "mock", "nose", "pygments (>=2.7.2)", "requests", "xmlschema"] +testing = ["argcomplete", "attrs (>=19.2.0)", "hypothesis (>=3.56)", "mock", "nose", "pygments (>=2.7.2)", "requests", "xmlschema"] [[package]] name = "pytest-asyncio" @@ -2947,4 +2946,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "7e23f8e0a367c9f424c791d2d56212f7c219d06c29f9e231828aef82577a60ed" +content-hash = "e098402c12436d282fc2dd37a4403da0b133959910609df1286d237bec0284ad" diff --git a/pyproject.toml b/pyproject.toml index d94300c0..c8614588 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -25,7 +25,7 @@ discord-ext-menus = {git = "https://github.com/Rapptz/discord-ext-menus", rev = starlight-dpy = {git = "https://github.com/InterStella0/starlight-dpy", rev = "3f48f562926125e3fbc277d2338de40c3a5a92fe"} [tool.poetry.group.test.dependencies] -pytest = "^7.2.2" +pytest = "^7.3.0" pytest-asyncio = "^0.21.0" nox = "^2022.11.21" nox-poetry = "^1.0.2" From 0d4c4df8a9eda30d948529b40671e89277d104c2 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Mon, 10 Apr 2023 21:07:58 +0000 Subject: [PATCH 009/184] [pip](deps): Bump orjson from 3.8.9 to 3.8.10 (#303) Bumps [orjson](https://github.com/ijl/orjson) from 3.8.9 to 3.8.10. - [Release notes](https://github.com/ijl/orjson/releases) - [Changelog](https://github.com/ijl/orjson/blob/master/CHANGELOG.md) - [Commits](https://github.com/ijl/orjson/compare/3.8.9...3.8.10) --- updated-dependencies: - dependency-name: orjson dependency-type: direct:production update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 113 ++++++++++++++++++++++++++----------------------- pyproject.toml | 2 +- 2 files changed, 61 insertions(+), 54 deletions(-) diff --git a/poetry.lock b/poetry.lock index f56d112c..7e8e2994 100644 --- a/poetry.lock +++ b/poetry.lock @@ -1677,61 +1677,68 @@ tomlkit = ">=0.7" [[package]] name = "orjson" -version = "3.8.9" +version = "3.8.10" description = "Fast, correct Python JSON library supporting dataclasses, datetimes, and numpy" category = "main" optional = false -python-versions = ">=3.7" -files = [ - {file = "orjson-3.8.9-cp310-cp310-macosx_10_7_x86_64.whl", hash = "sha256:5d029843eae7b6cbd6468b63517b8b61471afed6572162171d8b6471b6dbf41f"}, - {file = "orjson-3.8.9-cp310-cp310-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:405933c05490efb209d0f940d8ef1403d2932a97e47010a26d2694e9dd49f84d"}, - {file = "orjson-3.8.9-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:183de66eff4d41c330a3006f210ab0bce7affe398da6f6eda9579b67245a34ff"}, - {file = "orjson-3.8.9-cp310-cp310-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:bb4081fe340ed1df42dddfd055e1d50479cb0ccb976d13e6b5e8667a07fec6f4"}, - {file = "orjson-3.8.9-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:d11593a2e736055dd7b9587dbf89cd1cbe4a42a70e70f186e51aee7e1b38902e"}, - {file = "orjson-3.8.9-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:e20649359e28f34d01b2570e4650a076f439a959bae3a8bbe7f5923ad80f54e8"}, - {file = "orjson-3.8.9-cp310-cp310-manylinux_2_28_x86_64.whl", hash = "sha256:c02ece4f36a160c83efe74adfba5f189c7c7702361f02b809ab73744923ee139"}, - {file = "orjson-3.8.9-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:f0e19801836cf1b30f333d475b05d79051b8ae8639a8e2422fb5f64e82676ae7"}, - {file = "orjson-3.8.9-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:d4850fe5650cead3c0f8822192e381cee9d4c3b8162eb082c86c927124572dc6"}, - {file = "orjson-3.8.9-cp310-none-win_amd64.whl", hash = "sha256:5fd4193f260d9d30112b5e379d0870b54dc88040807c93cbe8d67bfea148ba5a"}, - {file = "orjson-3.8.9-cp311-cp311-macosx_10_7_x86_64.whl", hash = "sha256:70eae063ad8d7405dc63873760567b600fc10728ba0da24a69d49c1a5d318d6d"}, - {file = "orjson-3.8.9-cp311-cp311-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:251653437632583d02203e6b118b72b99c04425175853f35340f4bac7034a36e"}, - {file = "orjson-3.8.9-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:6ea833751f017ba321c277e7425b51c0b1a18a2c60f8c9c0f4c6c4d7e16cbd6c"}, - {file = "orjson-3.8.9-cp311-cp311-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:8563c2cdeb923b82a5cc5bfc76c28c786777428263ee39292d928e9687165fb4"}, - {file = "orjson-3.8.9-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:6f33e9ea45b4c9457eedca0c40f38cf5732c91b0fb68f091ac59e6ea68e03eb2"}, - {file = "orjson-3.8.9-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:855dee152daecb7de7b4cd7069d7854e11aa291687bffe8433156af0a224417e"}, - {file = "orjson-3.8.9-cp311-cp311-manylinux_2_28_x86_64.whl", hash = "sha256:74fa9e02589339defc9d3662de9e7eef51d8f9f3a7f6304b43b18b39d7bbf10f"}, - {file = "orjson-3.8.9-cp311-none-win_amd64.whl", hash = "sha256:6c5b10ba1e62df8f96cbc37f6d5ae9acb3f6475926dea8b1b6a1a60f201a64f7"}, - {file = "orjson-3.8.9-cp37-cp37m-macosx_10_7_x86_64.whl", hash = "sha256:a651123d01bc399fcd866e56acc2d76512e62aae3673652b13b470ea69faf1f4"}, - {file = "orjson-3.8.9-cp37-cp37m-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:73019b6d2cc998c99556020c6bd8f8bc28420c69583186ca290c66a27916a3b7"}, - {file = "orjson-3.8.9-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:8f5c3daa8b02786ad5f0e14ae16a59bbb4e02cbae3a41989a25188e5a6c962ff"}, - {file = "orjson-3.8.9-cp37-cp37m-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:598598b7f81f8fda7c3e09c88165f844152b7be223bc4ea929ec8ad59b00ea17"}, - {file = "orjson-3.8.9-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:090b10bdb06baae6d5cd3550d772ecbabd833bfceed7592ff167c0a82f5b4c20"}, - {file = "orjson-3.8.9-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:bd46f688ddf9c2ea10367446fe9bf3ceba0f7490c15b4f96420491c7f00bb283"}, - {file = "orjson-3.8.9-cp37-cp37m-manylinux_2_28_x86_64.whl", hash = "sha256:b8ed8d780e9fab01bc404a70d755a8b2b34ea6c0b6604b65de135daaaadaf9a9"}, - {file = "orjson-3.8.9-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:8a32c9fb742868a34346f3c52e12d893a9d27f8e0c0bf3c480db7e6903d8be28"}, - {file = "orjson-3.8.9-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:2ba366009b98ac8899e935eff6fef7672d3ea43d3ce9deb3ee33452134b6cc3a"}, - {file = "orjson-3.8.9-cp37-none-win_amd64.whl", hash = "sha256:236b9313425cb2570626c64dd5cb6caff13882d1717d491da542cff228b96e97"}, - {file = "orjson-3.8.9-cp38-cp38-macosx_10_7_x86_64.whl", hash = "sha256:e8efc7e9ec35336f7cc98b6692536b1262046ff1d2a545295a4d89b8a2495903"}, - {file = "orjson-3.8.9-cp38-cp38-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:8c7eba3610ae69f4aba4032ecb61b0a6fbd1e4537283d1553eb8c1cb136e9118"}, - {file = "orjson-3.8.9-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:7742649e4c357d4e7ad483a35ff5f55d519e895de56772cc486913614ee7d23b"}, - {file = "orjson-3.8.9-cp38-cp38-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:b6566fb8daa538c7848fd6822e2409a7e1c41dae8e65e6536598d505f641a318"}, - {file = "orjson-3.8.9-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:0ce8a2a667221e2e5160021e26b09e9c13eeedafb5cda1981340c8c0c0bc8f9d"}, - {file = "orjson-3.8.9-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:4c0399631b88fa4868956badef2561fba07dffcaf050bf53959ee50d26edf6f6"}, - {file = "orjson-3.8.9-cp38-cp38-manylinux_2_28_x86_64.whl", hash = "sha256:189ccb16ed140a824d133fa1c55175cf0d2207edaade54f1db0456a526cb5fd8"}, - {file = "orjson-3.8.9-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:b707fa4481e1af19b3052ec9352c688bad3f539d7bdd8aa4a451f6dd7e4bae73"}, - {file = "orjson-3.8.9-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:c3d988eb562da1dda7d49e9abd8a64b3cabc632b4299d177fb9e0c0ca9f06b8c"}, - {file = "orjson-3.8.9-cp38-none-win_amd64.whl", hash = "sha256:b30240eb6b22daab604f1595f6aacf92bcdac0d29e2d7ad507dfac68d2b39182"}, - {file = "orjson-3.8.9-cp39-cp39-macosx_10_7_x86_64.whl", hash = "sha256:81869a6de00bc676d10056fa8bb28cbe805b1cf498a45c14cb7b1765eee33fcb"}, - {file = "orjson-3.8.9-cp39-cp39-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:a25a5a215b19d414de8d416a3c5414f29165843a06f704cc0345ded9eac34ac1"}, - {file = "orjson-3.8.9-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:dec0f2bea52e30ea98ce095f1f42da04535791f9a31b2aab2499caa88307bc49"}, - {file = "orjson-3.8.9-cp39-cp39-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:7b91d88fe96b698b28bb1b95b1fce226f72757ab3ab7d8d97551e23bc629c84f"}, - {file = "orjson-3.8.9-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:7629841ccdcccd3c43ebc6a4165abe9844909fcedb2041994c0153470f610801"}, - {file = "orjson-3.8.9-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:d875b304e19f4b2758d233bbf2b9d627c66fac50b3150b8d31a35ba6cda3db67"}, - {file = "orjson-3.8.9-cp39-cp39-manylinux_2_28_x86_64.whl", hash = "sha256:723ec880c5290fe4de330febb8030e57c1978fbd624fc5b9399969e7d7d74984"}, - {file = "orjson-3.8.9-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:b11f8a71c82d19fce11ce487efeec2ca0dc3bcf5b4564445fecfc68d9c268744"}, - {file = "orjson-3.8.9-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:b2079bf86dec62731c1b90fdfea3211f993f0c894d9261e0ce9b68ed9c9dfbec"}, - {file = "orjson-3.8.9-cp39-none-win_amd64.whl", hash = "sha256:97d94322a2eaab767ba8d52f6bf9d0ec0f35313fe36287be6e6085dd65d55d37"}, - {file = "orjson-3.8.9.tar.gz", hash = "sha256:c40bece58c11cb09aff17424d21b41f6f767d2b1252b2f745ec3ff29cce6a240"}, +python-versions = ">= 3.7" +files = [ + {file = "orjson-3.8.10-cp310-cp310-macosx_10_7_x86_64.whl", hash = "sha256:4dfe0651e26492d5d929bbf4322de9afbd1c51ac2e3947a7f78492b20359711d"}, + {file = "orjson-3.8.10-cp310-cp310-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:bc30de5c7b3a402eb59cc0656b8ee53ca36322fc52ab67739c92635174f88336"}, + {file = "orjson-3.8.10-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:c08b426fae7b9577b528f99af0f7e0ff3ce46858dd9a7d1bf86d30f18df89a4c"}, + {file = "orjson-3.8.10-cp310-cp310-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:bce970f293825e008dbf739268dfa41dfe583aa2a1b5ef4efe53a0e92e9671ea"}, + {file = "orjson-3.8.10-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:9b23fb0264bbdd7218aa685cb6fc71f0dcecf34182f0a8596a3a0dff010c06f9"}, + {file = "orjson-3.8.10-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:0826ad2dc1cea1547edff14ce580374f0061d853cbac088c71162dbfe2e52205"}, + {file = "orjson-3.8.10-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:a7bce6e61cea6426309259b04c6ee2295b3f823ea51a033749459fe2dd0423b2"}, + {file = "orjson-3.8.10-cp310-cp310-manylinux_2_28_x86_64.whl", hash = "sha256:0b470d31244a6f647e5402aac7d2abaf7bb4f52379acf67722a09d35a45c9417"}, + {file = "orjson-3.8.10-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:48824649019a25d3e52f6454435cf19fe1eb3d05ee697e65d257f58ae3aa94d9"}, + {file = "orjson-3.8.10-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:faee89e885796a9cc493c930013fa5cfcec9bfaee431ddf00f0fbfb57166a8b3"}, + {file = "orjson-3.8.10-cp310-none-win_amd64.whl", hash = "sha256:3cfe32b1227fe029a5ad989fbec0b453a34e5e6d9a977723f7c3046d062d3537"}, + {file = "orjson-3.8.10-cp311-cp311-macosx_10_7_x86_64.whl", hash = "sha256:2073b62822738d6740bd2492f6035af5c2fd34aa198322b803dc0e70559a17b7"}, + {file = "orjson-3.8.10-cp311-cp311-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:b2c4faf20b6bb5a2d7ac0c16f58eb1a3800abcef188c011296d1dc2bb2224d48"}, + {file = "orjson-3.8.10-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:8c1825997232a324911d11c75d91e1e0338c7b723c149cf53a5fc24496c048a4"}, + {file = "orjson-3.8.10-cp311-cp311-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:f7e85d4682f3ed7321d36846cad0503e944ea9579ef435d4c162e1b73ead8ac9"}, + {file = "orjson-3.8.10-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:2b8cdaacecb92997916603ab232bb096d0fa9e56b418ca956b9754187d65ca06"}, + {file = "orjson-3.8.10-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:ddabc5e44702d13137949adee3c60b7091e73a664f6e07c7b428eebb2dea7bbf"}, + {file = "orjson-3.8.10-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:27bb26e171e9cfdbec39c7ca4739b6bef8bd06c293d56d92d5e3a3fc017df17d"}, + {file = "orjson-3.8.10-cp311-cp311-manylinux_2_28_x86_64.whl", hash = "sha256:1810e5446fe68d61732e9743592da0ec807e63972eef076d09e02878c2f5958e"}, + {file = "orjson-3.8.10-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:61e2e51cefe7ef90c4fbbc9fd38ecc091575a3ea7751d56fad95cbebeae2a054"}, + {file = "orjson-3.8.10-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:f3e9ac9483c2b4cd794e760316966b7bd1e6afb52b0218f068a4e80c9b2db4f6"}, + {file = "orjson-3.8.10-cp311-none-win_amd64.whl", hash = "sha256:26aee557cf8c93b2a971b5a4a8e3cca19780573531493ce6573aa1002f5c4378"}, + {file = "orjson-3.8.10-cp37-cp37m-macosx_10_7_x86_64.whl", hash = "sha256:11ae68f995a50724032af297c92f20bcde31005e0bf3653b12bff9356394615b"}, + {file = "orjson-3.8.10-cp37-cp37m-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:35d879b46b8029e1e01e9f6067928b470a4efa1ca749b6d053232b873c2dcf66"}, + {file = "orjson-3.8.10-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:345e41abd1d9e3ecfb554e1e75ff818cf42e268bd06ad25a96c34e00f73a327e"}, + {file = "orjson-3.8.10-cp37-cp37m-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:45a5afc9cda6b8aac066dd50d8194432fbc33e71f7164f95402999b725232d78"}, + {file = "orjson-3.8.10-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:ad632dc330a7b39da42530c8d146f76f727d476c01b719dc6743c2b5701aaf6b"}, + {file = "orjson-3.8.10-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:4bf2556ba99292c4dc550560384dd22e88b5cdbe6d98fb4e202e902b5775cf9f"}, + {file = "orjson-3.8.10-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:b88afd662190f19c3bb5036a903589f88b1d2c2608fbb97281ce000db6b08897"}, + {file = "orjson-3.8.10-cp37-cp37m-manylinux_2_28_x86_64.whl", hash = "sha256:abce8d319aae800fd2d774db1106f926dee0e8a5ca85998fd76391fcb58ef94f"}, + {file = "orjson-3.8.10-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:e999abca892accada083f7079612307d94dd14cc105a699588a324f843216509"}, + {file = "orjson-3.8.10-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:a3fdee68c4bb3c5d6f89ed4560f1384b5d6260e48fbf868bae1a245a3c693d4d"}, + {file = "orjson-3.8.10-cp37-none-win_amd64.whl", hash = "sha256:e5d7f82506212e047b184c06e4bcd48c1483e101969013623cebcf51cf12cad9"}, + {file = "orjson-3.8.10-cp38-cp38-macosx_10_7_x86_64.whl", hash = "sha256:d953e6c2087dcd990e794f8405011369ee11cf13e9aaae3172ee762ee63947f2"}, + {file = "orjson-3.8.10-cp38-cp38-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:81aa3f321d201bff0bd0f4014ea44e51d58a9a02d8f2b0eeab2cee22611be8e1"}, + {file = "orjson-3.8.10-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:7d27b6182f75896dd8c10ea0f78b9265a3454be72d00632b97f84d7031900dd4"}, + {file = "orjson-3.8.10-cp38-cp38-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:1486600bc1dd1db26c588dd482689edba3d72d301accbe4301db4b2b28bd7aa4"}, + {file = "orjson-3.8.10-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:344ea91c556a2ce6423dc13401b83ab0392aa697a97fa4142c2c63a6fd0bbfef"}, + {file = "orjson-3.8.10-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:979f231e3bad1c835627eef1a30db12a8af58bfb475a6758868ea7e81897211f"}, + {file = "orjson-3.8.10-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:6fa3a26dcf0f5f2912a8ce8e87273e68b2a9526854d19fd09ea671b154418e88"}, + {file = "orjson-3.8.10-cp38-cp38-manylinux_2_28_x86_64.whl", hash = "sha256:b6e79d8864794635974b18821b49a7f27859d17b93413d4603efadf2e92da7a5"}, + {file = "orjson-3.8.10-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:ce49999bcbbc14791c61844bc8a69af44f5205d219be540e074660038adae6bf"}, + {file = "orjson-3.8.10-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:c2ef690335b24f9272dbf6639353c1ffc3f196623a92b851063e28e9515cf7dd"}, + {file = "orjson-3.8.10-cp38-none-win_amd64.whl", hash = "sha256:5a0b1f4e4fa75e26f814161196e365fc0e1a16e3c07428154505b680a17df02f"}, + {file = "orjson-3.8.10-cp39-cp39-macosx_10_7_x86_64.whl", hash = "sha256:af7601a78b99f0515af2f8ab12c955c0072ffcc1e437fb2556f4465783a4d813"}, + {file = "orjson-3.8.10-cp39-cp39-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:6bbd7b3a3e2030b03c68c4d4b19a2ef5b89081cbb43c05fe2010767ef5e408db"}, + {file = "orjson-3.8.10-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:4355c9aedfefe60904e8bd7901315ebbc8bb828f665e4c9bc94b1432e67cb6f7"}, + {file = "orjson-3.8.10-cp39-cp39-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:b7b0ba074375e25c1594e770e2215941e2017c3cd121889150737fa1123e8bfe"}, + {file = "orjson-3.8.10-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:34b6901c110c06ab9e8d7d0496db4bc9a0c162ca8d77f67539d22cb39e0a1ef4"}, + {file = "orjson-3.8.10-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:cb62ec16a1c26ad9487727b529103cb6a94a1d4969d5b32dd0eab5c3f4f5a6f2"}, + {file = "orjson-3.8.10-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:595e1e7d04aaaa3d41113e4eb9f765ab642173c4001182684ae9ddc621bb11c8"}, + {file = "orjson-3.8.10-cp39-cp39-manylinux_2_28_x86_64.whl", hash = "sha256:64ffd92328473a2f9af059410bd10c703206a4bbc7b70abb1bedcd8761e39eb8"}, + {file = "orjson-3.8.10-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:b1f648ec89c6a426098868460c0ef8c86b457ce1378d7569ff4acb6c0c454048"}, + {file = "orjson-3.8.10-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:6a286ad379972e4f46579e772f0477e6b505f1823aabcd64ef097dbb4549e1a4"}, + {file = "orjson-3.8.10-cp39-none-win_amd64.whl", hash = "sha256:d2874cee6856d7c386b596e50bc517d1973d73dc40b2bd6abec057b5e7c76b2f"}, + {file = "orjson-3.8.10.tar.gz", hash = "sha256:dcf6adb4471b69875034afab51a14b64f1026bc968175a2bb02c5f6b358bd413"}, ] [[package]] @@ -2946,4 +2953,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "e098402c12436d282fc2dd37a4403da0b133959910609df1286d237bec0284ad" +content-hash = "acc0c02a5231e00e7c0605cb252bdde5313e4d16986d723f98970508a3d18908" diff --git a/pyproject.toml b/pyproject.toml index c8614588..1a7b6bc8 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -10,7 +10,7 @@ python = ">=3.8,<4.0" python-dotenv = "^1.0.0" aiodns = "^3.0.0" Brotli = "^1.0.9" -orjson = "^3.8.9" +orjson = "^3.8.10" asyncpraw = "^7.7.0" uvloop = "^0.17.0" gql = { extras = ["aiohttp"], version = "^3.4.0" } From 44b96552a27971b0c3d0f053bad0d36bfd2971ca Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Thu, 13 Apr 2023 01:14:13 -0700 Subject: [PATCH 010/184] Add an UI to the register command --- Bot/Cogs/economy.py | 22 +++++------------ Bot/Libs/ui/economy/__init__.py | 3 +++ Bot/Libs/ui/economy/views.py | 44 +++++++++++++++++++++++++++++++++ 3 files changed, 53 insertions(+), 16 deletions(-) create mode 100644 Bot/Libs/ui/economy/__init__.py create mode 100644 Bot/Libs/ui/economy/views.py diff --git a/Bot/Cogs/economy.py b/Bot/Cogs/economy.py index 54583ecc..c23836ea 100644 --- a/Bot/Cogs/economy.py +++ b/Bot/Cogs/economy.py @@ -1,8 +1,8 @@ import discord from discord.ext import commands from Libs.economy import getUser +from Libs.ui.economy import RegisterView from Libs.utils import Embed -from prisma.models import User class Economy(commands.Cog): @@ -25,22 +25,12 @@ async def marketplaceBuy(self, ctx: commands.Context) -> None: @commands.hybrid_command(name="register") async def register(self, ctx: commands.Context) -> discord.Message: """Create an account for the economy""" - doesUserExist = ( - await User.prisma().count(where={"id": ctx.author.id}, take=1) == 1 - ) - if doesUserExist: - return await ctx.send( - embed=Embed( - title="Already Registered", - description="You already have an account!", - ) - ) - await User.prisma().create(data={"id": ctx.author.id, "name": ctx.author.name}) - return await ctx.send( - embed=Embed( - title="Registered", description="You have successfully registered!" - ) + view = RegisterView() + embed = Embed( + title="Register", + description="Register for the economy! Before you do so, please make sure to follow the TOS. By registering, you are agreeing to use these services.", ) + return await ctx.send(embed=embed, view=view) @commands.hybrid_command(name="wallet") async def wallet(self, ctx: commands.Context) -> discord.Message: diff --git a/Bot/Libs/ui/economy/__init__.py b/Bot/Libs/ui/economy/__init__.py new file mode 100644 index 00000000..80a66e3a --- /dev/null +++ b/Bot/Libs/ui/economy/__init__.py @@ -0,0 +1,3 @@ +from .views import RegisterView + +__all__ = ["RegisterView"] diff --git a/Bot/Libs/ui/economy/views.py b/Bot/Libs/ui/economy/views.py new file mode 100644 index 00000000..0e50cc81 --- /dev/null +++ b/Bot/Libs/ui/economy/views.py @@ -0,0 +1,44 @@ +import discord +from Libs.utils import Embed +from prisma.models import User + + +class RegisterView(discord.ui.View): + def __init__(self) -> None: + super().__init__() + + @discord.ui.button(label="Confirm", style=discord.ButtonStyle.green) + async def confirm( + self, interaction: discord.Interaction, button: discord.ui.Button + ) -> None: + button.disabled = True + doesUserExist = ( + await User.prisma().count(where={"id": interaction.user.id}, take=1) == 1 + ) + if doesUserExist: + return await interaction.response.edit_message( + embed=Embed( + title="Already Registered", + description="You already have an account!", + ), + view=self, + ) + await User.prisma().create( + data={"id": interaction.user.id, "name": interaction.user.name} + ) + await interaction.edit_original_response( + embed=Embed( + title="Registered", description="You have successfully registered!" + ) + ) + self.stop() + + @discord.ui.button(label="Cancel", style=discord.ButtonStyle.red) + async def cancel( + self, interaction: discord.Interaction, button: discord.ui.Button + ) -> None: + button.disabled = True + await interaction.response.edit_message( + embed=Embed(title="Cancelled"), view=self + ) + self.stop() From f1e95fda7b7ca2145e43faaa64c8714480dd6591 Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Thu, 13 Apr 2023 23:56:14 -0700 Subject: [PATCH 011/184] Add a paginated help command --- Bot/Libs/utils/help/__init__.py | 107 +------ Bot/Libs/utils/help/kumiko_help.py | 32 +- Bot/Libs/utils/help/kumiko_help_paginated.py | 140 +++++++++ Bot/Libs/utils/pages/sources.py | 4 +- Bot/kumikocore.py | 6 +- poetry.lock | 301 +------------------ pyproject.toml | 1 - 7 files changed, 160 insertions(+), 431 deletions(-) create mode 100644 Bot/Libs/utils/help/kumiko_help_paginated.py diff --git a/Bot/Libs/utils/help/__init__.py b/Bot/Libs/utils/help/__init__.py index 7550d69d..4423cad1 100644 --- a/Bot/Libs/utils/help/__init__.py +++ b/Bot/Libs/utils/help/__init__.py @@ -1,105 +1,4 @@ -import contextlib +from .kumiko_help import KumikoHelp +from .kumiko_help_paginated import KumikoHelpPaginated -from discord.ext import commands -from Libs.utils import Embed - - -class KumikoHelp(commands.HelpCommand): - def __init__(self): - super().__init__( # create our class with some aliases and cooldown - command_attrs={ - "help": "The help command for the bot", - "cooldown": commands.CooldownMapping.from_cooldown( - 1, 3.0, commands.BucketType.user - ), - "aliases": ["commands"], - } - ) - - async def send(self, **kwargs): - """a shortcut to sending to get_destination""" - await self.get_destination().send(**kwargs) - - async def send_bot_help(self, mapping): - """triggers when a `help` is called""" - ctx = self.context - embed = Embed(title=f"{ctx.me.display_name} Help") - embed.set_thumbnail(url=ctx.me.display_avatar) - usable = 0 - - for ( - cog, - commands, - ) in mapping.items(): # iterating through our mapping of cog: commands - if filtered_commands := await self.filter_commands(commands): - # if no commands are usable in this category, we don't want to display it - amount_commands = len(filtered_commands) - usable += amount_commands - if cog: # getting attributes dependent on if a cog exists or not - name = cog.qualified_name - description = cog.description or "No description" - else: - name = "No" - description = "Commands with no category" - - embed.add_field( - name=f"{name} Category [{amount_commands}]", value=description - ) - - # embed.description = f"{len(bot.commands)} commands | {usable} usable" - - await self.send(embed=embed) - - async def send_command_help(self, command): - """triggers when a `help ` is called""" - signature = self.get_command_signature( - command - ) # get_command_signature gets the signature of a command in [optional] - embed = Embed(title=signature, description=command.help or "No help found...") - - if cog := command.cog: - embed.add_field(name="Category", value=cog.qualified_name) - - can_run = "No" - # command.can_run to test if the cog is usable - with contextlib.suppress(commands.CommandError): - if await command.can_run(self.context): - can_run = "Yes" - - embed.add_field(name="Usable", value=can_run) - - if command._buckets and ( - cooldown := command._buckets._cooldown - ): # use of internals to get the cooldown of the command - embed.add_field( - name="Cooldown", - value=f"{cooldown.rate} per {cooldown.per:.0f} seconds", - ) - - await self.send(embed=embed) - - async def send_help_embed( - self, title, description, commands - ): # a helper function to add commands to an embed - embed = Embed(title=title, description=description or "No help found...") - - if filtered_commands := await self.filter_commands(commands): - for command in filtered_commands: - embed.add_field( - name=self.get_command_signature(command), - value=command.help or "No help found...", - ) - - await self.send(embed=embed) - - async def send_group_help(self, group): - """triggers when a `help ` is called""" - title = self.get_command_signature(group) - await self.send_help_embed(title, group.help, group.commands) - - async def send_cog_help(self, cog): - """triggers when a `help ` is called""" - title = cog.qualified_name or "No" - await self.send_help_embed( - f"{title} Category", cog.description, cog.get_commands() - ) +__all__ = ["KumikoHelpPaginated", "KumikoHelp"] diff --git a/Bot/Libs/utils/help/kumiko_help.py b/Bot/Libs/utils/help/kumiko_help.py index 4cd74f52..7550d69d 100644 --- a/Bot/Libs/utils/help/kumiko_help.py +++ b/Bot/Libs/utils/help/kumiko_help.py @@ -1,5 +1,4 @@ import contextlib -from typing import List, Mapping, Optional from discord.ext import commands from Libs.utils import Embed @@ -7,7 +6,7 @@ class KumikoHelp(commands.HelpCommand): def __init__(self): - super().__init__( + super().__init__( # create our class with some aliases and cooldown command_attrs={ "help": "The help command for the bot", "cooldown": commands.CooldownMapping.from_cooldown( @@ -17,22 +16,15 @@ def __init__(self): } ) - async def send(self, **kwargs) -> None: + async def send(self, **kwargs): """a shortcut to sending to get_destination""" await self.get_destination().send(**kwargs) - async def send_bot_help( - self, mapping: Mapping[Optional[commands.Cog], List[commands.Command]] - ) -> None: - """Generates the help embed when the default help command is called - - Args: - mapping (Mapping[Optional[commands.Cog], List[commands.Command]]): Mapping of cogs to commands - """ + async def send_bot_help(self, mapping): + """triggers when a `help` is called""" ctx = self.context embed = Embed(title=f"{ctx.me.display_name} Help") embed.set_thumbnail(url=ctx.me.display_avatar) - embed.description = f"{ctx.me.display_name} is a multipurpose bot built with freedom and choice in mind." usable = 0 for ( @@ -54,7 +46,7 @@ async def send_bot_help( name=f"{name} Category [{amount_commands}]", value=description ) - # embed.description = f"{len(ctx.commands)} commands | {usable} usable" + # embed.description = f"{len(bot.commands)} commands | {usable} usable" await self.send(embed=embed) @@ -63,9 +55,7 @@ async def send_command_help(self, command): signature = self.get_command_signature( command ) # get_command_signature gets the signature of a command in [optional] - embed = Embed( - title=signature, description=command.short_doc or "No help found..." - ) + embed = Embed(title=signature, description=command.help or "No help found...") if cog := command.cog: embed.add_field(name="Category", value=cog.qualified_name) @@ -97,18 +87,10 @@ async def send_help_embed( for command in filtered_commands: embed.add_field( name=self.get_command_signature(command), - value=command.short_doc or "No help found...", + value=command.help or "No help found...", ) await self.send(embed=embed) - # cmdList = [] - # if filtered_commands := await self.filter_commands(commands): - # for command in filtered_commands: - # cmdList.append((self.get_command_signature(command), command.help or "No help found...")) - - # source = FieldPageSource(cmdList, per_page=3) - # pages = KumikoPages(source, ctx=self.context) - # await pages.start_help(channel=self.get_destination()) async def send_group_help(self, group): """triggers when a `help ` is called""" diff --git a/Bot/Libs/utils/help/kumiko_help_paginated.py b/Bot/Libs/utils/help/kumiko_help_paginated.py new file mode 100644 index 00000000..a5f7cc7e --- /dev/null +++ b/Bot/Libs/utils/help/kumiko_help_paginated.py @@ -0,0 +1,140 @@ +import contextlib +from typing import List, Mapping, Optional + +from discord.ext import commands +from Libs.utils import Embed +from Libs.utils.pages import FieldPageSource, KumikoPages + + +class KumikoHelpPaginated(commands.HelpCommand): + def __init__(self) -> None: + super().__init__( + command_attrs={ + "help": "The help command for the bot", + "cooldown": commands.CooldownMapping.from_cooldown( + 1, 3.0, commands.BucketType.user + ), + "aliases": ["commands"], + } + ) + + async def send(self, **kwargs) -> None: + """a shortcut to sending to get_destination""" + await self.get_destination().send(**kwargs) + + async def help_embed( + self, title: str, description: str, commands: List[commands.Command] + ) -> None: + """The default help embed builder + + Mainly used so we don't repeat ourselves when building help embeds + + Args: + title (str): The title of the embed. Usually the name of the cog, group, etc + description (str): The description of the embed. Usually the desc of the cog or group + commands (List[commands.Command]): List of commands + """ + filteredCommands = await self.filter_commands(commands) + fieldSource = [ + (self.get_command_signature(command), command.help or "No help found...") + for command in filteredCommands + ] + sources = FieldPageSource( + entries=fieldSource, + per_page=6, + inline=True, + clear_description=False, + title=title or "No", + description=description or "No help found...", + ) + pages = KumikoPages(source=sources, ctx=self.context) + await pages.start() + + async def send_bot_help( + self, mapping: Mapping[Optional[commands.Cog], List[commands.Command]] + ) -> None: + """Generates the help embed when the default help command is called + + Args: + mapping (Mapping[Optional[commands.Cog], List[commands.Command]]): Mapping of cogs to commands + """ + ctx = self.context + embed = Embed(title=f"{ctx.me.display_name} Help") + embed.set_thumbnail(url=ctx.me.display_avatar) + embed.description = f"{ctx.me.display_name} is a multipurpose bot built with freedom and choice in mind." + usable = 0 + + for ( + cog, + commands, + ) in mapping.items(): # iterating through our mapping of cog: commands + if filtered_commands := await self.filter_commands(commands): + # if no commands are usable in this category, we don't want to display it + amount_commands = len(filtered_commands) + usable += amount_commands + if cog: # getting attributes dependent on if a cog exists or not + name = cog.qualified_name + description = cog.description or "No description" + else: + name = "No" + description = "Commands with no category" + + embed.add_field( + name=f"{name} Category [{amount_commands}]", value=description + ) + + # embed.description = f"{len(ctx.commands)} commands | {usable} usable" + + await self.send(embed=embed) + + async def send_command_help(self, command: commands.Command) -> None: + """Triggers when a `help ` is called + + Args: + command (commands.Command): The command to get help for + """ + signature = self.get_command_signature( + command + ) # get_command_signature gets the signature of a command in [optional] + embed = Embed(title=signature, description=command.help or "No help found...") + + if cog := command.cog: + embed.add_field(name="Category", value=cog.qualified_name) + + can_run = "No" + # command.can_run to test if the cog is usable + with contextlib.suppress(commands.CommandError): + if await command.can_run(self.context): + can_run = "Yes" + + embed.add_field(name="Usable", value=can_run) + + if command._buckets and ( + cooldown := command._buckets._cooldown + ): # use of internals to get the cooldown of the command + embed.add_field( + name="Cooldown", + value=f"{cooldown.rate} per {cooldown.per:.0f} seconds", + ) + + await self.send(embed=embed) + + async def send_cog_help(self, cog: commands.Cog) -> None: + """Send the help command when a `help ` is called + + Args: + cog (commands.Cog): The cog requested + """ + title = cog.qualified_name or "No" + await self.help_embed( + title=f"{title} Category", + description=cog.description, + commands=cog.get_commands(), + ) + + async def send_group_help(self, group): + """triggers when a `help ` is called""" + title = self.get_command_signature(group) + await self.help_embed( + title=title, description=group.help, commands=group.commands + ) diff --git a/Bot/Libs/utils/pages/sources.py b/Bot/Libs/utils/pages/sources.py index 62ef1c77..f1dfae4d 100644 --- a/Bot/Libs/utils/pages/sources.py +++ b/Bot/Libs/utils/pages/sources.py @@ -39,9 +39,11 @@ def __init__( per_page: int = 5, inline: bool = False, clear_description: bool = True, + title: str = "", + description: str = "", ) -> None: super().__init__(entries, per_page=per_page) - self.embed: Embed = Embed() + self.embed: Embed = Embed(title=title, description=description) self.clear_description: bool = clear_description self.inline: bool = inline diff --git a/Bot/kumikocore.py b/Bot/kumikocore.py index 801cfc29..59ffff15 100644 --- a/Bot/kumikocore.py +++ b/Bot/kumikocore.py @@ -2,9 +2,9 @@ from pathlib import Path as SyncPath import discord -import starlight from anyio import Path from discord.ext import commands +from Libs.utils.help import KumikoHelpPaginated from Libs.utils.redis import redisCheck # Some weird import logic to ensure that watchfiles is there @@ -28,9 +28,7 @@ def __init__( super().__init__( intents=intents, command_prefix=commands.when_mentioned_or(">"), - help_command=starlight.MenuHelpCommand( - per_page=5, accent_color=0xFFCCCB, error_color=discord.Color.red() - ), + help_command=KumikoHelpPaginated(), activity=discord.Activity(type=discord.ActivityType.watching, name="/help"), *args, **kwargs, diff --git a/poetry.lock b/poetry.lock index 7e8e2994..e02dced3 100644 --- a/poetry.lock +++ b/poetry.lock @@ -1,4 +1,4 @@ -# This file is automatically @generated by Poetry and should not be changed by hand. +# This file is automatically @generated by Poetry 1.4.0 and should not be changed by hand. [[package]] name = "aiodns" @@ -166,18 +166,6 @@ files = [ [package.dependencies] typing_extensions = ">=3.7.2" -[[package]] -name = "alabaster" -version = "0.7.13" -description = "A configurable sidebar-enabled Sphinx theme" -category = "main" -optional = false -python-versions = ">=3.6" -files = [ - {file = "alabaster-0.7.13-py3-none-any.whl", hash = "sha256:1ee19aca801bbabb5ba3f5f258e4422dfa86f82f3e9cefb0859b283cdd7f62a3"}, - {file = "alabaster-0.7.13.tar.gz", hash = "sha256:a27a4a084d5e690e16e01e03ad2b2e552c61a65469419b907243193de1a84ae2"}, -] - [[package]] name = "anyio" version = "3.6.2" @@ -341,21 +329,6 @@ docs = ["furo", "myst-parser", "sphinx", "sphinx-notfound-page", "sphinxcontrib- tests = ["attrs[tests-no-zope]", "zope.interface"] tests-no-zope = ["cloudpickle", "cloudpickle", "hypothesis", "hypothesis", "mypy (>=0.971,<0.990)", "mypy (>=0.971,<0.990)", "pympler", "pympler", "pytest (>=4.3.0)", "pytest (>=4.3.0)", "pytest-mypy-plugins", "pytest-mypy-plugins", "pytest-xdist[psutil]", "pytest-xdist[psutil]"] -[[package]] -name = "babel" -version = "2.12.1" -description = "Internationalization utilities" -category = "main" -optional = false -python-versions = ">=3.7" -files = [ - {file = "Babel-2.12.1-py3-none-any.whl", hash = "sha256:b4246fb7677d3b98f501a39d43396d3cafdc8eadb045f4a31be01863f655c610"}, - {file = "Babel-2.12.1.tar.gz", hash = "sha256:cc2d99999cd01d44420ae725a21c9e3711b3aadc7976d6147f622d8581963455"}, -] - -[package.dependencies] -pytz = {version = ">=2015.7", markers = "python_version < \"3.9\""} - [[package]] name = "backoff" version = "2.2.1" @@ -893,18 +866,6 @@ files = [ {file = "distlib-0.3.6.tar.gz", hash = "sha256:14bad2d9b04d3a36127ac97f30b12a19268f211063d8f8ee4f47108896e11b46"}, ] -[[package]] -name = "docutils" -version = "0.18.1" -description = "Docutils -- Python Documentation Utilities" -category = "main" -optional = false -python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, !=3.4.*" -files = [ - {file = "docutils-0.18.1-py2.py3-none-any.whl", hash = "sha256:23010f129180089fbcd3bc08cfefccb3b890b0050e1ca00c867036e9d161b98c"}, - {file = "docutils-0.18.1.tar.gz", hash = "sha256:679987caf361a7539d76e584cbeddc311e3aee937877c87346f31debc63e9d06"}, -] - [[package]] name = "exceptiongroup" version = "1.1.0" @@ -1307,18 +1268,6 @@ files = [ {file = "idna-3.4.tar.gz", hash = "sha256:814f528e8dead7d329833b91c5faa87d60bf71824cd12a7530b5526063d02cb4"}, ] -[[package]] -name = "imagesize" -version = "1.4.1" -description = "Getting image size from png/jpeg/jpeg2000/gif file" -category = "main" -optional = false -python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*" -files = [ - {file = "imagesize-1.4.1-py2.py3-none-any.whl", hash = "sha256:0d8d18d08f840c19d0ee7ca1fd82490fdc3729b7ac93f49870406ddde8ef8d8b"}, - {file = "imagesize-1.4.1.tar.gz", hash = "sha256:69150444affb9cb0d5cc5a92b3676f0b2fb7cd9ae39e947a5e11a36b4497cd4a"}, -] - [[package]] name = "import-expression" version = "1.1.4" @@ -1341,7 +1290,7 @@ test = ["pytest", "pytest-cov"] name = "importlib-metadata" version = "6.1.0" description = "Read metadata from Python packages" -category = "main" +category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1745,7 +1694,7 @@ files = [ name = "packaging" version = "22.0" description = "Core utilities for Python packages" -category = "main" +category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1963,21 +1912,6 @@ typing-extensions = ">=4.2.0" dotenv = ["python-dotenv (>=0.10.4)"] email = ["email-validator (>=1.0.3)"] -[[package]] -name = "pygments" -version = "2.14.0" -description = "Pygments is a syntax highlighting package written in Python." -category = "main" -optional = false -python-versions = ">=3.6" -files = [ - {file = "Pygments-2.14.0-py3-none-any.whl", hash = "sha256:fa7bd7bd2771287c0de303af8bfdfc731f51bd2c6a47ab69d117138893b82717"}, - {file = "Pygments-2.14.0.tar.gz", hash = "sha256:b3ed06a9e8ac9a9aae5a6f5dbe78a8a58655d17b43b93c078f094ddc476ae297"}, -] - -[package.extras] -plugins = ["importlib-metadata"] - [[package]] name = "pyinstrument" version = "4.4.0" @@ -2163,18 +2097,6 @@ files = [ [package.extras] cli = ["click (>=5.0)"] -[[package]] -name = "pytz" -version = "2023.3" -description = "World timezone definitions, modern and historical" -category = "main" -optional = false -python-versions = "*" -files = [ - {file = "pytz-2023.3-py2.py3-none-any.whl", hash = "sha256:a151b3abb88eda1d4e34a9814df37de2a80e301e68ba0fd856fb9b46bfbbbffb"}, - {file = "pytz-2023.3.tar.gz", hash = "sha256:1d8ce29db189191fb55338ee6d0387d82ab59f3d00eac103412d64e0ebd0c588"}, -] - [[package]] name = "pyyaml" version = "6.0" @@ -2365,219 +2287,6 @@ files = [ {file = "sniffio-1.3.0.tar.gz", hash = "sha256:e60305c5e5d314f5389259b7f22aaa33d8f7dee49763119234af3755c55b9101"}, ] -[[package]] -name = "snowballstemmer" -version = "2.2.0" -description = "This package provides 29 stemmers for 28 languages generated from Snowball algorithms." -category = "main" -optional = false -python-versions = "*" -files = [ - {file = "snowballstemmer-2.2.0-py2.py3-none-any.whl", hash = "sha256:c8e1716e83cc398ae16824e5572ae04e0d9fc2c6b985fb0f900f5f0c96ecba1a"}, - {file = "snowballstemmer-2.2.0.tar.gz", hash = "sha256:09b16deb8547d3412ad7b590689584cd0fe25ec8db3be37788be3810cbf19cb1"}, -] - -[[package]] -name = "sphinx" -version = "6.1.3" -description = "Python documentation generator" -category = "main" -optional = false -python-versions = ">=3.8" -files = [ - {file = "Sphinx-6.1.3.tar.gz", hash = "sha256:0dac3b698538ffef41716cf97ba26c1c7788dba73ce6f150c1ff5b4720786dd2"}, - {file = "sphinx-6.1.3-py3-none-any.whl", hash = "sha256:807d1cb3d6be87eb78a381c3e70ebd8d346b9a25f3753e9947e866b2786865fc"}, -] - -[package.dependencies] -alabaster = ">=0.7,<0.8" -babel = ">=2.9" -colorama = {version = ">=0.4.5", markers = "sys_platform == \"win32\""} -docutils = ">=0.18,<0.20" -imagesize = ">=1.3" -importlib-metadata = {version = ">=4.8", markers = "python_version < \"3.10\""} -Jinja2 = ">=3.0" -packaging = ">=21.0" -Pygments = ">=2.13" -requests = ">=2.25.0" -snowballstemmer = ">=2.0" -sphinxcontrib-applehelp = "*" -sphinxcontrib-devhelp = "*" -sphinxcontrib-htmlhelp = ">=2.0.0" -sphinxcontrib-jsmath = "*" -sphinxcontrib-qthelp = "*" -sphinxcontrib-serializinghtml = ">=1.1.5" - -[package.extras] -docs = ["sphinxcontrib-websupport"] -lint = ["docutils-stubs", "flake8 (>=3.5.0)", "flake8-simplify", "isort", "mypy (>=0.990)", "ruff", "sphinx-lint", "types-requests"] -test = ["cython", "html5lib", "pytest (>=4.6)"] - -[[package]] -name = "sphinx-rtd-dark-mode" -version = "1.2.4" -description = "Dark mode for the Sphinx Read the Docs theme." -category = "main" -optional = false -python-versions = ">=3.4" -files = [ - {file = "sphinx_rtd_dark_mode-1.2.4-py3-none-any.whl", hash = "sha256:1d97c1e4f7902fb77ae86adcf72926c3b0e48a300f93eeba49266da5aeed8a29"}, - {file = "sphinx_rtd_dark_mode-1.2.4.tar.gz", hash = "sha256:935bc1f3e62fc76eadd7d2760ac7f48bab907a97e44beda749a48a2706aeed63"}, -] - -[package.dependencies] -sphinx-rtd-theme = "*" - -[[package]] -name = "sphinx-rtd-theme" -version = "1.2.0" -description = "Read the Docs theme for Sphinx" -category = "main" -optional = false -python-versions = "!=3.0.*,!=3.1.*,!=3.2.*,!=3.3.*,!=3.4.*,!=3.5.*,>=2.7" -files = [ - {file = "sphinx_rtd_theme-1.2.0-py2.py3-none-any.whl", hash = "sha256:f823f7e71890abe0ac6aaa6013361ea2696fc8d3e1fa798f463e82bdb77eeff2"}, - {file = "sphinx_rtd_theme-1.2.0.tar.gz", hash = "sha256:a0d8bd1a2ed52e0b338cbe19c4b2eef3c5e7a048769753dac6a9f059c7b641b8"}, -] - -[package.dependencies] -docutils = "<0.19" -sphinx = ">=1.6,<7" -sphinxcontrib-jquery = {version = ">=2.0.0,<3.0.0 || >3.0.0", markers = "python_version > \"3\""} - -[package.extras] -dev = ["bump2version", "sphinxcontrib-httpdomain", "transifex-client", "wheel"] - -[[package]] -name = "sphinxcontrib-applehelp" -version = "1.0.4" -description = "sphinxcontrib-applehelp is a Sphinx extension which outputs Apple help books" -category = "main" -optional = false -python-versions = ">=3.8" -files = [ - {file = "sphinxcontrib-applehelp-1.0.4.tar.gz", hash = "sha256:828f867945bbe39817c210a1abfd1bc4895c8b73fcaade56d45357a348a07d7e"}, - {file = "sphinxcontrib_applehelp-1.0.4-py3-none-any.whl", hash = "sha256:29d341f67fb0f6f586b23ad80e072c8e6ad0b48417db2bde114a4c9746feb228"}, -] - -[package.extras] -lint = ["docutils-stubs", "flake8", "mypy"] -test = ["pytest"] - -[[package]] -name = "sphinxcontrib-devhelp" -version = "1.0.2" -description = "sphinxcontrib-devhelp is a sphinx extension which outputs Devhelp document." -category = "main" -optional = false -python-versions = ">=3.5" -files = [ - {file = "sphinxcontrib-devhelp-1.0.2.tar.gz", hash = "sha256:ff7f1afa7b9642e7060379360a67e9c41e8f3121f2ce9164266f61b9f4b338e4"}, - {file = "sphinxcontrib_devhelp-1.0.2-py2.py3-none-any.whl", hash = "sha256:8165223f9a335cc1af7ffe1ed31d2871f325254c0423bc0c4c7cd1c1e4734a2e"}, -] - -[package.extras] -lint = ["docutils-stubs", "flake8", "mypy"] -test = ["pytest"] - -[[package]] -name = "sphinxcontrib-htmlhelp" -version = "2.0.1" -description = "sphinxcontrib-htmlhelp is a sphinx extension which renders HTML help files" -category = "main" -optional = false -python-versions = ">=3.8" -files = [ - {file = "sphinxcontrib-htmlhelp-2.0.1.tar.gz", hash = "sha256:0cbdd302815330058422b98a113195c9249825d681e18f11e8b1f78a2f11efff"}, - {file = "sphinxcontrib_htmlhelp-2.0.1-py3-none-any.whl", hash = "sha256:c38cb46dccf316c79de6e5515e1770414b797162b23cd3d06e67020e1d2a6903"}, -] - -[package.extras] -lint = ["docutils-stubs", "flake8", "mypy"] -test = ["html5lib", "pytest"] - -[[package]] -name = "sphinxcontrib-jquery" -version = "4.1" -description = "Extension to include jQuery on newer Sphinx releases" -category = "main" -optional = false -python-versions = ">=2.7" -files = [ - {file = "sphinxcontrib-jquery-4.1.tar.gz", hash = "sha256:1620739f04e36a2c779f1a131a2dfd49b2fd07351bf1968ced074365933abc7a"}, - {file = "sphinxcontrib_jquery-4.1-py2.py3-none-any.whl", hash = "sha256:f936030d7d0147dd026a4f2b5a57343d233f1fc7b363f68b3d4f1cb0993878ae"}, -] - -[package.dependencies] -Sphinx = ">=1.8" - -[[package]] -name = "sphinxcontrib-jsmath" -version = "1.0.1" -description = "A sphinx extension which renders display math in HTML via JavaScript" -category = "main" -optional = false -python-versions = ">=3.5" -files = [ - {file = "sphinxcontrib-jsmath-1.0.1.tar.gz", hash = "sha256:a9925e4a4587247ed2191a22df5f6970656cb8ca2bd6284309578f2153e0c4b8"}, - {file = "sphinxcontrib_jsmath-1.0.1-py2.py3-none-any.whl", hash = "sha256:2ec2eaebfb78f3f2078e73666b1415417a116cc848b72e5172e596c871103178"}, -] - -[package.extras] -test = ["flake8", "mypy", "pytest"] - -[[package]] -name = "sphinxcontrib-qthelp" -version = "1.0.3" -description = "sphinxcontrib-qthelp is a sphinx extension which outputs QtHelp document." -category = "main" -optional = false -python-versions = ">=3.5" -files = [ - {file = "sphinxcontrib-qthelp-1.0.3.tar.gz", hash = "sha256:4c33767ee058b70dba89a6fc5c1892c0d57a54be67ddd3e7875a18d14cba5a72"}, - {file = "sphinxcontrib_qthelp-1.0.3-py2.py3-none-any.whl", hash = "sha256:bd9fc24bcb748a8d51fd4ecaade681350aa63009a347a8c14e637895444dfab6"}, -] - -[package.extras] -lint = ["docutils-stubs", "flake8", "mypy"] -test = ["pytest"] - -[[package]] -name = "sphinxcontrib-serializinghtml" -version = "1.1.5" -description = "sphinxcontrib-serializinghtml is a sphinx extension which outputs \"serialized\" HTML files (json and pickle)." -category = "main" -optional = false -python-versions = ">=3.5" -files = [ - {file = "sphinxcontrib-serializinghtml-1.1.5.tar.gz", hash = "sha256:aa5f6de5dfdf809ef505c4895e51ef5c9eac17d0f287933eb49ec495280b6952"}, - {file = "sphinxcontrib_serializinghtml-1.1.5-py2.py3-none-any.whl", hash = "sha256:352a9a00ae864471d3a7ead8d7d79f5fc0b57e8b3f95e9867eb9eb28999b92fd"}, -] - -[package.extras] -lint = ["docutils-stubs", "flake8", "mypy"] -test = ["pytest"] - -[[package]] -name = "starlight-dpy" -version = "0.0.1b3" -description = "A Utility library for discord.py" -category = "main" -optional = false -python-versions = ">=3.8.0" -files = [] -develop = false - -[package.dependencies] -"discord.py" = ">=2.1.0" -sphinx_rtd_dark_mode = ">=1.2.4" - -[package.source] -type = "git" -url = "https://github.com/InterStella0/starlight-dpy" -reference = "3f48f562926125e3fbc277d2338de40c3a5a92fe" -resolved_reference = "3f48f562926125e3fbc277d2338de40c3a5a92fe" - [[package]] name = "tomli" version = "2.0.1" @@ -2938,7 +2647,7 @@ multidict = ">=4.0" name = "zipp" version = "3.15.0" description = "Backport of pathlib-compatible object wrapper for zip files" -category = "main" +category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2953,4 +2662,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "acc0c02a5231e00e7c0605cb252bdde5313e4d16986d723f98970508a3d18908" +content-hash = "6f0ab9ce64e1ed3e6647205e1eb837b6362a6eacfdf54ffbf1df7f4080193354" diff --git a/pyproject.toml b/pyproject.toml index 1a7b6bc8..b47c3e50 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -22,7 +22,6 @@ ciso8601 = "^2.3.0" faust-cchardet = "^2.1.18" discord-py = {extras = ["voice"], version = "^2.2.2"} discord-ext-menus = {git = "https://github.com/Rapptz/discord-ext-menus", rev = "8686b5d1bbc1d3c862292eb436ab630d6e9c9b53"} -starlight-dpy = {git = "https://github.com/InterStella0/starlight-dpy", rev = "3f48f562926125e3fbc277d2338de40c3a5a92fe"} [tool.poetry.group.test.dependencies] pytest = "^7.3.0" From d0c37e2c6c76a782bdab779c31d688bbe5947e79 Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Thu, 13 Apr 2023 23:59:14 -0700 Subject: [PATCH 012/184] Remove some unused libs + Bump version up --- poetry.lock | 14 +------------- pyproject.toml | 3 +-- 2 files changed, 2 insertions(+), 15 deletions(-) diff --git a/poetry.lock b/poetry.lock index e02dced3..65609608 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2207,18 +2207,6 @@ idna = {version = "*", optional = true, markers = "extra == \"idna2008\""} [package.extras] idna2008 = ["idna"] -[[package]] -name = "rin-exceptions" -version = "1.0.3" -description = "A set of base exceptions for Rin" -category = "main" -optional = false -python-versions = ">=3.7,<4.0" -files = [ - {file = "rin-exceptions-1.0.3.tar.gz", hash = "sha256:8044e89f50280b0d0e14639e0727405b49a0cf54a73b6993c2dd4cc56d0182c2"}, - {file = "rin_exceptions-1.0.3-py3-none-any.whl", hash = "sha256:7d0e467a313d208589f1340c6225636ae2325e5b0a7be39e0361f1ab0d986fee"}, -] - [[package]] name = "ruff" version = "0.0.261" @@ -2662,4 +2650,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "6f0ab9ce64e1ed3e6647205e1eb837b6362a6eacfdf54ffbf1df7f4080193354" +content-hash = "f08f2b08d55989439c792d295d7b62189b4e23d968fa626cb7d8af7aa4dd0eaf" diff --git a/pyproject.toml b/pyproject.toml index b47c3e50..015515c3 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -1,6 +1,6 @@ [tool.poetry] name = "Kumiko" -version = "0.7.0" +version = "0.9.0" description = "A multipurpose Discord bot built with freedom and choice in mind" authors = ["No767 <73260931+No767@users.noreply.github.com>"] license = "Apache-2.0" @@ -14,7 +14,6 @@ orjson = "^3.8.10" asyncpraw = "^7.7.0" uvloop = "^0.17.0" gql = { extras = ["aiohttp"], version = "^3.4.0" } -rin-exceptions = "^1.0.3" better-ipc = "^2.0.3" prisma = "^0.8.2" redis = {extras = ["hiredis"], version = "^4.5.4"} From 578fd75879a6bde13d00745e6de24f55c5461a4c Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Fri, 14 Apr 2023 18:59:57 +0000 Subject: [PATCH 013/184] [pip](deps-dev): Bump pytest from 7.3.0 to 7.3.1 (#304) Bumps [pytest](https://github.com/pytest-dev/pytest) from 7.3.0 to 7.3.1. - [Release notes](https://github.com/pytest-dev/pytest/releases) - [Changelog](https://github.com/pytest-dev/pytest/blob/main/CHANGELOG.rst) - [Commits](https://github.com/pytest-dev/pytest/compare/7.3.0...7.3.1) --- updated-dependencies: - dependency-name: pytest dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 10 +++++----- pyproject.toml | 2 +- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/poetry.lock b/poetry.lock index 65609608..75b55b69 100644 --- a/poetry.lock +++ b/poetry.lock @@ -1,4 +1,4 @@ -# This file is automatically @generated by Poetry 1.4.0 and should not be changed by hand. +# This file is automatically @generated by Poetry and should not be changed by hand. [[package]] name = "aiodns" @@ -2023,14 +2023,14 @@ dev = ["twine (>=3.4.1)"] [[package]] name = "pytest" -version = "7.3.0" +version = "7.3.1" description = "pytest: simple powerful testing with Python" category = "dev" optional = false python-versions = ">=3.7" files = [ - {file = "pytest-7.3.0-py3-none-any.whl", hash = "sha256:933051fa1bfbd38a21e73c3960cebdad4cf59483ddba7696c48509727e17f201"}, - {file = "pytest-7.3.0.tar.gz", hash = "sha256:58ecc27ebf0ea643ebfdf7fb1249335da761a00c9f955bcd922349bcb68ee57d"}, + {file = "pytest-7.3.1-py3-none-any.whl", hash = "sha256:3799fa815351fea3a5e96ac7e503a96fa51cc9942c3753cda7651b93c1cfa362"}, + {file = "pytest-7.3.1.tar.gz", hash = "sha256:434afafd78b1d78ed0addf160ad2b77a30d35d4bdf8af234fe621919d9ed15e3"}, ] [package.dependencies] @@ -2650,4 +2650,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "f08f2b08d55989439c792d295d7b62189b4e23d968fa626cb7d8af7aa4dd0eaf" +content-hash = "a7ddf66cd7f051a3410de7226ef8d7358793667784a1f1788e675a42f72dfa7a" diff --git a/pyproject.toml b/pyproject.toml index 015515c3..2962f0ea 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -23,7 +23,7 @@ discord-py = {extras = ["voice"], version = "^2.2.2"} discord-ext-menus = {git = "https://github.com/Rapptz/discord-ext-menus", rev = "8686b5d1bbc1d3c862292eb436ab630d6e9c9b53"} [tool.poetry.group.test.dependencies] -pytest = "^7.3.0" +pytest = "^7.3.1" pytest-asyncio = "^0.21.0" nox = "^2022.11.21" nox-poetry = "^1.0.2" From 2ed985891631e9378504159703d031dfa1208f8e Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Fri, 14 Apr 2023 23:02:51 +0000 Subject: [PATCH 014/184] [pip](deps-dev): Bump pyright from 1.1.302 to 1.1.303 (#305) Bumps [pyright](https://github.com/RobertCraigie/pyright-python) from 1.1.302 to 1.1.303. - [Release notes](https://github.com/RobertCraigie/pyright-python/releases) - [Commits](https://github.com/RobertCraigie/pyright-python/compare/v1.1.302...v1.1.303) --- updated-dependencies: - dependency-name: pyright dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index 75b55b69..190607a5 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2004,14 +2004,14 @@ tests = ["hypothesis (>=3.27.0)", "pytest (>=3.2.1,!=3.3.0)"] [[package]] name = "pyright" -version = "1.1.302" +version = "1.1.303" description = "Command line wrapper for pyright" category = "dev" optional = false python-versions = ">=3.7" files = [ - {file = "pyright-1.1.302-py3-none-any.whl", hash = "sha256:1929e3126b664b5281dba66a789e8e04358afca48c10994ee0243b8c2a14acdf"}, - {file = "pyright-1.1.302.tar.gz", hash = "sha256:e74a7dfbbb1d754941d015cccea8a6d29b395d8e4cb0e45dcfcaf3b6c6cfd540"}, + {file = "pyright-1.1.303-py3-none-any.whl", hash = "sha256:8fe3d122d7e965e2df2cef64e1ceb98cff8200f458e7892d92a4c21ee85689c7"}, + {file = "pyright-1.1.303.tar.gz", hash = "sha256:7daa516424555681e8974b21a95c108c5def791bf5381522b1410026d4da62c1"}, ] [package.dependencies] @@ -2650,4 +2650,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "a7ddf66cd7f051a3410de7226ef8d7358793667784a1f1788e675a42f72dfa7a" +content-hash = "027cec6eb1e012bb292447c6e1f0b0ec0de3974ab4e85e13607b001eebb748fc" diff --git a/pyproject.toml b/pyproject.toml index 2962f0ea..2b59ec5c 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -32,7 +32,7 @@ pytest-cov = "^4.0.0" [tool.poetry.group.dev.dependencies] pre-commit = "^3.2.2" pyinstrument = "^4.4.0" -pyright = "^1.1.302" +pyright = "^1.1.303" watchfiles = "^0.19.0" jishaku = "^2.5.1" ruff = "^0.0.261" From 25bac4ab73bb5ef357d17603e9721f1fa5f6c5a8 Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Fri, 14 Apr 2023 22:54:41 -0700 Subject: [PATCH 015/184] Reuse AIOHTTP + GQL client sessions throughout the lifecycle of Kumiko When reused, the client sessions become much more efficient. It's the same idea behind the Redis connection pooling system, and this speeds up the commands that pull from APIs by a ton. It's also generally good practice, and the client sessions will automatically close when the bot is being shut down --- Bot/Cogs/actions.py | 112 +++++------ Bot/Cogs/github.py | 205 ++++++++++---------- Bot/Cogs/kumiko.py | 2 +- Bot/Cogs/reddit.py | 5 +- Bot/Cogs/search.py | 463 +++++++++++++++++++++----------------------- Bot/Cogs/waifus.py | 51 +++-- Bot/kumikobot.py | 17 +- Bot/kumikocore.py | 27 +++ 8 files changed, 450 insertions(+), 432 deletions(-) diff --git a/Bot/Cogs/actions.py b/Bot/Cogs/actions.py index 7fb828f7..39c7eafb 100644 --- a/Bot/Cogs/actions.py +++ b/Bot/Cogs/actions.py @@ -1,82 +1,78 @@ -import aiohttp import discord import orjson from discord import app_commands from discord.ext import commands from discord.ext.commands import Greedy +from kumikocore import KumikoCore from Libs.utils import Embed, formatGreedy class Actions(commands.Cog): """Hug, pet, or kiss someone on Discord!""" - def __init__(self, bot: commands.Bot) -> None: + def __init__(self, bot: KumikoCore) -> None: self.bot = bot + self.session = self.bot.session @commands.hybrid_command(name="hug") @app_commands.describe(user="The user to hug") async def hug(self, ctx: commands.Context, user: Greedy[discord.Member]) -> None: """Hug someone on Discord!""" - async with aiohttp.ClientSession() as session: - async with session.get("https://nekos.life/api/v2/img/hug") as r: - data = await r.json(loads=orjson.loads) - embed = Embed( - title=f"{ctx.author.name} hugs {formatGreedy([items.name for items in user])}!" - ) - embed.set_image(url=data["url"]) - await ctx.send(embed=embed) + async with self.session.get("https://nekos.life/api/v2/img/hug") as r: + data = await r.json(loads=orjson.loads) + embed = Embed( + title=f"{ctx.author.name} hugs {formatGreedy([items.name for items in user])}!" + ) + embed.set_image(url=data["url"]) + await ctx.send(embed=embed) @commands.hybrid_command(name="pat") @app_commands.describe(user="The user to pat") async def pat(self, ctx: commands.Context, user: Greedy[discord.Member]) -> None: """Give someone a headpat!""" - async with aiohttp.ClientSession() as session: - async with session.get("https://nekos.life/api/v2/img/pat") as r: - data = await r.json(loads=orjson.loads) - embed = Embed( - title=f"{ctx.author.name} pats {formatGreedy([items.name for items in user])}!" - ) - embed.set_image(url=data["url"]) - await ctx.send(embed=embed) + async with self.session.get("https://nekos.life/api/v2/img/pat") as r: + data = await r.json(loads=orjson.loads) + embed = Embed( + title=f"{ctx.author.name} pats {formatGreedy([items.name for items in user])}!" + ) + embed.set_image(url=data["url"]) + await ctx.send(embed=embed) @commands.hybrid_command(name="kiss") @app_commands.describe(user="The user to kiss") async def kiss(self, ctx: commands.Context, user: Greedy[discord.Member]) -> None: """Give someone a kiss!""" - async with aiohttp.ClientSession() as session: - async with session.get("https://nekos.life/api/v2/img/kiss") as r: - data = await r.json(loads=orjson.loads) - embed = Embed( - title=f"{ctx.author.name} kisses {formatGreedy([items.name for items in user])}!" - ) - embed.set_image(url=data["url"]) - await ctx.send(embed=embed) + async with self.session.get("https://nekos.life/api/v2/img/kiss") as r: + data = await r.json(loads=orjson.loads) + embed = Embed( + title=f"{ctx.author.name} kisses {formatGreedy([items.name for items in user])}!" + ) + embed.set_image(url=data["url"]) + await ctx.send(embed=embed) @commands.hybrid_command(name="cuddle") @app_commands.describe(user="The user to cuddle") async def cuddle(self, ctx: commands.Context, user: Greedy[discord.Member]) -> None: """Cuddle someone on Discord!""" - async with aiohttp.ClientSession() as session: - async with session.get("https://nekos.life/api/v2/img/cuddle") as r: - data = await r.json(loads=orjson.loads) - embed = Embed( - title=f"{ctx.author.name} cuddles {formatGreedy([items.name for items in user])}!" - ) - embed.set_image(url=data["url"]) - await ctx.send(embed=embed) + async with self.session.get("https://nekos.life/api/v2/img/cuddle") as r: + data = await r.json(loads=orjson.loads) + embed = Embed( + title=f"{ctx.author.name} cuddles {formatGreedy([items.name for items in user])}!" + ) + embed.set_image(url=data["url"]) + await ctx.send(embed=embed) @commands.hybrid_command(name="slap") @app_commands.describe(user="The user to slap") async def slap(self, ctx: commands.Context, user: Greedy[discord.Member]) -> None: """Slaps someone on Discord!""" - async with aiohttp.ClientSession() as session: - async with session.get("https://nekos.life/api/v2/img/slap") as r: - data = await r.json(loads=orjson.loads) - embed = Embed( - title=f"{ctx.author.name} slaps {formatGreedy([items.name for items in user])}!" - ) - embed.set_image(url=data["url"]) - await ctx.send(embed=embed) + async with self.session.get("https://nekos.life/api/v2/img/slap") as r: + data = await r.json(loads=orjson.loads) + embed = Embed( + title=f"{ctx.author.name} slaps {formatGreedy([items.name for items in user])}!" + ) + embed.set_image(url=data["url"]) + await ctx.send(embed=embed) @commands.hybrid_command(name="tickle") @app_commands.describe(user="The user to tickle") @@ -84,28 +80,26 @@ async def tickles( self, ctx: commands.Context, user: Greedy[discord.Member] ) -> None: """Tickle someone on Discord!""" - async with aiohttp.ClientSession() as session: - async with session.get("https://nekos.life/api/v2/img/tickle") as r: - data = await r.json(loads=orjson.loads) - embed = Embed( - title=f"{ctx.author.name} tickles {formatGreedy([items.name for items in user])}!" - ) - embed.set_image(url=data["url"]) - await ctx.send(embed=embed) + async with self.session.get("https://nekos.life/api/v2/img/tickle") as r: + data = await r.json(loads=orjson.loads) + embed = Embed( + title=f"{ctx.author.name} tickles {formatGreedy([items.name for items in user])}!" + ) + embed.set_image(url=data["url"]) + await ctx.send(embed=embed) @commands.hybrid_command(name="poke") @app_commands.describe(user="The user to poke") async def poke(self, ctx: commands.Context, user: Greedy[discord.Member]) -> None: """Poke someone on Discord!""" - async with aiohttp.ClientSession() as session: - async with session.get("https://nekos.life/api/v2/img/poke") as r: - data = await r.json(loads=orjson.loads) - embed = Embed( - title=f"{ctx.author.name} pokes {formatGreedy([items.name for items in user])}!" - ) - embed.set_image(url=data["url"]) - await ctx.send(embed=embed) + async with self.session.get("https://nekos.life/api/v2/img/poke") as r: + data = await r.json(loads=orjson.loads) + embed = Embed( + title=f"{ctx.author.name} pokes {formatGreedy([items.name for items in user])}!" + ) + embed.set_image(url=data["url"]) + await ctx.send(embed=embed) -async def setup(bot: commands.Bot) -> None: +async def setup(bot: KumikoCore) -> None: await bot.add_cog(Actions(bot)) diff --git a/Bot/Cogs/github.py b/Bot/Cogs/github.py index 48a2360d..136b4b57 100644 --- a/Bot/Cogs/github.py +++ b/Bot/Cogs/github.py @@ -1,12 +1,12 @@ import os -import aiohttp import ciso8601 import orjson from discord import app_commands from discord.ext import commands from discord.utils import format_dt from dotenv import load_dotenv +from kumikocore import KumikoCore from Libs.errors import NotFoundError from Libs.utils import Embed from Libs.utils.pages import EmbedListSource, KumikoPages @@ -19,8 +19,9 @@ class Github(commands.Cog): """Search for releases and repos on GitHub""" - def __init__(self, bot: commands.Bot) -> None: + def __init__(self, bot: KumikoCore) -> None: self.bot = bot + self.session = self.bot.session @commands.hybrid_group(name="github") async def github(self, ctx: commands.Context) -> None: @@ -34,115 +35,109 @@ async def githubReleasesList( self, ctx: commands.Context, owner: str, repo: str ) -> None: """Get up to 25 releases for a repo""" - async with aiohttp.ClientSession() as session: - headers = { - "Authorization": f"token {GITHUB_API_KEY}", - "accept": "application/vnd.github.v3+json", - } - params = {"per_page": 25} - async with session.get( - f"https://api.github.com/repos/{owner}/{repo}/releases", - headers=headers, - params=params, - ) as r: - data = await r.json(loads=orjson.loads) - if r.status == 404: - raise NotFoundError - else: - mainData = [ - { - "title": item["name"], - "description": item["body"], - "thumbnail": item["author"]["avatar_url"], - "fields": [ - {"name": "Author", "value": item["author"]["login"]}, - {"name": "URL", "value": item["html_url"]}, - { - "name": "Created At", - "value": format_dt( - ciso8601.parse_datetime(item["created_at"]) - ), - }, - { - "name": "Published At", - "value": format_dt( - ciso8601.parse_datetime(item["published_at"]) - ), - }, - {"name": "Tarball URL", "value": item["tarball_url"]}, - {"name": "Zip URL", "value": item["zipball_url"]}, - { - "name": "Download URL", - "value": [ - subItems["browser_download_url"] + headers = { + "Authorization": f"token {GITHUB_API_KEY}", + "accept": "application/vnd.github.v3+json", + } + params = {"per_page": 25} + async with self.session.get( + f"https://api.github.com/repos/{owner}/{repo}/releases", + headers=headers, + params=params, + ) as r: + data = await r.json(loads=orjson.loads) + if r.status == 404: + raise NotFoundError + else: + mainData = [ + { + "title": item["name"], + "description": item["body"], + "thumbnail": item["author"]["avatar_url"], + "fields": [ + {"name": "Author", "value": item["author"]["login"]}, + {"name": "URL", "value": item["html_url"]}, + { + "name": "Created At", + "value": format_dt( + ciso8601.parse_datetime(item["created_at"]) + ), + }, + { + "name": "Published At", + "value": format_dt( + ciso8601.parse_datetime(item["published_at"]) + ), + }, + {"name": "Tarball URL", "value": item["tarball_url"]}, + {"name": "Zip URL", "value": item["zipball_url"]}, + { + "name": "Download URL", + "value": [ + subItems["browser_download_url"] + for subItems in item["assets"] + ], + }, + { + "name": "Download Count", + "value": str( + [ + subItems["download_count"] for subItems in item["assets"] - ], - }, - { - "name": "Download Count", - "value": str( - [ - subItems["download_count"] - for subItems in item["assets"] - ] - ).replace("'", ""), - }, - ], - } - for item in data - ] - embedSource = EmbedListSource(mainData, per_page=1) - pages = KumikoPages(source=embedSource, ctx=ctx) - await pages.start() + ] + ).replace("'", ""), + }, + ], + } + for item in data + ] + embedSource = EmbedListSource(mainData, per_page=1) + pages = KumikoPages(source=embedSource, ctx=ctx) + await pages.start() @github.command(name="repo") @app_commands.describe(owner="The owner of the repo", repo="The repo to search") async def searchGitHub(self, ctx: commands.Context, owner: str, repo: str) -> None: """Searches for one repo on GitHub""" - async with aiohttp.ClientSession() as session: - headers = { - "Authorization": f"token {GITHUB_API_KEY}", - "accept": "application/vnd.github.v3+json", - } - async with session.get( - f"https://api.github.com/repos/{owner}/{repo}", headers=headers - ) as r: - data = await r.json(loads=orjson.loads) - if r.status == 404: - raise NotFoundError - else: - embed = Embed(title=data["name"], description=data["description"]) - embed.set_thumbnail(url=data["owner"]["avatar_url"]) - embed.add_field(name="Fork?", value=data["fork"]) - embed.add_field(name="Private", value=data["private"]) - embed.add_field(name="Stars", value=data["stargazers_count"]) - embed.add_field( - name="Language", - value=data["language"] - if data["language"] is not None - else "None", - ) - embed.add_field(name="URL", value=data["html_url"]) - embed.add_field( - name="Homepage", - value=data["homepage"] - if data["homepage"] is not None - else "None", - ) - embed.add_field( - name="Created At", - value=format_dt(ciso8601.parse_datetime(data["created_at"])), - ) - embed.add_field( - name="Updated At", - value=format_dt(ciso8601.parse_datetime(data["updated_at"])), - ) - embed.add_field( - name="Pushed At", - value=format_dt(ciso8601.parse_datetime(data["pushed_at"])), - ) - await ctx.send(embed=embed) + headers = { + "Authorization": f"token {GITHUB_API_KEY}", + "accept": "application/vnd.github.v3+json", + } + async with self.session.get( + f"https://api.github.com/repos/{owner}/{repo}", headers=headers + ) as r: + data = await r.json(loads=orjson.loads) + if r.status == 404: + raise NotFoundError + else: + embed = Embed(title=data["name"], description=data["description"]) + embed.set_thumbnail(url=data["owner"]["avatar_url"]) + embed.add_field(name="Fork?", value=data["fork"]) + embed.add_field(name="Private", value=data["private"]) + embed.add_field(name="Stars", value=data["stargazers_count"]) + embed.add_field( + name="Language", + value=data["language"] if data["language"] is not None else "None", + ) + embed.add_field(name="URL", value=data["html_url"]) + embed.add_field( + name="Homepage", + value=data["homepage"] if data["homepage"] is not None else "None", + ) + embed.add_field( + name="Created At", + value=format_dt(ciso8601.parse_datetime(data["created_at"])), + ) + embed.add_field( + name="Updated At", + value=format_dt(ciso8601.parse_datetime(data["updated_at"])), + ) + embed.add_field( + name="Pushed At", + value=format_dt(ciso8601.parse_datetime(data["pushed_at"])), + ) + await ctx.send(embed=embed) -async def setup(bot: commands.Bot) -> None: +async def setup(bot: KumikoCore) -> None: await bot.add_cog(Github(bot)) diff --git a/Bot/Cogs/kumiko.py b/Bot/Cogs/kumiko.py index e61cdbac..7450e794 100644 --- a/Bot/Cogs/kumiko.py +++ b/Bot/Cogs/kumiko.py @@ -6,7 +6,7 @@ from discord.ext import commands from Libs.utils import Embed -VERSION = "v0.7.0" +VERSION = "v0.9.0" class Kumiko(commands.Cog): diff --git a/Bot/Cogs/reddit.py b/Bot/Cogs/reddit.py index 2e143b92..9da0e39d 100644 --- a/Bot/Cogs/reddit.py +++ b/Bot/Cogs/reddit.py @@ -9,6 +9,7 @@ from discord.ext import commands from discord.utils import format_dt from dotenv import load_dotenv +from kumikocore import KumikoCore from Libs.utils import parseSubreddit from Libs.utils.pages import EmbedListSource, KumikoPages @@ -21,7 +22,7 @@ class Reddit(commands.Cog): """Search, and view posts and memes from Reddit""" - def __init__(self, bot: commands.Bot) -> None: + def __init__(self, bot: KumikoCore) -> None: self.bot = bot @commands.hybrid_group(name="reddit") @@ -211,5 +212,5 @@ async def searchMemes( await pages.start() -async def setup(bot: commands.Bot) -> None: +async def setup(bot: KumikoCore) -> None: await bot.add_cog(Reddit(bot)) diff --git a/Bot/Cogs/search.py b/Bot/Cogs/search.py index 6e736e8d..42134730 100644 --- a/Bot/Cogs/search.py +++ b/Bot/Cogs/search.py @@ -1,15 +1,14 @@ import os from typing import Literal, Optional -import aiohttp import ciso8601 import orjson from discord import app_commands from discord.ext import commands from discord.utils import format_dt from dotenv import load_dotenv -from gql import Client, gql -from gql.transport.aiohttp import AIOHTTPTransport +from gql import gql +from kumikocore import KumikoCore from Libs.errors import NoItemsError from Libs.utils.pages import EmbedListSource, KumikoPages @@ -21,8 +20,10 @@ class Searches(commands.Cog): """Search for anime, manga, gifs, memes, and much more!""" - def __init__(self, bot: commands.Bot) -> None: + def __init__(self, bot: KumikoCore) -> None: self.bot = bot + self.session = self.bot.session + self.gql_session = self.bot.gql_session @commands.hybrid_group(name="search") async def search(self, ctx: commands.Context) -> None: @@ -34,210 +35,199 @@ async def search(self, ctx: commands.Context) -> None: @app_commands.describe(name="The name of the anime to search") async def searchAnime(self, ctx: commands.Context, *, name: str) -> None: """Searches up animes""" - transport = AIOHTTPTransport(url="https://graphql.anilist.co/") - async with Client( - transport=transport, - fetch_schema_from_transport=True, - ) as session: - query = gql( - """ - query ($animeName: String!, $perPage: Int, $isAdult: Boolean!) { - Page (perPage: $perPage){ - media(search: $animeName, isAdult: $isAdult, type: ANIME) { - title { - native - english - romaji - } - description - format - status - seasonYear - startDate { - day - month - year - } - endDate { - day - month - year - } - coverImage { - extraLarge - } - genres - tags { - name - } - synonyms - id - + query = gql( + """ + query ($animeName: String!, $perPage: Int, $isAdult: Boolean!) { + Page (perPage: $perPage){ + media(search: $animeName, isAdult: $isAdult, type: ANIME) { + title { + native + english + romaji } + description + format + status + seasonYear + startDate { + day + month + year + } + endDate { + day + month + year + } + coverImage { + extraLarge + } + genres + tags { + name + } + synonyms + id + } } + } """ - ) + ) - params = {"animeName": name, "perPage": 25, "isAdult": False} - data = await session.execute(query, variable_values=params) + params = {"animeName": name, "perPage": 25, "isAdult": False} + data = await self.gql_session.execute(query, variable_values=params) - if len(data["Page"]["media"]) == 0: - raise NoItemsError - else: - mainData = [ - { - "title": item["title"]["romaji"], - "description": str(item["description"]).replace("
", ""), - "image": item["coverImage"]["extraLarge"], - "fields": [ - {"name": "Native Name", "value": item["title"]["native"]}, - {"name": "English Name", "value": item["title"]["english"]}, - {"name": "Status", "value": item["status"]}, - { - "name": "Start Date", - "value": f'{item["startDate"]["year"]}-{item["startDate"]["month"]}-{item["startDate"]["day"]}', - }, - { - "name": "End Date", - "value": f'{item["endDate"]["year"]}-{item["endDate"]["month"]}-{item["endDate"]["day"]}', - }, - {"name": "Genres", "value": item["genres"]}, - {"name": "Synonyms", "value": item["synonyms"]}, - {"name": "Format", "value": item["format"]}, - {"name": "Season Year", "value": item["seasonYear"]}, - { - "name": "Tags", - "value": [tagItem["name"] for tagItem in item["tags"]], - }, - { - "name": "AniList URL", - "value": f"https://anilist.co/anime/{item['id']}", - }, - ], - } - for item in data["Page"]["media"] - ] - embedSource = EmbedListSource(mainData, per_page=1) - pages = KumikoPages(source=embedSource, ctx=ctx) - await pages.start() + if len(data["Page"]["media"]) == 0: + raise NoItemsError + else: + mainData = [ + { + "title": item["title"]["romaji"], + "description": str(item["description"]).replace("
", ""), + "image": item["coverImage"]["extraLarge"], + "fields": [ + {"name": "Native Name", "value": item["title"]["native"]}, + {"name": "English Name", "value": item["title"]["english"]}, + {"name": "Status", "value": item["status"]}, + { + "name": "Start Date", + "value": f'{item["startDate"]["year"]}-{item["startDate"]["month"]}-{item["startDate"]["day"]}', + }, + { + "name": "End Date", + "value": f'{item["endDate"]["year"]}-{item["endDate"]["month"]}-{item["endDate"]["day"]}', + }, + {"name": "Genres", "value": item["genres"]}, + {"name": "Synonyms", "value": item["synonyms"]}, + {"name": "Format", "value": item["format"]}, + {"name": "Season Year", "value": item["seasonYear"]}, + { + "name": "Tags", + "value": [tagItem["name"] for tagItem in item["tags"]], + }, + { + "name": "AniList URL", + "value": f"https://anilist.co/anime/{item['id']}", + }, + ], + } + for item in data["Page"]["media"] + ] + embedSource = EmbedListSource(mainData, per_page=1) + pages = KumikoPages(source=embedSource, ctx=ctx) + await pages.start() @search.command(name="manga") @app_commands.describe(name="The name of the manga to search") async def searchManga(self, ctx: commands.Context, *, name: str): """Searches for manga on AniList""" - transport = AIOHTTPTransport(url="https://graphql.anilist.co/") - async with Client( - transport=transport, - fetch_schema_from_transport=True, - ) as session: - query = gql( - """ - query ($mangaName: String!, $perPage: Int, $isAdult: Boolean!) { - Page (perPage: $perPage){ - media(search: $mangaName, isAdult: $isAdult, type: MANGA) { - title { - native - english - romaji - } - description - format - status - startDate { - day - month - year - } - endDate { - day - month - year - } - coverImage { - extraLarge - } - genres - tags { - name - } - synonyms - id - + query = gql( + """ + query ($mangaName: String!, $perPage: Int, $isAdult: Boolean!) { + Page (perPage: $perPage){ + media(search: $mangaName, isAdult: $isAdult, type: MANGA) { + title { + native + english + romaji + } + description + format + status + startDate { + day + month + year + } + endDate { + day + month + year + } + coverImage { + extraLarge } + genres + tags { + name + } + synonyms + id + } } + } """ - ) + ) + + params = {"mangaName": name, "perPage": 25, "isAdult": False} + data = await self.gql_session.execute(query, variable_values=params) + if len(data["Page"]["media"]) == 0: + raise NoItemsError + else: + mainData = [ + { + "title": item["title"]["romaji"], + "description": str(item["description"]).replace("
", ""), + "image": item["coverImage"]["extraLarge"], + "fields": [ + {"name": "Native Name", "value": item["title"]["native"]}, + {"name": "English Name", "value": item["title"]["english"]}, + {"name": "Status", "value": item["status"]}, + { + "name": "Start Date", + "value": f'{item["startDate"]["year"]}-{item["startDate"]["month"]}-{item["startDate"]["day"]}', + }, + { + "name": "End Date", + "value": f'{item["endDate"]["year"]}-{item["endDate"]["month"]}-{item["endDate"]["day"]}', + }, + {"name": "Genres", "value": item["genres"]}, + {"name": "Synonyms", "value": item["synonyms"]}, + {"name": "Format", "value": item["format"]}, + { + "name": "Tags", + "value": [tagItem["name"] for tagItem in item["tags"]], + }, + { + "name": "AniList URL", + "value": f"https://anilist.co/anime/{item['id']}", + }, + ], + } + for item in data["Page"]["media"] + ] + embedSource = EmbedListSource(mainData, per_page=1) + pages = KumikoPages(source=embedSource, ctx=ctx) + await pages.start() - params = {"mangaName": name, "perPage": 25, "isAdult": False} - data = await session.execute(query, variable_values=params) - if len(data["Page"]["media"]) == 0: + @search.command(name="gifs") + @app_commands.describe(search="The search term to use") + async def searchGifs(self, ctx: commands.Context, *, search: str) -> None: + """Searches for gifs on Tenor""" + params = { + "q": search, + "key": TENOR_API_KEY, + "contentfilter": "medium", + "limit": 25, + "media_filter": "minimal", + } + async with self.session.get( + "https://tenor.googleapis.com/v2/search", params=params + ) as r: + data = await r.json(loads=orjson.loads) + if len(data["results"]) == 0 or r.status == 404: raise NoItemsError else: mainData = [ - { - "title": item["title"]["romaji"], - "description": str(item["description"]).replace("
", ""), - "image": item["coverImage"]["extraLarge"], - "fields": [ - {"name": "Native Name", "value": item["title"]["native"]}, - {"name": "English Name", "value": item["title"]["english"]}, - {"name": "Status", "value": item["status"]}, - { - "name": "Start Date", - "value": f'{item["startDate"]["year"]}-{item["startDate"]["month"]}-{item["startDate"]["day"]}', - }, - { - "name": "End Date", - "value": f'{item["endDate"]["year"]}-{item["endDate"]["month"]}-{item["endDate"]["day"]}', - }, - {"name": "Genres", "value": item["genres"]}, - {"name": "Synonyms", "value": item["synonyms"]}, - {"name": "Format", "value": item["format"]}, - { - "name": "Tags", - "value": [tagItem["name"] for tagItem in item["tags"]], - }, - { - "name": "AniList URL", - "value": f"https://anilist.co/anime/{item['id']}", - }, - ], - } - for item in data["Page"]["media"] + {"image": item["media_formats"]["gif"]["url"]} + for item in data["results"] ] embedSource = EmbedListSource(mainData, per_page=1) pages = KumikoPages(source=embedSource, ctx=ctx) await pages.start() - @search.command(name="gifs") - @app_commands.describe(search="The search term to use") - async def searchGifs(self, ctx: commands.Context, *, search: str) -> None: - """Searches for gifs on Tenor""" - async with aiohttp.ClientSession() as session: - params = { - "q": search, - "key": TENOR_API_KEY, - "contentfilter": "medium", - "limit": 25, - "media_filter": "minimal", - } - async with session.get( - "https://tenor.googleapis.com/v2/search", params=params - ) as r: - data = await r.json(loads=orjson.loads) - if len(data["results"]) == 0 or r.status == 404: - raise NoItemsError - else: - mainData = [ - {"image": item["media_formats"]["gif"]["url"]} - for item in data["results"] - ] - embedSource = EmbedListSource(mainData, per_page=1) - pages = KumikoPages(source=embedSource, ctx=ctx) - await pages.start() - @search.command(name="mc-mods") @app_commands.describe( mod_name="The name of the mod to search for", @@ -251,59 +241,58 @@ async def searchMods( modloader: Optional[Literal["Forge", "Fabric"]] = "Forge", ) -> None: """Search for Minecraft mods and plugins on Modrinth""" - async with aiohttp.ClientSession() as session: - params = { - "query": mod_name, - "index": "relevance", - "limit": 25, - "facets": f'[["categories:{str(modloader).lower()}"]]', - } - async with session.get( - "https://api.modrinth.com/v2/search", params=params - ) as r: - data = await r.json(loads=orjson.loads) - if len(data["hits"]) == 0: - raise NoItemsError - else: - mainData = [ - { - "title": item["title"], - "description": item["description"], - "thumbnail": item["icon_url"], - "fields": [ - {"name": "Author", "value": item["author"]}, - {"name": "Categories", "value": item["categories"]}, - {"name": "Versions", "value": item["versions"]}, - { - "name": "Latest Version", - "value": item["latest_version"], - }, - { - "name": "Date Created", - "value": format_dt( - ciso8601.parse_datetime(item["date_created"]) - ), - }, - { - "name": "Date Modified", - "value": format_dt( - ciso8601.parse_datetime(item["date_modified"]) - ), - }, - {"name": "Downloads", "value": item["downloads"]}, - {"name": "License", "value": item["license"]}, - { - "name": "Modrinth URL", - "value": f"https://modrinth.com/{item['project_type']}/{item['slug']}", - }, - ], - } - for item in data["hits"] - ] - embedSource = EmbedListSource(mainData, per_page=1) - pages = KumikoPages(source=embedSource, ctx=ctx) - await pages.start() + params = { + "query": mod_name, + "index": "relevance", + "limit": 25, + "facets": f'[["categories:{str(modloader).lower()}"]]', + } + async with self.session.get( + "https://api.modrinth.com/v2/search", params=params + ) as r: + data = await r.json(loads=orjson.loads) + if len(data["hits"]) == 0: + raise NoItemsError + else: + mainData = [ + { + "title": item["title"], + "description": item["description"], + "thumbnail": item["icon_url"], + "fields": [ + {"name": "Author", "value": item["author"]}, + {"name": "Categories", "value": item["categories"]}, + {"name": "Versions", "value": item["versions"]}, + { + "name": "Latest Version", + "value": item["latest_version"], + }, + { + "name": "Date Created", + "value": format_dt( + ciso8601.parse_datetime(item["date_created"]) + ), + }, + { + "name": "Date Modified", + "value": format_dt( + ciso8601.parse_datetime(item["date_modified"]) + ), + }, + {"name": "Downloads", "value": item["downloads"]}, + {"name": "License", "value": item["license"]}, + { + "name": "Modrinth URL", + "value": f"https://modrinth.com/{item['project_type']}/{item['slug']}", + }, + ], + } + for item in data["hits"] + ] + embedSource = EmbedListSource(mainData, per_page=1) + pages = KumikoPages(source=embedSource, ctx=ctx) + await pages.start() -async def setup(bot: commands.Bot) -> None: +async def setup(bot: KumikoCore) -> None: await bot.add_cog(Searches(bot)) diff --git a/Bot/Cogs/waifus.py b/Bot/Cogs/waifus.py index 71956e3f..5b86bbfd 100644 --- a/Bot/Cogs/waifus.py +++ b/Bot/Cogs/waifus.py @@ -1,8 +1,8 @@ import random -import aiohttp import orjson from discord.ext import commands +from kumikocore import KumikoCore from Libs.utils import Embed from Libs.utils.pages import EmbedListSource, KumikoPages @@ -10,8 +10,9 @@ class Waifu(commands.Cog): """Commands for getting some waifu pics""" - def __init__(self, bot: commands.Bot) -> None: + def __init__(self, bot: KumikoCore) -> None: self.bot = bot + self.session = self.bot.session @commands.hybrid_group(name="waifu") async def waifu(self, ctx: commands.Context) -> None: @@ -31,16 +32,15 @@ async def randomWaifu(self, ctx: commands.Context) -> None: "raiden-shogun", "selfies", ] - async with aiohttp.ClientSession() as session: - params = { - "included_tags": random.choice(waifuTagList), - "is_nsfw": "false", - "excluded_tags": "oppai", - } - async with session.get("https://api.waifu.im/search/", params=params) as r: - data = await r.json(loads=orjson.loads) - embed = Embed().set_image(url=data["images"][0]["url"]) - await ctx.send(embed=embed) + params = { + "included_tags": random.choice(waifuTagList), + "is_nsfw": "false", + "excluded_tags": "oppai", + } + async with self.session.get("https://api.waifu.im/search/", params=params) as r: + data = await r.json(loads=orjson.loads) + embed = Embed().set_image(url=data["images"][0]["url"]) + await ctx.send(embed=embed) @waifu.command(name="many") async def randomWaifuMany(self, ctx: commands.Context) -> None: @@ -54,20 +54,19 @@ async def randomWaifuMany(self, ctx: commands.Context) -> None: "raiden-shogun", "selfies", ] - async with aiohttp.ClientSession() as session: - params = { - "included_tags": random.choice(waifuTagList), - "is_nsfw": "False", - "excluded_tags": "oppai", - "many": "true", - } - async with session.get("https://api.waifu.im/search/", params=params) as r: - data = await r.json(loads=orjson.loads) - mainData = [{"image": item["url"]} for item in data["images"]] - embedSource = EmbedListSource(mainData, per_page=1) - menu = KumikoPages(source=embedSource, ctx=ctx, compact=False) - await menu.start() + params = { + "included_tags": random.choice(waifuTagList), + "is_nsfw": "False", + "excluded_tags": "oppai", + "many": "true", + } + async with self.session.get("https://api.waifu.im/search/", params=params) as r: + data = await r.json(loads=orjson.loads) + mainData = [{"image": item["url"]} for item in data["images"]] + embedSource = EmbedListSource(mainData, per_page=1) + menu = KumikoPages(source=embedSource, ctx=ctx, compact=False) + await menu.start() -async def setup(bot: commands.Bot) -> None: +async def setup(bot: KumikoCore) -> None: await bot.add_cog(Waifu(bot)) diff --git a/Bot/kumikobot.py b/Bot/kumikobot.py index 8abff7b5..76c23b1c 100644 --- a/Bot/kumikobot.py +++ b/Bot/kumikobot.py @@ -2,8 +2,11 @@ import os import discord +from aiohttp import ClientSession from anyio import run from dotenv import load_dotenv +from gql import Client +from gql.transport.aiohttp import AIOHTTPTransport from kumikocore import KumikoCore load_dotenv() @@ -23,8 +26,18 @@ async def main() -> None: - async with KumikoCore(intents=intents, dev_mode=DEV_MODE) as bot: - await bot.start(KUMIKO_TOKEN) + async with ClientSession() as session: + async with Client( + transport=AIOHTTPTransport(url="https://graphql.anilist.co/"), + fetch_schema_from_transport=True, + ) as gql_session: + async with KumikoCore( + intents=intents, + session=session, + gql_session=gql_session, + dev_mode=DEV_MODE, + ) as bot: + await bot.start(KUMIKO_TOKEN) if __name__ == "__main__": diff --git a/Bot/kumikocore.py b/Bot/kumikocore.py index 59ffff15..c964bfda 100644 --- a/Bot/kumikocore.py +++ b/Bot/kumikocore.py @@ -1,9 +1,12 @@ import logging from pathlib import Path as SyncPath +from typing import Union import discord +from aiohttp import ClientSession from anyio import Path from discord.ext import commands +from gql.client import AsyncClientSession, ReconnectingAsyncClientSession from Libs.utils.help import KumikoHelpPaginated from Libs.utils.redis import redisCheck @@ -21,6 +24,8 @@ class KumikoCore(commands.Bot): def __init__( self, intents: discord.Intents, + session: ClientSession, + gql_session: Union[ReconnectingAsyncClientSession, AsyncClientSession], dev_mode: bool = False, *args, **kwargs, @@ -34,8 +39,30 @@ def __init__( **kwargs, ) self.dev_mode = dev_mode + self._session = session + self._gql_session = gql_session self.logger: logging.Logger = logging.getLogger("kumikobot") + @property + def session(self) -> ClientSession: + """A global web session used throughout the lifetime of the bot + + Returns: + ClientSession: AIOHTTP's ClientSession + """ + return self._session + + @property + def gql_session(self) -> Union[ReconnectingAsyncClientSession, AsyncClientSession]: + """A global GraphQL session used throughout the lifetime of the bot + + This is exclusively used for the AniList integration, thus the URL is set to the AniList GraphQL endpoints. + + Returns: + Union[ReconnectingAsyncClientSession, AsyncClientSession]: The current GQL session + """ + return self._gql_session + async def fsWatcher(self) -> None: cogsPath = SyncPath(__file__).parent.joinpath("Cogs") async for changes in awatch(cogsPath): From defa3a3d535443e8c0dca18772945e516fcae2a4 Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Fri, 14 Apr 2023 23:04:14 -0700 Subject: [PATCH 016/184] Replace `commands.Bot` typehint w/ `KumikoCore` typehint --- Bot/Cogs/db.py | 5 +++-- Bot/Cogs/dev-tools.py | 5 +++-- Bot/Cogs/economy.py | 5 +++-- Bot/Cogs/error-handler.py | 5 +++-- Bot/Cogs/ipc.py | 5 +++-- Bot/Cogs/kumiko.py | 5 +++-- Bot/Cogs/moderation.py | 5 +++-- 7 files changed, 21 insertions(+), 14 deletions(-) diff --git a/Bot/Cogs/db.py b/Bot/Cogs/db.py index cbc92568..32a2e2b3 100644 --- a/Bot/Cogs/db.py +++ b/Bot/Cogs/db.py @@ -2,13 +2,14 @@ import logging from discord.ext import commands, tasks +from kumikocore import KumikoCore from Libs.utils import backoff from prisma import Prisma # type: ignore from prisma.engine.errors import EngineConnectionError # type: ignore class PrismaClientSession(commands.Cog): - def __init__(self, bot: commands.Bot): + def __init__(self, bot: KumikoCore): self.bot = bot self.backoffSec = 10 self.backoffSecIndex = 0 @@ -44,5 +45,5 @@ async def connError(self, exc: Exception) -> None: self.connect.restart() -async def setup(bot: commands.Bot): +async def setup(bot: KumikoCore): await bot.add_cog(PrismaClientSession(bot)) diff --git a/Bot/Cogs/dev-tools.py b/Bot/Cogs/dev-tools.py index 334dc1dc..0c2fdd09 100644 --- a/Bot/Cogs/dev-tools.py +++ b/Bot/Cogs/dev-tools.py @@ -3,10 +3,11 @@ import discord from discord.ext import commands from discord.ext.commands import Context, Greedy +from kumikocore import KumikoCore class DevTools(commands.Cog): - def __init__(self, bot: commands.Bot): + def __init__(self, bot: KumikoCore): self.bot = bot @commands.hybrid_command(name="sync") @@ -56,5 +57,5 @@ async def sync( await ctx.send(f"Synced the tree to {ret}/{len(guilds)}.") -async def setup(bot: commands.Bot): +async def setup(bot: KumikoCore): await bot.add_cog(DevTools(bot)) diff --git a/Bot/Cogs/economy.py b/Bot/Cogs/economy.py index c23836ea..1e3a1d22 100644 --- a/Bot/Cogs/economy.py +++ b/Bot/Cogs/economy.py @@ -1,5 +1,6 @@ import discord from discord.ext import commands +from kumikocore import KumikoCore from Libs.economy import getUser from Libs.ui.economy import RegisterView from Libs.utils import Embed @@ -8,7 +9,7 @@ class Economy(commands.Cog): """Earn, sell, and interact with Kumiko's economy!""" - def __init__(self, bot: commands.Bot) -> None: + def __init__(self, bot: KumikoCore) -> None: self.bot = bot super().__init__() @@ -49,5 +50,5 @@ async def wallet(self, ctx: commands.Context) -> discord.Message: return await ctx.send(embed=embed) -async def setup(bot: commands.Bot) -> None: +async def setup(bot: KumikoCore) -> None: await bot.add_cog(Economy(bot)) diff --git a/Bot/Cogs/error-handler.py b/Bot/Cogs/error-handler.py index 40fbc36a..58eea2d6 100644 --- a/Bot/Cogs/error-handler.py +++ b/Bot/Cogs/error-handler.py @@ -2,6 +2,7 @@ from discord.app_commands.errors import CommandInvokeError from discord.ext import commands +from kumikocore import KumikoCore from Libs.errors import HTTPError, KumikoException, NoItemsError, NotFoundError from Libs.utils import Embed, ErrorEmbed @@ -9,7 +10,7 @@ class ErrorHandler(commands.Cog): """Cog to handle errors""" - def __init__(self, bot: commands.Bot) -> None: + def __init__(self, bot: KumikoCore) -> None: self.bot = bot def fullException(self, obj): @@ -145,5 +146,5 @@ async def on_command_error( await ctx.send(embed=errorEmbed) -async def setup(bot: commands.Bot) -> None: +async def setup(bot: KumikoCore) -> None: await bot.add_cog(ErrorHandler(bot)) diff --git a/Bot/Cogs/ipc.py b/Bot/Cogs/ipc.py index 7c6661a9..84039150 100644 --- a/Bot/Cogs/ipc.py +++ b/Bot/Cogs/ipc.py @@ -5,6 +5,7 @@ from discord.ext.ipc.objects import ClientPayload from discord.ext.ipc.server import Server from dotenv import load_dotenv +from kumikocore import KumikoCore load_dotenv() @@ -13,7 +14,7 @@ class IPCServer(commands.Cog): - def __init__(self, bot: commands.Bot): + def __init__(self, bot: KumikoCore): self.bot = bot self.ipc = ipc.Server( # type: ignore self.bot, secret_key=IPC_SECRET_KEY, host=IPC_HOST @@ -31,5 +32,5 @@ async def get_user_data(self, data: ClientPayload) -> Dict: return user._to_minimal_user_json() # type: ignore -async def setup(bot: commands.Bot): +async def setup(bot: KumikoCore): await bot.add_cog(IPCServer(bot)) diff --git a/Bot/Cogs/kumiko.py b/Bot/Cogs/kumiko.py index 7450e794..89300dc6 100644 --- a/Bot/Cogs/kumiko.py +++ b/Bot/Cogs/kumiko.py @@ -4,6 +4,7 @@ import discord from discord.ext import commands +from kumikocore import KumikoCore from Libs.utils import Embed VERSION = "v0.9.0" @@ -12,7 +13,7 @@ class Kumiko(commands.Cog): """Commands to get basic info about Kumiko""" - def __init__(self, bot: commands.Bot) -> None: + def __init__(self, bot: KumikoCore) -> None: self.bot = bot @commands.Cog.listener() @@ -66,5 +67,5 @@ async def ping(self, ctx: commands.Context) -> None: await ctx.send(embed=embed) -async def setup(bot: commands.Bot) -> None: +async def setup(bot: KumikoCore) -> None: await bot.add_cog(Kumiko(bot)) diff --git a/Bot/Cogs/moderation.py b/Bot/Cogs/moderation.py index 8e466920..ee351814 100644 --- a/Bot/Cogs/moderation.py +++ b/Bot/Cogs/moderation.py @@ -4,13 +4,14 @@ import discord from discord import app_commands from discord.ext import commands +from kumikocore import KumikoCore from Libs.utils import Embed, parseTimeStr class Moderation(commands.Cog): """A set of fine-tuned moderation commands""" - def __init__(self, bot: commands.Bot) -> None: + def __init__(self, bot: KumikoCore) -> None: self.bot = bot @commands.hybrid_group(name="mod") @@ -205,5 +206,5 @@ async def unmute( await ctx.send(embed=embed) -async def setup(bot: commands.Bot) -> None: +async def setup(bot: KumikoCore) -> None: await bot.add_cog(Moderation(bot)) From 705b093c5dc48fec0b10ae7047640e0ee3a7e12e Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Sat, 15 Apr 2023 11:14:58 -0700 Subject: [PATCH 017/184] [skip ci] Update Python version --- .python-version | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.python-version b/.python-version index f4687fd4..d2c96c0a 100644 --- a/.python-version +++ b/.python-version @@ -1 +1 @@ -3.11.2 \ No newline at end of file +3.11.3 From 9579972789d6bc21800e8a9fd5c3b9f60403f13f Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Sun, 16 Apr 2023 23:43:16 -0700 Subject: [PATCH 018/184] [skip ci] Add Docs --- .gitignore | 3 +- Kumiko-Docs/Makefile | 23 +++++++ Kumiko-Docs/make.bat | 35 ++++++++++ Kumiko-Docs/source/conf.py | 32 +++++++++ .../source/guides/dev/dev-contributing.rst | 2 + Kumiko-Docs/source/guides/dev/index.rst | 12 ++++ .../source/guides/dev/requirements.rst | 67 +++++++++++++++++++ Kumiko-Docs/source/guides/dev/setup.rst | 49 ++++++++++++++ Kumiko-Docs/source/guides/user/index.rst | 9 +++ Kumiko-Docs/source/index.rst | 62 +++++++++++++++++ .../terms-of-service/privacy-policy.rst | 2 + Kumiko-Docs/source/terms-of-service/tos.rst | 2 + 12 files changed, 297 insertions(+), 1 deletion(-) create mode 100644 Kumiko-Docs/Makefile create mode 100644 Kumiko-Docs/make.bat create mode 100644 Kumiko-Docs/source/conf.py create mode 100644 Kumiko-Docs/source/guides/dev/dev-contributing.rst create mode 100644 Kumiko-Docs/source/guides/dev/index.rst create mode 100644 Kumiko-Docs/source/guides/dev/requirements.rst create mode 100644 Kumiko-Docs/source/guides/dev/setup.rst create mode 100644 Kumiko-Docs/source/guides/user/index.rst create mode 100644 Kumiko-Docs/source/index.rst create mode 100644 Kumiko-Docs/source/terms-of-service/privacy-policy.rst create mode 100644 Kumiko-Docs/source/terms-of-service/tos.rst diff --git a/.gitignore b/.gitignore index 33bb74b8..b7375cd9 100644 --- a/.gitignore +++ b/.gitignore @@ -80,4 +80,5 @@ image-testspy migrations .env-old database.db -json-tests \ No newline at end of file +json-tests +Kumiko-Docs/build \ No newline at end of file diff --git a/Kumiko-Docs/Makefile b/Kumiko-Docs/Makefile new file mode 100644 index 00000000..d2efd273 --- /dev/null +++ b/Kumiko-Docs/Makefile @@ -0,0 +1,23 @@ +# Minimal makefile for Sphinx documentation +# + +# You can set these variables from the command line, and also +# from the environment for the first two. +SPHINXOPTS ?= +SPHINXBUILD ?= sphinx-build +SOURCEDIR = source +BUILDDIR = build + +# Put it first so that "make" without argument is like "make help". +help: + @$(SPHINXBUILD) -M help "$(SOURCEDIR)" "$(BUILDDIR)" $(SPHINXOPTS) $(O) + +.PHONY: help Makefile + +# Catch-all target: route all unknown targets to Sphinx using the new +# "make mode" option. $(O) is meant as a shortcut for $(SPHINXOPTS). +%: Makefile + @$(SPHINXBUILD) -M $@ "$(SOURCEDIR)" "$(BUILDDIR)" $(SPHINXOPTS) $(O) + +autobuild: + sphinx-autobuild source build/html \ No newline at end of file diff --git a/Kumiko-Docs/make.bat b/Kumiko-Docs/make.bat new file mode 100644 index 00000000..747ffb7b --- /dev/null +++ b/Kumiko-Docs/make.bat @@ -0,0 +1,35 @@ +@ECHO OFF + +pushd %~dp0 + +REM Command file for Sphinx documentation + +if "%SPHINXBUILD%" == "" ( + set SPHINXBUILD=sphinx-build +) +set SOURCEDIR=source +set BUILDDIR=build + +%SPHINXBUILD% >NUL 2>NUL +if errorlevel 9009 ( + echo. + echo.The 'sphinx-build' command was not found. Make sure you have Sphinx + echo.installed, then set the SPHINXBUILD environment variable to point + echo.to the full path of the 'sphinx-build' executable. Alternatively you + echo.may add the Sphinx directory to PATH. + echo. + echo.If you don't have Sphinx installed, grab it from + echo.https://www.sphinx-doc.org/ + exit /b 1 +) + +if "%1" == "" goto help + +%SPHINXBUILD% -M %1 %SOURCEDIR% %BUILDDIR% %SPHINXOPTS% %O% +goto end + +:help +%SPHINXBUILD% -M help %SOURCEDIR% %BUILDDIR% %SPHINXOPTS% %O% + +:end +popd diff --git a/Kumiko-Docs/source/conf.py b/Kumiko-Docs/source/conf.py new file mode 100644 index 00000000..fd5da40c --- /dev/null +++ b/Kumiko-Docs/source/conf.py @@ -0,0 +1,32 @@ +# Configuration file for the Sphinx documentation builder. +# +# For the full list of built-in configuration values, see the documentation: +# https://www.sphinx-doc.org/en/master/usage/configuration.html + +# -- Project information ----------------------------------------------------- +# https://www.sphinx-doc.org/en/master/usage/configuration.html#project-information + +project = "Kumiko" +copyright = "2023, Noelle" +author = "Noelle" + +# -- General configuration --------------------------------------------------- +# https://www.sphinx-doc.org/en/master/usage/configuration.html#general-configuration + +extensions = [] + + +templates_path = ["_templates"] +exclude_patterns = [] + +latex_elements = { + "sphinxsetup": "verbatimwithframe=false", +} + +html_title = "Kumiko" + +# -- Options for HTML output ------------------------------------------------- +# https://www.sphinx-doc.org/en/master/usage/configuration.html#options-for-html-output + +html_theme = "furo" +html_static_path = ["_static"] diff --git a/Kumiko-Docs/source/guides/dev/dev-contributing.rst b/Kumiko-Docs/source/guides/dev/dev-contributing.rst new file mode 100644 index 00000000..a76ed1ca --- /dev/null +++ b/Kumiko-Docs/source/guides/dev/dev-contributing.rst @@ -0,0 +1,2 @@ +Dev Contributing Guide +====================== diff --git a/Kumiko-Docs/source/guides/dev/index.rst b/Kumiko-Docs/source/guides/dev/index.rst new file mode 100644 index 00000000..3f95831d --- /dev/null +++ b/Kumiko-Docs/source/guides/dev/index.rst @@ -0,0 +1,12 @@ +================ +Developer Guide +================ + +Kumiko offers a developer guide so future developers can easily get started with the project. + +.. toctree:: + :maxdepth: 2 + + requirements + setup + dev-contributing \ No newline at end of file diff --git a/Kumiko-Docs/source/guides/dev/requirements.rst b/Kumiko-Docs/source/guides/dev/requirements.rst new file mode 100644 index 00000000..c55d64d3 --- /dev/null +++ b/Kumiko-Docs/source/guides/dev/requirements.rst @@ -0,0 +1,67 @@ +Requirements +================================== + + +Software Requirements +--------------------- +Before you get started, please ensure you have the following installed: + +- `Git `_ +- `Python 3 `_ +- `Poetry `_ +- `WSL2 `_ (If working on Windows) +- `Docker `_ +- Discord Account + App + +.. NOTE:: + Kumiko is natively developed for Linux. If you are using Windows, please use WSL2. + +Package Prerequisites +---------------------- + +Debian/Ubuntu +^^^^^^^^^^^^^ + +.. code-block:: bash + + sudo apt-get install libffi-dev python3-dev libnacl-dev libopus-dev libopus0 \ + libopusenc-dev build-essentials libssl-dev curl wget git + +RHEL/CentOS/Fedora 22 or below +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +.. code-block:: bash + + sudo yum install make gcc libffi-devel python-devel \ + openssl-devel opus-devel opus curl wget git + +Fedora 23+ +^^^^^^^^^^ + +.. code-block:: bash + + sudo dnf install make automake gcc gcc-c++ kernel-devel \ + libffi-devel python3-libnacl python3.11-devel openssl11-devel \ + openssl-devel opus opus-devel curl wget git + +OpenSUSE +^^^^^^^^ + +.. code-block:: bash + + sudo zypper install gcc make automake openssl-devel openssl-1_1 openssl-1_1-devel \ + libffi-devel python311-devel python311-libnacl opus libopus0 wget git curl + +Arch Linux +^^^^^^^^^^ + +.. code-block:: bash + + sudo pacman -S --needed base-devel openssl openssl-1.1 libffi python python-libnacl opus + +MacOS +^^^^^ + +.. code-block:: bash + + brew install openssl openssl@1.1 libffi git curl make opus \ No newline at end of file diff --git a/Kumiko-Docs/source/guides/dev/setup.rst b/Kumiko-Docs/source/guides/dev/setup.rst new file mode 100644 index 00000000..b297016b --- /dev/null +++ b/Kumiko-Docs/source/guides/dev/setup.rst @@ -0,0 +1,49 @@ +Setup +======== + +Local Setup +----------- + +1. Fork and clone the repo + + .. code-block:: bash + + git clone https://github.com/[username]/Kumiko.git && cd Kumiko + + + Or if you have the `gh` cli tool installed: + + .. code-block:: bash + + gh repo clone [username]/Kumiko + + +2. Install all of the dependencies (including dev dependencies) + + .. code-block:: bash + + poetry install --with=dev,test + + +3. Start the Docker Compose stack + + .. code-block:: bash + + sudo docker compose -f docker-compose-dev.yml up -d + + +4. Run the database migrations + + .. code-block:: bash + + poetry run prisma db push + +Vagrant +------- + +Kumiko also supports using Vagrant as a development environment. In order to use Vagrant, you will need Oracle VirtualBox or VMWare Workstation installed on your machine. Once installed and properly configured, you can just run ``vagrant up`` to provision and start it up, and connect to it by SSH or by VSCode. + +Environment Variables +--------------------- + +Kumiko v0.7+ includes an development mode feature, which will set up jishaku and a custom FS watcher. Later on, there may be more development features that will be included. Make sure you first install the dev dependencies first! And in order to enable it, set an environment variable called ``DEV_MODE`` to ``True``. \ No newline at end of file diff --git a/Kumiko-Docs/source/guides/user/index.rst b/Kumiko-Docs/source/guides/user/index.rst new file mode 100644 index 00000000..eb464750 --- /dev/null +++ b/Kumiko-Docs/source/guides/user/index.rst @@ -0,0 +1,9 @@ +User Guide +============ + +Kumiko offers a user guide where users can find information on commands, features, and many others. This section is incomplete, but will be completed in the future. + +.. toctree:: + :maxdepth: 2 + :hidden: + \ No newline at end of file diff --git a/Kumiko-Docs/source/index.rst b/Kumiko-Docs/source/index.rst new file mode 100644 index 00000000..79d8e545 --- /dev/null +++ b/Kumiko-Docs/source/index.rst @@ -0,0 +1,62 @@ +.. Kumiko documentation master file, created by + sphinx-quickstart on Sun Apr 16 21:15:08 2023. + You can adapt this file completely to your liking, but it should at least + contain the root `toctree` directive. + + +Welcome to Kumiko +================================== + +.. toctree:: + :maxdepth: 2 + :hidden: + :caption: Guides + + guides/user/index + guides/dev/index + +.. toctree:: + :maxdepth: 2 + :hidden: + :caption: Terms of Service + + terms-of-service/tos.rst + terms-of-service/privacy-policy.rst + + +.. figure:: https://raw.githubusercontent.com/No767/Kumiko/dev/assets/kumiko-resized-round.svg + :align: center + +Kumiko is a multipurpose Discord bot built with freedom and choice in mind. Kumiko takes a unique approach to what a multipurpose bot is defined as. + +Features +---------- +- Customizable prefix module +- Global or guild economy with jobs and marketplaces +- Custom logging module +- Basic moderation commands +- Search for memes, posts, anime, manga, and others! + +And some ones that are planned: + +- Complete Web Dashboard + Custom Embeds (WIP, pinned for v2) +- Event Logging (Pinned for v1) +- Annoucement releaser with support from GitHub (Pinned for v2) +- AI Driven GAN Anime Waifu Generator (Not implemented yet) +- Selector Roles (pinned for v2) + +Guides +---------------- + +Are you interested in contributing to Kumiko as a developer? Or are you interested in learning how to use Kumiko as the end user? This is the place to get started! + +- :doc:`guides/dev/index` +- :doc:`guides/user/index` + +Resources and Links +------------------- + +- `Docker Hub `_ +- `GHCR `_ +- `GitHub `_ +- Discord Server \ No newline at end of file diff --git a/Kumiko-Docs/source/terms-of-service/privacy-policy.rst b/Kumiko-Docs/source/terms-of-service/privacy-policy.rst new file mode 100644 index 00000000..c3d07c9e --- /dev/null +++ b/Kumiko-Docs/source/terms-of-service/privacy-policy.rst @@ -0,0 +1,2 @@ +Privacy Policy +============== \ No newline at end of file diff --git a/Kumiko-Docs/source/terms-of-service/tos.rst b/Kumiko-Docs/source/terms-of-service/tos.rst new file mode 100644 index 00000000..95cb4f66 --- /dev/null +++ b/Kumiko-Docs/source/terms-of-service/tos.rst @@ -0,0 +1,2 @@ +Terms of Service +================= \ No newline at end of file From 954a781930e36a20422a5923c658db7a4fc52acc Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Sun, 16 Apr 2023 23:45:35 -0700 Subject: [PATCH 019/184] Update Pyproject.toml w/ new deps --- poetry.lock | 433 ++++++++++++++++++++++++++++++++++++++++++++++++- pyproject.toml | 7 + 2 files changed, 438 insertions(+), 2 deletions(-) diff --git a/poetry.lock b/poetry.lock index 190607a5..40baf0e6 100644 --- a/poetry.lock +++ b/poetry.lock @@ -1,4 +1,4 @@ -# This file is automatically @generated by Poetry and should not be changed by hand. +# This file is automatically @generated by Poetry 1.4.2 and should not be changed by hand. [[package]] name = "aiodns" @@ -166,6 +166,18 @@ files = [ [package.dependencies] typing_extensions = ">=3.7.2" +[[package]] +name = "alabaster" +version = "0.7.13" +description = "A configurable sidebar-enabled Sphinx theme" +category = "dev" +optional = false +python-versions = ">=3.6" +files = [ + {file = "alabaster-0.7.13-py3-none-any.whl", hash = "sha256:1ee19aca801bbabb5ba3f5f258e4422dfa86f82f3e9cefb0859b283cdd7f62a3"}, + {file = "alabaster-0.7.13.tar.gz", hash = "sha256:a27a4a084d5e690e16e01e03ad2b2e552c61a65469419b907243193de1a84ae2"}, +] + [[package]] name = "anyio" version = "3.6.2" @@ -329,6 +341,21 @@ docs = ["furo", "myst-parser", "sphinx", "sphinx-notfound-page", "sphinxcontrib- tests = ["attrs[tests-no-zope]", "zope.interface"] tests-no-zope = ["cloudpickle", "cloudpickle", "hypothesis", "hypothesis", "mypy (>=0.971,<0.990)", "mypy (>=0.971,<0.990)", "pympler", "pympler", "pytest (>=4.3.0)", "pytest (>=4.3.0)", "pytest-mypy-plugins", "pytest-mypy-plugins", "pytest-xdist[psutil]", "pytest-xdist[psutil]"] +[[package]] +name = "babel" +version = "2.12.1" +description = "Internationalization utilities" +category = "dev" +optional = false +python-versions = ">=3.7" +files = [ + {file = "Babel-2.12.1-py3-none-any.whl", hash = "sha256:b4246fb7677d3b98f501a39d43396d3cafdc8eadb045f4a31be01863f655c610"}, + {file = "Babel-2.12.1.tar.gz", hash = "sha256:cc2d99999cd01d44420ae725a21c9e3711b3aadc7976d6147f622d8581963455"}, +] + +[package.dependencies] +pytz = {version = ">=2015.7", markers = "python_version < \"3.9\""} + [[package]] name = "backoff" version = "2.2.1" @@ -341,6 +368,25 @@ files = [ {file = "backoff-2.2.1.tar.gz", hash = "sha256:03f829f5bb1923180821643f8753b0502c3b682293992485b0eef2807afa5cba"}, ] +[[package]] +name = "beautifulsoup4" +version = "4.12.2" +description = "Screen-scraping library" +category = "dev" +optional = false +python-versions = ">=3.6.0" +files = [ + {file = "beautifulsoup4-4.12.2-py3-none-any.whl", hash = "sha256:bd2520ca0d9d7d12694a53d44ac482d181b4ec1888909b035a3dbf40d0f57d4a"}, + {file = "beautifulsoup4-4.12.2.tar.gz", hash = "sha256:492bbc69dca35d12daac71c4db1bfff0c876c00ef4a2ffacce226d4638eb72da"}, +] + +[package.dependencies] +soupsieve = ">1.2" + +[package.extras] +html5lib = ["html5lib"] +lxml = ["lxml"] + [[package]] name = "better-ipc" version = "2.0.3" @@ -866,6 +912,18 @@ files = [ {file = "distlib-0.3.6.tar.gz", hash = "sha256:14bad2d9b04d3a36127ac97f30b12a19268f211063d8f8ee4f47108896e11b46"}, ] +[[package]] +name = "docutils" +version = "0.19" +description = "Docutils -- Python Documentation Utilities" +category = "dev" +optional = false +python-versions = ">=3.7" +files = [ + {file = "docutils-0.19-py3-none-any.whl", hash = "sha256:5e1de4d849fee02c63b040a4a3fd567f4ab104defd8a5511fbbc24a8a017efbc"}, + {file = "docutils-0.19.tar.gz", hash = "sha256:33995a6753c30b7f577febfc2c50411fec6aac7f7ffeb7c4cfe5991072dcf9e6"}, +] + [[package]] name = "exceptiongroup" version = "1.1.0" @@ -1044,6 +1102,24 @@ files = [ {file = "frozenlist-1.3.3.tar.gz", hash = "sha256:58bcc55721e8a90b88332d6cd441261ebb22342e238296bb330968952fbb3a6a"}, ] +[[package]] +name = "furo" +version = "2023.3.27" +description = "A clean customisable Sphinx documentation theme." +category = "dev" +optional = false +python-versions = ">=3.7" +files = [ + {file = "furo-2023.3.27-py3-none-any.whl", hash = "sha256:4ab2be254a2d5e52792d0ca793a12c35582dd09897228a6dd47885dabd5c9521"}, + {file = "furo-2023.3.27.tar.gz", hash = "sha256:b99e7867a5cc833b2b34d7230631dd6558c7a29f93071fdbb5709634bb33c5a5"}, +] + +[package.dependencies] +beautifulsoup4 = "*" +pygments = ">=2.7" +sphinx = ">=5.0,<7.0" +sphinx-basic-ng = "*" + [[package]] name = "gql" version = "3.4.0" @@ -1268,6 +1344,18 @@ files = [ {file = "idna-3.4.tar.gz", hash = "sha256:814f528e8dead7d329833b91c5faa87d60bf71824cd12a7530b5526063d02cb4"}, ] +[[package]] +name = "imagesize" +version = "1.4.1" +description = "Getting image size from png/jpeg/jpeg2000/gif file" +category = "dev" +optional = false +python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*" +files = [ + {file = "imagesize-1.4.1-py2.py3-none-any.whl", hash = "sha256:0d8d18d08f840c19d0ee7ca1fd82490fdc3729b7ac93f49870406ddde8ef8d8b"}, + {file = "imagesize-1.4.1.tar.gz", hash = "sha256:69150444affb9cb0d5cc5a92b3676f0b2fb7cd9ae39e947a5e11a36b4497cd4a"}, +] + [[package]] name = "import-expression" version = "1.1.4" @@ -1427,6 +1515,47 @@ ipython-strict = ["IPython (==0.13)", "IPython (==0.13)"] tests = ["IPython", "IPython", "coverage[toml]", "pytest", "pytest-cov", "ubelt"] tests-strict = ["IPython (==0.13)", "IPython (==0.13)", "coverage[toml] (==5.3)", "pytest (==4.6.11)", "pytest-cov (==2.10.1)", "ubelt (==1.0.1)"] +[[package]] +name = "livereload" +version = "2.6.3" +description = "Python LiveReload is an awesome tool for web developers" +category = "dev" +optional = false +python-versions = "*" +files = [ + {file = "livereload-2.6.3-py2.py3-none-any.whl", hash = "sha256:ad4ac6f53b2d62bb6ce1a5e6e96f1f00976a32348afedcb4b6d68df2a1d346e4"}, + {file = "livereload-2.6.3.tar.gz", hash = "sha256:776f2f865e59fde56490a56bcc6773b6917366bce0c267c60ee8aaf1a0959869"}, +] + +[package.dependencies] +six = "*" +tornado = {version = "*", markers = "python_version > \"2.7\""} + +[[package]] +name = "markdown-it-py" +version = "2.2.0" +description = "Python port of markdown-it. Markdown parsing, done right!" +category = "dev" +optional = false +python-versions = ">=3.7" +files = [ + {file = "markdown-it-py-2.2.0.tar.gz", hash = "sha256:7c9a5e412688bc771c67432cbfebcdd686c93ce6484913dccf06cb5a0bea35a1"}, + {file = "markdown_it_py-2.2.0-py3-none-any.whl", hash = "sha256:5a35f8d1870171d9acc47b99612dc146129b631baf04970128b568f190d0cc30"}, +] + +[package.dependencies] +mdurl = ">=0.1,<1.0" + +[package.extras] +benchmarking = ["psutil", "pytest", "pytest-benchmark"] +code-style = ["pre-commit (>=3.0,<4.0)"] +compare = ["commonmark (>=0.9,<1.0)", "markdown (>=3.4,<4.0)", "mistletoe (>=1.0,<2.0)", "mistune (>=2.0,<3.0)", "panflute (>=2.3,<3.0)"] +linkify = ["linkify-it-py (>=1,<3)"] +plugins = ["mdit-py-plugins"] +profiling = ["gprof2dot"] +rtd = ["attrs", "myst-parser", "pyyaml", "sphinx", "sphinx-copybutton", "sphinx-design", "sphinx_book_theme"] +testing = ["coverage", "pytest", "pytest-cov", "pytest-regressions"] + [[package]] name = "markupsafe" version = "2.1.2" @@ -1487,6 +1616,38 @@ files = [ {file = "MarkupSafe-2.1.2.tar.gz", hash = "sha256:abcabc8c2b26036d62d4c746381a6f7cf60aafcc653198ad678306986b09450d"}, ] +[[package]] +name = "mdit-py-plugins" +version = "0.3.5" +description = "Collection of plugins for markdown-it-py" +category = "dev" +optional = false +python-versions = ">=3.7" +files = [ + {file = "mdit-py-plugins-0.3.5.tar.gz", hash = "sha256:eee0adc7195e5827e17e02d2a258a2ba159944a0748f59c5099a4a27f78fcf6a"}, + {file = "mdit_py_plugins-0.3.5-py3-none-any.whl", hash = "sha256:ca9a0714ea59a24b2b044a1831f48d817dd0c817e84339f20e7889f392d77c4e"}, +] + +[package.dependencies] +markdown-it-py = ">=1.0.0,<3.0.0" + +[package.extras] +code-style = ["pre-commit"] +rtd = ["attrs", "myst-parser (>=0.16.1,<0.17.0)", "sphinx-book-theme (>=0.1.0,<0.2.0)"] +testing = ["coverage", "pytest", "pytest-cov", "pytest-regressions"] + +[[package]] +name = "mdurl" +version = "0.1.2" +description = "Markdown URL utilities" +category = "dev" +optional = false +python-versions = ">=3.7" +files = [ + {file = "mdurl-0.1.2-py3-none-any.whl", hash = "sha256:84008a41e51615a49fc9966191ff91509e3c40b939176e643fd50a5c2196b8f8"}, + {file = "mdurl-0.1.2.tar.gz", hash = "sha256:bb413d29f5eea38f31dd4754dd7377d4465116fb207585f97bf925588687c1ba"}, +] + [[package]] name = "multidict" version = "6.0.4" @@ -1571,6 +1732,33 @@ files = [ {file = "multidict-6.0.4.tar.gz", hash = "sha256:3666906492efb76453c0e7b97f2cf459b0682e7402c0489a95484965dbc1da49"}, ] +[[package]] +name = "myst-parser" +version = "1.0.0" +description = "An extended [CommonMark](https://spec.commonmark.org/) compliant parser," +category = "dev" +optional = false +python-versions = ">=3.7" +files = [ + {file = "myst-parser-1.0.0.tar.gz", hash = "sha256:502845659313099542bd38a2ae62f01360e7dd4b1310f025dd014dfc0439cdae"}, + {file = "myst_parser-1.0.0-py3-none-any.whl", hash = "sha256:69fb40a586c6fa68995e6521ac0a525793935db7e724ca9bac1d33be51be9a4c"}, +] + +[package.dependencies] +docutils = ">=0.15,<0.20" +jinja2 = "*" +markdown-it-py = ">=1.0.0,<3.0.0" +mdit-py-plugins = ">=0.3.4,<0.4.0" +pyyaml = "*" +sphinx = ">=5,<7" + +[package.extras] +code-style = ["pre-commit (>=3.0,<4.0)"] +linkify = ["linkify-it-py (>=1.0,<2.0)"] +rtd = ["ipython", "pydata-sphinx-theme (==v0.13.0rc4)", "sphinx-autodoc2 (>=0.4.2,<0.5.0)", "sphinx-book-theme (==1.0.0rc2)", "sphinx-copybutton", "sphinx-design2", "sphinx-pyscript", "sphinx-tippy (>=0.3.1)", "sphinx-togglebutton", "sphinxext-opengraph (>=0.7.5,<0.8.0)", "sphinxext-rediraffe (>=0.2.7,<0.3.0)"] +testing = ["beautifulsoup4", "coverage[toml]", "pytest (>=7,<8)", "pytest-cov", "pytest-param-files (>=0.3.4,<0.4.0)", "pytest-regressions", "sphinx-pytest"] +testing-docutils = ["pygments", "pytest (>=7,<8)", "pytest-param-files (>=0.3.4,<0.4.0)"] + [[package]] name = "nodeenv" version = "1.7.0" @@ -1912,6 +2100,21 @@ typing-extensions = ">=4.2.0" dotenv = ["python-dotenv (>=0.10.4)"] email = ["email-validator (>=1.0.3)"] +[[package]] +name = "pygments" +version = "2.15.0" +description = "Pygments is a syntax highlighting package written in Python." +category = "dev" +optional = false +python-versions = ">=3.7" +files = [ + {file = "Pygments-2.15.0-py3-none-any.whl", hash = "sha256:77a3299119af881904cd5ecd1ac6a66214b6e9bed1f2db16993b54adede64094"}, + {file = "Pygments-2.15.0.tar.gz", hash = "sha256:f7e36cffc4c517fbc252861b9a6e4644ca0e5abadf9a113c72d1358ad09b9500"}, +] + +[package.extras] +plugins = ["importlib-metadata"] + [[package]] name = "pyinstrument" version = "4.4.0" @@ -2097,6 +2300,18 @@ files = [ [package.extras] cli = ["click (>=5.0)"] +[[package]] +name = "pytz" +version = "2023.3" +description = "World timezone definitions, modern and historical" +category = "dev" +optional = false +python-versions = "*" +files = [ + {file = "pytz-2023.3-py2.py3-none-any.whl", hash = "sha256:a151b3abb88eda1d4e34a9814df37de2a80e301e68ba0fd856fb9b46bfbbbffb"}, + {file = "pytz-2023.3.tar.gz", hash = "sha256:1d8ce29db189191fb55338ee6d0387d82ab59f3d00eac103412d64e0ebd0c588"}, +] + [[package]] name = "pyyaml" version = "6.0" @@ -2275,6 +2490,199 @@ files = [ {file = "sniffio-1.3.0.tar.gz", hash = "sha256:e60305c5e5d314f5389259b7f22aaa33d8f7dee49763119234af3755c55b9101"}, ] +[[package]] +name = "snowballstemmer" +version = "2.2.0" +description = "This package provides 29 stemmers for 28 languages generated from Snowball algorithms." +category = "dev" +optional = false +python-versions = "*" +files = [ + {file = "snowballstemmer-2.2.0-py2.py3-none-any.whl", hash = "sha256:c8e1716e83cc398ae16824e5572ae04e0d9fc2c6b985fb0f900f5f0c96ecba1a"}, + {file = "snowballstemmer-2.2.0.tar.gz", hash = "sha256:09b16deb8547d3412ad7b590689584cd0fe25ec8db3be37788be3810cbf19cb1"}, +] + +[[package]] +name = "soupsieve" +version = "2.4.1" +description = "A modern CSS selector implementation for Beautiful Soup." +category = "dev" +optional = false +python-versions = ">=3.7" +files = [ + {file = "soupsieve-2.4.1-py3-none-any.whl", hash = "sha256:1c1bfee6819544a3447586c889157365a27e10d88cde3ad3da0cf0ddf646feb8"}, + {file = "soupsieve-2.4.1.tar.gz", hash = "sha256:89d12b2d5dfcd2c9e8c22326da9d9aa9cb3dfab0a83a024f05704076ee8d35ea"}, +] + +[[package]] +name = "sphinx" +version = "6.1.3" +description = "Python documentation generator" +category = "dev" +optional = false +python-versions = ">=3.8" +files = [ + {file = "Sphinx-6.1.3.tar.gz", hash = "sha256:0dac3b698538ffef41716cf97ba26c1c7788dba73ce6f150c1ff5b4720786dd2"}, + {file = "sphinx-6.1.3-py3-none-any.whl", hash = "sha256:807d1cb3d6be87eb78a381c3e70ebd8d346b9a25f3753e9947e866b2786865fc"}, +] + +[package.dependencies] +alabaster = ">=0.7,<0.8" +babel = ">=2.9" +colorama = {version = ">=0.4.5", markers = "sys_platform == \"win32\""} +docutils = ">=0.18,<0.20" +imagesize = ">=1.3" +importlib-metadata = {version = ">=4.8", markers = "python_version < \"3.10\""} +Jinja2 = ">=3.0" +packaging = ">=21.0" +Pygments = ">=2.13" +requests = ">=2.25.0" +snowballstemmer = ">=2.0" +sphinxcontrib-applehelp = "*" +sphinxcontrib-devhelp = "*" +sphinxcontrib-htmlhelp = ">=2.0.0" +sphinxcontrib-jsmath = "*" +sphinxcontrib-qthelp = "*" +sphinxcontrib-serializinghtml = ">=1.1.5" + +[package.extras] +docs = ["sphinxcontrib-websupport"] +lint = ["docutils-stubs", "flake8 (>=3.5.0)", "flake8-simplify", "isort", "mypy (>=0.990)", "ruff", "sphinx-lint", "types-requests"] +test = ["cython", "html5lib", "pytest (>=4.6)"] + +[[package]] +name = "sphinx-autobuild" +version = "2021.3.14" +description = "Rebuild Sphinx documentation on changes, with live-reload in the browser." +category = "dev" +optional = false +python-versions = ">=3.6" +files = [ + {file = "sphinx-autobuild-2021.3.14.tar.gz", hash = "sha256:de1ca3b66e271d2b5b5140c35034c89e47f263f2cd5db302c9217065f7443f05"}, + {file = "sphinx_autobuild-2021.3.14-py3-none-any.whl", hash = "sha256:8fe8cbfdb75db04475232f05187c776f46f6e9e04cacf1e49ce81bdac649ccac"}, +] + +[package.dependencies] +colorama = "*" +livereload = "*" +sphinx = "*" + +[package.extras] +test = ["pytest", "pytest-cov"] + +[[package]] +name = "sphinx-basic-ng" +version = "1.0.0b1" +description = "A modern skeleton for Sphinx themes." +category = "dev" +optional = false +python-versions = ">=3.7" +files = [ + {file = "sphinx_basic_ng-1.0.0b1-py3-none-any.whl", hash = "sha256:ade597a3029c7865b24ad0eda88318766bcc2f9f4cef60df7e28126fde94db2a"}, + {file = "sphinx_basic_ng-1.0.0b1.tar.gz", hash = "sha256:89374bd3ccd9452a301786781e28c8718e99960f2d4f411845ea75fc7bb5a9b0"}, +] + +[package.dependencies] +sphinx = ">=4.0" + +[package.extras] +docs = ["furo", "ipython", "myst-parser", "sphinx-copybutton", "sphinx-inline-tabs"] + +[[package]] +name = "sphinxcontrib-applehelp" +version = "1.0.4" +description = "sphinxcontrib-applehelp is a Sphinx extension which outputs Apple help books" +category = "dev" +optional = false +python-versions = ">=3.8" +files = [ + {file = "sphinxcontrib-applehelp-1.0.4.tar.gz", hash = "sha256:828f867945bbe39817c210a1abfd1bc4895c8b73fcaade56d45357a348a07d7e"}, + {file = "sphinxcontrib_applehelp-1.0.4-py3-none-any.whl", hash = "sha256:29d341f67fb0f6f586b23ad80e072c8e6ad0b48417db2bde114a4c9746feb228"}, +] + +[package.extras] +lint = ["docutils-stubs", "flake8", "mypy"] +test = ["pytest"] + +[[package]] +name = "sphinxcontrib-devhelp" +version = "1.0.2" +description = "sphinxcontrib-devhelp is a sphinx extension which outputs Devhelp document." +category = "dev" +optional = false +python-versions = ">=3.5" +files = [ + {file = "sphinxcontrib-devhelp-1.0.2.tar.gz", hash = "sha256:ff7f1afa7b9642e7060379360a67e9c41e8f3121f2ce9164266f61b9f4b338e4"}, + {file = "sphinxcontrib_devhelp-1.0.2-py2.py3-none-any.whl", hash = "sha256:8165223f9a335cc1af7ffe1ed31d2871f325254c0423bc0c4c7cd1c1e4734a2e"}, +] + +[package.extras] +lint = ["docutils-stubs", "flake8", "mypy"] +test = ["pytest"] + +[[package]] +name = "sphinxcontrib-htmlhelp" +version = "2.0.1" +description = "sphinxcontrib-htmlhelp is a sphinx extension which renders HTML help files" +category = "dev" +optional = false +python-versions = ">=3.8" +files = [ + {file = "sphinxcontrib-htmlhelp-2.0.1.tar.gz", hash = "sha256:0cbdd302815330058422b98a113195c9249825d681e18f11e8b1f78a2f11efff"}, + {file = "sphinxcontrib_htmlhelp-2.0.1-py3-none-any.whl", hash = "sha256:c38cb46dccf316c79de6e5515e1770414b797162b23cd3d06e67020e1d2a6903"}, +] + +[package.extras] +lint = ["docutils-stubs", "flake8", "mypy"] +test = ["html5lib", "pytest"] + +[[package]] +name = "sphinxcontrib-jsmath" +version = "1.0.1" +description = "A sphinx extension which renders display math in HTML via JavaScript" +category = "dev" +optional = false +python-versions = ">=3.5" +files = [ + {file = "sphinxcontrib-jsmath-1.0.1.tar.gz", hash = "sha256:a9925e4a4587247ed2191a22df5f6970656cb8ca2bd6284309578f2153e0c4b8"}, + {file = "sphinxcontrib_jsmath-1.0.1-py2.py3-none-any.whl", hash = "sha256:2ec2eaebfb78f3f2078e73666b1415417a116cc848b72e5172e596c871103178"}, +] + +[package.extras] +test = ["flake8", "mypy", "pytest"] + +[[package]] +name = "sphinxcontrib-qthelp" +version = "1.0.3" +description = "sphinxcontrib-qthelp is a sphinx extension which outputs QtHelp document." +category = "dev" +optional = false +python-versions = ">=3.5" +files = [ + {file = "sphinxcontrib-qthelp-1.0.3.tar.gz", hash = "sha256:4c33767ee058b70dba89a6fc5c1892c0d57a54be67ddd3e7875a18d14cba5a72"}, + {file = "sphinxcontrib_qthelp-1.0.3-py2.py3-none-any.whl", hash = "sha256:bd9fc24bcb748a8d51fd4ecaade681350aa63009a347a8c14e637895444dfab6"}, +] + +[package.extras] +lint = ["docutils-stubs", "flake8", "mypy"] +test = ["pytest"] + +[[package]] +name = "sphinxcontrib-serializinghtml" +version = "1.1.5" +description = "sphinxcontrib-serializinghtml is a sphinx extension which outputs \"serialized\" HTML files (json and pickle)." +category = "dev" +optional = false +python-versions = ">=3.5" +files = [ + {file = "sphinxcontrib-serializinghtml-1.1.5.tar.gz", hash = "sha256:aa5f6de5dfdf809ef505c4895e51ef5c9eac17d0f287933eb49ec495280b6952"}, + {file = "sphinxcontrib_serializinghtml-1.1.5-py2.py3-none-any.whl", hash = "sha256:352a9a00ae864471d3a7ead8d7d79f5fc0b57e8b3f95e9867eb9eb28999b92fd"}, +] + +[package.extras] +lint = ["docutils-stubs", "flake8", "mypy"] +test = ["pytest"] + [[package]] name = "tomli" version = "2.0.1" @@ -2299,6 +2707,27 @@ files = [ {file = "tomlkit-0.11.6.tar.gz", hash = "sha256:71b952e5721688937fb02cf9d354dbcf0785066149d2855e44531ebdd2b65d73"}, ] +[[package]] +name = "tornado" +version = "6.2" +description = "Tornado is a Python web framework and asynchronous networking library, originally developed at FriendFeed." +category = "dev" +optional = false +python-versions = ">= 3.7" +files = [ + {file = "tornado-6.2-cp37-abi3-macosx_10_9_universal2.whl", hash = "sha256:20f638fd8cc85f3cbae3c732326e96addff0a15e22d80f049e00121651e82e72"}, + {file = "tornado-6.2-cp37-abi3-macosx_10_9_x86_64.whl", hash = "sha256:87dcafae3e884462f90c90ecc200defe5e580a7fbbb4365eda7c7c1eb809ebc9"}, + {file = "tornado-6.2-cp37-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ba09ef14ca9893954244fd872798b4ccb2367c165946ce2dd7376aebdde8e3ac"}, + {file = "tornado-6.2-cp37-abi3-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:b8150f721c101abdef99073bf66d3903e292d851bee51910839831caba341a75"}, + {file = "tornado-6.2-cp37-abi3-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:d3a2f5999215a3a06a4fc218026cd84c61b8b2b40ac5296a6db1f1451ef04c1e"}, + {file = "tornado-6.2-cp37-abi3-musllinux_1_1_aarch64.whl", hash = "sha256:5f8c52d219d4995388119af7ccaa0bcec289535747620116a58d830e7c25d8a8"}, + {file = "tornado-6.2-cp37-abi3-musllinux_1_1_i686.whl", hash = "sha256:6fdfabffd8dfcb6cf887428849d30cf19a3ea34c2c248461e1f7d718ad30b66b"}, + {file = "tornado-6.2-cp37-abi3-musllinux_1_1_x86_64.whl", hash = "sha256:1d54d13ab8414ed44de07efecb97d4ef7c39f7438cf5e976ccd356bebb1b5fca"}, + {file = "tornado-6.2-cp37-abi3-win32.whl", hash = "sha256:5c87076709343557ef8032934ce5f637dbb552efa7b21d08e89ae7619ed0eb23"}, + {file = "tornado-6.2-cp37-abi3-win_amd64.whl", hash = "sha256:e5f923aa6a47e133d1cf87d60700889d7eae68988704e20c75fb2d65677a8e4b"}, + {file = "tornado-6.2.tar.gz", hash = "sha256:9b630419bde84ec666bfd7ea0a4cb2a8a651c2d5cccdbdd1972a0c859dfc3c13"}, +] + [[package]] name = "typing-extensions" version = "4.4.0" @@ -2650,4 +3079,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "027cec6eb1e012bb292447c6e1f0b0ec0de3974ab4e85e13607b001eebb748fc" +content-hash = "9c0df86bf38d46e2773a2e81f39096504ca54b294f93709f7098739974353178" diff --git a/pyproject.toml b/pyproject.toml index 2b59ec5c..22e760d2 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -37,6 +37,13 @@ watchfiles = "^0.19.0" jishaku = "^2.5.1" ruff = "^0.0.261" + +[tool.poetry.group.docs.dependencies] +sphinx = "^6.1.3" +myst-parser = "^1.0.0" +sphinx-autobuild = "^2021.3.14" +furo = "^2023.3.27" + [tool.isort] profile = 'black' From d01112850a2ed25f4cecb0b60a4e505276478d88 Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Sun, 16 Apr 2023 23:51:03 -0700 Subject: [PATCH 020/184] [skip ci] Add requirements.txt for docs --- Kumiko-Docs/requirements.txt | 38 ++++++++++++++++++++++++++++++++++++ 1 file changed, 38 insertions(+) create mode 100644 Kumiko-Docs/requirements.txt diff --git a/Kumiko-Docs/requirements.txt b/Kumiko-Docs/requirements.txt new file mode 100644 index 00000000..16b0b44d --- /dev/null +++ b/Kumiko-Docs/requirements.txt @@ -0,0 +1,38 @@ +alabaster==0.7.13 ; python_version >= "3.8" and python_version < "4.0" +babel==2.12.1 ; python_version >= "3.8" and python_version < "4.0" +beautifulsoup4==4.12.2 ; python_version >= "3.8" and python_version < "4.0" +certifi==2022.12.7 ; python_version >= "3.8" and python_version < "4" +charset-normalizer==3.1.0 ; python_version >= "3.8" and python_version < "4" +colorama==0.4.6 ; python_version >= "3.8" and python_version < "4.0" +docutils==0.19 ; python_version >= "3.8" and python_version < "4.0" +furo==2023.3.27 ; python_version >= "3.8" and python_version < "4.0" +idna==3.4 ; python_version >= "3.8" and python_version < "4" +imagesize==1.4.1 ; python_version >= "3.8" and python_version < "4.0" +importlib-metadata==6.1.0 ; python_version >= "3.8" and python_version < "3.10" +jinja2==3.1.2 ; python_version >= "3.8" and python_version < "4.0" +livereload==2.6.3 ; python_version >= "3.8" and python_version < "4.0" +markdown-it-py==2.2.0 ; python_version >= "3.8" and python_version < "4.0" +markupsafe==2.1.2 ; python_version >= "3.8" and python_version < "4.0" +mdit-py-plugins==0.3.5 ; python_version >= "3.8" and python_version < "4.0" +mdurl==0.1.2 ; python_version >= "3.8" and python_version < "4.0" +myst-parser==1.0.0 ; python_version >= "3.8" and python_version < "4.0" +packaging==22.0 ; python_version >= "3.8" and python_version < "4.0" +pygments==2.15.0 ; python_version >= "3.8" and python_version < "4.0" +pytz==2023.3 ; python_version >= "3.8" and python_version < "3.9" +pyyaml==6.0 ; python_version >= "3.8" and python_version < "4.0" +requests==2.28.2 ; python_version >= "3.8" and python_version < "4" +six==1.16.0 ; python_version >= "3.8" and python_version < "4.0" +snowballstemmer==2.2.0 ; python_version >= "3.8" and python_version < "4.0" +soupsieve==2.4.1 ; python_version >= "3.8" and python_version < "4.0" +sphinx-autobuild==2021.3.14 ; python_version >= "3.8" and python_version < "4.0" +sphinx-basic-ng==1.0.0b1 ; python_version >= "3.8" and python_version < "4.0" +sphinx==6.1.3 ; python_version >= "3.8" and python_version < "4.0" +sphinxcontrib-applehelp==1.0.4 ; python_version >= "3.8" and python_version < "4.0" +sphinxcontrib-devhelp==1.0.2 ; python_version >= "3.8" and python_version < "4.0" +sphinxcontrib-htmlhelp==2.0.1 ; python_version >= "3.8" and python_version < "4.0" +sphinxcontrib-jsmath==1.0.1 ; python_version >= "3.8" and python_version < "4.0" +sphinxcontrib-qthelp==1.0.3 ; python_version >= "3.8" and python_version < "4.0" +sphinxcontrib-serializinghtml==1.1.5 ; python_version >= "3.8" and python_version < "4.0" +tornado==6.2 ; python_version >= "3.8" and python_version < "4.0" +urllib3==1.26.14 ; python_version >= "3.8" and python_version < "4" +zipp==3.15.0 ; python_version >= "3.8" and python_version < "3.10" From e81e23e861e515452b5aaebc62bbc9b630810e6a Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Sun, 16 Apr 2023 23:57:48 -0700 Subject: [PATCH 021/184] [skip ci] Add RTD config --- .readthedocs.yaml | 6 ++++++ 1 file changed, 6 insertions(+) create mode 100644 .readthedocs.yaml diff --git a/.readthedocs.yaml b/.readthedocs.yaml new file mode 100644 index 00000000..10c1b017 --- /dev/null +++ b/.readthedocs.yaml @@ -0,0 +1,6 @@ +version: 2 + +build: + os: ubuntu-22.04 + tools: + python: "3.11" \ No newline at end of file From 2de9ee86185727b716c5c1c06bdd71684099dc17 Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Mon, 17 Apr 2023 00:01:40 -0700 Subject: [PATCH 022/184] [skip ci] Fix RTD config --- .readthedocs.yaml | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/.readthedocs.yaml b/.readthedocs.yaml index 10c1b017..1979109d 100644 --- a/.readthedocs.yaml +++ b/.readthedocs.yaml @@ -3,4 +3,11 @@ version: 2 build: os: ubuntu-22.04 tools: - python: "3.11" \ No newline at end of file + python: "3.11" + +sphinx: + configuration: Kumiko-Docs/source/conf.py + +python: + install: + - requirements: Kumiko-Docs/requirements.txt From 2f5942980c018655eb6dbd069346411075decbec Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Mon, 17 Apr 2023 00:14:47 -0700 Subject: [PATCH 023/184] [skip ci] Update readme --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 88ed560f..5c59ad09 100644 --- a/README.md +++ b/README.md @@ -6,7 +6,7 @@ ![Kumiko](./assets/kumiko-resized-round.svg) -[![Required Python Version](https://img.shields.io/badge/Python-3.8%20|%203.9%20|%203.10%20|%203.11-blue?logo=python&logoColor=white)](https://github.com/No767/Kumiko/blob/dev/pyproject.toml) [![CodeQL](https://github.com/No767/Kumiko/actions/workflows/codeql-analysis.yml/badge.svg?branch=dev)](https://github.com/No767/Kumiko/actions/workflows/codeql-analysis.yml) [![Snyk](https://github.com/No767/Kumiko/actions/workflows/snyk.yml/badge.svg?branch=dev)](https://github.com/No767/Kumiko/actions/workflows/snyk.yml) [![Lint](https://github.com/No767/Kumiko/actions/workflows/lint.yml/badge.svg)](https://github.com/No767/Kumiko/actions/workflows/lint.yml) [![Docker Build](https://github.com/No767/Kumiko/actions/workflows/docker-build.yml/badge.svg)](https://github.com/No767/Kumiko/actions/workflows/docker-build.yml) [![Tests](https://github.com/No767/Kumiko/actions/workflows/tests.yml/badge.svg)](https://github.com/No767/Kumiko/actions/workflows/tests.yml) [![Codacy Badge](https://app.codacy.com/project/badge/Grade/950cd812f1e04f0d813bb0298fdaa225)](https://www.codacy.com/gh/No767/Kumiko/dashboard?utm_source=github.com&utm_medium=referral&utm_content=No767/Kumiko&utm_campaign=Badge_Grade) [![codecov](https://codecov.io/gh/No767/Kumiko/branch/dev/graph/badge.svg?token=CwcMp3LIFx)](https://codecov.io/gh/No767/Kumiko) [![GitHub release (latest SemVer)](https://img.shields.io/github/v/release/No767/Kumiko?label=Release&logo=github&sort=semver)](https://github.com/No767/Kumiko/releases) ![Docker Image Version (latest semver)](https://img.shields.io/docker/v/no767/kumiko?label=Docker%20Release&logo=docker&logoColor=white&sort=semver) [![GitHub License](https://img.shields.io/github/license/No767/Rin?label=License&logo=github)](https://github.com/No767/Kumiko/blob/dev/LICENSE) [![Kumiko](https://img.shields.io/badge/Kumiko-Oumae-white)](https://hibike-euphonium.fandom.com/wiki/Kumiko_Oumae) +[![Required Python Version](https://img.shields.io/badge/Python-3.8%20|%203.9%20|%203.10%20|%203.11-blue?logo=python&logoColor=white)](https://github.com/No767/Kumiko/blob/dev/pyproject.toml) [![CodeQL](https://github.com/No767/Kumiko/actions/workflows/codeql-analysis.yml/badge.svg?branch=dev)](https://github.com/No767/Kumiko/actions/workflows/codeql-analysis.yml) [![Snyk](https://github.com/No767/Kumiko/actions/workflows/snyk.yml/badge.svg?branch=dev)](https://github.com/No767/Kumiko/actions/workflows/snyk.yml) [![Lint](https://github.com/No767/Kumiko/actions/workflows/lint.yml/badge.svg)](https://github.com/No767/Kumiko/actions/workflows/lint.yml) [![Docker Build](https://github.com/No767/Kumiko/actions/workflows/docker-build.yml/badge.svg)](https://github.com/No767/Kumiko/actions/workflows/docker-build.yml) [![Tests](https://github.com/No767/Kumiko/actions/workflows/tests.yml/badge.svg)](https://github.com/No767/Kumiko/actions/workflows/tests.yml) ![Read the Docs](https://img.shields.io/readthedocs/kumiko?label=Docs&logo=readthedocs&logoColor=white) [![Codacy Badge](https://app.codacy.com/project/badge/Grade/950cd812f1e04f0d813bb0298fdaa225)](https://www.codacy.com/gh/No767/Kumiko/dashboard?utm_source=github.com&utm_medium=referral&utm_content=No767/Kumiko&utm_campaign=Badge_Grade) [![codecov](https://codecov.io/gh/No767/Kumiko/branch/dev/graph/badge.svg?token=CwcMp3LIFx)](https://codecov.io/gh/No767/Kumiko) [![GitHub release (latest SemVer)](https://img.shields.io/github/v/release/No767/Kumiko?label=Release&logo=github&sort=semver)](https://github.com/No767/Kumiko/releases) ![Docker Image Version (latest semver)](https://img.shields.io/docker/v/no767/kumiko?label=Docker%20Release&logo=docker&logoColor=white&sort=semver) [![GitHub License](https://img.shields.io/github/license/No767/Rin?label=License&logo=github)](https://github.com/No767/Kumiko/blob/dev/LICENSE) [![Kumiko](https://img.shields.io/badge/Kumiko-Oumae-white)](https://hibike-euphonium.fandom.com/wiki/Kumiko_Oumae) A multipurpose Discord bot built with freedom and choice in mind From df0a7e3c68f799348aa73dba8a921b2222b75ce9 Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Mon, 17 Apr 2023 00:46:13 -0700 Subject: [PATCH 024/184] [skip ci] Update docs once again --- Kumiko-Docs/source/index.rst | 16 ++++++++++++++-- 1 file changed, 14 insertions(+), 2 deletions(-) diff --git a/Kumiko-Docs/source/index.rst b/Kumiko-Docs/source/index.rst index 79d8e545..863cd20c 100644 --- a/Kumiko-Docs/source/index.rst +++ b/Kumiko-Docs/source/index.rst @@ -4,7 +4,7 @@ contain the root `toctree` directive. -Welcome to Kumiko +Kumiko ================================== .. toctree:: @@ -25,12 +25,24 @@ Welcome to Kumiko .. figure:: https://raw.githubusercontent.com/No767/Kumiko/dev/assets/kumiko-resized-round.svg - :align: center + :align: right + +.. image:: https://img.shields.io/github/v/release/No767/Kumiko?label=Release&logo=github&sort=semver + :alt: GitHub release (latest SemVer) + +.. image:: https://img.shields.io/github/license/No767/Kumiko?label=License&logo=github + :alt: GitHub + +.. image:: https://img.shields.io/badge/Kumiko-Oumae-white Kumiko is a multipurpose Discord bot built with freedom and choice in mind. Kumiko takes a unique approach to what a multipurpose bot is defined as. Features ---------- + +.. CAUTION:: + Some of these features are not implemented yet. Kumiko is still under heavy development. + - Customizable prefix module - Global or guild economy with jobs and marketplaces - Custom logging module From f5441786347aee5f3a57ca39ccae7327d6cf514b Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Mon, 17 Apr 2023 18:38:23 -0700 Subject: [PATCH 025/184] [skip ci] Update docs --- Kumiko-Docs/source/conf.py | 11 +++ .../source/guides/dev/dev-contributing.rst | 92 +++++++++++++++++++ Kumiko-Docs/source/index.rst | 3 +- .../terms-of-service/privacy-policy.rst | 31 ++++++- Kumiko-Docs/source/terms-of-service/tos.rst | 42 ++++++++- 5 files changed, 175 insertions(+), 4 deletions(-) diff --git a/Kumiko-Docs/source/conf.py b/Kumiko-Docs/source/conf.py index fd5da40c..f7b628c3 100644 --- a/Kumiko-Docs/source/conf.py +++ b/Kumiko-Docs/source/conf.py @@ -30,3 +30,14 @@ html_theme = "furo" html_static_path = ["_static"] + +html_theme_options = { + "dark_css_variables": { + "color-brand-primary": "#A685E2", + "color-brand-content": "#FFABE1", + }, + "light_css_variables": { + "color-brand-primary": "#6867AC", + "color-brand-content": "#CE7BB0", + }, +} diff --git a/Kumiko-Docs/source/guides/dev/dev-contributing.rst b/Kumiko-Docs/source/guides/dev/dev-contributing.rst index a76ed1ca..ca4c47ff 100644 --- a/Kumiko-Docs/source/guides/dev/dev-contributing.rst +++ b/Kumiko-Docs/source/guides/dev/dev-contributing.rst @@ -1,2 +1,94 @@ Dev Contributing Guide ====================== + +We are glad that you're willing to contribute to this project. We are usually very lenient and relaxed with the submissions of PRs, and Issues reports. But there are some stuff that you need to know before contributing. + +Note to new contributors +--------------------------- + +When you contribute to this project, you are subject to the `Code of Conduct `_. Any violations of the Code Of Conduct will be handled as stated. Read the contributing guide. **Support is not given if you didn't bother reading the documentation for setting up any of the requirements, or if you didn't bother to read the contributing guide.** + +Before Starting +---------------- + +Make suer to read these guides listed below (read them in order): + +- :doc:`requirements` +- :doc:`setup` + +Coding Style +------------- + +Variables +^^^^^^^^^^ +Most of the code written uses ``camelCasing`` for variables, ``PascalCasing`` for classes, and ``snake_casing`` for args. To sum it up: + +- ``camelCasing`` for variables +- ``PascalCasing`` for classes +- ``snake_casing`` for args +- ``ALL_CAPS`` for constants +- ``kebab-casing`` for files + +Formatting +^^^^^^^^^^^ + +Kumiko uses pre-commit hooks to format all of the code. Make sure run ``git add --all`` before committing to add all of the files. More than likely you'll need to commit twice due to the formatting that pre-commit does afterwards. + +Docstrings +^^^^^^^^^^^ + +Just like how major programs are documented, the libraries that are custom made for Kumiko also have to be documented. The current standard for this project is to use `Google's Docstring Guide `_. A handy VS Code extension that should be used is the `autoDocstring `_ extension. By default it will generate the docstring in the Google format. Docstrings should be used on all coroutines and methods (excluding cogs), and on classes as well. + +Google, Numpy, and Sphinx docstrings are also supported for commands. Kumiko is documented w/ Google docstrings, so please make sure to use that format. + +Example Cog: + +.. code-block:: python + + import discord + from discord.ext import commands + from discord.ext.commands import Context, Bot + + class MyCog(commands.Cog): + """An example cog for demo purposes""" + def __init__(self, bot: Bot): + self.bot = bot + + @commands.hybrid_command(name="hello") + async def myCommand(self, ctx: Context): + """This is an example of a description for a slash command""" + await ctx.send(f"Hello {ctx.user.name}!") + + async def setup(bot: Bot): + await bot.add_cog(MyCog(bot)) + +GitHub Contributing Guidelines +----------------------------------- + +Issue and Feature Requests Reports +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +If there is an issue or a feature you want to be added, use the built-in GitHub issue tracker. Though a system like Jira could be used, it would be more efficient to just use the issue tracker that GitHub provides. + +- If submitting a issue report, follow the template. Duplicates will not receive support +- If submitting a feature request, follow the template as well. As with issue reports, duplicate requests will not receive support + +Git Commit Styleguides +^^^^^^^^^^^^^^^^^^^^^^^ + +- If updating any other files that aren't project files or not important (stuff like README.md, contributing.md, etc), add the [skip ci] label in the front +- With each new commit, the message should be more or less describing the changes. Please don't write useless commit messages... +- If releasing tags, have it in this style. ``Release: v[version number]``, ``Update: v[version number]``, and ``Fix: v[version number]``. Release is a major release. This means it bumps from 1.0.0 to 2.0.0. Minor means it bumps up the version from 1.4 to 1.5 for example. And fix just applies a patch, which would be 1.4.1 to 1.4.2. + +Releasing Tags +^^^^^^^^^^^^^^^ + +In order to automate the release system, you have to make sure that in order to use it, the git commit message must be done correctly. Only use this if there is a new update that is ready to be released. Kumiko uses `SemVer `_ as the standard for versioning. Here's a table that should help with explaining this: + + =============================================================== ===================== + Type of Release, Update, or Patch Example + =============================================================== ===================== + Major Release (For updates that are not backwards compatible) ``Release: v2.0.0`` + Minor Release (For updates that are backwards compatible) ``Update: v2.5.0`` + Patch Release (For critical security patches and bug fixes) ``Fix: v2.5.1`` + =============================================================== ===================== diff --git a/Kumiko-Docs/source/index.rst b/Kumiko-Docs/source/index.rst index 863cd20c..16eea75e 100644 --- a/Kumiko-Docs/source/index.rst +++ b/Kumiko-Docs/source/index.rst @@ -54,7 +54,6 @@ And some ones that are planned: - Complete Web Dashboard + Custom Embeds (WIP, pinned for v2) - Event Logging (Pinned for v1) - Annoucement releaser with support from GitHub (Pinned for v2) -- AI Driven GAN Anime Waifu Generator (Not implemented yet) - Selector Roles (pinned for v2) Guides @@ -62,8 +61,8 @@ Guides Are you interested in contributing to Kumiko as a developer? Or are you interested in learning how to use Kumiko as the end user? This is the place to get started! -- :doc:`guides/dev/index` - :doc:`guides/user/index` +- :doc:`guides/dev/index` Resources and Links ------------------- diff --git a/Kumiko-Docs/source/terms-of-service/privacy-policy.rst b/Kumiko-Docs/source/terms-of-service/privacy-policy.rst index c3d07c9e..16832fec 100644 --- a/Kumiko-Docs/source/terms-of-service/privacy-policy.rst +++ b/Kumiko-Docs/source/terms-of-service/privacy-policy.rst @@ -1,2 +1,31 @@ Privacy Policy -============== \ No newline at end of file +============== +Kumiko is designed to only use what it needs. This means no other data, unless specified, is used or granted to Kumiko, or any other staff and administration members. By using Kumiko, and in turn any of the services provided, you truthfully agree to follow such terms and conditions in exchange for use of Kumiko and their services. Those shall be stated as: + +Collections of interest +----------------------- +Kumiko is designed to only take what the bot needs. The data will not be viewed by anyone else unless authorized to do so. The information collected as so is of the following: + +- Discord user IDs + +Kumiko and her services will only collect the info listed above. Kumiko does not collect IPs, and any other sensitive info unless needed + +Reasons for Collecting Info +--------------------------- +The info is only used to associate the Discord user with their economy account. The IDs are stored on a database, and are not viewed unless needed. + +Data Retention +-------------- +All data will be retained for as however long it is needed. If an user decides to create an economy account, the Discord ID of the user is stored, and purged when the user deletes his/her/their account. This applies to the web dashboard and other services as well. + +Data Sharing +------------ +Kumiko does not share any information with anyone. Kumiko only shares info between her internal services (the web dashboard), and only between the services. All data can only be accessed by the owner of those bots. + +Request to Access Such Data +--------------------------- +If you feel the need to request for your own data for purposes of security only, please reach out to either the staff, or the owner directly. If you wish to remove such data, please also reach out to either the staff or the owner directly. + +Changes to this Policy +---------------------- +The staff and the owner reserves the right to change this policy at any time. Any changes will be posted on the Discord server, and will be reflected on this page. \ No newline at end of file diff --git a/Kumiko-Docs/source/terms-of-service/tos.rst b/Kumiko-Docs/source/terms-of-service/tos.rst index 95cb4f66..983e2283 100644 --- a/Kumiko-Docs/source/terms-of-service/tos.rst +++ b/Kumiko-Docs/source/terms-of-service/tos.rst @@ -1,2 +1,42 @@ Terms of Service -================= \ No newline at end of file +================= + +By using the services provided by Kumiko, you agree to follow these terms stated below. + +TOS for Kumiko +-------------- + +1. All users who wish to use Kumiko, and any of its features are subject to all terms and conditions mentioned within this page + +2. Upon registration with the approved providers, it means that he/she/they completely aggress with the terms and conditions mentioned, and any others that may be added + +3. Users may not exploit the marketplace or any of the economy based features. This means selling items that are named inappropriately (e.g names that imply sexual behavior, nsfw content, advertisement, etc) can get you banned from using any of Kumiko's services + +4. It is forbidden to sell any of the services and use it for unauthorized commercial use or in use of malicious gains + +5. Bribes for coins are forbidden. This can lead to severe punishments, including perma-bans + +6. Community support is available via GitHub Discussions and Issues, while commercial support is allowed via the discord server. DO NOT spam GitHub issues and/or discussions with spam comments, or reviews. + +7. It is completely possible that these terms of services can change at any time, or add new ones as needed. Please keep up to date with any announcements on the Discord server + +TOS for Kumiko's Dashboard and Website +-------------------------------------- + +1. All info should be ideally truthful. This is needed in order to provide accurate data to the user + +2. Upon registration with the approved providers, it means that he/she/they completely aggress with the terms and conditions mentioned, and any others that may be added + +3. It is forbidden to sell subscriptions to other people, and to sell any part of the website or any of its features to other people. + +4. It is forbidden to sell any of the services and use it for unauthorized commercial use or in use of malicious gains + +5. The owner and its staff claim no responsibilities if such users causes damage or losses to the client as a result of improper treatment of the site. + +6. It is against such terms of service to use the services provided to you against any law, which must legally bind to the sovereign nation or of the case of none, to the international laws, to cause harm or for malicious intents to the site, any providers of the site, and to any other person legally bound to such terms and conditions + +7. The owner, and thus any member of the administration team has the right to suspend any subscription or account of such client if he/she/they violates the terms and conditions of the site + +8. The client truthfully will acknownledge that the features, and services provided within this site cannot be used for purposes of any gain, or to cause physical, mental, or emotional harm of any kind to another user or such persons + +**If any of such rules are violated, such persons is required to expose themselves or such company for liability and prosecution by the administration of the site.** From 35a1570ec29c1a600425d5adb11e4efaeeec269b Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Wed, 19 Apr 2023 01:04:35 -0700 Subject: [PATCH 026/184] [skip ci] Add the final parts of the docs --- Kumiko-Docs/requirements.txt | 11 + Kumiko-Docs/source/_static/1-Getting-Bot.png | Bin 0 -> 111077 bytes .../source/_static/2-Create-Bot-Page.png | Bin 0 -> 50788 bytes .../source/_static/3-Auth-Bot-Creation.png | Bin 0 -> 16585 bytes .../_static/4-Ensure-Intents-Are-Enabled.png | Bin 0 -> 65992 bytes Kumiko-Docs/source/_static/5-Copy-Token.png | Bin 0 -> 100165 bytes .../source/_static/kumiko-resized-round.svg | 9 + Kumiko-Docs/source/conf.py | 11 +- Kumiko-Docs/source/guides/user/bot-setup.rst | 36 ++ .../guides/user/configurations/bot-config.rst | 4 + .../guides/user/configurations/index.rst | 9 + Kumiko-Docs/source/guides/user/index.rst | 6 +- Kumiko-Docs/source/guides/user/trying-out.rst | 74 +++ Kumiko-Docs/source/index.rst | 11 +- poetry.lock | 439 +++++++++++++++++- pyproject.toml | 1 + 16 files changed, 603 insertions(+), 8 deletions(-) create mode 100644 Kumiko-Docs/source/_static/1-Getting-Bot.png create mode 100644 Kumiko-Docs/source/_static/2-Create-Bot-Page.png create mode 100644 Kumiko-Docs/source/_static/3-Auth-Bot-Creation.png create mode 100644 Kumiko-Docs/source/_static/4-Ensure-Intents-Are-Enabled.png create mode 100644 Kumiko-Docs/source/_static/5-Copy-Token.png create mode 100644 Kumiko-Docs/source/_static/kumiko-resized-round.svg create mode 100644 Kumiko-Docs/source/guides/user/bot-setup.rst create mode 100644 Kumiko-Docs/source/guides/user/configurations/bot-config.rst create mode 100644 Kumiko-Docs/source/guides/user/configurations/index.rst create mode 100644 Kumiko-Docs/source/guides/user/trying-out.rst diff --git a/Kumiko-Docs/requirements.txt b/Kumiko-Docs/requirements.txt index 16b0b44d..e3355692 100644 --- a/Kumiko-Docs/requirements.txt +++ b/Kumiko-Docs/requirements.txt @@ -4,20 +4,30 @@ beautifulsoup4==4.12.2 ; python_version >= "3.8" and python_version < "4.0" certifi==2022.12.7 ; python_version >= "3.8" and python_version < "4" charset-normalizer==3.1.0 ; python_version >= "3.8" and python_version < "4" colorama==0.4.6 ; python_version >= "3.8" and python_version < "4.0" +contourpy==1.0.7 ; python_version >= "3.8" and python_version < "4.0" +cycler==0.11.0 ; python_version >= "3.8" and python_version < "4.0" docutils==0.19 ; python_version >= "3.8" and python_version < "4.0" +fonttools==4.39.3 ; python_version >= "3.8" and python_version < "4.0" furo==2023.3.27 ; python_version >= "3.8" and python_version < "4.0" idna==3.4 ; python_version >= "3.8" and python_version < "4" imagesize==1.4.1 ; python_version >= "3.8" and python_version < "4.0" importlib-metadata==6.1.0 ; python_version >= "3.8" and python_version < "3.10" +importlib-resources==5.12.0 ; python_version >= "3.8" and python_version < "3.10" jinja2==3.1.2 ; python_version >= "3.8" and python_version < "4.0" +kiwisolver==1.4.4 ; python_version >= "3.8" and python_version < "4.0" livereload==2.6.3 ; python_version >= "3.8" and python_version < "4.0" markdown-it-py==2.2.0 ; python_version >= "3.8" and python_version < "4.0" markupsafe==2.1.2 ; python_version >= "3.8" and python_version < "4.0" +matplotlib==3.7.1 ; python_version >= "3.8" and python_version < "4.0" mdit-py-plugins==0.3.5 ; python_version >= "3.8" and python_version < "4.0" mdurl==0.1.2 ; python_version >= "3.8" and python_version < "4.0" myst-parser==1.0.0 ; python_version >= "3.8" and python_version < "4.0" +numpy==1.24.2 ; python_version >= "3.8" and python_version < "4.0" packaging==22.0 ; python_version >= "3.8" and python_version < "4.0" +pillow==9.5.0 ; python_version >= "3.8" and python_version < "4.0" pygments==2.15.0 ; python_version >= "3.8" and python_version < "4.0" +pyparsing==3.0.9 ; python_version >= "3.8" and python_version < "4.0" +python-dateutil==2.8.2 ; python_version >= "3.8" and python_version < "4.0" pytz==2023.3 ; python_version >= "3.8" and python_version < "3.9" pyyaml==6.0 ; python_version >= "3.8" and python_version < "4.0" requests==2.28.2 ; python_version >= "3.8" and python_version < "4" @@ -33,6 +43,7 @@ sphinxcontrib-htmlhelp==2.0.1 ; python_version >= "3.8" and python_version < "4. sphinxcontrib-jsmath==1.0.1 ; python_version >= "3.8" and python_version < "4.0" sphinxcontrib-qthelp==1.0.3 ; python_version >= "3.8" and python_version < "4.0" sphinxcontrib-serializinghtml==1.1.5 ; python_version >= "3.8" and python_version < "4.0" +sphinxext-opengraph==0.8.2 ; python_version >= "3.8" and python_version < "4.0" tornado==6.2 ; python_version >= "3.8" and python_version < "4.0" urllib3==1.26.14 ; python_version >= "3.8" and python_version < "4" zipp==3.15.0 ; python_version >= "3.8" and python_version < "3.10" diff --git a/Kumiko-Docs/source/_static/1-Getting-Bot.png b/Kumiko-Docs/source/_static/1-Getting-Bot.png new file mode 100644 index 0000000000000000000000000000000000000000..455e78b8a8ac8a2abdbc79b74541a0cec0618347 GIT binary patch literal 111077 zcmeFZWmMct^Dc@6w-DSdgb+M943OY~;O_1&gFC@JxVyW%ySux)3@!s4vd`K3-S7F| zulLJcx7M1U^qMuRyQ})Cr>eRqNLo?^1rZ++0s;c%hp3<|1O%KH1O#+0JnUObXy~K# z+YQoAR)im-Y>e>m?d6@(cZu&15S0-~U>%sZcLZxu6*~wB)b2kY$bPE=eF%ux+#iD9 z<()K7RuRVl4(shj8!Q$X zsJ0~<2heX58>92yC}XPrgfQPIo

;~_rnC&eW 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ξ;h7g{~Z%R9ennva3k!tBiR15D0y#M+*h+ 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

=w~2ut<-g2sQwa$)N}^-As~XQ3nYAjO9_WkqYV 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 literal 0 HcmV?d00001 diff --git a/Kumiko-Docs/source/_static/2-Create-Bot-Page.png b/Kumiko-Docs/source/_static/2-Create-Bot-Page.png new file mode 100644 index 0000000000000000000000000000000000000000..6f05def872a6ade80fac51f0914ea992e0654ba5 GIT binary patch literal 50788 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%0Ai@t)_&n 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 literal 0 HcmV?d00001 diff --git a/Kumiko-Docs/source/_static/3-Auth-Bot-Creation.png b/Kumiko-Docs/source/_static/3-Auth-Bot-Creation.png new file mode 100644 index 0000000000000000000000000000000000000000..6100c2966ebfb0dde57cee3f3b7725c551070acd GIT binary patch literal 16585 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 z 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 + + + + + + + + diff --git a/Kumiko-Docs/source/conf.py b/Kumiko-Docs/source/conf.py index f7b628c3..a10ddf6b 100644 --- a/Kumiko-Docs/source/conf.py +++ b/Kumiko-Docs/source/conf.py @@ -7,13 +7,13 @@ # https://www.sphinx-doc.org/en/master/usage/configuration.html#project-information project = "Kumiko" -copyright = "2023, Noelle" -author = "Noelle" +copyright = "2023, No767" +author = "No767" # -- General configuration --------------------------------------------------- # https://www.sphinx-doc.org/en/master/usage/configuration.html#general-configuration -extensions = [] +extensions = ["sphinx.ext.napoleon", "sphinxext.opengraph"] templates_path = ["_templates"] @@ -41,3 +41,8 @@ "color-brand-content": "#CE7BB0", }, } + +ogp_site_url = "https://kumiko.readthedocs.io" +ogp_image = ( + "https://raw.githubusercontent.com/No767/Kumiko/dev/assets/kumiko-resized-round.png" +) diff --git a/Kumiko-Docs/source/guides/user/bot-setup.rst b/Kumiko-Docs/source/guides/user/bot-setup.rst new file mode 100644 index 00000000..867419a0 --- /dev/null +++ b/Kumiko-Docs/source/guides/user/bot-setup.rst @@ -0,0 +1,36 @@ +Bot Setup +================ + +This guide provides the steps for setting up a testing bot. This testing bot should only be used for development purposes, or for trying out a self hosted version of Kumiko. **DO NOT RUN THESE BOTS IN PRODUCTION** + + +1. Create a new application at https://discord.com/developers/applications + + .. figure:: /_static/1-Getting-Bot.png + :alt: Create a new application + +2. Click on the "Bot" tab and click "Add Bot" + + .. figure:: /_static/2-Create-Bot-Page.png + :alt: Add a bot + +3. Click "Yes, do it!". Optionally if you have 2FA enabled, you'll need to enter in your MFA token. + + .. figure:: /_static/3-Auth-Bot-Creation.png + :alt: Confirm bot creation + +4. Ensure that the intents shown in the pink square are enabled. ``message_content`` intents are required for the bot to function. + + .. figure:: /_static/4-Ensure-Intents-Are-Enabled.png + :alt: Enable intents + +5. Copy the bot token + + .. figure:: /_static/5-Copy-Token.png + :alt: Copy bot token + +6. Now paste this token in the ``.env`` file located in ``Bot/.env``. If you are using the Docker image for Kumiko, put it in the ``.env`` file located in the root of the repo. + + .. code-block:: bash + + DEV_BOT_TOKEN=YOUR_TOKEN_HERE \ No newline at end of file diff --git a/Kumiko-Docs/source/guides/user/configurations/bot-config.rst b/Kumiko-Docs/source/guides/user/configurations/bot-config.rst new file mode 100644 index 00000000..41517f93 --- /dev/null +++ b/Kumiko-Docs/source/guides/user/configurations/bot-config.rst @@ -0,0 +1,4 @@ +Bot Config +================= + +All configs are handled via the ``Bot/.env`` file. Consult the ``.env.example`` file for an example. \ No newline at end of file diff --git a/Kumiko-Docs/source/guides/user/configurations/index.rst b/Kumiko-Docs/source/guides/user/configurations/index.rst new file mode 100644 index 00000000..d34416ff --- /dev/null +++ b/Kumiko-Docs/source/guides/user/configurations/index.rst @@ -0,0 +1,9 @@ +User Configurations +==================== + +These contains any configs for the bot for the end user + +.. toctree:: + :maxdepth: 2 + + bot-config \ No newline at end of file diff --git a/Kumiko-Docs/source/guides/user/index.rst b/Kumiko-Docs/source/guides/user/index.rst index eb464750..46fe04ec 100644 --- a/Kumiko-Docs/source/guides/user/index.rst +++ b/Kumiko-Docs/source/guides/user/index.rst @@ -5,5 +5,7 @@ Kumiko offers a user guide where users can find information on commands, feature .. toctree:: :maxdepth: 2 - :hidden: - \ No newline at end of file + + bot-setup + trying-out + configurations/index \ No newline at end of file diff --git a/Kumiko-Docs/source/guides/user/trying-out.rst b/Kumiko-Docs/source/guides/user/trying-out.rst new file mode 100644 index 00000000..c3eb8dd5 --- /dev/null +++ b/Kumiko-Docs/source/guides/user/trying-out.rst @@ -0,0 +1,74 @@ +Trying out Kumiko +================== + +Kumiko can be tried out by running the Docker image. For the official versions of Kumiko, please invite the bot into your guild instead. For those who want to try out the latest breaking features, using Docker is recommended. + +Prerequisites +------------- + +1. Make sure you have set up your bot token. Refer to :doc:`bot-setup` for the full guide. +2. Make sure you have these installed: + - `Docker `_ + - curl or wget + +Standalone Requirements +^^^^^^^^^^^^^^^^^^^^^^^ + +If you are running Kumiko on a standalone machine (w/o Docker Compose), you will need to install the following: + +- `PostgreSQL `_ +- `Redis Stack `_ (or Redis w/ RedisJSON and RedisSearch modules loaded) + +Standalone (Docker CLI) +----------------------- + +1. Pull the image from either GHCR or Docker Hub + + - GHCR + + .. code-block:: bash + + docker pull ghcr.io/no767/kumiko:latest + + - Docker Hub + + .. code-block:: bash + + docker pull no767/kumiko:latest + +2. Download the example docker env file and standalone-setup script. This is the file where you'll put all of your env and credentials in + + .. code-block:: bash + + curl -o https://raw.githubusercontent.com/no767/kumiko/master/.env-docker-example .env + + # Or using wget: + + wget -O .env https://raw.githubusercontent.com/no767/kumiko/master/.env-docker-example + +3. Obtain the API keys, access tokens, discord bot token, and database credentials for Kumiko. Open up the ``.env`` file with an editor like Vim and add the needed values. + +4. Now it's time to run Kumiko. Just run this command to run the bot: + + .. code-block:: bash + + sudo docker run -d --env-file .env --name Kumiko no767/kumiko:latest + +Docker Compose +-------------- + +1. Download the `.env` file and `docker-compose.yml` file via the `setup.sh` script + + .. code-block:: bash + + curl -s https://raw.githubusercontent.com/No767/Kumiko/master/scripts/setup.sh | sh + +2. Obtain the API keys, access tokens, discord bot token, and database credentials for Kumiko. Open up the ``.env`` file with an editor like Vim and add the needed values. + +3. Once everything is set, literally just fire up the whole entire Docker Compose stack. All of the database creation, and the seeding of the data will be handled automatically + + .. code-block:: bash + + sudo docker-compose up -d + + diff --git a/Kumiko-Docs/source/index.rst b/Kumiko-Docs/source/index.rst index 16eea75e..22666e16 100644 --- a/Kumiko-Docs/source/index.rst +++ b/Kumiko-Docs/source/index.rst @@ -24,7 +24,7 @@ Kumiko terms-of-service/privacy-policy.rst -.. figure:: https://raw.githubusercontent.com/No767/Kumiko/dev/assets/kumiko-resized-round.svg +.. figure:: /_static/kumiko-resized-round.svg :align: right .. image:: https://img.shields.io/github/v/release/No767/Kumiko?label=Release&logo=github&sort=semver @@ -70,4 +70,11 @@ Resources and Links - `Docker Hub `_ - `GHCR `_ - `GitHub `_ -- Discord Server \ No newline at end of file +- Discord Server + +Project Links +^^^^^^^^^^^^^ + +- `Contributing `_ +- `Roadmap `_ +- `Project License `_ \ No newline at end of file diff --git a/poetry.lock b/poetry.lock index 40baf0e6..665c10b2 100644 --- a/poetry.lock +++ b/poetry.lock @@ -792,6 +792,81 @@ colorama = {version = "*", markers = "sys_platform == \"win32\""} [package.extras] development = ["black", "flake8", "mypy", "pytest", "types-colorama"] +[[package]] +name = "contourpy" +version = "1.0.7" +description = "Python library for calculating contours of 2D quadrilateral grids" +category = "dev" +optional = false +python-versions = ">=3.8" +files = [ + {file = "contourpy-1.0.7-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:95c3acddf921944f241b6773b767f1cbce71d03307270e2d769fd584d5d1092d"}, + {file = "contourpy-1.0.7-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:fc1464c97579da9f3ab16763c32e5c5d5bb5fa1ec7ce509a4ca6108b61b84fab"}, + {file = "contourpy-1.0.7-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:8acf74b5d383414401926c1598ed77825cd530ac7b463ebc2e4f46638f56cce6"}, + {file = "contourpy-1.0.7-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:1c71fdd8f1c0f84ffd58fca37d00ca4ebaa9e502fb49825484da075ac0b0b803"}, + {file = "contourpy-1.0.7-cp310-cp310-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:f99e9486bf1bb979d95d5cffed40689cb595abb2b841f2991fc894b3452290e8"}, + {file = "contourpy-1.0.7-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:87f4d8941a9564cda3f7fa6a6cd9b32ec575830780677932abdec7bcb61717b0"}, + {file = "contourpy-1.0.7-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:9e20e5a1908e18aaa60d9077a6d8753090e3f85ca25da6e25d30dc0a9e84c2c6"}, + {file = "contourpy-1.0.7-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:a877ada905f7d69b2a31796c4b66e31a8068b37aa9b78832d41c82fc3e056ddd"}, + {file = "contourpy-1.0.7-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:6381fa66866b0ea35e15d197fc06ac3840a9b2643a6475c8fff267db8b9f1e69"}, + {file = "contourpy-1.0.7-cp310-cp310-win32.whl", hash = "sha256:3c184ad2433635f216645fdf0493011a4667e8d46b34082f5a3de702b6ec42e3"}, + {file = "contourpy-1.0.7-cp310-cp310-win_amd64.whl", hash = "sha256:3caea6365b13119626ee996711ab63e0c9d7496f65641f4459c60a009a1f3e80"}, + {file = "contourpy-1.0.7-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:ed33433fc3820263a6368e532f19ddb4c5990855e4886088ad84fd7c4e561c71"}, + {file = "contourpy-1.0.7-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:38e2e577f0f092b8e6774459317c05a69935a1755ecfb621c0a98f0e3c09c9a5"}, + {file = "contourpy-1.0.7-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:ae90d5a8590e5310c32a7630b4b8618cef7563cebf649011da80874d0aa8f414"}, + {file = "contourpy-1.0.7-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:130230b7e49825c98edf0b428b7aa1125503d91732735ef897786fe5452b1ec2"}, + {file = "contourpy-1.0.7-cp311-cp311-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:58569c491e7f7e874f11519ef46737cea1d6eda1b514e4eb5ac7dab6aa864d02"}, + {file = "contourpy-1.0.7-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:54d43960d809c4c12508a60b66cb936e7ed57d51fb5e30b513934a4a23874fae"}, + {file = "contourpy-1.0.7-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:152fd8f730c31fd67fe0ffebe1df38ab6a669403da93df218801a893645c6ccc"}, + {file = "contourpy-1.0.7-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:9056c5310eb1daa33fc234ef39ebfb8c8e2533f088bbf0bc7350f70a29bde1ac"}, + {file = "contourpy-1.0.7-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:a9d7587d2fdc820cc9177139b56795c39fb8560f540bba9ceea215f1f66e1566"}, + {file = "contourpy-1.0.7-cp311-cp311-win32.whl", hash = "sha256:4ee3ee247f795a69e53cd91d927146fb16c4e803c7ac86c84104940c7d2cabf0"}, + {file = "contourpy-1.0.7-cp311-cp311-win_amd64.whl", hash = "sha256:5caeacc68642e5f19d707471890f037a13007feba8427eb7f2a60811a1fc1350"}, + {file = "contourpy-1.0.7-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:fd7dc0e6812b799a34f6d12fcb1000539098c249c8da54f3566c6a6461d0dbad"}, + {file = "contourpy-1.0.7-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:0f9d350b639db6c2c233d92c7f213d94d2e444d8e8fc5ca44c9706cf72193772"}, + {file = "contourpy-1.0.7-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:e96a08b62bb8de960d3a6afbc5ed8421bf1a2d9c85cc4ea73f4bc81b4910500f"}, + {file = "contourpy-1.0.7-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:031154ed61f7328ad7f97662e48660a150ef84ee1bc8876b6472af88bf5a9b98"}, + {file = "contourpy-1.0.7-cp38-cp38-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:2e9ebb4425fc1b658e13bace354c48a933b842d53c458f02c86f371cecbedecc"}, + {file = "contourpy-1.0.7-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:efb8f6d08ca7998cf59eaf50c9d60717f29a1a0a09caa46460d33b2924839dbd"}, + {file = "contourpy-1.0.7-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:6c180d89a28787e4b73b07e9b0e2dac7741261dbdca95f2b489c4f8f887dd810"}, + {file = "contourpy-1.0.7-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:b8d587cc39057d0afd4166083d289bdeff221ac6d3ee5046aef2d480dc4b503c"}, + {file = "contourpy-1.0.7-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:769eef00437edf115e24d87f8926955f00f7704bede656ce605097584f9966dc"}, + {file = "contourpy-1.0.7-cp38-cp38-win32.whl", hash = "sha256:62398c80ef57589bdbe1eb8537127321c1abcfdf8c5f14f479dbbe27d0322e66"}, + {file = "contourpy-1.0.7-cp38-cp38-win_amd64.whl", hash = "sha256:57119b0116e3f408acbdccf9eb6ef19d7fe7baf0d1e9aaa5381489bc1aa56556"}, + {file = "contourpy-1.0.7-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:30676ca45084ee61e9c3da589042c24a57592e375d4b138bd84d8709893a1ba4"}, + {file = "contourpy-1.0.7-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:3e927b3868bd1e12acee7cc8f3747d815b4ab3e445a28d2e5373a7f4a6e76ba1"}, + {file = "contourpy-1.0.7-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:366a0cf0fc079af5204801786ad7a1c007714ee3909e364dbac1729f5b0849e5"}, + {file = "contourpy-1.0.7-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:89ba9bb365446a22411f0673abf6ee1fea3b2cf47b37533b970904880ceb72f3"}, + {file = "contourpy-1.0.7-cp39-cp39-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:71b0bf0c30d432278793d2141362ac853859e87de0a7dee24a1cea35231f0d50"}, + {file = "contourpy-1.0.7-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:e7281244c99fd7c6f27c1c6bfafba878517b0b62925a09b586d88ce750a016d2"}, + {file = "contourpy-1.0.7-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:b6d0f9e1d39dbfb3977f9dd79f156c86eb03e57a7face96f199e02b18e58d32a"}, + {file = "contourpy-1.0.7-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:7f6979d20ee5693a1057ab53e043adffa1e7418d734c1532e2d9e915b08d8ec2"}, + {file = "contourpy-1.0.7-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:5dd34c1ae752515318224cba7fc62b53130c45ac6a1040c8b7c1a223c46e8967"}, + {file = "contourpy-1.0.7-cp39-cp39-win32.whl", hash = "sha256:c5210e5d5117e9aec8c47d9156d1d3835570dd909a899171b9535cb4a3f32693"}, + {file = "contourpy-1.0.7-cp39-cp39-win_amd64.whl", hash = "sha256:60835badb5ed5f4e194a6f21c09283dd6e007664a86101431bf870d9e86266c4"}, + {file = "contourpy-1.0.7-pp38-pypy38_pp73-macosx_10_9_x86_64.whl", hash = "sha256:ce41676b3d0dd16dbcfabcc1dc46090aaf4688fd6e819ef343dbda5a57ef0161"}, + {file = "contourpy-1.0.7-pp38-pypy38_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:5a011cf354107b47c58ea932d13b04d93c6d1d69b8b6dce885e642531f847566"}, + {file = "contourpy-1.0.7-pp38-pypy38_pp73-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:31a55dccc8426e71817e3fe09b37d6d48ae40aae4ecbc8c7ad59d6893569c436"}, + {file = "contourpy-1.0.7-pp38-pypy38_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:69f8ff4db108815addd900a74df665e135dbbd6547a8a69333a68e1f6e368ac2"}, + {file = "contourpy-1.0.7-pp38-pypy38_pp73-win_amd64.whl", hash = "sha256:efe99298ba37e37787f6a2ea868265465410822f7bea163edcc1bd3903354ea9"}, + {file = "contourpy-1.0.7-pp39-pypy39_pp73-macosx_10_9_x86_64.whl", hash = "sha256:a1e97b86f73715e8670ef45292d7cc033548266f07d54e2183ecb3c87598888f"}, + {file = "contourpy-1.0.7-pp39-pypy39_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:cc331c13902d0f50845099434cd936d49d7a2ca76cb654b39691974cb1e4812d"}, + {file = "contourpy-1.0.7-pp39-pypy39_pp73-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:24847601071f740837aefb730e01bd169fbcaa610209779a78db7ebb6e6a7051"}, + {file = "contourpy-1.0.7-pp39-pypy39_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:abf298af1e7ad44eeb93501e40eb5a67abbf93b5d90e468d01fc0c4451971afa"}, + {file = "contourpy-1.0.7-pp39-pypy39_pp73-win_amd64.whl", hash = "sha256:64757f6460fc55d7e16ed4f1de193f362104285c667c112b50a804d482777edd"}, + {file = "contourpy-1.0.7.tar.gz", hash = "sha256:d8165a088d31798b59e91117d1f5fc3df8168d8b48c4acc10fc0df0d0bdbcc5e"}, +] + +[package.dependencies] +numpy = ">=1.16" + +[package.extras] +bokeh = ["bokeh", "chromedriver", "selenium"] +docs = ["furo", "sphinx-copybutton"] +mypy = ["contourpy[bokeh]", "docutils-stubs", "mypy (==0.991)", "types-Pillow"] +test = ["Pillow", "matplotlib", "pytest"] +test-no-images = ["pytest"] + [[package]] name = "coverage" version = "7.0.5" @@ -859,6 +934,18 @@ tomli = {version = "*", optional = true, markers = "python_full_version <= \"3.1 [package.extras] toml = ["tomli"] +[[package]] +name = "cycler" +version = "0.11.0" +description = "Composable style cycles" +category = "dev" +optional = false +python-versions = ">=3.6" +files = [ + {file = "cycler-0.11.0-py3-none-any.whl", hash = "sha256:3a27e95f763a428a739d2add979fa7494c912a32c17c4c38c4d5f082cad165a3"}, + {file = "cycler-0.11.0.tar.gz", hash = "sha256:9c87405839a19696e837b3b818fed3f5f69f16f1eec1a1ad77e043dcea9c772f"}, +] + [[package]] name = "discord-ext-menus" version = "1.0.0a32+g8686b5d" @@ -1018,6 +1105,32 @@ files = [ docs = ["furo (>=2022.12.7)", "sphinx (>=5.3)", "sphinx-autodoc-typehints (>=1.19.5)"] testing = ["covdefaults (>=2.2.2)", "coverage (>=7.0.1)", "pytest (>=7.2)", "pytest-cov (>=4)", "pytest-timeout (>=2.1)"] +[[package]] +name = "fonttools" +version = "4.39.3" +description = "Tools to manipulate font files" +category = "dev" +optional = false +python-versions = ">=3.8" +files = [ + {file = "fonttools-4.39.3-py3-none-any.whl", hash = "sha256:64c0c05c337f826183637570ac5ab49ee220eec66cf50248e8df527edfa95aeb"}, + {file = "fonttools-4.39.3.zip", hash = "sha256:9234b9f57b74e31b192c3fc32ef1a40750a8fbc1cd9837a7b7bfc4ca4a5c51d7"}, +] + +[package.extras] +all = ["brotli (>=1.0.1)", "brotlicffi (>=0.8.0)", "fs (>=2.2.0,<3)", "lxml (>=4.0,<5)", "lz4 (>=1.7.4.2)", "matplotlib", "munkres", "scipy", "skia-pathops (>=0.5.0)", "sympy", "uharfbuzz (>=0.23.0)", "unicodedata2 (>=15.0.0)", "xattr", "zopfli (>=0.1.4)"] +graphite = ["lz4 (>=1.7.4.2)"] +interpolatable = ["munkres", "scipy"] +lxml = ["lxml (>=4.0,<5)"] +pathops = ["skia-pathops (>=0.5.0)"] +plot = ["matplotlib"] +repacker = ["uharfbuzz (>=0.23.0)"] +symfont = ["sympy"] +type1 = ["xattr"] +ufo = ["fs (>=2.2.0,<3)"] +unicode = ["unicodedata2 (>=15.0.0)"] +woff = ["brotli (>=1.0.1)", "brotlicffi (>=0.8.0)", "zopfli (>=0.1.4)"] + [[package]] name = "frozenlist" version = "1.3.3" @@ -1394,6 +1507,25 @@ docs = ["furo", "jaraco.packaging (>=9)", "jaraco.tidelift (>=1.4)", "rst.linker perf = ["ipython"] testing = ["flake8 (<5)", "flufl.flake8", "importlib-resources (>=1.3)", "packaging", "pyfakefs", "pytest (>=6)", "pytest-black (>=0.3.7)", "pytest-checkdocs (>=2.4)", "pytest-cov", "pytest-enabler (>=1.3)", "pytest-flake8", "pytest-mypy (>=0.9.1)", "pytest-perf (>=0.9.2)"] +[[package]] +name = "importlib-resources" +version = "5.12.0" +description = "Read resources from Python packages" +category = "dev" +optional = false +python-versions = ">=3.7" +files = [ + {file = "importlib_resources-5.12.0-py3-none-any.whl", hash = "sha256:7b1deeebbf351c7578e09bf2f63fa2ce8b5ffec296e0d349139d43cca061a81a"}, + {file = "importlib_resources-5.12.0.tar.gz", hash = "sha256:4be82589bf5c1d7999aedf2a45159d10cb3ca4f19b2271f8792bc8e6da7b22f6"}, +] + +[package.dependencies] +zipp = {version = ">=3.1.0", markers = "python_version < \"3.10\""} + +[package.extras] +docs = ["furo", "jaraco.packaging (>=9)", "jaraco.tidelift (>=1.4)", "rst.linker (>=1.9)", "sphinx (>=3.5)", "sphinx-lint"] +testing = ["flake8 (<5)", "pytest (>=6)", "pytest-black (>=0.3.7)", "pytest-checkdocs (>=2.4)", "pytest-cov", "pytest-enabler (>=1.3)", "pytest-flake8", "pytest-mypy (>=0.9.1)"] + [[package]] name = "iniconfig" version = "2.0.0" @@ -1452,6 +1584,84 @@ publish = ["Jinja2 (>=3.0.3)"] test = ["coverage (>=6.3.2)", "flake8 (>=4.0.1)", "isort (>=5.10.1)", "pylint (>=2.11.1)", "pytest (>=7.0.1)", "pytest-asyncio (>=0.18.1)", "pytest-cov (>=3.0.0)", "pytest-mock (>=3.7.0)"] voice = ["yt-dlp (>=2022.3.8)"] +[[package]] +name = "kiwisolver" +version = "1.4.4" +description = "A fast implementation of the Cassowary constraint solver" +category = "dev" +optional = false +python-versions = ">=3.7" +files = [ + {file = "kiwisolver-1.4.4-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:2f5e60fabb7343a836360c4f0919b8cd0d6dbf08ad2ca6b9cf90bf0c76a3c4f6"}, + {file = "kiwisolver-1.4.4-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:10ee06759482c78bdb864f4109886dff7b8a56529bc1609d4f1112b93fe6423c"}, + {file = "kiwisolver-1.4.4-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:c79ebe8f3676a4c6630fd3f777f3cfecf9289666c84e775a67d1d358578dc2e3"}, + {file = "kiwisolver-1.4.4-cp310-cp310-manylinux_2_12_i686.manylinux2010_i686.whl", hash = "sha256:abbe9fa13da955feb8202e215c4018f4bb57469b1b78c7a4c5c7b93001699938"}, + {file = "kiwisolver-1.4.4-cp310-cp310-manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:7577c1987baa3adc4b3c62c33bd1118c3ef5c8ddef36f0f2c950ae0b199e100d"}, + {file = "kiwisolver-1.4.4-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:f8ad8285b01b0d4695102546b342b493b3ccc6781fc28c8c6a1bb63e95d22f09"}, + {file = "kiwisolver-1.4.4-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:8ed58b8acf29798b036d347791141767ccf65eee7f26bde03a71c944449e53de"}, + {file = "kiwisolver-1.4.4-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:a68b62a02953b9841730db7797422f983935aeefceb1679f0fc85cbfbd311c32"}, + {file = "kiwisolver-1.4.4-cp310-cp310-win32.whl", hash = "sha256:e92a513161077b53447160b9bd8f522edfbed4bd9759e4c18ab05d7ef7e49408"}, + {file = "kiwisolver-1.4.4-cp310-cp310-win_amd64.whl", hash = "sha256:3fe20f63c9ecee44560d0e7f116b3a747a5d7203376abeea292ab3152334d004"}, + {file = "kiwisolver-1.4.4-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:e0ea21f66820452a3f5d1655f8704a60d66ba1191359b96541eaf457710a5fc6"}, + {file = "kiwisolver-1.4.4-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:bc9db8a3efb3e403e4ecc6cd9489ea2bac94244f80c78e27c31dcc00d2790ac2"}, + {file = "kiwisolver-1.4.4-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:d5b61785a9ce44e5a4b880272baa7cf6c8f48a5180c3e81c59553ba0cb0821ca"}, + {file = "kiwisolver-1.4.4-cp311-cp311-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:c2dbb44c3f7e6c4d3487b31037b1bdbf424d97687c1747ce4ff2895795c9bf69"}, + {file = "kiwisolver-1.4.4-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:6295ecd49304dcf3bfbfa45d9a081c96509e95f4b9d0eb7ee4ec0530c4a96514"}, + {file = "kiwisolver-1.4.4-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:4bd472dbe5e136f96a4b18f295d159d7f26fd399136f5b17b08c4e5f498cd494"}, + {file = "kiwisolver-1.4.4-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:bf7d9fce9bcc4752ca4a1b80aabd38f6d19009ea5cbda0e0856983cf6d0023f5"}, + {file = "kiwisolver-1.4.4-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:78d6601aed50c74e0ef02f4204da1816147a6d3fbdc8b3872d263338a9052c51"}, + {file = "kiwisolver-1.4.4-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:877272cf6b4b7e94c9614f9b10140e198d2186363728ed0f701c6eee1baec1da"}, + {file = "kiwisolver-1.4.4-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:db608a6757adabb32f1cfe6066e39b3706d8c3aa69bbc353a5b61edad36a5cb4"}, + {file = "kiwisolver-1.4.4-cp311-cp311-musllinux_1_1_ppc64le.whl", hash = "sha256:5853eb494c71e267912275e5586fe281444eb5e722de4e131cddf9d442615626"}, + {file = "kiwisolver-1.4.4-cp311-cp311-musllinux_1_1_s390x.whl", hash = "sha256:f0a1dbdb5ecbef0d34eb77e56fcb3e95bbd7e50835d9782a45df81cc46949750"}, + {file = "kiwisolver-1.4.4-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:283dffbf061a4ec60391d51e6155e372a1f7a4f5b15d59c8505339454f8989e4"}, + {file = "kiwisolver-1.4.4-cp311-cp311-win32.whl", hash = "sha256:d06adcfa62a4431d404c31216f0f8ac97397d799cd53800e9d3efc2fbb3cf14e"}, + {file = "kiwisolver-1.4.4-cp311-cp311-win_amd64.whl", hash = "sha256:e7da3fec7408813a7cebc9e4ec55afed2d0fd65c4754bc376bf03498d4e92686"}, + {file = "kiwisolver-1.4.4-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:62ac9cc684da4cf1778d07a89bf5f81b35834cb96ca523d3a7fb32509380cbf6"}, + {file = "kiwisolver-1.4.4-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:41dae968a94b1ef1897cb322b39360a0812661dba7c682aa45098eb8e193dbdf"}, + {file = "kiwisolver-1.4.4-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:02f79693ec433cb4b5f51694e8477ae83b3205768a6fb48ffba60549080e295b"}, + {file = "kiwisolver-1.4.4-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:d0611a0a2a518464c05ddd5a3a1a0e856ccc10e67079bb17f265ad19ab3c7597"}, + {file = "kiwisolver-1.4.4-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:db5283d90da4174865d520e7366801a93777201e91e79bacbac6e6927cbceede"}, + {file = "kiwisolver-1.4.4-cp37-cp37m-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:1041feb4cda8708ce73bb4dcb9ce1ccf49d553bf87c3954bdfa46f0c3f77252c"}, + {file = "kiwisolver-1.4.4-cp37-cp37m-win32.whl", hash = "sha256:a553dadda40fef6bfa1456dc4be49b113aa92c2a9a9e8711e955618cd69622e3"}, + {file = "kiwisolver-1.4.4-cp37-cp37m-win_amd64.whl", hash = "sha256:03baab2d6b4a54ddbb43bba1a3a2d1627e82d205c5cf8f4c924dc49284b87166"}, + {file = "kiwisolver-1.4.4-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:841293b17ad704d70c578f1f0013c890e219952169ce8a24ebc063eecf775454"}, + {file = "kiwisolver-1.4.4-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:f4f270de01dd3e129a72efad823da90cc4d6aafb64c410c9033aba70db9f1ff0"}, + {file = "kiwisolver-1.4.4-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:f9f39e2f049db33a908319cf46624a569b36983c7c78318e9726a4cb8923b26c"}, + {file = "kiwisolver-1.4.4-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:c97528e64cb9ebeff9701e7938653a9951922f2a38bd847787d4a8e498cc83ae"}, + {file = "kiwisolver-1.4.4-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:1d1573129aa0fd901076e2bfb4275a35f5b7aa60fbfb984499d661ec950320b0"}, + {file = "kiwisolver-1.4.4-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:ad881edc7ccb9d65b0224f4e4d05a1e85cf62d73aab798943df6d48ab0cd79a1"}, + {file = "kiwisolver-1.4.4-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:b428ef021242344340460fa4c9185d0b1f66fbdbfecc6c63eff4b7c29fad429d"}, + {file = "kiwisolver-1.4.4-cp38-cp38-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:2e407cb4bd5a13984a6c2c0fe1845e4e41e96f183e5e5cd4d77a857d9693494c"}, + {file = "kiwisolver-1.4.4-cp38-cp38-win32.whl", hash = "sha256:75facbe9606748f43428fc91a43edb46c7ff68889b91fa31f53b58894503a191"}, + {file = "kiwisolver-1.4.4-cp38-cp38-win_amd64.whl", hash = "sha256:5bce61af018b0cb2055e0e72e7d65290d822d3feee430b7b8203d8a855e78766"}, + {file = "kiwisolver-1.4.4-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:8c808594c88a025d4e322d5bb549282c93c8e1ba71b790f539567932722d7bd8"}, + {file = "kiwisolver-1.4.4-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:f0a71d85ecdd570ded8ac3d1c0f480842f49a40beb423bb8014539a9f32a5897"}, + {file = "kiwisolver-1.4.4-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:b533558eae785e33e8c148a8d9921692a9fe5aa516efbdff8606e7d87b9d5824"}, + {file = "kiwisolver-1.4.4-cp39-cp39-manylinux_2_12_i686.manylinux2010_i686.whl", hash = "sha256:efda5fc8cc1c61e4f639b8067d118e742b812c930f708e6667a5ce0d13499e29"}, + {file = "kiwisolver-1.4.4-cp39-cp39-manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:7c43e1e1206cd421cd92e6b3280d4385d41d7166b3ed577ac20444b6995a445f"}, + {file = "kiwisolver-1.4.4-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:bc8d3bd6c72b2dd9decf16ce70e20abcb3274ba01b4e1c96031e0c4067d1e7cd"}, + {file = "kiwisolver-1.4.4-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:4ea39b0ccc4f5d803e3337dd46bcce60b702be4d86fd0b3d7531ef10fd99a1ac"}, + {file = "kiwisolver-1.4.4-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:968f44fdbf6dd757d12920d63b566eeb4d5b395fd2d00d29d7ef00a00582aac9"}, + {file = "kiwisolver-1.4.4-cp39-cp39-win32.whl", hash = "sha256:da7e547706e69e45d95e116e6939488d62174e033b763ab1496b4c29b76fabea"}, + {file = "kiwisolver-1.4.4-cp39-cp39-win_amd64.whl", hash = "sha256:ba59c92039ec0a66103b1d5fe588fa546373587a7d68f5c96f743c3396afc04b"}, + {file = "kiwisolver-1.4.4-pp37-pypy37_pp73-manylinux_2_12_i686.manylinux2010_i686.whl", hash = "sha256:91672bacaa030f92fc2f43b620d7b337fd9a5af28b0d6ed3f77afc43c4a64b5a"}, + {file = "kiwisolver-1.4.4-pp37-pypy37_pp73-manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:787518a6789009c159453da4d6b683f468ef7a65bbde796bcea803ccf191058d"}, + {file = "kiwisolver-1.4.4-pp37-pypy37_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:da152d8cdcab0e56e4f45eb08b9aea6455845ec83172092f09b0e077ece2cf7a"}, + {file = "kiwisolver-1.4.4-pp37-pypy37_pp73-win_amd64.whl", hash = "sha256:ecb1fa0db7bf4cff9dac752abb19505a233c7f16684c5826d1f11ebd9472b871"}, + {file = "kiwisolver-1.4.4-pp38-pypy38_pp73-macosx_10_9_x86_64.whl", hash = "sha256:28bc5b299f48150b5f822ce68624e445040595a4ac3d59251703779836eceff9"}, + {file = "kiwisolver-1.4.4-pp38-pypy38_pp73-manylinux_2_12_i686.manylinux2010_i686.whl", hash = "sha256:81e38381b782cc7e1e46c4e14cd997ee6040768101aefc8fa3c24a4cc58e98f8"}, + {file = "kiwisolver-1.4.4-pp38-pypy38_pp73-manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:2a66fdfb34e05b705620dd567f5a03f239a088d5a3f321e7b6ac3239d22aa286"}, + {file = "kiwisolver-1.4.4-pp38-pypy38_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:872b8ca05c40d309ed13eb2e582cab0c5a05e81e987ab9c521bf05ad1d5cf5cb"}, + {file = "kiwisolver-1.4.4-pp38-pypy38_pp73-win_amd64.whl", hash = "sha256:70e7c2e7b750585569564e2e5ca9845acfaa5da56ac46df68414f29fea97be9f"}, + {file = "kiwisolver-1.4.4-pp39-pypy39_pp73-macosx_10_9_x86_64.whl", hash = "sha256:9f85003f5dfa867e86d53fac6f7e6f30c045673fa27b603c397753bebadc3008"}, + {file = "kiwisolver-1.4.4-pp39-pypy39_pp73-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:2e307eb9bd99801f82789b44bb45e9f541961831c7311521b13a6c85afc09767"}, + {file = "kiwisolver-1.4.4-pp39-pypy39_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:b1792d939ec70abe76f5054d3f36ed5656021dcad1322d1cc996d4e54165cef9"}, + {file = "kiwisolver-1.4.4-pp39-pypy39_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f6cb459eea32a4e2cf18ba5fcece2dbdf496384413bc1bae15583f19e567f3b2"}, + {file = "kiwisolver-1.4.4-pp39-pypy39_pp73-win_amd64.whl", hash = "sha256:36dafec3d6d6088d34e2de6b85f9d8e2324eb734162fba59d2ba9ed7a2043d5b"}, + {file = "kiwisolver-1.4.4.tar.gz", hash = "sha256:d41997519fcba4a1e46eb4a2fe31bc12f0ff957b2b81bac28db24744f333e955"}, +] + [[package]] name = "line-profiler" version = "4.0.3" @@ -1616,6 +1826,69 @@ files = [ {file = "MarkupSafe-2.1.2.tar.gz", hash = "sha256:abcabc8c2b26036d62d4c746381a6f7cf60aafcc653198ad678306986b09450d"}, ] +[[package]] +name = "matplotlib" +version = "3.7.1" +description = "Python plotting package" +category = "dev" +optional = false +python-versions = ">=3.8" +files = [ + {file = "matplotlib-3.7.1-cp310-cp310-macosx_10_12_universal2.whl", hash = "sha256:95cbc13c1fc6844ab8812a525bbc237fa1470863ff3dace7352e910519e194b1"}, + {file = "matplotlib-3.7.1-cp310-cp310-macosx_10_12_x86_64.whl", hash = "sha256:08308bae9e91aca1ec6fd6dda66237eef9f6294ddb17f0d0b3c863169bf82353"}, + {file = "matplotlib-3.7.1-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:544764ba51900da4639c0f983b323d288f94f65f4024dc40ecb1542d74dc0500"}, + {file = "matplotlib-3.7.1-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:56d94989191de3fcc4e002f93f7f1be5da476385dde410ddafbb70686acf00ea"}, + {file = "matplotlib-3.7.1-cp310-cp310-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:e99bc9e65901bb9a7ce5e7bb24af03675cbd7c70b30ac670aa263240635999a4"}, + {file = "matplotlib-3.7.1-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:eb7d248c34a341cd4c31a06fd34d64306624c8cd8d0def7abb08792a5abfd556"}, + {file = "matplotlib-3.7.1-cp310-cp310-win32.whl", hash = "sha256:ce463ce590f3825b52e9fe5c19a3c6a69fd7675a39d589e8b5fbe772272b3a24"}, + {file = "matplotlib-3.7.1-cp310-cp310-win_amd64.whl", hash = "sha256:3d7bc90727351fb841e4d8ae620d2d86d8ed92b50473cd2b42ce9186104ecbba"}, + {file = "matplotlib-3.7.1-cp311-cp311-macosx_10_12_universal2.whl", hash = "sha256:770a205966d641627fd5cf9d3cb4b6280a716522cd36b8b284a8eb1581310f61"}, + {file = "matplotlib-3.7.1-cp311-cp311-macosx_10_12_x86_64.whl", hash = "sha256:f67bfdb83a8232cb7a92b869f9355d677bce24485c460b19d01970b64b2ed476"}, + {file = "matplotlib-3.7.1-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:2bf092f9210e105f414a043b92af583c98f50050559616930d884387d0772aba"}, + {file = "matplotlib-3.7.1-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:89768d84187f31717349c6bfadc0e0d8c321e8eb34522acec8a67b1236a66332"}, + {file = "matplotlib-3.7.1-cp311-cp311-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:83111e6388dec67822e2534e13b243cc644c7494a4bb60584edbff91585a83c6"}, + {file = "matplotlib-3.7.1-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:a867bf73a7eb808ef2afbca03bcdb785dae09595fbe550e1bab0cd023eba3de0"}, + {file = "matplotlib-3.7.1-cp311-cp311-win32.whl", hash = "sha256:fbdeeb58c0cf0595efe89c05c224e0a502d1aa6a8696e68a73c3efc6bc354304"}, + {file = "matplotlib-3.7.1-cp311-cp311-win_amd64.whl", hash = "sha256:c0bd19c72ae53e6ab979f0ac6a3fafceb02d2ecafa023c5cca47acd934d10be7"}, + {file = "matplotlib-3.7.1-cp38-cp38-macosx_10_12_universal2.whl", hash = "sha256:6eb88d87cb2c49af00d3bbc33a003f89fd9f78d318848da029383bfc08ecfbfb"}, + {file = "matplotlib-3.7.1-cp38-cp38-macosx_10_12_x86_64.whl", hash = "sha256:cf0e4f727534b7b1457898c4f4ae838af1ef87c359b76dcd5330fa31893a3ac7"}, + {file = "matplotlib-3.7.1-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:46a561d23b91f30bccfd25429c3c706afe7d73a5cc64ef2dfaf2b2ac47c1a5dc"}, + {file = "matplotlib-3.7.1-cp38-cp38-manylinux_2_12_i686.manylinux2010_i686.whl", hash = "sha256:8704726d33e9aa8a6d5215044b8d00804561971163563e6e6591f9dcf64340cc"}, + {file = "matplotlib-3.7.1-cp38-cp38-manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:4cf327e98ecf08fcbb82685acaf1939d3338548620ab8dfa02828706402c34de"}, + {file = "matplotlib-3.7.1-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:617f14ae9d53292ece33f45cba8503494ee199a75b44de7717964f70637a36aa"}, + {file = "matplotlib-3.7.1-cp38-cp38-win32.whl", hash = "sha256:7c9a4b2da6fac77bcc41b1ea95fadb314e92508bf5493ceff058e727e7ecf5b0"}, + {file = "matplotlib-3.7.1-cp38-cp38-win_amd64.whl", hash = "sha256:14645aad967684e92fc349493fa10c08a6da514b3d03a5931a1bac26e6792bd1"}, + {file = "matplotlib-3.7.1-cp39-cp39-macosx_10_12_universal2.whl", hash = "sha256:81a6b377ea444336538638d31fdb39af6be1a043ca5e343fe18d0f17e098770b"}, + {file = "matplotlib-3.7.1-cp39-cp39-macosx_10_12_x86_64.whl", hash = "sha256:28506a03bd7f3fe59cd3cd4ceb2a8d8a2b1db41afede01f66c42561b9be7b4b7"}, + {file = "matplotlib-3.7.1-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:8c587963b85ce41e0a8af53b9b2de8dddbf5ece4c34553f7bd9d066148dc719c"}, + {file = "matplotlib-3.7.1-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:8bf26ade3ff0f27668989d98c8435ce9327d24cffb7f07d24ef609e33d582439"}, + {file = "matplotlib-3.7.1-cp39-cp39-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:def58098f96a05f90af7e92fd127d21a287068202aa43b2a93476170ebd99e87"}, + {file = "matplotlib-3.7.1-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f883a22a56a84dba3b588696a2b8a1ab0d2c3d41be53264115c71b0a942d8fdb"}, + {file = "matplotlib-3.7.1-cp39-cp39-win32.whl", hash = "sha256:4f99e1b234c30c1e9714610eb0c6d2f11809c9c78c984a613ae539ea2ad2eb4b"}, + {file = "matplotlib-3.7.1-cp39-cp39-win_amd64.whl", hash = "sha256:3ba2af245e36990facf67fde840a760128ddd71210b2ab6406e640188d69d136"}, + {file = "matplotlib-3.7.1-pp38-pypy38_pp73-macosx_10_12_x86_64.whl", hash = "sha256:3032884084f541163f295db8a6536e0abb0db464008fadca6c98aaf84ccf4717"}, + {file = "matplotlib-3.7.1-pp38-pypy38_pp73-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:3a2cb34336110e0ed8bb4f650e817eed61fa064acbefeb3591f1b33e3a84fd96"}, + {file = "matplotlib-3.7.1-pp38-pypy38_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:b867e2f952ed592237a1828f027d332d8ee219ad722345b79a001f49df0936eb"}, + {file = "matplotlib-3.7.1-pp38-pypy38_pp73-win_amd64.whl", hash = "sha256:57bfb8c8ea253be947ccb2bc2d1bb3862c2bccc662ad1b4626e1f5e004557042"}, + {file = "matplotlib-3.7.1-pp39-pypy39_pp73-macosx_10_12_x86_64.whl", hash = "sha256:438196cdf5dc8d39b50a45cb6e3f6274edbcf2254f85fa9b895bf85851c3a613"}, + {file = "matplotlib-3.7.1-pp39-pypy39_pp73-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:21e9cff1a58d42e74d01153360de92b326708fb205250150018a52c70f43c290"}, + {file = "matplotlib-3.7.1-pp39-pypy39_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:75d4725d70b7c03e082bbb8a34639ede17f333d7247f56caceb3801cb6ff703d"}, + {file = "matplotlib-3.7.1-pp39-pypy39_pp73-win_amd64.whl", hash = "sha256:97cc368a7268141afb5690760921765ed34867ffb9655dd325ed207af85c7529"}, + {file = "matplotlib-3.7.1.tar.gz", hash = "sha256:7b73305f25eab4541bd7ee0b96d87e53ae9c9f1823be5659b806cd85786fe882"}, +] + +[package.dependencies] +contourpy = ">=1.0.1" +cycler = ">=0.10" +fonttools = ">=4.22.0" +importlib-resources = {version = ">=3.2.0", markers = "python_version < \"3.10\""} +kiwisolver = ">=1.0.1" +numpy = ">=1.20" +packaging = ">=20.0" +pillow = ">=6.2.0" +pyparsing = ">=2.3.1" +python-dateutil = ">=2.7" + [[package]] name = "mdit-py-plugins" version = "0.3.5" @@ -1812,6 +2085,44 @@ nox = ">=2020.8.22" packaging = ">=20.9" tomlkit = ">=0.7" +[[package]] +name = "numpy" +version = "1.24.2" +description = "Fundamental package for array computing in Python" +category = "dev" +optional = false +python-versions = ">=3.8" +files = [ + {file = "numpy-1.24.2-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:eef70b4fc1e872ebddc38cddacc87c19a3709c0e3e5d20bf3954c147b1dd941d"}, + {file = "numpy-1.24.2-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:e8d2859428712785e8a8b7d2b3ef0a1d1565892367b32f915c4a4df44d0e64f5"}, + {file = "numpy-1.24.2-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:6524630f71631be2dabe0c541e7675db82651eb998496bbe16bc4f77f0772253"}, + {file = "numpy-1.24.2-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:a51725a815a6188c662fb66fb32077709a9ca38053f0274640293a14fdd22978"}, + {file = "numpy-1.24.2-cp310-cp310-win32.whl", hash = "sha256:2620e8592136e073bd12ee4536149380695fbe9ebeae845b81237f986479ffc9"}, + {file = "numpy-1.24.2-cp310-cp310-win_amd64.whl", hash = "sha256:97cf27e51fa078078c649a51d7ade3c92d9e709ba2bfb97493007103c741f1d0"}, + {file = "numpy-1.24.2-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:7de8fdde0003f4294655aa5d5f0a89c26b9f22c0a58790c38fae1ed392d44a5a"}, + {file = "numpy-1.24.2-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:4173bde9fa2a005c2c6e2ea8ac1618e2ed2c1c6ec8a7657237854d42094123a0"}, + {file = "numpy-1.24.2-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:4cecaed30dc14123020f77b03601559fff3e6cd0c048f8b5289f4eeabb0eb281"}, + {file = "numpy-1.24.2-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:9a23f8440561a633204a67fb44617ce2a299beecf3295f0d13c495518908e910"}, + {file = "numpy-1.24.2-cp311-cp311-win32.whl", hash = "sha256:e428c4fbfa085f947b536706a2fc349245d7baa8334f0c5723c56a10595f9b95"}, + {file = "numpy-1.24.2-cp311-cp311-win_amd64.whl", hash = "sha256:557d42778a6869c2162deb40ad82612645e21d79e11c1dc62c6e82a2220ffb04"}, + {file = "numpy-1.24.2-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:d0a2db9d20117bf523dde15858398e7c0858aadca7c0f088ac0d6edd360e9ad2"}, + {file = "numpy-1.24.2-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:c72a6b2f4af1adfe193f7beb91ddf708ff867a3f977ef2ec53c0ffb8283ab9f5"}, + {file = "numpy-1.24.2-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:c29e6bd0ec49a44d7690ecb623a8eac5ab8a923bce0bea6293953992edf3a76a"}, + {file = "numpy-1.24.2-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:2eabd64ddb96a1239791da78fa5f4e1693ae2dadc82a76bc76a14cbb2b966e96"}, + {file = "numpy-1.24.2-cp38-cp38-win32.whl", hash = "sha256:e3ab5d32784e843fc0dd3ab6dcafc67ef806e6b6828dc6af2f689be0eb4d781d"}, + {file = "numpy-1.24.2-cp38-cp38-win_amd64.whl", hash = "sha256:76807b4063f0002c8532cfeac47a3068a69561e9c8715efdad3c642eb27c0756"}, + {file = "numpy-1.24.2-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:4199e7cfc307a778f72d293372736223e39ec9ac096ff0a2e64853b866a8e18a"}, + {file = "numpy-1.24.2-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:adbdce121896fd3a17a77ab0b0b5eedf05a9834a18699db6829a64e1dfccca7f"}, + {file = "numpy-1.24.2-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:889b2cc88b837d86eda1b17008ebeb679d82875022200c6e8e4ce6cf549b7acb"}, + {file = "numpy-1.24.2-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f64bb98ac59b3ea3bf74b02f13836eb2e24e48e0ab0145bbda646295769bd780"}, + {file = "numpy-1.24.2-cp39-cp39-win32.whl", hash = "sha256:63e45511ee4d9d976637d11e6c9864eae50e12dc9598f531c035265991910468"}, + {file = "numpy-1.24.2-cp39-cp39-win_amd64.whl", hash = "sha256:a77d3e1163a7770164404607b7ba3967fb49b24782a6ef85d9b5f54126cc39e5"}, + {file = "numpy-1.24.2-pp38-pypy38_pp73-macosx_10_9_x86_64.whl", hash = "sha256:92011118955724465fb6853def593cf397b4a1367495e0b59a7e69d40c4eb71d"}, + {file = "numpy-1.24.2-pp38-pypy38_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f9006288bcf4895917d02583cf3411f98631275bc67cce355a7f39f8c14338fa"}, + {file = "numpy-1.24.2-pp38-pypy38_pp73-win_amd64.whl", hash = "sha256:150947adbdfeceec4e5926d956a06865c1c690f2fd902efede4ca6fe2e657c3f"}, + {file = "numpy-1.24.2.tar.gz", hash = "sha256:003a9f530e880cb2cd177cba1af7220b9aa42def9c4afc2a2fc3ee6be7eb2b22"}, +] + [[package]] name = "orjson" version = "3.8.10" @@ -1890,6 +2201,86 @@ files = [ {file = "packaging-22.0.tar.gz", hash = "sha256:2198ec20bd4c017b8f9717e00f0c8714076fc2fd93816750ab48e2c41de2cfd3"}, ] +[[package]] +name = "pillow" +version = "9.5.0" +description = "Python Imaging Library (Fork)" +category = "dev" +optional = false +python-versions = ">=3.7" +files = [ + {file = "Pillow-9.5.0-cp310-cp310-macosx_10_10_x86_64.whl", hash = "sha256:ace6ca218308447b9077c14ea4ef381ba0b67ee78d64046b3f19cf4e1139ad16"}, + {file = "Pillow-9.5.0-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:d3d403753c9d5adc04d4694d35cf0391f0f3d57c8e0030aac09d7678fa8030aa"}, + {file = "Pillow-9.5.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:5ba1b81ee69573fe7124881762bb4cd2e4b6ed9dd28c9c60a632902fe8db8b38"}, + {file = "Pillow-9.5.0-cp310-cp310-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:fe7e1c262d3392afcf5071df9afa574544f28eac825284596ac6db56e6d11062"}, + {file = "Pillow-9.5.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:8f36397bf3f7d7c6a3abdea815ecf6fd14e7fcd4418ab24bae01008d8d8ca15e"}, + {file = "Pillow-9.5.0-cp310-cp310-manylinux_2_28_aarch64.whl", hash = "sha256:252a03f1bdddce077eff2354c3861bf437c892fb1832f75ce813ee94347aa9b5"}, + {file = "Pillow-9.5.0-cp310-cp310-manylinux_2_28_x86_64.whl", hash = "sha256:85ec677246533e27770b0de5cf0f9d6e4ec0c212a1f89dfc941b64b21226009d"}, + {file = "Pillow-9.5.0-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:b416f03d37d27290cb93597335a2f85ed446731200705b22bb927405320de903"}, + {file = "Pillow-9.5.0-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:1781a624c229cb35a2ac31cc4a77e28cafc8900733a864870c49bfeedacd106a"}, + {file = "Pillow-9.5.0-cp310-cp310-win32.whl", hash = "sha256:8507eda3cd0608a1f94f58c64817e83ec12fa93a9436938b191b80d9e4c0fc44"}, + {file = "Pillow-9.5.0-cp310-cp310-win_amd64.whl", hash = "sha256:d3c6b54e304c60c4181da1c9dadf83e4a54fd266a99c70ba646a9baa626819eb"}, + {file = "Pillow-9.5.0-cp311-cp311-macosx_10_10_x86_64.whl", hash = "sha256:7ec6f6ce99dab90b52da21cf0dc519e21095e332ff3b399a357c187b1a5eee32"}, + {file = "Pillow-9.5.0-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:560737e70cb9c6255d6dcba3de6578a9e2ec4b573659943a5e7e4af13f298f5c"}, + {file = "Pillow-9.5.0-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:96e88745a55b88a7c64fa49bceff363a1a27d9a64e04019c2281049444a571e3"}, + {file = "Pillow-9.5.0-cp311-cp311-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:d9c206c29b46cfd343ea7cdfe1232443072bbb270d6a46f59c259460db76779a"}, + {file = "Pillow-9.5.0-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:cfcc2c53c06f2ccb8976fb5c71d448bdd0a07d26d8e07e321c103416444c7ad1"}, + {file = "Pillow-9.5.0-cp311-cp311-manylinux_2_28_aarch64.whl", hash = "sha256:a0f9bb6c80e6efcde93ffc51256d5cfb2155ff8f78292f074f60f9e70b942d99"}, + {file = "Pillow-9.5.0-cp311-cp311-manylinux_2_28_x86_64.whl", hash = "sha256:8d935f924bbab8f0a9a28404422da8af4904e36d5c33fc6f677e4c4485515625"}, + {file = "Pillow-9.5.0-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:fed1e1cf6a42577953abbe8e6cf2fe2f566daebde7c34724ec8803c4c0cda579"}, + {file = "Pillow-9.5.0-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:c1170d6b195555644f0616fd6ed929dfcf6333b8675fcca044ae5ab110ded296"}, + {file = "Pillow-9.5.0-cp311-cp311-win32.whl", hash = "sha256:54f7102ad31a3de5666827526e248c3530b3a33539dbda27c6843d19d72644ec"}, + {file = "Pillow-9.5.0-cp311-cp311-win_amd64.whl", hash = "sha256:cfa4561277f677ecf651e2b22dc43e8f5368b74a25a8f7d1d4a3a243e573f2d4"}, + {file = "Pillow-9.5.0-cp311-cp311-win_arm64.whl", hash = "sha256:965e4a05ef364e7b973dd17fc765f42233415974d773e82144c9bbaaaea5d089"}, + {file = "Pillow-9.5.0-cp312-cp312-win32.whl", hash = "sha256:22baf0c3cf0c7f26e82d6e1adf118027afb325e703922c8dfc1d5d0156bb2eeb"}, + {file = "Pillow-9.5.0-cp312-cp312-win_amd64.whl", hash = "sha256:432b975c009cf649420615388561c0ce7cc31ce9b2e374db659ee4f7d57a1f8b"}, + {file = "Pillow-9.5.0-cp37-cp37m-macosx_10_10_x86_64.whl", hash = "sha256:5d4ebf8e1db4441a55c509c4baa7a0587a0210f7cd25fcfe74dbbce7a4bd1906"}, + {file = "Pillow-9.5.0-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:375f6e5ee9620a271acb6820b3d1e94ffa8e741c0601db4c0c4d3cb0a9c224bf"}, + {file = "Pillow-9.5.0-cp37-cp37m-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:99eb6cafb6ba90e436684e08dad8be1637efb71c4f2180ee6b8f940739406e78"}, + {file = "Pillow-9.5.0-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:2dfaaf10b6172697b9bceb9a3bd7b951819d1ca339a5ef294d1f1ac6d7f63270"}, + {file = "Pillow-9.5.0-cp37-cp37m-manylinux_2_28_aarch64.whl", hash = "sha256:763782b2e03e45e2c77d7779875f4432e25121ef002a41829d8868700d119392"}, + {file = "Pillow-9.5.0-cp37-cp37m-manylinux_2_28_x86_64.whl", hash = "sha256:35f6e77122a0c0762268216315bf239cf52b88865bba522999dc38f1c52b9b47"}, + {file = "Pillow-9.5.0-cp37-cp37m-win32.whl", hash = "sha256:aca1c196f407ec7cf04dcbb15d19a43c507a81f7ffc45b690899d6a76ac9fda7"}, + {file = "Pillow-9.5.0-cp37-cp37m-win_amd64.whl", hash = "sha256:322724c0032af6692456cd6ed554bb85f8149214d97398bb80613b04e33769f6"}, + {file = "Pillow-9.5.0-cp38-cp38-macosx_10_10_x86_64.whl", hash = "sha256:a0aa9417994d91301056f3d0038af1199eb7adc86e646a36b9e050b06f526597"}, + {file = "Pillow-9.5.0-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:f8286396b351785801a976b1e85ea88e937712ee2c3ac653710a4a57a8da5d9c"}, + {file = "Pillow-9.5.0-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:c830a02caeb789633863b466b9de10c015bded434deb3ec87c768e53752ad22a"}, + {file = "Pillow-9.5.0-cp38-cp38-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:fbd359831c1657d69bb81f0db962905ee05e5e9451913b18b831febfe0519082"}, + {file = "Pillow-9.5.0-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f8fc330c3370a81bbf3f88557097d1ea26cd8b019d6433aa59f71195f5ddebbf"}, + {file = "Pillow-9.5.0-cp38-cp38-manylinux_2_28_aarch64.whl", hash = "sha256:7002d0797a3e4193c7cdee3198d7c14f92c0836d6b4a3f3046a64bd1ce8df2bf"}, + {file = "Pillow-9.5.0-cp38-cp38-manylinux_2_28_x86_64.whl", hash = "sha256:229e2c79c00e85989a34b5981a2b67aa079fd08c903f0aaead522a1d68d79e51"}, + {file = "Pillow-9.5.0-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:9adf58f5d64e474bed00d69bcd86ec4bcaa4123bfa70a65ce72e424bfb88ed96"}, + {file = "Pillow-9.5.0-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:662da1f3f89a302cc22faa9f14a262c2e3951f9dbc9617609a47521c69dd9f8f"}, + {file = "Pillow-9.5.0-cp38-cp38-win32.whl", hash = "sha256:6608ff3bf781eee0cd14d0901a2b9cc3d3834516532e3bd673a0a204dc8615fc"}, + {file = "Pillow-9.5.0-cp38-cp38-win_amd64.whl", hash = "sha256:e49eb4e95ff6fd7c0c402508894b1ef0e01b99a44320ba7d8ecbabefddcc5569"}, + {file = "Pillow-9.5.0-cp39-cp39-macosx_10_10_x86_64.whl", hash = "sha256:482877592e927fd263028c105b36272398e3e1be3269efda09f6ba21fd83ec66"}, + {file = "Pillow-9.5.0-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:3ded42b9ad70e5f1754fb7c2e2d6465a9c842e41d178f262e08b8c85ed8a1d8e"}, + {file = "Pillow-9.5.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:c446d2245ba29820d405315083d55299a796695d747efceb5717a8b450324115"}, + {file = "Pillow-9.5.0-cp39-cp39-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:8aca1152d93dcc27dc55395604dcfc55bed5f25ef4c98716a928bacba90d33a3"}, + {file = "Pillow-9.5.0-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:608488bdcbdb4ba7837461442b90ea6f3079397ddc968c31265c1e056964f1ef"}, + {file = "Pillow-9.5.0-cp39-cp39-manylinux_2_28_aarch64.whl", hash = "sha256:60037a8db8750e474af7ffc9faa9b5859e6c6d0a50e55c45576bf28be7419705"}, + {file = "Pillow-9.5.0-cp39-cp39-manylinux_2_28_x86_64.whl", hash = "sha256:07999f5834bdc404c442146942a2ecadd1cb6292f5229f4ed3b31e0a108746b1"}, + {file = "Pillow-9.5.0-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:a127ae76092974abfbfa38ca2d12cbeddcdeac0fb71f9627cc1135bedaf9d51a"}, + {file = "Pillow-9.5.0-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:489f8389261e5ed43ac8ff7b453162af39c3e8abd730af8363587ba64bb2e865"}, + {file = "Pillow-9.5.0-cp39-cp39-win32.whl", hash = "sha256:9b1af95c3a967bf1da94f253e56b6286b50af23392a886720f563c547e48e964"}, + {file = "Pillow-9.5.0-cp39-cp39-win_amd64.whl", hash = "sha256:77165c4a5e7d5a284f10a6efaa39a0ae8ba839da344f20b111d62cc932fa4e5d"}, + {file = "Pillow-9.5.0-pp38-pypy38_pp73-macosx_10_10_x86_64.whl", hash = "sha256:833b86a98e0ede388fa29363159c9b1a294b0905b5128baf01db683672f230f5"}, + {file = "Pillow-9.5.0-pp38-pypy38_pp73-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:aaf305d6d40bd9632198c766fb64f0c1a83ca5b667f16c1e79e1661ab5060140"}, + {file = "Pillow-9.5.0-pp38-pypy38_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:0852ddb76d85f127c135b6dd1f0bb88dbb9ee990d2cd9aa9e28526c93e794fba"}, + {file = "Pillow-9.5.0-pp38-pypy38_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:91ec6fe47b5eb5a9968c79ad9ed78c342b1f97a091677ba0e012701add857829"}, + {file = "Pillow-9.5.0-pp38-pypy38_pp73-win_amd64.whl", hash = "sha256:cb841572862f629b99725ebaec3287fc6d275be9b14443ea746c1dd325053cbd"}, + {file = "Pillow-9.5.0-pp39-pypy39_pp73-macosx_10_10_x86_64.whl", hash = "sha256:c380b27d041209b849ed246b111b7c166ba36d7933ec6e41175fd15ab9eb1572"}, + {file = "Pillow-9.5.0-pp39-pypy39_pp73-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:7c9af5a3b406a50e313467e3565fc99929717f780164fe6fbb7704edba0cebbe"}, + {file = "Pillow-9.5.0-pp39-pypy39_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5671583eab84af046a397d6d0ba25343c00cd50bce03787948e0fff01d4fd9b1"}, + {file = "Pillow-9.5.0-pp39-pypy39_pp73-manylinux_2_28_x86_64.whl", hash = "sha256:84a6f19ce086c1bf894644b43cd129702f781ba5751ca8572f08aa40ef0ab7b7"}, + {file = "Pillow-9.5.0-pp39-pypy39_pp73-win_amd64.whl", hash = "sha256:1e7723bd90ef94eda669a3c2c19d549874dd5badaeefabefd26053304abe5799"}, + {file = "Pillow-9.5.0.tar.gz", hash = "sha256:bf548479d336726d7a0eceb6e767e179fbde37833ae42794602631a070d630f1"}, +] + +[package.extras] +docs = ["furo", "olefile", "sphinx (>=2.4)", "sphinx-copybutton", "sphinx-inline-tabs", "sphinx-removed-in", "sphinxext-opengraph"] +tests = ["check-manifest", "coverage", "defusedxml", "markdown2", "olefile", "packaging", "pyroma", "pytest", "pytest-cov", "pytest-timeout"] + [[package]] name = "platformdirs" version = "2.6.2" @@ -2205,6 +2596,21 @@ cffi = ">=1.4.1" docs = ["sphinx (>=1.6.5)", "sphinx-rtd-theme"] tests = ["hypothesis (>=3.27.0)", "pytest (>=3.2.1,!=3.3.0)"] +[[package]] +name = "pyparsing" +version = "3.0.9" +description = "pyparsing module - Classes and methods to define and execute parsing grammars" +category = "dev" +optional = false +python-versions = ">=3.6.8" +files = [ + {file = "pyparsing-3.0.9-py3-none-any.whl", hash = "sha256:5026bae9a10eeaefb61dab2f09052b9f4307d44aee4eda64b309723d8d206bbc"}, + {file = "pyparsing-3.0.9.tar.gz", hash = "sha256:2b020ecf7d21b687f219b71ecad3631f644a47f01403fa1d1036b0c6416d70fb"}, +] + +[package.extras] +diagrams = ["jinja2", "railroad-diagrams"] + [[package]] name = "pyright" version = "1.1.303" @@ -2285,6 +2691,21 @@ pytest = ">=4.6" [package.extras] testing = ["fields", "hunter", "process-tests", "pytest-xdist", "six", "virtualenv"] +[[package]] +name = "python-dateutil" +version = "2.8.2" +description = "Extensions to the standard Python datetime module" +category = "dev" +optional = false +python-versions = "!=3.0.*,!=3.1.*,!=3.2.*,>=2.7" +files = [ + {file = "python-dateutil-2.8.2.tar.gz", hash = "sha256:0123cacc1627ae19ddf3c27a5de5bd67ee4586fbdd6440d9748f8abb483d3e86"}, + {file = "python_dateutil-2.8.2-py2.py3-none-any.whl", hash = "sha256:961d03dc3453ebbc59dbdea9e4e11c5651520a876d0f4db161e8674aae935da9"}, +] + +[package.dependencies] +six = ">=1.5" + [[package]] name = "python-dotenv" version = "1.0.0" @@ -2683,6 +3104,22 @@ files = [ lint = ["docutils-stubs", "flake8", "mypy"] test = ["pytest"] +[[package]] +name = "sphinxext-opengraph" +version = "0.8.2" +description = "Sphinx Extension to enable OGP support" +category = "dev" +optional = false +python-versions = ">=3.7" +files = [ + {file = "sphinxext-opengraph-0.8.2.tar.gz", hash = "sha256:45a693b6704052c426576f0a1f630649c55b4188bc49eb63e9587e24a923db39"}, + {file = "sphinxext_opengraph-0.8.2-py3-none-any.whl", hash = "sha256:6a05bdfe5176d9dd0a1d58a504f17118362ab976631213cd36fb44c4c40544c9"}, +] + +[package.dependencies] +matplotlib = "*" +sphinx = ">=4.0" + [[package]] name = "tomli" version = "2.0.1" @@ -3079,4 +3516,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "9c0df86bf38d46e2773a2e81f39096504ca54b294f93709f7098739974353178" +content-hash = "ece9e205daf1f2c8278fd2e9a8a91bc1b6e213f65a84aa3d898371ed55d567ef" diff --git a/pyproject.toml b/pyproject.toml index 22e760d2..6aaaa004 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -43,6 +43,7 @@ sphinx = "^6.1.3" myst-parser = "^1.0.0" sphinx-autobuild = "^2021.3.14" furo = "^2023.3.27" +sphinxext-opengraph = "^0.8.2" [tool.isort] profile = 'black' From 68c2e69195fa780d8d07e75f2e4e11bf8cd8920e Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Wed, 19 Apr 2023 14:35:55 -0700 Subject: [PATCH 027/184] [skip ci] Update Readme --- README.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index 5c59ad09..e22c4de3 100644 --- a/README.md +++ b/README.md @@ -54,13 +54,13 @@ If you would like to support me with projects like this, please consider starrin If you would like to get started, here are some links to help you with that: -- [Manual Deployment (Self Hosting)](https://kumiko-docs.vercel.app/docs/deployment/manual-deployment) +- [Trying out Kumiko](https://kumiko.readthedocs.io/en/latest/guides/user/trying-out.html) - [Contributing](contributing.md) -- [Documentation](https://kumiko-docs.vercel.app/) +- [Documentation](https://kumiko.readthedocs.io/) ## Resources and Links -- [Documentation](https://kumiko-docs.vercel.app/) +- [Documentation](https://kumiko.readthedocs.io/) - [Docker Hub](https://hub.docker.com/r/no767/kumiko) - [GHCR](https://github.com/No767/Kumiko/pkgs/container/kumiko) From 63eefd1a9514669edab77e5c0547656b47c8adab Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Wed, 19 Apr 2023 19:48:42 -0700 Subject: [PATCH 028/184] Now we have 4 context managers stacked up It's very cursed --- Bot/Cogs/economy.py | 40 ++++++- Bot/Cogs/reddit.py | 266 ++++++++++++++++++++------------------------ Bot/kumikobot.py | 25 +++-- Bot/kumikocore.py | 12 ++ schema.prisma | 69 ++++++------ 5 files changed, 219 insertions(+), 193 deletions(-) diff --git a/Bot/Cogs/economy.py b/Bot/Cogs/economy.py index 1e3a1d22..b501c600 100644 --- a/Bot/Cogs/economy.py +++ b/Bot/Cogs/economy.py @@ -1,9 +1,12 @@ +from typing import Union + import discord from discord.ext import commands from kumikocore import KumikoCore from Libs.economy import getUser from Libs.ui.economy import RegisterView from Libs.utils import Embed +from prisma.models import User class Economy(commands.Cog): @@ -23,18 +26,44 @@ async def marketplaceBuy(self, ctx: commands.Context) -> None: """Buy an item from the marketplace""" await ctx.send("Buy") + @eco.command(name="inventory", aliases=["inv"]) + async def marketplaceInv(self, ctx: commands.Context) -> None: + """View your marketplace inventory""" + currUser = await User.prisma().find_first( + where={"id": ctx.author.id}, include={"user_inv": True} + ) + if currUser is None: + await ctx.send( + embed=Embed( + title="No account!", + description="You don't even have an account yet!", + ) + ) + else: + if len() == 0: # type: ignore + await ctx.send( + embed=Embed( + title="No items!", + description="You don't have any items in your inventory!", + ) + ) + else: + await ctx.send( + embed=Embed(title="Inventory", description="Here are your items!") + ) + @commands.hybrid_command(name="register") - async def register(self, ctx: commands.Context) -> discord.Message: + async def register(self, ctx: commands.Context) -> None: """Create an account for the economy""" view = RegisterView() embed = Embed( title="Register", description="Register for the economy! Before you do so, please make sure to follow the TOS. By registering, you are agreeing to use these services.", ) - return await ctx.send(embed=embed, view=view) + await ctx.send(embed=embed, view=view) @commands.hybrid_command(name="wallet") - async def wallet(self, ctx: commands.Context) -> discord.Message: + async def wallet(self, ctx: commands.Context) -> Union[discord.Message, None]: """Checks your wallet""" user = await getUser(ctx.author.id) if user is None: @@ -43,11 +72,12 @@ async def wallet(self, ctx: commands.Context) -> discord.Message: title="No Wallet", description="You don't have a wallet yet!" ) ) + userDesc = f"**Rank**: {user['rank']}\n\n**Balance**: {user['petals']}" embed = Embed( title=f"{ctx.author.name}'s Wallet", - description=f"Balance: {user['petals']}", + description=userDesc, ) - return await ctx.send(embed=embed) + await ctx.send(embed=embed) async def setup(bot: KumikoCore) -> None: diff --git a/Bot/Cogs/reddit.py b/Bot/Cogs/reddit.py index 9da0e39d..e413eb0d 100644 --- a/Bot/Cogs/reddit.py +++ b/Bot/Cogs/reddit.py @@ -1,29 +1,21 @@ -import os from datetime import datetime from typing import Literal, Optional -import aiohttp -import asyncpraw import orjson from discord import app_commands from discord.ext import commands from discord.utils import format_dt -from dotenv import load_dotenv from kumikocore import KumikoCore from Libs.utils import parseSubreddit from Libs.utils.pages import EmbedListSource, KumikoPages -load_dotenv() - -REDDIT_ID = os.environ["REDDIT_ID"] -REDDIT_SECRET = os.environ["REDDIT_SECRET"] - class Reddit(commands.Cog): """Search, and view posts and memes from Reddit""" def __init__(self, bot: KumikoCore) -> None: self.bot = bot + self.prawReddit = self.bot.reddit_session @commands.hybrid_group(name="reddit") async def reddit(self, ctx: commands.Context) -> None: @@ -40,40 +32,33 @@ async def redditSearch( self, ctx: commands.Context, *, search: str, subreddit: Optional[str] = "all" ) -> None: """Searches for posts on Reddit""" - async with asyncpraw.Reddit( - client_id=REDDIT_ID, - client_secret=REDDIT_SECRET, - user_agent="Kumiko (by /u/No767)", - ) as reddit: - sub = await reddit.subreddit(parseSubreddit(subreddit)) - data = [ - { - "title": post.title, - "description": post.selftext, - "image": post.url, - "fields": [ - {"name": "Author", "value": post.author}, - {"name": "Upvotes", "value": post.score}, - {"name": "NSFW", "value": post.over_18}, - {"name": "Flair", "value": post.link_flair_text}, - {"name": "Number of Comments", "value": post.num_comments}, - { - "name": "Reddit URL", - "value": f"https://reddit.com{post.permalink}", - }, - { - "name": "Created At", - "value": format_dt( - datetime.fromtimestamp(post.created_utc) - ), - }, - ], - } - async for post in sub.search(search) - ] - embedSource = EmbedListSource(data, per_page=1) - pages = KumikoPages(source=embedSource, ctx=ctx) - await pages.start() + sub = await self.prawReddit.subreddit(parseSubreddit(subreddit)) + data = [ + { + "title": post.title, + "description": post.selftext, + "image": post.url, + "fields": [ + {"name": "Author", "value": post.author}, + {"name": "Upvotes", "value": post.score}, + {"name": "NSFW", "value": post.over_18}, + {"name": "Flair", "value": post.link_flair_text}, + {"name": "Number of Comments", "value": post.num_comments}, + { + "name": "Reddit URL", + "value": f"https://reddit.com{post.permalink}", + }, + { + "name": "Created At", + "value": format_dt(datetime.fromtimestamp(post.created_utc)), + }, + ], + } + async for post in sub.search(search) + ] + embedSource = EmbedListSource(data, per_page=1) + pages = KumikoPages(source=embedSource, ctx=ctx) + await pages.start() @reddit.command(name="eggirl") @app_commands.describe(filter="Sort filters. Defaults to New") @@ -83,47 +68,40 @@ async def redditEggIRL( filter: Optional[Literal["New", "Hot", "Rising"]] = "New", ) -> None: """Literally just shows you r/egg_irl posts. No comment.""" - async with asyncpraw.Reddit( - client_id=REDDIT_ID, - client_secret=REDDIT_SECRET, - user_agent="Kumiko (by /u/No767)", - ) as reddit: - sub = await reddit.subreddit(parseSubreddit("egg_irl")) - subGen = ( - sub.new(limit=25) - if filter == "New" - else sub.hot(limit=25) - if filter == "Hot" - else sub.rising(limit=25) - ) - data = [ - { - "title": post.title, - "description": post.selftext, - "image": post.url, - "fields": [ - {"name": "Author", "value": post.author}, - {"name": "Upvotes", "value": post.score}, - {"name": "NSFW", "value": post.over_18}, - {"name": "Flair", "value": post.link_flair_text}, - {"name": "Number of Comments", "value": post.num_comments}, - { - "name": "Reddit URL", - "value": f"https://reddit.com{post.permalink}", - }, - { - "name": "Created At", - "value": format_dt( - datetime.fromtimestamp(post.created_utc) - ), - }, - ], - } - async for post in subGen - ] - embedSource = EmbedListSource(data, per_page=1) - pages = KumikoPages(source=embedSource, ctx=ctx) - await pages.start() + sub = await self.prawReddit.subreddit(parseSubreddit("egg_irl")) + subGen = ( + sub.new(limit=10) + if filter == "New" + else sub.hot(limit=10) + if filter == "Hot" + else sub.rising(limit=10) + ) + data = [ + { + "title": post.title, + "description": post.selftext, + "image": post.url, + "fields": [ + {"name": "Author", "value": post.author}, + {"name": "Upvotes", "value": post.score}, + {"name": "NSFW", "value": post.over_18}, + {"name": "Flair", "value": post.link_flair_text}, + {"name": "Number of Comments", "value": post.num_comments}, + { + "name": "Reddit URL", + "value": f"https://reddit.com{post.permalink}", + }, + { + "name": "Created At", + "value": format_dt(datetime.fromtimestamp(post.created_utc)), + }, + ], + } + async for post in subGen + ] + embedSource = EmbedListSource(data, per_page=1) + pages = KumikoPages(source=embedSource, ctx=ctx) + await pages.start() @reddit.command(name="feed") @app_commands.describe( @@ -136,47 +114,40 @@ async def redditFeed( filter: Optional[Literal["New", "Hot", "Rising"]] = "New", ) -> None: """Gets a feed of posts from a subreddit""" - async with asyncpraw.Reddit( - client_id=REDDIT_ID, - client_secret=REDDIT_SECRET, - user_agent="Kumiko (by /u/No767)", - ) as reddit: - sub = await reddit.subreddit(parseSubreddit(subreddit)) - subGen = ( - sub.new(limit=25) - if filter == "New" - else sub.hot(limit=25) - if filter == "Hot" - else sub.rising(limit=25) - ) - data = [ - { - "title": post.title, - "description": post.selftext, - "image": post.url, - "fields": [ - {"name": "Author", "value": post.author}, - {"name": "Upvotes", "value": post.score}, - {"name": "NSFW", "value": post.over_18}, - {"name": "Flair", "value": post.link_flair_text}, - {"name": "Number of Comments", "value": post.num_comments}, - { - "name": "Reddit URL", - "value": f"https://reddit.com{post.permalink}", - }, - { - "name": "Created At", - "value": format_dt( - datetime.fromtimestamp(post.created_utc) - ), - }, - ], - } - async for post in subGen - ] - embedSource = EmbedListSource(data, per_page=1) - pages = KumikoPages(source=embedSource, ctx=ctx) - await pages.start() + sub = await self.prawReddit.subreddit(parseSubreddit(subreddit)) + subGen = ( + sub.new(limit=10) + if filter == "New" + else sub.hot(limit=10) + if filter == "Hot" + else sub.rising(limit=10) + ) + data = [ + { + "title": post.title, + "description": post.selftext, + "image": post.url, + "fields": [ + {"name": "Author", "value": post.author}, + {"name": "Upvotes", "value": post.score}, + {"name": "NSFW", "value": post.over_18}, + {"name": "Flair", "value": post.link_flair_text}, + {"name": "Number of Comments", "value": post.num_comments}, + { + "name": "Reddit URL", + "value": f"https://reddit.com{post.permalink}", + }, + { + "name": "Created At", + "value": format_dt(datetime.fromtimestamp(post.created_utc)), + }, + ], + } + async for post in subGen + ] + embedSource = EmbedListSource(data, per_page=1) + pages = KumikoPages(source=embedSource, ctx=ctx) + await pages.start() @reddit.command(name="memes") @app_commands.describe( @@ -187,29 +158,28 @@ async def searchMemes( self, ctx: commands.Context, subreddit: str, amount: Optional[int] = 5 ) -> None: """Searches for memes on Reddit""" - async with aiohttp.ClientSession() as session: - async with session.get( - f"https://meme-api.com/gimme/{parseSubreddit(subreddit)}/{amount}" - ) as r: - data = await r.json(loads=orjson.loads) - mainData = [ - { - "title": item["title"], - "image": item["url"], - "fields": [ - {"name": "Author", "value": item["author"]}, - {"name": "Subreddit", "value": item["subreddit"]}, - {"name": "Upvotes", "value": item["ups"]}, - {"name": "NSFW", "value": item["nsfw"]}, - {"name": "Spoiler", "value": item["spoiler"]}, - {"name": "Reddit URL", "value": item["postLink"]}, - ], - } - for item in data["memes"] - ] - embedSource = EmbedListSource(mainData, per_page=1) - pages = KumikoPages(source=embedSource, ctx=ctx) - await pages.start() + async with self.bot.session.get( + f"https://meme-api.com/gimme/{parseSubreddit(subreddit)}/{amount}" + ) as r: + data = await r.json(loads=orjson.loads) + mainData = [ + { + "title": item["title"], + "image": item["url"], + "fields": [ + {"name": "Author", "value": item["author"]}, + {"name": "Subreddit", "value": item["subreddit"]}, + {"name": "Upvotes", "value": item["ups"]}, + {"name": "NSFW", "value": item["nsfw"]}, + {"name": "Spoiler", "value": item["spoiler"]}, + {"name": "Reddit URL", "value": item["postLink"]}, + ], + } + for item in data["memes"] + ] + embedSource = EmbedListSource(mainData, per_page=1) + pages = KumikoPages(source=embedSource, ctx=ctx) + await pages.start() async def setup(bot: KumikoCore) -> None: diff --git a/Bot/kumikobot.py b/Bot/kumikobot.py index 76c23b1c..7d5c63b3 100644 --- a/Bot/kumikobot.py +++ b/Bot/kumikobot.py @@ -1,6 +1,7 @@ import logging import os +import asyncpraw import discord from aiohttp import ClientSession from anyio import run @@ -11,6 +12,10 @@ load_dotenv() + +REDDIT_ID = os.environ["REDDIT_ID"] +REDDIT_SECRET = os.environ["REDDIT_SECRET"] + KUMIKO_TOKEN = os.environ["DEV_BOT_TOKEN"] DEV_MODE = os.getenv("DEV_MODE") in ("True", "TRUE") intents = discord.Intents.default() @@ -31,13 +36,19 @@ async def main() -> None: transport=AIOHTTPTransport(url="https://graphql.anilist.co/"), fetch_schema_from_transport=True, ) as gql_session: - async with KumikoCore( - intents=intents, - session=session, - gql_session=gql_session, - dev_mode=DEV_MODE, - ) as bot: - await bot.start(KUMIKO_TOKEN) + async with asyncpraw.Reddit( + client_id=REDDIT_ID, + client_secret=REDDIT_SECRET, + user_agent="Kumiko (by /u/No767)", + ) as reddit: + async with KumikoCore( + intents=intents, + session=session, + gql_session=gql_session, + reddit_session=reddit, + dev_mode=DEV_MODE, + ) as bot: + await bot.start(KUMIKO_TOKEN) if __name__ == "__main__": diff --git a/Bot/kumikocore.py b/Bot/kumikocore.py index c964bfda..61798711 100644 --- a/Bot/kumikocore.py +++ b/Bot/kumikocore.py @@ -5,6 +5,7 @@ import discord from aiohttp import ClientSession from anyio import Path +from asyncpraw import Reddit from discord.ext import commands from gql.client import AsyncClientSession, ReconnectingAsyncClientSession from Libs.utils.help import KumikoHelpPaginated @@ -26,6 +27,7 @@ def __init__( intents: discord.Intents, session: ClientSession, gql_session: Union[ReconnectingAsyncClientSession, AsyncClientSession], + reddit_session: Reddit, dev_mode: bool = False, *args, **kwargs, @@ -41,6 +43,7 @@ def __init__( self.dev_mode = dev_mode self._session = session self._gql_session = gql_session + self._reddit_session = reddit_session self.logger: logging.Logger = logging.getLogger("kumikobot") @property @@ -63,6 +66,15 @@ def gql_session(self) -> Union[ReconnectingAsyncClientSession, AsyncClientSessio """ return self._gql_session + @property + def reddit_session(self) -> Reddit: + """A global Reddit session used throughout the lifetime of the bot + + Returns: + Reddit: The current Reddit session + """ + return self._reddit_session + async def fsWatcher(self) -> None: cogsPath = SyncPath(__file__).parent.joinpath("Cogs") async for changes in awatch(cogsPath): diff --git a/schema.prisma b/schema.prisma index efcd2b36..2ab24cb9 100644 --- a/schema.prisma +++ b/schema.prisma @@ -9,55 +9,34 @@ generator client { } model User { - id BigInt @id @unique - name String - rank Int @default(0) - petals Int @default(0) - date_joined DateTime @default(now()) - marketplace Marketplace? // A user can also optionally own a marketplace - inv Inv[] // Give the user a default inventory that has one item that is worth 0 petals + id BigInt @id @unique + name String + rank Int @default(0) + petals Int @default(0) + date_joined DateTime @default(now()) + marketplace Marketplace? // A user can also optionally own a marketplace + user_inv UserInv[] // Give the user a default inventory that has one item that is worth 0 petals // quests Quest[] // This default quest may be used to get the user to explore the marketplace // QuestClaimer QuestClaimer? // A user can only claim one quest } -// model QuestClaimer { -// id BigInt @id @unique -// user User @relation(fields: [user_id], references: [id]) -// user_id BigInt @unique -// claimed_at DateTime -// quest Quest[] -// } - -model Inv { +model UserInv { id BigInt @id @unique user User @relation(fields: [user_id], references: [id]) + items Item[] user_id BigInt + amount Int } -// model Quest { -// id String @id @default(uuid()) -// author User @relation(fields: [author_id], references: [id]) -// author_id BigInt -// claimer QuestClaimer @relation(fields: [claimer_id], references: [id]) -// claimer_id BigInt -// name String -// description String @db.Text -// reward Int @default(0) -// active Boolean @default(true) -// claimed Boolean @default(false) -// date_created DateTime @default(now()) -// date_completed DateTime? -// end_datetime DateTime? -// } - model Item { id String @id @default(uuid()) marketplace Marketplace @relation(fields: [marketplace_id], references: [id]) marketplace_id String + user_inv UserInv @relation(fields: [user_inv_id], references: [id]) + user_inv_id BigInt name String description String @db.Text price Float - amount Int } model Marketplace { @@ -69,3 +48,27 @@ model Marketplace { owner_id BigInt @unique items Item[] } + +// model QuestClaimer { +// id BigInt @id @unique +// user User @relation(fields: [user_id], references: [id]) +// user_id BigInt @unique +// claimed_at DateTime +// quest Quest[] +// } + +// model Quest { +// id String @id @default(uuid()) +// author User @relation(fields: [author_id], references: [id]) +// author_id BigInt +// claimer QuestClaimer @relation(fields: [claimer_id], references: [id]) +// claimer_id BigInt +// name String +// description String @db.Text +// reward Int @default(0) +// active Boolean @default(true) +// claimed Boolean @default(false) +// date_created DateTime @default(now()) +// date_completed DateTime? +// end_datetime DateTime? +// } From 095e123bf6531e231585c471a82503ac07f34fce Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Wed, 19 Apr 2023 20:14:51 -0700 Subject: [PATCH 029/184] [skip ci] Fix some linting issues --- Bot/Libs/economy/cache_utils.py | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/Bot/Libs/economy/cache_utils.py b/Bot/Libs/economy/cache_utils.py index ee450110..2382de60 100644 --- a/Bot/Libs/economy/cache_utils.py +++ b/Bot/Libs/economy/cache_utils.py @@ -13,9 +13,7 @@ prefix="cache", namespace="kumiko", id=uuid.uuid4(), command="internal_get_user" ), ) -async def getUser( - user_id: int, includes: UserInclude = {"inv": False, "marketplace": False} -) -> Union[Dict, None]: +async def getUser(user_id: int, includes: UserInclude) -> Union[Dict, None]: """[Coroutine] Helper coroutine to obtain a user's profile from the database For reducing the latency for accessing the data, this helper coroutine is cached on Redis (w/ RedisJSON). Also note that this coroutine expects that the Prisma query engine and database are already connected. From 92e9a8ca6bf717116c51ae894da572b8b489c5dd Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Wed, 19 Apr 2023 20:55:41 -0700 Subject: [PATCH 030/184] Remove old eco, ui, and eco utils packages --- Bot/Libs/kumiko_economy/__init__.py | 11 - Bot/Libs/kumiko_economy/cache_utils.py | 88 --- Bot/Libs/kumiko_economy/models.py | 120 --- Bot/Libs/kumiko_economy_utils/__init__.py | 25 - .../kumiko_economy_utils/auction_house.py | 325 -------- Bot/Libs/kumiko_economy_utils/checkers.py | 72 -- Bot/Libs/kumiko_economy_utils/db_base.py | 3 - Bot/Libs/kumiko_economy_utils/eco_main.py | 239 ------ Bot/Libs/kumiko_economy_utils/eco_user.py | 188 ----- .../marketplace_models.py | 29 - Bot/Libs/kumiko_economy_utils/models.py | 103 --- Bot/Libs/kumiko_economy_utils/quests_utils.py | 375 --------- Bot/Libs/kumiko_economy_utils/user_inv.py | 171 ----- Bot/Libs/kumiko_ui_components/__init__.py | 43 -- Bot/Libs/kumiko_ui_components/modals.py | 721 ------------------ Bot/Libs/kumiko_ui_components/views.py | 452 ----------- 16 files changed, 2965 deletions(-) delete mode 100644 Bot/Libs/kumiko_economy/__init__.py delete mode 100644 Bot/Libs/kumiko_economy/cache_utils.py delete mode 100644 Bot/Libs/kumiko_economy/models.py delete mode 100644 Bot/Libs/kumiko_economy_utils/__init__.py delete mode 100644 Bot/Libs/kumiko_economy_utils/auction_house.py delete mode 100644 Bot/Libs/kumiko_economy_utils/checkers.py delete mode 100644 Bot/Libs/kumiko_economy_utils/db_base.py delete mode 100644 Bot/Libs/kumiko_economy_utils/eco_main.py delete mode 100644 Bot/Libs/kumiko_economy_utils/eco_user.py delete mode 100644 Bot/Libs/kumiko_economy_utils/marketplace_models.py delete mode 100644 Bot/Libs/kumiko_economy_utils/models.py delete mode 100644 Bot/Libs/kumiko_economy_utils/quests_utils.py delete mode 100644 Bot/Libs/kumiko_economy_utils/user_inv.py delete mode 100644 Bot/Libs/kumiko_ui_components/__init__.py delete mode 100644 Bot/Libs/kumiko_ui_components/modals.py delete mode 100644 Bot/Libs/kumiko_ui_components/views.py diff --git a/Bot/Libs/kumiko_economy/__init__.py b/Bot/Libs/kumiko_economy/__init__.py deleted file mode 100644 index c747efc0..00000000 --- a/Bot/Libs/kumiko_economy/__init__.py +++ /dev/null @@ -1,11 +0,0 @@ -from .cache_utils import KumikoEconomyCacheUtils -from .models import EcoAuctionHouse, EcoMarketplace, EcoQuests, EcoUser, EcoUserInv - -__all__ = [ - "EcoUser", - "EcoUserInv", - "EcoQuests", - "EcoAuctionHouse", - "EcoMarketplace", - "KumikoEconomyCacheUtils", -] diff --git a/Bot/Libs/kumiko_economy/cache_utils.py b/Bot/Libs/kumiko_economy/cache_utils.py deleted file mode 100644 index 836d5447..00000000 --- a/Bot/Libs/kumiko_economy/cache_utils.py +++ /dev/null @@ -1,88 +0,0 @@ -from typing import Dict, List, Union - -import simdjson -from kumiko_cache import KumikoCache, commandKeyBuilder -from tortoise.contrib.pydantic import pydantic_model_creator, pydantic_queryset_creator - -from .models import EcoMarketplace, EcoUser - - -class KumikoEconomyCacheUtils: - """Cache utilities used by Kumiko for her economy system""" - - def __init__(self, uri: str, models: List, redis_host: str, redis_port: int): - self.self = self - self.uri = uri - self.models = models - self.redis_host = redis_host - self.redis_port = redis_port - self.cache = KumikoCache(connection_pool=None, host=redis_host, port=redis_port) - - async def cacheUser(self, user_id: int, command_name: str) -> Union[Dict, None]: - """The abstraction layer for caching the requested user's data - - The purpose of this is a helper coroutine that caches the guild data if not cached. - If cached, it will return the cached data. - - Args: - user_id (int): Discord User ID - command_name (str): _description_ - - Returns: - Union[Dict, None]: _description_ - """ - key = commandKeyBuilder( - prefix="cache", - namespace="kumiko", - id=user_id, - command=f"{command_name}".replace(" ", "-"), - ) - if await self.cache.cacheExists(key=key) is False: - pydanticUserBridgeData = pydantic_model_creator(EcoUser) - userData = await EcoUser.filter(user_id=user_id).get_or_none() - if userData is None: - return None - userS = await pydanticUserBridgeData.from_tortoise_orm(userData) - await self.cache.setBasicCommandCache(key=key, value=userS.json(), ttl=15) - return userS.dict() - else: - jsonParser = simdjson.Parser() - return jsonParser.parse( - await self.cache.getBasicCommandCache(key=key), recursive=True - ) - - async def cacheMarketplace( - self, user_id: int, command_name: str - ) -> Union[Dict, None]: - """The abstraction layer for caching the requested user's data - - The purpose of this is a helper coroutine that caches the guild data if not cached. - If cached, it will return the cached data. - - Args: - user_id (int): Discord User ID - command_name (str): - - Returns: - Union[Dict, None]: _description_ - """ - key = commandKeyBuilder( - prefix="cache", - namespace="kumiko", - id=user_id, - command=f"{command_name}".replace(" ", "-"), - ) - jsonParser = simdjson.Parser() - if await self.cache.cacheExists(key=key) is False: - pydanticMarketplaceData = pydantic_queryset_creator(EcoMarketplace) - marketplaceS = await pydanticMarketplaceData.from_queryset( - EcoMarketplace.all().limit(25) - ) - mJson = marketplaceS.json() - parsedData = jsonParser.parse(mJson, recursive=True) - await self.cache.setBasicCommandCache(key=key, value=mJson, ttl=15) - return parsedData - else: - return jsonParser.parse( - await self.cache.getBasicCommandCache(key=key), recursive=True - ) diff --git a/Bot/Libs/kumiko_economy/models.py b/Bot/Libs/kumiko_economy/models.py deleted file mode 100644 index f6e216e1..00000000 --- a/Bot/Libs/kumiko_economy/models.py +++ /dev/null @@ -1,120 +0,0 @@ -import orjson -from pydantic.main import BaseConfig as PydanticBaseConfig -from tortoise import fields -from tortoise.models import Model - - -class EcoJSONConfig(PydanticBaseConfig): - json_loads = orjson.loads - json_dumps = orjson.dumps - - -class EcoUser(Model): - user_id = fields.BigIntField(pk=True) - user_inv: fields.ReverseRelation["EcoUserInv"] - quests: fields.ReverseRelation["EcoQuests"] - auction_house: fields.ReverseRelation["EcoAuctionHouse"] - marketplace: fields.ReverseRelation["EcoMarketplace"] - username = fields.CharField(max_length=255) - lavender_petals = fields.BigIntField(default=0) - rank = fields.IntField(default=0) - date_joined = fields.DatetimeField(auto_now_add=True) - - class Meta: - table = "eco_user" - - class PydanticMeta: - config_class = EcoJSONConfig - - def __str__(self): - return f"EcoUser({self.user_id}, {self.user_inv}, {self.quests}, {self.auction_house}, {self.marketplace}, {self.username}, {self.lavender_petals}, {self.rank}, {self.date_joined})" - - -class EcoUserInv(Model): - id = fields.UUIDField(pk=True) - user: fields.ForeignKeyRelation["EcoUser"] = fields.ForeignKeyField( - "models.EcoUser", related_name="user_inv", on_delete=fields.CASCADE - ) - item_uuid = fields.UUIDField() - name = fields.CharField(max_length=255) - description = fields.TextField() - amount = fields.IntField() - date_acquired = fields.DatetimeField(auto_now_add=True) - - class Meta: - table = "eco_user_inv" - - class PydanticMeta: - config_class = EcoJSONConfig - - def __str__(self): - return f"EcoUserInv({self.id}, {self.user}, {self.item_uuid}, {self.name}, {self.description}, {self.amount}, {self.date_acquired})" - - -class EcoQuests(Model): - id = fields.UUIDField(pk=True) - creator: fields.ForeignKeyRelation["EcoUser"] = fields.ForeignKeyField( - "models.EcoUser", related_name="quests", on_delete=fields.CASCADE - ) - claimer_id = fields.BigIntField(null=True) - date_created = fields.DatetimeField(auto_now_add=True) - name = fields.CharField(max_length=255) - description = fields.TextField() - end_datetime = fields.DatetimeField(auto_now_add=True) - reward = fields.IntField() - active = fields.BooleanField(default=True) - claimed = fields.BooleanField(default=False) - - class Meta: - table = "eco_quests" - - class PydanticMeta: - config_class = EcoJSONConfig - - def __str__(self): - return f"EcoQuests({self.id}, {self.creator}, {self.claimer_id}, {self.date_created}, {self.name}, {self.description}, {self.end_datetime}, {self.reward}, {self.active}, {self.claimed})" - - -class EcoAuctionHouse(Model): - id = fields.UUIDField(pk=True) - owner: fields.ForeignKeyRelation["EcoUser"] = fields.ForeignKeyField( - "models.EcoUser", related_name="auction_house", on_delete=fields.CASCADE - ) - name = fields.CharField(max_length=255) - description = fields.TextField() - price = fields.IntField() - date_added = fields.DatetimeField(auto_now_add=True) - passed = fields.BooleanField(default=False) - - class Meta: - table = "eco_auction_house" - - class PydanticMeta: - config_class = EcoJSONConfig - - def __str__(self): - return f"EcoAuctionHouse({self.id}, {self.owner}, {self.name}, {self.description}, {self.price}, {self.date_added}, {self.passed})" - - -class EcoMarketplace(Model): - id = fields.UUIDField(pk=True) - owner: fields.ForeignKeyRelation["EcoUser"] = fields.ForeignKeyField( - "models.EcoUser", related_name="marketplace", on_delete=fields.CASCADE - ) - owner_name = fields.CharField(max_length=255) - date_added = fields.DatetimeField(auto_now_add=True) - name = fields.CharField(max_length=255) - description = fields.TextField() - price = fields.IntField() - amount = fields.IntField() - updated_price = fields.BooleanField(default=False) - - class Meta: - table = "eco_marketplace" - - class PydanticMeta: - config_class = EcoJSONConfig - exclude = ("id",) - - def __str__(self): - return f"EcoMarketplace({self.id}, {self.owner}, {self.owner_name}, {self.date_added}, {self.name}, {self.description}, {self.price}, {self.amount}, {self.updated_price})" diff --git a/Bot/Libs/kumiko_economy_utils/__init__.py b/Bot/Libs/kumiko_economy_utils/__init__.py deleted file mode 100644 index 1428229b..00000000 --- a/Bot/Libs/kumiko_economy_utils/__init__.py +++ /dev/null @@ -1,25 +0,0 @@ -from .auction_house import KumikoAuctionHouseUtils -from .checkers import AHChecker, QuestsChecker -from .eco_main import KumikoEcoUtils -from .eco_user import KumikoEcoUserUtils -from .marketplace_models import ItemAuthProject, MarketplaceModel, PurchaseProject -from .models import AuctionHouseItem, KumikoEcoUser, KumikoQuests, UserInv -from .quests_utils import KumikoQuestsUtils -from .user_inv import KumikoUserInvUtils - -__all__ = [ - "KumikoEcoUtils", - "KumikoEcoUserUtils", - "KumikoAuctionHouseUtils", - "KumikoQuestsUtils", - "KumikoUserInvUtils", - "AuctionHouseItem", - "KumikoEcoUser", - "KumikoQuests", - "UserInv", - "MarketplaceModel", - "PurchaseProject", - "ItemAuthProject", - "QuestsChecker", - "AHChecker", -] diff --git a/Bot/Libs/kumiko_economy_utils/auction_house.py b/Bot/Libs/kumiko_economy_utils/auction_house.py deleted file mode 100644 index dd592563..00000000 --- a/Bot/Libs/kumiko_economy_utils/auction_house.py +++ /dev/null @@ -1,325 +0,0 @@ -import asyncio - -import uvloop -from coredis import Redis -from sqlalchemy import delete, select, update -from sqlalchemy.ext.asyncio import AsyncSession, create_async_engine -from sqlalchemy.orm import sessionmaker - -from . import models -from .db_base import Base - - -class KumikoAuctionHouseUtils: - def __init__(self): - self.self = self - - async def getItemKey( - self, key: str, db: int, redis_server_ip: str, redis_port: int - ): - """Gets the keys for an item within Redis - - Args: - key (str): The key to get - db (int): The database to get the key from - redis_server_ip (str): The Redis server IP - redis_port (int): The Redis server port - """ - conn = Redis(host=redis_server_ip, port=int(redis_port), db=db) - return await conn.get(key) - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def setItemKey( - self, - key: str, - value: int, - db: int, - ttl: int, - redis_server_ip: str, - redis_port: int, - ): - """Sets that key within Redis - - Args: - key (str): The key to set - value (int): The value to set - db (int): The database to set the key in - ttl (int): The TTL or expire time of the key - redis_server_ip (str): The Redis server IP - redis_port (int): The Redis server port - """ - conn = Redis(host=redis_server_ip, port=int(redis_port), db=db) - await conn.set(key=key, value=str(value), ex=ttl) - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def initAHTables(self, uri: str): - """Coroutine for creating AH tables - - Args: - uri (str): DB Connection URI - """ - engine = create_async_engine( - uri, - ) - async with engine.begin() as conn: - await conn.run_sync(Base.metadata.create_all) - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def addAuctionHouseItem( - self, - uuid: str, - user_id: int, - name: str, - description: str, - date_added: str, - price: int, - passed: bool, - uri: str, - ): - """Adds an item to the Auction House DB - - Args: - uuid (str): UUID of the item - user_id (int): Discord User ID - name (str): Name of the item - description (str): Description of the item - date_added (str / ISO-8601): The date that it was added - price (int): The base bidding price of the item - passed (bool): Whether or not the item has been passed - uri (str): DB Connection URI - """ - engine = create_async_engine(uri) - - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - auctionHouseItem = models.AuctionHouseItem( - uuid=uuid, - user_id=user_id, - name=name, - description=description, - date_added=date_added, - price=price, - passed=passed, - ) - session.add_all([auctionHouseItem]) - await session.commit() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def obtainItemUUIDAuth(self, user_id: int, uri: str): - """Obtains the UUID of an AH Item for auth purposes - - Args: - uri (str): DB Connection URI - """ - engine = create_async_engine(uri) - - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - selectItem = select(models.AuctionHouseItem.uuid).filter( - models.AuctionHouseItem.user_id == user_id - ) - res = await session.execute(selectItem) - return [row for row in res.scalars()] - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def obtainAHItemPassed(self, passed: bool, uri: str): - """Obtains the date from each item. This is needed after to purge - the item once it has expired. - - Args: - passed (bool): Whether or not the item has passed the time limit - uri (str): DB Connection URI - """ - engine = create_async_engine(uri) - - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - selItem = select(models.AuctionHouseItem).filter( - models.AuctionHouseItem.passed == passed - ) - res = await session.execute(selItem) - return [row for row in res.scalars()] - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def setAHItemBoolean(self, uuid: str, passed: bool, uri: str): - """Sets the passed col to a boolean value. This means that the - item probably has passed it's listing date. The item is not - purged from the db. - - Args: - uuid (str): Auction House Item UUID - passed (bool): Whether to set it to be passed or not - uri (str): DB Connection URI - """ - engine = create_async_engine(uri) - - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - updateItem = update( - models.AuctionHouseItem, - values={models.AuctionHouseItem.passed: passed}, - ).filter(models.AuctionHouseItem.uuid == uuid) - await session.execute(updateItem) - await session.commit() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def selectItemNotPassed(self, passed: bool, uri: str): - """Selects all items that have not passed the time limit. This is really - only used to be able to show to the users the items that are active. - - Args: - passed (bool): Whether or not the item has passed the time limit - uri (str): DB Connection URI - """ - engine = create_async_engine(uri) - - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - selItem = select(models.AuctionHouseItem).filter( - models.AuctionHouseItem.passed == passed - ) - res = await session.execute(selItem) - return [row for row in res.scalars()] - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def deleteUserAHItem(self, user_id: int, uuid: str, uri: str): - """Purges one item from the DB for the user - - Args: - user_id (int): Discord User ID - uuid (str): AH Item UUID - uri (str): DB Connection URI - """ - - engine = create_async_engine(uri) - - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - selectOneDelete = ( - select(models.AuctionHouseItem) - .filter(models.AuctionHouseItem.user_id == user_id) - .filter(models.AuctionHouseItem.uuid == uuid) - ) - itemSelected = await session.scalars(selectOneDelete) - itemSelectedOne = itemSelected.one() - await session.delete(itemSelectedOne) - await session.commit() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def purgeUserAHItems(self, user_id: int, uri: str): - """Purges ALL of the user's items listed on the Auction House. - - Args: - user_id (int): Discord User ID - uri (str): DB Connection URI - """ - engine = create_async_engine(uri) - - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - selAllDel = delete(models.AuctionHouseItem).filter( - models.AuctionHouseItem.user_id == user_id - ) - await session.execute(selAllDel) - await session.commit() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def selectUserItemNameFirst(self, user_id: int, name: str, uri: str): - """Selects the item via the name and just returns the first one found - - Args: - user_id (int): Discord User ID - name (str): Item Name - uri (str): Connection URI - """ - engine = create_async_engine(uri) - - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - selectItem = ( - select(models.AuctionHouseItem) - .filter(models.AuctionHouseItem.name == name) - .filter(models.AuctionHouseItem.user_id == user_id) - ) - res = await session.scalars(selectItem) - return res.first() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def selectFirstItem(self, name: str, uri: str): - """Gets and selects the first item from the given name - - Args: - name (str): AH Item Name - uri (str): Connection URI - """ - engine = create_async_engine(uri) - - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - selectItem = select(models.AuctionHouseItem).filter( - models.AuctionHouseItem.name == name - ) - res = await session.scalars(selectItem) - return res.first() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def selectFirstItemViaUUID(self, uuid: str, uri: str): - """Gets and selects the first item from the given UUID - - Args: - uuid (str): AH Item UUID - uri (str): Connection URI - """ - engine = create_async_engine(uri) - - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - selectItem = select(models.AuctionHouseItem).filter( - models.AuctionHouseItem.uuid == uuid - ) - res = await session.scalars(selectItem) - return res.first() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) diff --git a/Bot/Libs/kumiko_economy_utils/checkers.py b/Bot/Libs/kumiko_economy_utils/checkers.py deleted file mode 100644 index 999d37b2..00000000 --- a/Bot/Libs/kumiko_economy_utils/checkers.py +++ /dev/null @@ -1,72 +0,0 @@ -import logging - -from dateutil import parser -from discord.utils import utcnow -from rin_exceptions import ItemNotFound, NoItemsError - -from .auction_house import KumikoAuctionHouseUtils -from .quests_utils import KumikoQuestsUtils - -questUtils = KumikoQuestsUtils() -ahUtils = KumikoAuctionHouseUtils() - - -async def QuestsChecker(uri: str) -> None: - """Checks quests every hour and deactivates them if they're expired""" - activeQuests = await questUtils.getAllActiveQuests(active=True, uri=uri) - try: - if len(activeQuests) == 0: - raise NoItemsError - else: - for questItem in activeQuests: - today = utcnow() - parsedDate = parser.isoparse(dict(questItem)["end_datetime"]) - if parsedDate < today: - await questUtils.setQuestActiveStatus( - uuid=dict(questItem)["uuid"], - active=False, - uri=uri, - ) - elif parsedDate == today: - await questUtils.setQuestActiveStatus( - uuid=dict(questItem)["uuid"], - active=False, - uri=uri, - ) - except NoItemsError: - logging.warning( - "No quests found to be active in the DB. Continuing to check for more" - ) - - -async def AHChecker(uri: str) -> None: - """Checks every hour for new AH items - - Args: - uri (str): Connection URI - """ - mainRes = await ahUtils.obtainAHItemPassed(passed=False, uri=uri) - try: - if len(mainRes) == 0: - raise ItemNotFound - else: - for item in mainRes: - mainItem = dict(item) - today = utcnow() - parsedDate = parser.isoparse(dict(mainItem)["date_added"]) - if parsedDate < today: - await ahUtils.setAHItemBoolean( - uuid=dict(mainItem)["uuid"], - passed=True, - uri=uri, - ) - elif parsedDate == today: - await ahUtils.setAHItemBoolean( - uuid=dict(mainItem)["uuid"], - passed=True, - uri=uri, - ) - except ItemNotFound: - logging.warning( - "No items found in the AH database. Continuing to check for more" - ) diff --git a/Bot/Libs/kumiko_economy_utils/db_base.py b/Bot/Libs/kumiko_economy_utils/db_base.py deleted file mode 100644 index 59be7030..00000000 --- a/Bot/Libs/kumiko_economy_utils/db_base.py +++ /dev/null @@ -1,3 +0,0 @@ -from sqlalchemy.orm import declarative_base - -Base = declarative_base() diff --git a/Bot/Libs/kumiko_economy_utils/eco_main.py b/Bot/Libs/kumiko_economy_utils/eco_main.py deleted file mode 100644 index bcd9b4c5..00000000 --- a/Bot/Libs/kumiko_economy_utils/eco_main.py +++ /dev/null @@ -1,239 +0,0 @@ -import asyncio -import uuid -from typing import Optional, Union - -import motor.motor_asyncio -import uvloop -from beanie import init_beanie -from discord.utils import utcnow -from sqlalchemy.engine.row import Row - -from .marketplace_models import MarketplaceModel -from .user_inv import KumikoUserInvUtils - - -class KumikoEcoUtils: - def __init__(self): - self.self = self - self.userInvUtils = KumikoUserInvUtils() - - async def ins( - self, - uuid: str, - date_added: str, - owner: int, - owner_name: str, - uri: str, - name: Optional[str] = None, - description: Optional[str] = None, - amount: Optional[int] = None, - price: Optional[int] = None, - updatedPrice: Optional[bool] = False, - ): - """Inserts an item into the MongoDB database - - Args: - uuid (str): UUID of the item - date_added (str): Dated added - defaults to the current date - owner (int): Discord user's ID - owner_name (str): Discord user's name - uri (str): MongoDB Connection URI - name (Optional[str], optional): The name of the item. Defaults to None. - description (Optional[str], optional): The description of the item. Defaults to None. - amount (Optional[int], optional): The amount that the user has. Defaults to None. - price (Optional[int], optional): The price set by the user. Defaults to None. - updatedPrice (Optional[bool], optional): Whether the price has been updated. Defaults to False. - """ - client = motor.motor_asyncio.AsyncIOMotorClient(uri) - await init_beanie( - database=client.kumiko_marketplace, document_models=[MarketplaceModel] - ) - entry = MarketplaceModel( - name=name, - description=description, - amount=amount, - price=price, - date_added=date_added, - owner=owner, - owner_name=owner_name, - uuid=uuid, - updated_price=updatedPrice, - ) - await entry.create() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def obtain(self, uri: str): - """Obtains all of the items from the marketplace - - Args: - uri (str): MongoDB Connection URI - - Returns: - List: List of all items in the database - """ - clientObtain = motor.motor_asyncio.AsyncIOMotorClient(uri) - await init_beanie( - database=clientObtain.kumiko_marketplace, document_models=[MarketplaceModel] - ) - resMain = await MarketplaceModel.find_all().to_list() - return resMain - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def obtainUserItem(self, name: str, user_id: str, uri: str): - """Obtains the user item from the database - - Args: - name (str): The name of the item - user_id (str): The Discord User ID - uri (str): MongoDB Connection URI - - Returns: - Object: The object containing the data of the item - """ - clientObtainUserItem = motor.motor_asyncio.AsyncIOMotorClient(uri) - await init_beanie( - database=clientObtainUserItem.kumiko_marketplace, - document_models=[MarketplaceModel], - ) - resMain5 = await MarketplaceModel.find( - MarketplaceModel.name == name, MarketplaceModel.owner == user_id - ).first_or_none() - return resMain5 - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def getAllOwnersItems(self, owner: int, uri: str) -> list: - """Gets literally all of the items that the owner has in the marketplace - - Args: - owner (int): Discord User ID - uri (str): MongoDB Connection URI - - Returns: - list: A list of all of the items that the owner has in the marketplace - """ - getItems = motor.motor_asyncio.AsyncIOMotorClient(uri) - await init_beanie( - database=getItems.kumiko_marketplace, - document_models=[MarketplaceModel], - ) - return await MarketplaceModel.find(MarketplaceModel.owner == owner).to_list() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def purgeOwnersItems(self, uuid: str, owner: int, uri: str): - """Purges all of the owner's items listed on the marketplace - - Args: - uuid (str): Marketplace Item UUID - owner (int): Discord User ID - uri (str): MongoDB Connection URI - """ - purgeItems = motor.motor_asyncio.AsyncIOMotorClient(uri) - await init_beanie( - database=purgeItems.kumiko_marketplace, document_models=[MarketplaceModel] - ) - await MarketplaceModel.find( - MarketplaceModel.uuid == uuid, MarketplaceModel.owner == owner - ).delete() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def getRequestedPurchaseItem(self, name: str, uri: str): - """Gets the first or none item that matches the name - - This is used to first search up the item to purchase from the Marketplace - - Args: - name (str): The name of the item to search up - uri (str): MongoDB Connection URI - """ - clientPurchase = motor.motor_asyncio.AsyncIOMotorClient(uri) - await init_beanie( - database=clientPurchase.kumiko_marketplace, - document_models=[MarketplaceModel], - ) - return await MarketplaceModel.find( - MarketplaceModel.name == name - ).first_or_none() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def setCurrentStock(self, uuid: str, amount: int, uri: str) -> None: - """Sets the current stock amount for the requested item (checked using the UUID provided) - - Args: - uuid (str): Requested Item UUID - amount (int): The amount to set to. This is also commonly used to set it to be 0 - uri (str): MongoDB Connection URI - """ - clientUpdate = motor.motor_asyncio.AsyncIOMotorClient(uri) - await init_beanie( - database=clientUpdate.kumiko_marketplace, - document_models=[MarketplaceModel], - ) - marketplaceItem = await MarketplaceModel.find_one(MarketplaceModel.uuid == uuid) - marketplaceItem.amount = amount - await marketplaceItem.save() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def purchaseItem( - self, - user_inv: Union[Row, None], - requested_item: Union[MarketplaceModel, None], - current_stock: int, - requested_amount: int, - user_id: int, - mongo_uri: str, - postgres_uri: str, - ): - """Makes the purchase for the requested item - - This should be used with purchasing the item - - Args: - user_inv (Union[Row, None]): The object (can be None) of the user's inventory - requested_item (Union[MarketplaceModel, None]): Object (can be None) of the requested item - current_stock (int): The current stock that the requested item has - requested_amount (int): The amount that is requested to be purchased for - user_id (int): The Discord user's ID - mongo_uri (str): MongoDB Connection URI - postgres_uri (str): PostgreSQL Connection URI - """ - requestedItemUUID = dict(requested_item)["uuid"] - returnStr = "" - if user_inv is None: - await self.updateItemAmount( - uuid=requestedItemUUID, amount=current_stock, uri=mongo_uri - ) - await self.userInvUtils.insertItem( - user_uuid=str(uuid.uuid4()), - user_id=user_id, - date_acquired=utcnow().isoformat(), - name=dict(requested_item)["name"], - description=dict(requested_item)["description"], - amount=requested_amount, - uri=postgres_uri, - ) - returnStr = f"Purchased {requested_amount} {dict(requested_item)['name']} for {dict(requested_item)['price']} coins. Also added {dict(requested_item)['name']} to your inventory." - else: - amountAddingToUser = int(dict(user_inv[0])["amount"]) + int( - requested_amount - ) - await self.updateItemAmount( - uuid=requestedItemUUID, amount=current_stock, uri=mongo_uri - ) - await self.userInvUtils.updateItemAmount( - user_id=user_id, - uuid=requestedItemUUID, - amount=amountAddingToUser, - uri=postgres_uri, - ) - returnStr = f"Purchased {requested_amount} {dict(requested_item)['name']} for {dict(requested_item)['price']} coins." - - return returnStr - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) diff --git a/Bot/Libs/kumiko_economy_utils/eco_user.py b/Bot/Libs/kumiko_economy_utils/eco_user.py deleted file mode 100644 index 31e46e2d..00000000 --- a/Bot/Libs/kumiko_economy_utils/eco_user.py +++ /dev/null @@ -1,188 +0,0 @@ -import asyncio - -import uvloop -from sqlalchemy import delete, select, update -from sqlalchemy.ext.asyncio import AsyncSession, create_async_engine -from sqlalchemy.orm import sessionmaker - -from . import models -from .db_base import Base - - -class KumikoEcoUserUtils: - def __init__(self): - self.self = self - - async def initUserTables(self, uri: str): - """Creates the tables needed for each user - - Args: - uri (str): Connection URI - """ - engine = create_async_engine( - uri, - ) - async with engine.begin() as conn: - await conn.run_sync(Base.metadata.create_all) - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def initUserAcct( - self, user_id: int, username: str, date_joined: str, uri: str - ): - """Initializes a user's account - - Args: - user_id (int): Discord User ID - username (str): Discord username - date_joined (str): The date that the user has joined - uri (str): The Connection URI needed for connecting to the database - """ - engine = create_async_engine(uri) - - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - insertData = models.KumikoEcoUser( - user_id=user_id, - username=username, - lavender_petals=0, - rank=0, - date_joined=date_joined, - ) - session.add_all([insertData]) - await session.commit() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def obtainUserData(self, user_id: int, uri: str): - """Gets the data about a user - - Args: - user_id (int): Discord User ID - uri (str): Connection URI - """ - engine = create_async_engine(uri) - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - selectUser = select(models.KumikoEcoUser).filter( - models.KumikoEcoUser.user_id == user_id - ) - res = await session.execute(selectUser) - return [row for row in res.scalars()] - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def getFirstUser(self, user_id: int, uri: str): - """Gets the first user requested - - Args: - user_id (int): Discord User ID - uri (str): Connection URI - """ - engine = create_async_engine(uri) - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - selectUser = select(models.KumikoEcoUser).filter( - models.KumikoEcoUser.user_id == user_id - ) - res = await session.scalars(selectUser) - return res.first() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def selectUserRank(self, user_id: int, uri: str): - """Obtains the rank of the user - - Args: - user_id (int): Discord User ID - uri (str): Connection URI - """ - engine = create_async_engine(uri) - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - selectUser = select(models.KumikoEcoUser.rank).filter( - models.KumikoEcoUser.user_id == user_id - ) - res = await session.execute(selectUser) - return [row for row in res.scalars()] - - # This coroutine is only kept because the rank system will need this - async def updateUserRank(self, user_id: int, rank: int, uri: str): - """Updates a user's rank - - Args: - user_id (int): Discord User ID - rank (int): New Rank Level - uri (str): Connection URI - """ - engine = create_async_engine(uri) - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - updateUser = update( - models.KumikoEcoUser, values={models.KumikoEcoUser.rank: rank} - ).filter(models.KumikoEcoUser.user_id == user_id) - await session.execute(updateUser) - await session.commit() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def updateUserLavenderPetals( - self, user_id: int, lavender_petals: int, uri: str - ): - """Updates the amount of lavender petals that the user has - - Args: - user_id (int): Discord User ID - lavender_petals (int): New amount of Lavender Petals - uri (str): Connection URI - """ - engine = create_async_engine(uri) - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - updateUser = update( - models.KumikoEcoUser, - values={models.KumikoEcoUser.lavender_petals: lavender_petals}, - ).filter(models.KumikoEcoUser.user_id == user_id) - await session.execute(updateUser) - await session.commit() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def deleteUser(self, user_id: int, uri: str): - """Deletes a user from the database - - Args: - user_id (int): Discord User ID - uri (str): Connection URI - """ - engine = create_async_engine(uri) - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - deleteUser = delete(models.KumikoEcoUser).filter( - models.KumikoEcoUser.user_id == user_id - ) - await session.execute(deleteUser) - await session.commit() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) diff --git a/Bot/Libs/kumiko_economy_utils/marketplace_models.py b/Bot/Libs/kumiko_economy_utils/marketplace_models.py deleted file mode 100644 index ae85684c..00000000 --- a/Bot/Libs/kumiko_economy_utils/marketplace_models.py +++ /dev/null @@ -1,29 +0,0 @@ -from typing import Optional - -from beanie import Document -from pydantic import BaseModel - - -class MarketplaceModel(Document): - name: str - description: Optional[str] = None - amount: int - price: int - date_added: str - owner: int - owner_name: str - uuid: str - updated_price: bool - - -class PurchaseProject(BaseModel): - owner: int - name: str - description: str - price: int - amount: int - uuid: str - - -class ItemAuthProject(BaseModel): - uuid: str diff --git a/Bot/Libs/kumiko_economy_utils/models.py b/Bot/Libs/kumiko_economy_utils/models.py deleted file mode 100644 index a24a8a44..00000000 --- a/Bot/Libs/kumiko_economy_utils/models.py +++ /dev/null @@ -1,103 +0,0 @@ -from sqlalchemy import BigInteger, Boolean, Column, Integer, String, Text - -from .db_base import Base - - -class AuctionHouseItem(Base): - __tablename__ = "eco_auction_house_items" - - uuid = Column(String, primary_key=True) - user_id = Column(BigInteger) - name = Column(String) - description = Column(Text) - date_added = Column(String) - price = Column(BigInteger) - passed = Column(Boolean) - - def __iter__(self): - yield "uuid", self.uuid - yield "user_id", self.user_id - yield "name", self.name - yield "description", self.description - yield "date_added", self.date_added - yield "price", self.price - yield "passed", self.passed - - def __repr__(self): - return f"AuctionHouseItem(uuid={self.uuid!r}, user_id={self.user_id!r}, name={self.name!r}, description={self.description!r}, date_added={self.date_added!r}, price={self.price!r}, passed={self.passed!r})" - - -class KumikoEcoUser(Base): - __tablename__ = "eco_users" - - user_id = Column(BigInteger, primary_key=True) - username = Column(String) - lavender_petals = Column(Integer) - rank = Column(Integer) - date_joined = Column(String) - - def __iter__(self): - yield "user_id", self.user_id - yield "username", self.username - yield "lavender_petals", self.lavender_petals - yield "rank", self.rank - yield "date_joined", self.date_joined - - def __repr__(self): - return f"KumikoEcoUser(user_id={self.user_id!r}, username={self.username!r}, lavender_petals={self.lavender_petals!r}, rank={self.rank!r}, date_joined={self.date_joined!r})" - - -class KumikoQuests(Base): - __tablename__ = "eco_quests" - - uuid = Column(String, primary_key=True) - creator = Column(BigInteger) - claimed_by = Column(BigInteger) - date_created = Column(String) - end_datetime = Column(String) - name = Column(String) - description = Column(Text) - reward = Column(BigInteger) - active = Column(Boolean) - claimed = Column(Boolean) - - def __iter__(self): - yield "uuid", self.uuid - yield "creator", self.creator - yield "claimed_by", self.claimed_by - yield "date_created", self.date_created - yield "end_datetime", self.end_datetime - yield "name", self.name - yield "description", self.description - yield "reward", self.reward - yield "active", self.active - yield "claimed", self.claimed - - def __repr__(self): - return f"KumikoQuests(uuid={self.uuid!r}, creator={self.creator!r}, claimed_by={self.claimed_by!r}, date_created={self.date_created!r}, end_datetime={self.end_datetime!r}, name={self.name!r}, description={self.description!r}, reward={self.reward!r}, active={self.active!r}, claimed={self.claimed!r})" - - -class UserInv(Base): - __tablename__ = "user_inv" - - user_uuid = Column(String, primary_key=True) - user_id = Column( - BigInteger, - ) - date_acquired = Column(String) - uuid = Column(String) - name = Column(String) - description = Column(Text) - amount = Column(Integer) - - def __iter__(self): - yield "user_uuid", self.user_uuid - yield "user_id", self.user_id - yield "date_acquired", self.date_acquired - yield "uuid", self.uuid - yield "name", self.name - yield "description", self.description - yield "amount", self.amount - - def __repr__(self): - return f"UserInv(user_uuid={self.user_uuid!r}, user_id={self.user_id!r}, date_acquired={self.date_acquired!r}, uuid={self.uuid!r}, name={self.name!r}, description={self.description!r}, amount={self.amount!r})" diff --git a/Bot/Libs/kumiko_economy_utils/quests_utils.py b/Bot/Libs/kumiko_economy_utils/quests_utils.py deleted file mode 100644 index 9378cd4b..00000000 --- a/Bot/Libs/kumiko_economy_utils/quests_utils.py +++ /dev/null @@ -1,375 +0,0 @@ -import asyncio -from typing import Union - -import uvloop -from sqlalchemy import delete, select, update -from sqlalchemy.ext.asyncio import AsyncSession, create_async_engine -from sqlalchemy.orm import sessionmaker - -from . import models -from .db_base import Base - - -class KumikoQuestsUtils: - def __init__(self): - self.self = self - - async def initQuestsTables(self, uri: str) -> None: - """Initializes the tables for Kumiko's Quests system - - Args: - uri (str): Connection URI - """ - engine = create_async_engine(uri) - async with engine.begin() as conn: - await conn.run_sync(Base.metadata.create_all) - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def createQuests( - self, - uuid: str, - creator: int, - claimed_by: Union[None, int], - date_created: str, - end_datetime: str, - name: str, - description: str, - reward: int, - active: bool, - claimed: bool, - uri: str, - ) -> None: - """Inserts a new quest into the database - - Args: - uuid (str): Quests Item UUID - creator (int): Discord User ID of the creator - claimed_by (Union[None, int]): Discord User ID that claims this quest - date_created (str): The creation date of the quest - end_datetime (str): The end date and time of the quest - name (str): Quest Name - description (str): Quest Description - reward (int): Quest Reward - active (bool): Quest Active Status - claimed (bool): Is the quest already claimed? - uri (str): Connection URI - """ - engine = create_async_engine(uri) - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - addItemQuests = models.KumikoQuests( - uuid=uuid, - creator=creator, - claimed_by=claimed_by, - date_created=date_created, - end_datetime=end_datetime, - name=name, - description=description, - reward=reward, - active=active, - claimed=claimed, - ) - session.add_all([addItemQuests]) - await session.commit() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def getActiveQuests(self, active: bool, uri: str) -> list: - """Gets all active quests - - Args: - active (bool): Quest Active Status - uri (str): Connection URI - - Returns: - list: List of results - """ - engine = create_async_engine(uri) - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - selectItem = select(models.KumikoQuests).filter( - models.KumikoQuests.active == active - ) - res = await session.execute(selectItem) - return [row for row in res.scalars()] - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def getAllQuests(self, uri: str) -> list: - """Get all of the quests in the db. Even it is active - or not - - Args: - uri (str): Conenction URI - - Returns: - list: List of results - """ - engine = create_async_engine(uri) - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - selectItem = select(models.KumikoQuests) - res = await session.execute(selectItem) - return [row for row in res.scalars()] - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def updateDatetimeQuest( - self, uuid: str, new_end_datetime: str, uri: str - ) -> None: - """Updates a quest with the new date and time - - Args: - uuid (str): Quests Item UUID - new_end_datetime (str): The new date and time - uri (str): Connection URI - """ - engine = create_async_engine(uri) - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - updateItem = update( - models.KumikoQuests, - values={ - models.KumikoQuests.end_datetime: new_end_datetime, - }, - ).filter(models.KumikoQuests.uuid == uuid) - await session.execute(updateItem) - await session.commit() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def getQuestViaName(self, name: str, uri: str) -> list: - """Gets the quest via the name - - Args: - name (str): Quest Name - uri (str): Connection URI - - Returns: - list: List of results - """ - engine = create_async_engine(uri) - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - getQuest = select(models.KumikoQuests).filter( - models.KumikoQuests.name == name - ) - res = await session.execute(getQuest) - return [row for row in res.scalars()] - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def getUserQuestOne(self, user_id: int, name: str, uri: str) -> list: - """Gets one quest from the user - - Args: - user_id (int): Discord User ID - uri (str): Connection URI - - Returns: - list: List of results - """ - engine = create_async_engine(uri) - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - getQuest = ( - select(models.KumikoQuests) - .filter(models.KumikoQuests.creator == user_id) - .filter(models.KumikoQuests.name == name) - ) - getQuestSelected = await session.scalars(getQuest) - getQuestSelectedOne = getQuestSelected.first() - return getQuestSelectedOne - - async def deleteOneQuest(self, user_id: int, uuid: str, uri: str) -> None: - """Deletes one quest from the DB - - Args: - user_id (int): Discord User ID - uuid (str): Quest UUID - uri (str): Connection URI - """ - engine = create_async_engine(uri) - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - selectOneDelete = ( - select(models.KumikoQuests) - .filter(models.KumikoQuests.uuid == uuid) - .filter(models.KumikoQuests.creator == user_id) - ) - itemSelected = await session.scalars(selectOneDelete) - itemSelectedOne = itemSelected.one() - await session.delete(itemSelectedOne) - await session.commit() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def getItemUUIDAuth(self, user_id: int, uri: str) -> list: - """Gets the items's UUID for authorization in order to - purge the user's quests - - Args: - user_id (int): Discord User ID - uri (str): Connection URI - """ - engine = create_async_engine(uri) - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - getQuest = select(models.KumikoQuests.uuid).filter( - models.KumikoQuests.creator == user_id - ) - res = await session.execute(getQuest) - return [row for row in res.scalars()] - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def purgeUserQuests(self, user_id: int, uuid: str, uri: str) -> None: - """Completely purges all of the quests that the user has. This is - irreversible. - - Args: - user_id (int): Discord User ID - uuid (str): Quests Item UUID - uri (str): Connection URI - """ - engine = create_async_engine(uri) - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - selectAllDelete = ( - delete(models.KumikoQuests) - .filter(models.KumikoQuests.creator == user_id) - .filter(models.KumikoQuests.uuid == uuid) - ) - await session.execute(selectAllDelete) - await session.commit() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def claimQuest( - self, user_id: int, claimer_id: int, uuid: str, claimed: bool, uri: str - ) -> None: - """Goes ahead and claims the quest - - Args: - user_id (int): Discord User ID - claimer_id (int): The Discord User ID of the person who claims it - uuid (str): Quest Item UUID - uri (str): Connection URI - """ - engine = create_async_engine(uri) - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - updateQuestItem = ( - update( - models.KumikoQuests, - values={ - models.KumikoQuests.claimed_by: claimer_id, - models.KumikoQuests.claimed: claimed, - }, - ) - .filter(models.KumikoQuests.creator == user_id) - .filter(models.KumikoQuests.uuid == uuid) - ) - await session.execute(updateQuestItem) - await session.commit() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def viewClaimedQuests(self, claimed: bool, uri: str) -> list: - """Gets all of the claimed quests - - Args: - claimed (bool): Whether or not the quest is claimed - uri (str): Connection URI - """ - engine = create_async_engine(uri) - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - getQuest = select(models.KumikoQuests).filter( - models.KumikoQuests.claimed == claimed - ) - res = await session.execute(getQuest) - return [row for row in res.scalars()] - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def getAllActiveQuests(self, active: bool, uri: str) -> list: - """Gets all active quests regardless of guilds - - Args: - active (bool): Quest Active Status - uri (str): Connection URI - - Returns: - list: List of results - """ - engine = create_async_engine(uri) - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - selectItem = select(models.KumikoQuests).filter( - models.KumikoQuests.active == active - ) - res = await session.execute(selectItem) - return [row for row in res.scalars()] - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def setQuestActiveStatus(self, uuid: str, active: bool, uri: str) -> None: - """Sets the quest's active status. This is used to mark the - quest as active or not - - Args: - uuid (str): Quest Item UUID - active (bool): Whether the quests should be active or not - uri (str): Connection URI - """ - engine = create_async_engine(uri) - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - updateItem = update( - models.KumikoQuests, values={models.KumikoQuests.active: active} - ).filter(models.KumikoQuests.uuid == uuid) - await session.execute(updateItem) - await session.commit() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) diff --git a/Bot/Libs/kumiko_economy_utils/user_inv.py b/Bot/Libs/kumiko_economy_utils/user_inv.py deleted file mode 100644 index 0e4e1ad8..00000000 --- a/Bot/Libs/kumiko_economy_utils/user_inv.py +++ /dev/null @@ -1,171 +0,0 @@ -import asyncio - -import uvloop -from sqlalchemy import select, update -from sqlalchemy.ext.asyncio import AsyncSession, create_async_engine -from sqlalchemy.orm import sessionmaker - -from . import models -from .db_base import Base - - -class KumikoUserInvUtils: - def __init__(self): - self.self = self - - async def initUserInvTables(self, uri: str) -> None: - """_summary_ - - Args: - uri (str): Connection URI - """ - engine = create_async_engine(uri) - async with engine.begin() as conn: - await conn.run_sync(Base.metadata.create_all) - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def insertItem( - self, - user_uuid: str, - user_id: int, - date_acquired: str, - uuid: str, - name: str, - description: str, - amount: int, - uri: str, - ) -> None: - """Adds the item into the user's inventory - - Args: - user_uuid (str): User UUID - user_id (int): Discord User ID - date_acquired (str / ISO-8601): Date the item was acquired on or first acquired on - uuid (str): Item UUID - name (str): Item Name - description (str): Item Description - amount (int): Amount of items in the inv - uri (str): Connection URI - """ - engine = create_async_engine(uri) - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - insertUserInv = models.UserInv( - user_uuid=user_uuid, - user_id=user_id, - date_acquired=date_acquired, - uuid=uuid, - name=name, - description=description, - amount=amount, - ) - session.add_all([insertUserInv]) - await session.commit() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def updateItemAmount( - self, user_id: int, uuid: int, amount: int, uri: str - ) -> None: - """Updates the user to the new amount of items in the inv - - Args: - user_id (int): Discord User ID - uuid (str): Item UUID - amount (int): New amount of items - uri (str): Connection URI - """ - engine = create_async_engine(uri) - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - updateItem = ( - update(models.UserInv, values={models.UserInv.amount: amount}) - .filter(models.UserInv.uuid == uuid) - .filter(models.UserInv.user_id == user_id) - ) - await session.execute(updateItem) - await session.commit() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def checkIfItemInUserInv(self, user_id: int, uuid: str, uri: str) -> list: - """Checks if the item is already in the user's inv - - Args: - user_id (int): Discord User ID - uuid (str): Item UUID - uri (str): Connection URI - - Returns: - list: A list of results - """ - engine = create_async_engine(uri) - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - selectUser = select(models.UserInv).filter( - models.UserInv.user_id == user_id - ) - selectUserRes = await session.execute(selectUser) - return [ - row for row in selectUserRes.scalars() if dict(row)["uuid"] == uuid - ] - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def getUserInv(self, user_id: int, uri: str) -> list: - """Get's the user's inv - - Args: - user_id (int): Discord User ID - uri (str): Connection URI - - Returns: - list: List of Results - """ - engine = create_async_engine(uri) - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - selectUser = select(models.UserInv).filter( - models.UserInv.user_id == user_id - ) - res = await session.execute(selectUser) - return [row for row in res.scalars()] - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - async def findItem(self, user_id: int, item_name: str, uri: str): - """Finds one item from the user inv that is requested - - Args: - user_id (int): Discord User ID - item_name (str): Item name - uri (str): Connection URI - """ - engine = create_async_engine(uri) - async_session = sessionmaker( - engine, expire_on_commit=False, class_=AsyncSession - ) - async with async_session() as session: - async with session.begin(): - selectItem = ( - select(models.UserInv) - .filter(models.UserInv.user_id == user_id) - .filter(models.UserInv.name == item_name) - ) - res = await session.execute(selectItem) - return res.first() - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) diff --git a/Bot/Libs/kumiko_ui_components/__init__.py b/Bot/Libs/kumiko_ui_components/__init__.py deleted file mode 100644 index c8ab0d5e..00000000 --- a/Bot/Libs/kumiko_ui_components/__init__.py +++ /dev/null @@ -1,43 +0,0 @@ -from .modals import ( - EcoMarketplaceListItemModal, - GWSDeleteOneUserInvItemModal, - MarketplaceAddItem, - MarketplaceDeleteOneItem, - MarketplacePurchaseItemModal, - MarketplaceUpdateAmount, - MarketplaceUpdateItemPrice, - QuestsCreateModal, - QuestsDeleteOneModal, - QuestsUpdateTimeModal, -) -from .views import ( - CreateAccountView, - EcoUserCreationView, - EcoUserPurgeView, - GWSPurgeInvView, - MarketplacePurgeAllView, - PurgeAccountView, - QuestsDeleteOneConfirmView, - QuestsPurgeAllView, -) - -__all__ = [ - "MarketplacePurgeAllView", - "QuestsPurgeAllView", - "CreateAccountView", - "PurgeAccountView", - "QuestsDeleteOneModal", - "QuestsDeleteOneConfirmView", - "QuestsCreateModal", - "QuestsUpdateTimeModal", - "MarketplaceAddItem", - "MarketplaceDeleteOneItem", - "MarketplaceUpdateAmount", - "MarketplaceUpdateItemPrice", - "MarketplacePurchaseItemModal", - "GWSPurgeInvView", - "GWSDeleteOneUserInvItemModal", - "EcoUserCreationView", - "EcoUserPurgeView", - "EcoMarketplaceListItemModal", -] diff --git a/Bot/Libs/kumiko_ui_components/modals.py b/Bot/Libs/kumiko_ui_components/modals.py deleted file mode 100644 index 40dbf86b..00000000 --- a/Bot/Libs/kumiko_ui_components/modals.py +++ /dev/null @@ -1,721 +0,0 @@ -import asyncio -import uuid -from typing import List - -import discord -import uvloop -from dateutil import parser -from kumiko_economy import EcoMarketplace, EcoUser -from kumiko_economy_utils import ( - KumikoEcoUserUtils, - KumikoEcoUtils, - KumikoQuestsUtils, - KumikoUserInvUtils, -) -from kumiko_genshin_wish_sim import KumikoGWSCacheUtils, WSUserInv -from kumiko_utils import KumikoCM -from rin_exceptions import ItemNotFound - - -class QuestsDeleteOneModal(discord.ui.Modal): - def __init__(self, uri: str, *args, **kwargs) -> None: - super().__init__(*args, **kwargs) - self.uri = uri - self.questsUtil = KumikoQuestsUtils() - self.userUtils = KumikoEcoUserUtils() - - self.add_item( - discord.ui.InputText( - label="Quest name", - style=discord.InputTextStyle.short, - min_length=1, - required=True, - placeholder="Type in the quest name to delete", - ) - ) - - async def callback(self, interaction: discord.Interaction): - mainRes = await self.questsUtil.getUserQuestOne( - user_id=interaction.user.id, name=self.children[0].value, uri=self.uri - ) - userRank = await self.userUtils.selectUserRank( - user_id=interaction.user.id, uri=self.uri - ) - try: - if len(userRank) == 0: - raise ItemNotFound - else: - for items in userRank: - if int(items) < 5: - return await interaction.response.send_message( - f"Sorry, but you can't use the quests feature since you are current rank is {items}", - ephemeral=True, - ) - elif mainRes is None: - return await interaction.response.send_message( - f"Sorry, but the quest {self.children[0].value} could not be found. Please try again", - ephemeral=True, - ) - else: - await self.questsUtil.deleteOneQuest( - user_id=interaction.user.id, - uuid=dict(mainRes)["uuid"], - uri=self.uri, - ) - return await interaction.response.send_message( - f"Quest {self.children[0].value} has been deleted", - ephemeral=True, - ) - except ItemNotFound: - return await interaction.response.send_message( - "It seems like you either don't have an account yet, or the the quest you requested is not found. Please try again", - ephemeral=True, - ) - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - -class QuestsCreateModal(discord.ui.Modal): - def __init__(self, uri: str, *args, **kwargs) -> None: - super().__init__(*args, **kwargs) - self.uri = uri - self.questsUtil = KumikoQuestsUtils() - self.userUtils = KumikoEcoUserUtils() - - self.add_item( - discord.ui.InputText( - label="Name", - style=discord.InputTextStyle.short, - min_length=1, - required=True, - placeholder="Type in the quest name to create", - ) - ) - self.add_item( - discord.ui.InputText( - label="Description", - style=discord.InputTextStyle.long, - min_length=1, - required=True, - placeholder="Type in the quest description", - ) - ) - self.add_item( - discord.ui.InputText( - label="Reward", - style=discord.InputTextStyle.short, - min_length=1, - required=True, - placeholder="Type in the number of petals to reward", - ) - ) - self.add_item( - discord.ui.InputText( - label="End Date", - style=discord.InputTextStyle.short, - min_length=1, - required=True, - placeholder="Type in the end date of the quest", - ) - ) - self.add_item( - discord.ui.InputText( - label="End Time", - style=discord.InputTextStyle.short, - min_length=1, - required=True, - placeholder="Type in the end time of the quest", - ) - ) - - async def callback(self, interaction: discord.Interaction): - getUser = await self.userUtils.getFirstUser( - user_id=interaction.user.id, uri=self.uri - ) - if getUser is None: - await interaction.response.send_message( - "Probably should create an account first...", ephemeral=True - ) - elif int(dict(getUser)["rank"]) < 5: - await interaction.response.send_message( - f"Sorry, but you can't use the quests feature since you are current rank is {dict(getUser)['rank']}", - ephemeral=True, - ) - else: - questUUIDItem = str(uuid.uuid4()) - dateCreated = discord.utils.utcnow().isoformat() - endDateFormatted = parser.parse( - f"{self.children[3].value} {self.children[4].value}" - ).isoformat() - totalUserPetals = int(dict(getUser)["lavender_petals"]) - int( - self.children[2].value - ) - await self.userUtils.updateUserLavenderPetals( - user_id=interaction.user.id, - lavender_petals=totalUserPetals, - uri=self.uri, - ) - await self.questsUtil.createQuests( - uuid=questUUIDItem, - creator=interaction.user.id, - claimed_by=None, - date_created=dateCreated, - end_datetime=endDateFormatted, - name=self.children[0].value, - description=self.children[1].value, - reward=int(self.children[2].value), - active=True, - claimed=False, - uri=self.uri, - ) - await interaction.response.send_message( - f"Quest {self.children[0].value} has been created", ephemeral=True - ) - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - -class QuestsUpdateTimeModal(discord.ui.Modal): - def __init__(self, uri: str, *args, **kwargs) -> None: - super().__init__(*args, **kwargs) - self.uri = uri - self.questsUtil = KumikoQuestsUtils() - self.userUtils = KumikoEcoUserUtils() - - self.add_item( - discord.ui.InputText( - label="Name", - style=discord.InputTextStyle.short, - min_length=1, - required=True, - placeholder="Type in the quest name to search for", - ) - ) - self.add_item( - discord.ui.InputText( - label="End Date", - style=discord.InputTextStyle.short, - min_length=1, - required=True, - placeholder="Type in the new end date of the quest", - ) - ) - self.add_item( - discord.ui.InputText( - label="End Time", - style=discord.InputTextStyle.short, - min_length=1, - required=True, - placeholder="Type in the new end time of the quest", - ) - ) - - async def callback(self, interaction: discord.Interaction): - mainQuest = await self.questsUtil.getQuestViaName( - name=self.children[0].value, uri=self.uri - ) - mainUserData = await self.userUtils.obtainUserData( - user_id=interaction.user.id, uri=self.uri - ) - try: - if len(mainQuest) == 0 or len(mainUserData) == 0: - raise ItemNotFound - else: - fullDateTime = parser.parse( - f"{self.children[1].value} {self.children[2].value}" - ).isoformat() - for userData in mainUserData: - currentUserRank = dict(userData)["rank"] - if currentUserRank < 5: - await interaction.response.send_message( - f"Sorry, but you can't use the quests feature since you are current rank is {currentUserRank}" - ) - else: - for items in mainQuest: - await self.questsUtil.updateDatetimeQuest( - uuid=dict(items)["uuid"], - new_end_datetime=fullDateTime, - uri=self.uri, - ) - await interaction.response.send_message( - f"Quest {self.children[0].value} has been updated", - ephemeral=True, - ) - except ItemNotFound: - await interaction.response.send_message( - "It seems like there no quests with that name (or you haven't created an account yet). Please try again" - ) - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - -class MarketplaceAddItem(discord.ui.Modal): - def __init__(self, mongo_uri: str, postgres_uri: str, *args, **kwargs) -> None: - super().__init__(*args, **kwargs) - self.mongoURI = mongo_uri - self.postgresURI = postgres_uri - self.user = KumikoEcoUserUtils() - self.mUtils = KumikoEcoUtils() - - self.add_item( - discord.ui.InputText( - label="Name", - style=discord.InputTextStyle.short, - min_length=1, - max_length=255, - required=True, - placeholder="Type in the item name here", - ) - ) - self.add_item( - discord.ui.InputText( - label="Description", - style=discord.InputTextStyle.long, - min_length=1, - required=True, - placeholder="Type in the item description here", - ) - ) - self.add_item( - discord.ui.InputText( - label="Amount", - style=discord.InputTextStyle.short, - min_length=1, - required=True, - placeholder="Type in how much you are willing to sell here", - ) - ) - self.add_item( - discord.ui.InputText( - label="Price", - style=discord.InputTextStyle.short, - min_length=1, - required=True, - placeholder="Type in the price of the item here", - ) - ) - - async def callback(self, interaction: discord.Interaction): - getUserData = await self.user.getFirstUser( - user_id=interaction.user.id, uri=self.postgresURI - ) - try: - if getUserData is None: - raise ItemNotFound - else: - finalBal = int(dict(getUserData)["lavender_petals"]) - 10 - await self.user.updateUserLavenderPetals( - user_id=interaction.user.id, - lavender_petals=finalBal, - uri=self.postgresURI, - ) - await self.mUtils.ins( - uuid=str(uuid.uuid4()), - date_added=discord.utils.utcnow().isoformat(), - owner=interaction.user.id, - owner_name=interaction.user.name, - uri=self.mongoURI, - name=self.children[0].value, - description=self.children[1].value, - amount=self.children[2].value, - price=self.children[3].value, - updatedPrice=False, - ) - await interaction.response.send_message( - f"The item {self.children[0].value} has been added to the marketplace", - ephemeral=True, - ) - except ItemNotFound: - embed = discord.Embed() - embed.description = "It seems like your account was not found. Please initialize your account first" - await interaction.response.send_message(embed=embed, ephemeral=True) - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - -class MarketplaceDeleteOneItem(discord.ui.Modal): - def __init__(self, mongo_uri: str, *args, **kwargs) -> None: - super().__init__(*args, **kwargs) - self.mongoURI = mongo_uri - self.mUtils = KumikoEcoUtils() - - self.add_item( - discord.ui.InputText( - label="Name", - style=discord.InputTextStyle.short, - min_length=1, - max_length=255, - required=True, - placeholder="Type in the item name here to delete", - ) - ) - - async def callback(self, interaction: discord.Interaction): - getUserItem = await self.mUtils.obtainUserItem( - name=self.children[0].value, user_id=interaction.user.id, uri=self.mongoURI - ) - try: - if getUserItem is None: - raise ItemNotFound - else: - await getUserItem.delete() - await interaction.response.send_message( - f"The item {self.children[0].value} has been deleted from the marketplace", - ephemeral=True, - ) - except ItemNotFound: - embed = discord.Embed() - embed.description = f"It seems like there is no item called {self.children[0].value} in the marketplace. Please try again" - await interaction.response.send_message(embed=embed, ephemeral=True) - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - -class MarketplaceUpdateAmount(discord.ui.Modal): - def __init__(self, mongo_uri: str, *args, **kwargs) -> None: - super().__init__(*args, **kwargs) - self.mongoURI = mongo_uri - self.mUtils = KumikoEcoUtils() - - self.add_item( - discord.ui.InputText( - label="Name", - style=discord.InputTextStyle.short, - min_length=1, - max_length=255, - required=True, - placeholder="Type in the item name here to restorck", - ) - ) - self.add_item( - discord.ui.InputText( - label="Amount", - style=discord.InputTextStyle.short, - min_length=1, - max_length=255, - required=True, - placeholder="Type in the amount of the item here to restock", - ) - ) - - async def callback(self, interaction: discord.Interaction): - getUserItem = await self.mUtils.obtainUserItem( - name=self.children[0].value, user_id=interaction.user.id, uri=self.mongoURI - ) - try: - if getUserItem is None: - raise ItemNotFound - else: - totalAmount = int(dict(getUserItem)["amount"]) + int( - self.children[1].value - ) - getUserItem.amount = totalAmount - await getUserItem.save() - await interaction.response.send_message( - f"Updated {self.children[0].value}'s amount to {totalAmount}", - ephemeral=True, - ) - except ItemNotFound: - embedError = discord.Embed() - embedError.description = "Sorry, it seems like the item you are trying to update does not exist in the Marketplace. Please try again." - await interaction.response.send_message(embed=embedError, ephemeral=True) - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - -class MarketplaceUpdateItemPrice(discord.ui.Modal): - def __init__(self, mongo_uri: str, *args, **kwargs) -> None: - super().__init__(*args, **kwargs) - self.mongoURI = mongo_uri - self.mUtils = KumikoEcoUtils() - - self.add_item( - discord.ui.InputText( - label="Name", - style=discord.InputTextStyle.short, - min_length=1, - max_length=255, - required=True, - placeholder="Type in the item name here to restorck", - ) - ) - self.add_item( - discord.ui.InputText( - label="Price", - style=discord.InputTextStyle.short, - min_length=1, - max_length=255, - required=True, - placeholder="Type in the new price of the item", - ) - ) - - async def callback(self, interaction: discord.Interaction): - getUserItem = await self.mUtils.obtainUserItem( - name=self.children[0].value, user_id=interaction.user.id, uri=self.mongoURI - ) - try: - if getUserItem is None: - raise ItemNotFound - elif dict(getUserItem)["updated_price"] is True: - await interaction.response.send_message( - f"Sorry, you cannot update the price of {self.children[0].value} anymore", - ephemeral=True, - ) - else: - getUserItem.price = int(self.children[1].value) - getUserItem.updated_price = True - await getUserItem.save() - await interaction.response.send_message( - f"Updated {self.children[0].value}'s price {int(self.children[1].value)}", - ephemeral=True, - ) - except ItemNotFound: - embedError = discord.Embed() - embedError.description = "Sorry, it seems like the item you are trying to update does not exist in the Marketplace. Please try again." - await interaction.response.send_message(embed=embedError, ephemeral=True) - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - -class MarketplacePurchaseItemModal(discord.ui.Modal): - def __init__(self, mongo_uri: str, postgres_uri: str, *args, **kwargs) -> None: - super().__init__(*args, **kwargs) - self.mongo_uri = mongo_uri - self.postgres_uri = postgres_uri - self.mUtils = KumikoEcoUtils() - self.userUtils = KumikoEcoUserUtils() - self.userInvUtils = KumikoUserInvUtils() - self.add_item( - discord.ui.InputText( - label="Item Name", - style=discord.InputTextStyle.short, - min_length=1, - max_length=255, - required=True, - placeholder="Type in the item name here to purchase", - ) - ) - self.add_item( - discord.ui.InputText( - label="Amount", - style=discord.InputTextStyle.short, - min_length=1, - max_length=255, - required=True, - placeholder="Type in the item amount to purchase", - ) - ) - - async def callback(self, interaction: discord.Interaction): - await interaction.response.defer() - getUserInv = await self.userInvUtils.findItem( - user_id=interaction.user.id, - item_name=self.children[0].value, - uri=self.postgres_uri, - ) - getUser = await self.userUtils.getFirstUser( - user_id=interaction.user.id, uri=self.postgres_uri - ) - getRequestedItem = await self.mUtils.getRequestedPurchaseItem( - name=self.children[0].value, uri=self.mongo_uri - ) - - if getRequestedItem is None: - await interaction.followup.send( - f"The item {self.children[0].value} could not be found. Please try again", - ephemeral=True, - ) - elif getUser is None: - await interaction.followup.send( - "It seems like you forgot to create an account first. Please do that first", - ephemeral=True, - ) - else: - stock = dict(getRequestedItem)["amount"] - requestedAmount = int(self.children[1].value) - totalRemaining = stock - requestedAmount - totalToDeduct = int(dict(getUser)["lavender_petals"]) - int( - dict(getRequestedItem)["price"] - ) - - if stock <= 0: - await interaction.followup.send( - f"The item {self.children[0].value} is out of stock. Please try again later", - ephemeral=True, - ) - elif requestedAmount > stock: - await interaction.followup.send( - f"The amount requested ({requestedAmount}) is more than the stock ({stock}). Please try again", - ephemeral=True, - ) - elif requestedAmount == stock: - await self.userUtils.updateUserLavenderPetals( - user_id=interaction.user.id, - lavender_petals=totalToDeduct, - uri=self.postgres_uri, - ) - purchaseItem = await self.mUtils.purchaseItem( - user_inv=getUserInv, - requested_item=getRequestedItem, - current_stock=totalRemaining if totalRemaining > 0 else 0, - requested_amount=self.children[1].value, - user_id=interaction.user.id, - mongo_uri=self.mongo_uri, - postgres_uri=self.postgres_uri, - ) - await interaction.followup.send(purchaseItem, ephemeral=True) - elif requestedAmount < stock: - await self.userUtils.updateUserLavenderPetals( - user_id=interaction.user.id, - lavender_petals=totalToDeduct, - uri=self.postgres_uri, - ) - purchaseItem = await self.mUtils.purchaseItem( - user_inv=getUserInv, - requested_item=getRequestedItem, - current_stock=totalRemaining if totalRemaining > 0 else 0, - requested_amount=self.children[1].value, - user_id=interaction.user.id, - mongo_uri=self.mongo_uri, - postgres_uri=self.postgres_uri, - ) - await interaction.followup.send(purchaseItem, ephemeral=True) - else: - await interaction.followup.send( - "The transaction was not successful. Please try again", - ephemeral=True, - ) - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - -class GWSDeleteOneUserInvItemModal(discord.ui.Modal): - def __init__( - self, - uri: str, - models: List, - redis_host: str, - redis_port: int, - command_name: str, - *args, - **kwargs, - ): - super().__init__(*args, **kwargs) - self.uri = uri - self.models = models - self.redis_host = redis_host - self.redis_port = redis_port - self.command_name = command_name - self.cache = KumikoGWSCacheUtils( - uri=self.uri, - models=self.models, - redis_host=self.redis_host, - redis_port=self.redis_port, - ) - self.add_item( - discord.ui.InputText( - label="Name", - placeholder="Type in the item name to delete", - min_length=1, - max_length=255, - required=True, - style=discord.InputTextStyle.short, - ) - ) - self.add_item( - discord.ui.InputText( - label="Amount", - placeholder="Type in the item amount to delete", - min_length=1, - max_length=255, - required=True, - style=discord.InputTextStyle.short, - ) - ) - - async def callback(self, interaction: discord.Interaction): - async with KumikoCM(uri=self.uri, models=self.models): - userInvItem = await self.cache.cacheUserInvItem( - user_id=interaction.user.id, - name=self.children[0].value, - command_name=self.command_name, - ) - if userInvItem is None: - return await interaction.response.send_message( - f"The item ({self.children[0].value}) could not be found. Please try again", - ephemeral=True, - ) - elif int(self.children[1].value) > userInvItem["amount"]: - return await interaction.response.send_message( - f"The amount requested ({self.children[1].value}) is more than the amount you have ({userInvItem['amount']}). Please try again", - ephemeral=True, - ) - else: - await WSUserInv.filter( - user_id=interaction.user.id, name=userInvItem["name"] - ).update(amount=userInvItem["amount"] - int(self.children[1].value)) - return await interaction.response.send_message( - f"Deleted {self.children[1].value} {self.children[0].value}(s) from your inventory", - ephemeral=True, - ) - - -class EcoMarketplaceListItemModal(discord.ui.Modal): - def __init__( - self, - *args, - **kwargs, - ): - super().__init__(*args, **kwargs) - self.add_item( - discord.ui.InputText( - style=discord.InputTextStyle.short, - label="Item Name", - min_length=3, - max_length=255, - required=True, - row=0, - ) - ) - self.add_item( - discord.ui.InputText( - style=discord.InputTextStyle.short, - label="Price", - min_length=1, - max_length=20, - required=True, - row=2, - ) - ) - self.add_item( - discord.ui.InputText( - style=discord.InputTextStyle.long, - label="Description", - min_length=1, - max_length=512, - required=True, - row=1, - ) - ) - - async def callback(self, interaction: discord.Interaction) -> None: - # Wish i could use the cache here... but whatever - currUser = await EcoUser.filter(user_id=interaction.user.id).get_or_none() - if currUser is None: - await interaction.response.send_message( - "You do not have an account. Please create one using the /eco-user init command", - ephemeral=True, - ) - else: - await EcoMarketplace( - owner=currUser, - owner_name=interaction.user.name, - name=self.children[0].value, - description=self.children[2].value, - price=self.children[1].value, - amount=1, - ).save() - await interaction.response.send_message( - f"Added {self.children[0].value} to the marketplace", ephemeral=True - ) diff --git a/Bot/Libs/kumiko_ui_components/views.py b/Bot/Libs/kumiko_ui_components/views.py deleted file mode 100644 index ba1a7dcb..00000000 --- a/Bot/Libs/kumiko_ui_components/views.py +++ /dev/null @@ -1,452 +0,0 @@ -import asyncio -from typing import List - -import discord -import uvloop -from kumiko_economy import EcoUser -from kumiko_economy_utils import KumikoEcoUserUtils, KumikoEcoUtils, KumikoQuestsUtils -from kumiko_genshin_wish_sim import WSUserInv -from kumiko_utils import KumikoCM -from rin_exceptions import ItemNotFound, NoItemsError - -from .modals import QuestsDeleteOneModal - - -class MarketplacePurgeAllView(discord.ui.View): - async def on_timeout(self): - for child in self.children: - child.disabled = True - - def __init__(self, uri: str, *args, **kwargs): - super().__init__(*args, **kwargs) - self.uri = uri - self.utilsMain = KumikoEcoUtils() - - @discord.ui.button( - label="Yes", - row=0, - style=discord.ButtonStyle.primary, - emoji=discord.PartialEmoji.from_str("<:check:314349398811475968>"), - ) - async def button_callback(self, button, interaction): - mainChecker = await self.utilsMain.getAllOwnersItems( - owner=interaction.user.id, uri=self.uri - ) - try: - if len(mainChecker) == 0: - raise NoItemsError - else: - for items in mainChecker: - await self.utilsMain.purgeOwnersItems( - uuid=dict(items)["uuid"], - owner=dict(items)["owner"], - uri=self.uri, - ) - await interaction.response.send_message( - "All of your items listed on the marketplace have been deleted", - ephemeral=True, - ) - except NoItemsError: - await interaction.response.send_message( - "You don't have any items listed on the marketplace to delete. The transaction has been cancelled.", - ephemeral=True, - ) - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - @discord.ui.button( - label="No", - row=0, - style=discord.ButtonStyle.primary, - emoji=discord.PartialEmoji.from_str("<:xmark:314349398824058880>"), - ) - async def second_button_callback(self, button, interaction): - await interaction.response.send_message( - "Welp, you choose not to ig...", ephemeral=True - ) - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - -class QuestsPurgeAllView(discord.ui.View): - async def on_timeout(self): - for child in self.children: - child.disabled = True - - def __init__(self, user_uri: str, quests_uri: str, *args, **kwargs): - super().__init__(*args, **kwargs) - self.user_uri = user_uri - self.quests_uri = quests_uri - self.questsUtil = KumikoQuestsUtils() - self.userUtils = KumikoEcoUserUtils() - - @discord.ui.button( - label="Yes", - row=0, - style=discord.ButtonStyle.primary, - emoji=discord.PartialEmoji.from_str("<:check:314349398811475968>"), - ) - async def button_callback(self, button, interaction: discord.Interaction): - itemUUIDAuth = await self.questsUtil.getItemUUIDAuth( - user_id=interaction.user.id, - uri=self.user_uri, - ) - userRank = await self.userUtils.selectUserRank( - user_id=interaction.user.id, uri=self.user_uri - ) - try: - if len(itemUUIDAuth) == 0: - raise ItemNotFound - else: - for rank in userRank: - if int(rank) < 5: - await interaction.response.send_message( - f"Sorry, but you can't use the quests feature since you are current rank is {rank}", - ephemeral=True, - ) - else: - for item in itemUUIDAuth: - await self.questsUtil.purgeUserQuests( - user_id=interaction.user.id, - uuid=item, - uri=self.quests_uri, - ) - await interaction.response.send_message( - "All quests belonging to you have been purged.", - ephemeral=True, - ) - except ItemNotFound: - await interaction.response.send_message( - "You don't have any quests to delete!", ephemeral=True - ) - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - @discord.ui.button( - label="No", - row=0, - style=discord.ButtonStyle.primary, - emoji=discord.PartialEmoji.from_str("<:xmark:314349398824058880>"), - ) - async def second_button_callback(self, button, interaction: discord.Interaction): - await interaction.response.send_message( - "Well glad you choose not to...", ephemeral=True - ) - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - -class CreateAccountView(discord.ui.View): - async def on_timeout(self): - for child in self.children: - child.disabled = True - - def __init__(self, uri: str, *args, **kwargs): - super().__init__(*args, **kwargs) - self.uri = uri - self.utilsUser = KumikoEcoUserUtils() - - @discord.ui.button( - label="Yes", - row=0, - style=discord.ButtonStyle.primary, - emoji=discord.PartialEmoji.from_str("<:check:314349398811475968>"), - ) - async def button_callback(self, button, interaction): - getUser = await self.utilsUser.getFirstUser( - user_id=interaction.user.id, uri=self.uri - ) - if getUser is None: - await self.utilsUser.initUserAcct( - user_id=interaction.user.id, - username=interaction.user.name, - date_joined=discord.utils.utcnow().isoformat(), - uri=self.uri, - ) - await interaction.response.send_message( - "Confirmed. Now you have access to the marketplace!", ephemeral=True - ) - else: - await interaction.response.send_message( - "Looks like you already have an account. You can't sign up for extras", - ephemeral=True, - ) - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - @discord.ui.button( - label="No", - row=0, - style=discord.ButtonStyle.primary, - emoji=discord.PartialEmoji.from_str("<:xmark:314349398824058880>"), - ) - async def second_button_callback(self, button, interaction): - await interaction.response.send_message( - f"The operation has been canceled by the user {interaction.user.name}", - ephemeral=True, - ) - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - -class PurgeAccountView(discord.ui.View): - async def on_timeout(self): - for child in self.children: - child.disabled = True - - def __init__(self, uri: str, *args, **kwargs): - super().__init__(*args, **kwargs) - self.uri = uri - self.utilsUser = KumikoEcoUserUtils() - - @discord.ui.button( - label="Yes", - row=0, - style=discord.ButtonStyle.primary, - emoji=discord.PartialEmoji.from_str("<:check:314349398811475968>"), - ) - async def button_callback(self, button, interaction): - getUser = await self.utilsUser.getFirstUser( - user_id=interaction.user.id, uri=self.uri - ) - if getUser is None: - await interaction.response.send_message( - "You probably have already deleted the account...", ephemeral=True - ) - else: - await self.utilsUser.deleteUser(user_id=interaction.user.id, uri=self.uri) - await interaction.response.send_message( - "Confirmed. Your have permanently deleted your account.", ephemeral=True - ) - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - @discord.ui.button( - label="No", - row=0, - style=discord.ButtonStyle.primary, - emoji=discord.PartialEmoji.from_str("<:xmark:314349398824058880>"), - ) - async def second_button_callback(self, button, interaction): - await interaction.response.send_message( - f"The action has been cancelled by the user {interaction.user.name}", - ephemeral=True, - ) - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - -class QuestsDeleteOneConfirmView(discord.ui.View): - async def on_timeout(self): - for child in self.children: - child.disabled = True - - def __init__(self, uri: str, *args, **kwargs): - super().__init__(*args, **kwargs) - self.uri = uri - - @discord.ui.button( - label="Yes", - row=0, - style=discord.ButtonStyle.primary, - emoji=discord.PartialEmoji.from_str("<:check:314349398811475968>"), - ) - async def button_callback(self, button, interaction): - await interaction.response.send_modal( - QuestsDeleteOneModal(uri=self.uri, title="Delete a quest") - ) - - @discord.ui.button( - label="No", - row=0, - style=discord.ButtonStyle.primary, - emoji=discord.PartialEmoji.from_str("<:xmark:314349398824058880>"), - ) - async def second_button_callback(self, button, interaction): - await interaction.response.send_message( - f"The action has been cancelled by the user {interaction.user.name}", - ephemeral=True, - ) - - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) - - -class GWSPurgeInvView(discord.ui.View): - async def on_timeout(self): - for child in self.children: - child.disabled = True - - def __init__(self, uri: str, models: List, *args, **kwargs) -> None: - super().__init__(*args, **kwargs) - self.uri = uri - self.models = models - - @discord.ui.button( - label="Yes", - row=0, - style=discord.ButtonStyle.primary, - emoji=discord.PartialEmoji.from_str("<:check:314349398811475968>"), - ) - async def button_callback(self, button, interaction: discord.Interaction): - async with KumikoCM(uri=self.uri, models=self.models): - invExist = await WSUserInv.filter(user_id=interaction.user.id).exists() - if invExist is False: - for child in self.children: - child.disabled = True - await interaction.response.edit_message( - embed=discord.Embed( - description="It seems like you don't have anything in your GWS inventory. Please try again" - ), - view=self, - delete_after=15.0, - ) - else: - await WSUserInv.filter(user_id=interaction.user.id).delete() - for child in self.children: - child.disabled = True - await interaction.response.edit_message( - embed=discord.Embed( - description="Everything has been purged from your inventory. This cannot be recovered from." - ), - view=self, - delete_after=15.0, - ) - - @discord.ui.button( - label="No", - row=0, - style=discord.ButtonStyle.primary, - emoji=discord.PartialEmoji.from_str("<:xmark:314349398824058880>"), - ) - async def second_button_callback(self, button, interaction: discord.Interaction): - for child in self.children: - child.disabled = True - await interaction.response.edit_message( - embed=discord.Embed( - description=f"This action has been canceled by {interaction.user.name}" - ), - view=self, - delete_after=15.0, - ) - - -class EcoUserCreationView(discord.ui.View): - async def on_timeout(self): - for child in self.children: - child.disabled = True - - def __init__(self, *args, **kwargs): - super().__init__(*args, **kwargs) - - @discord.ui.button( - label="Yes", - row=0, - style=discord.ButtonStyle.primary, - emoji=discord.PartialEmoji.from_str("<:check:314349398811475968>"), - ) - async def confirm_create_callabck( - self, button, interaction: discord.Interaction - ) -> None: - doesUserExist = await EcoUser.filter(user_id=interaction.user.id).exists() - if doesUserExist is False: - await EcoUser( - user_id=interaction.user.id, - username=interaction.user.name, - date_joined=discord.utils.utcnow(), - ).save() - for child in self.children: - child.disabled = True - return await interaction.response.edit_message( - embed=discord.Embed( - description="Your economy account has been created! Have fun!" - ), - view=self, - delete_after=15.0, - ) - else: - for child in self.children: - child.disabled = True - return await interaction.response.edit_message( - embed=discord.Embed(description="You already have an economy account!"), - view=self, - delete_after=15.0, - ) - - @discord.ui.button( - label="No", - row=0, - style=discord.ButtonStyle.primary, - emoji=discord.PartialEmoji.from_str("<:xmark:314349398824058880>"), - ) - async def cancel_action_callback( - self, button, interaction: discord.Interaction - ) -> None: - for child in self.children: - child.disabled = True - await interaction.response.edit_message( - embed=discord.Embed( - description=f"This action has been canceled by {interaction.user.name}" - ), - view=self, - delete_after=15.0, - ) - - -class EcoUserPurgeView(discord.ui.View): - async def on_timeout(self): - for child in self.children: - child.disabled = True - - def __init__(self, *args, **kwargs): - super().__init__(*args, **kwargs) - - @discord.ui.button( - label="Yes", - row=0, - style=discord.ButtonStyle.primary, - emoji=discord.PartialEmoji.from_str("<:check:314349398811475968>"), - ) - async def confirm_create_callabck( - self, button, interaction: discord.Interaction - ) -> None: - doesUserExist = await EcoUser.filter(user_id=interaction.user.id).exists() - if doesUserExist is True: - await EcoUser.filter(user_id=interaction.user.id).delete() - for child in self.children: - child.disabled = True - return await interaction.response.edit_message( - embed=discord.Embed( - description="Your economy account has been deleted. All of your items that is associated with your account has been deleted as well." - ), - view=self, - delete_after=15.0, - ) - else: - for child in self.children: - child.disabled = True - return await interaction.response.edit_message( - embed=discord.Embed( - description="You don't have an economy account to delete!" - ), - view=self, - delete_after=15.0, - ) - - @discord.ui.button( - label="No", - row=0, - style=discord.ButtonStyle.primary, - emoji=discord.PartialEmoji.from_str("<:xmark:314349398824058880>"), - ) - async def cancel_action_callback( - self, button, interaction: discord.Interaction - ) -> None: - for child in self.children: - child.disabled = True - await interaction.response.edit_message( - embed=discord.Embed( - description=f"This action has been canceled by {interaction.user.name}" - ), - view=self, - delete_after=15.0, - ) From 05cf71e423278e7bb2df584137b632da02aefeb9 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Thu, 20 Apr 2023 19:00:06 +0000 Subject: [PATCH 031/184] [pip](deps-dev): Bump ruff from 0.0.261 to 0.0.262 (#306) Bumps [ruff](https://github.com/charliermarsh/ruff) from 0.0.261 to 0.0.262. - [Release notes](https://github.com/charliermarsh/ruff/releases) - [Changelog](https://github.com/charliermarsh/ruff/blob/main/BREAKING_CHANGES.md) - [Commits](https://github.com/charliermarsh/ruff/compare/v0.0.261...v0.0.262) --- updated-dependencies: - dependency-name: ruff dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 40 ++++++++++++++++++++-------------------- pyproject.toml | 2 +- 2 files changed, 21 insertions(+), 21 deletions(-) diff --git a/poetry.lock b/poetry.lock index 665c10b2..6447d7bb 100644 --- a/poetry.lock +++ b/poetry.lock @@ -1,4 +1,4 @@ -# This file is automatically @generated by Poetry 1.4.2 and should not be changed by hand. +# This file is automatically @generated by Poetry and should not be changed by hand. [[package]] name = "aiodns" @@ -2845,29 +2845,29 @@ idna2008 = ["idna"] [[package]] name = "ruff" -version = "0.0.261" +version = "0.0.262" description = "An extremely fast Python linter, written in Rust." category = "dev" optional = false python-versions = ">=3.7" files = [ - {file = "ruff-0.0.261-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:6624a966c4a21110cee6780333e2216522a831364896f3d98f13120936eff40a"}, - {file = "ruff-0.0.261-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:2dba68a9e558ab33e6dd5d280af798a2d9d3c80c913ad9c8b8e97d7b287f1cc9"}, - {file = "ruff-0.0.261-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:8dbd0cee5a81b0785dc0feeb2640c1e31abe93f0d77c5233507ac59731a626f1"}, - {file = "ruff-0.0.261-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:581e64fa1518df495ca890a605ee65065101a86db56b6858f848bade69fc6489"}, - {file = "ruff-0.0.261-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:cc970f6ece0b4950e419f0252895ee42e9e8e5689c6494d18f5dc2c6ebb7f798"}, - {file = "ruff-0.0.261-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:8fa98e747e0fe185d65a40b0ea13f55c492f3b5f9a032a1097e82edaddb9e52e"}, - {file = "ruff-0.0.261-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:f268d52a71bf410aa45c232870c17049df322a7d20e871cfe622c9fc784aab7b"}, - {file = "ruff-0.0.261-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:d1293acc64eba16a11109678dc4743df08c207ed2edbeaf38b3e10eb2597321b"}, - {file = "ruff-0.0.261-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:d95596e2f4cafead19a6d1ec0b86f8fda45ba66fe934de3956d71146a87959b3"}, - {file = "ruff-0.0.261-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:4bcec45abdf65c1328a269cf6cc193f7ff85b777fa2865c64cf2c96b80148a2c"}, - {file = "ruff-0.0.261-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:6c5f397ec0af42a434ad4b6f86565027406c5d0d0ebeea0d5b3f90c4bf55bc82"}, - {file = "ruff-0.0.261-py3-none-musllinux_1_2_i686.whl", hash = "sha256:39abd02342cec0c131b2ddcaace08b2eae9700cab3ca7dba64ae5fd4f4881bd0"}, - {file = "ruff-0.0.261-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:aaa4f52a6e513f8daa450dac4859e80390d947052f592f0d8e796baab24df2fc"}, - {file = "ruff-0.0.261-py3-none-win32.whl", hash = "sha256:daff64b4e86e42ce69e6367d63aab9562fc213cd4db0e146859df8abc283dba0"}, - {file = "ruff-0.0.261-py3-none-win_amd64.whl", hash = "sha256:0fbc689c23609edda36169c8708bb91bab111d8f44cb4a88330541757770ab30"}, - {file = "ruff-0.0.261-py3-none-win_arm64.whl", hash = "sha256:d2eddc60ae75fc87f8bb8fd6e8d5339cf884cd6de81e82a50287424309c187ba"}, - {file = "ruff-0.0.261.tar.gz", hash = "sha256:c1c715b0d1e18f9c509d7c411ca61da3543a4aa459325b1b1e52b8301d65c6d2"}, + {file = "ruff-0.0.262-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:c26c1abd420d041592d05d63aee8c6a18feb24aed4deb6e91129e9f2c7b4914a"}, + {file = "ruff-0.0.262-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:b379e9765afa679316e52288a942df085e590862f8945088936a7bce3116d8f3"}, + {file = "ruff-0.0.262-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:9b7e0ca6821aafbd2b059df3119fcd5881250721ca8e825789fd2c471f7c59be"}, + {file = "ruff-0.0.262-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:4cca35e2aeddff72bb4379a1dabc134e0c0d25ebc754a2cb733a1f8d4dbbb5e0"}, + {file = "ruff-0.0.262-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:15bf5533ce169aebbafa00017987f673e879f60a625d932b464b8cdaf32a4fce"}, + {file = "ruff-0.0.262-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:3909e249d984c4517194005a1c30eaa0c3a6d906c789d9fc0c9c7e007fb3e759"}, + {file = "ruff-0.0.262-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:4e2813013a19b3e147e840bdb2e42db5825b53b47364e58e7b467c5fa47ffda2"}, + {file = "ruff-0.0.262-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:d25a94996b2037e566c2a801c8b324c0a826194d5d4d90ad7c1ccb8cf06521fa"}, + {file = "ruff-0.0.262-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:85ca04348372efc59f6ee808d903d35e0d352cf2c78e487757cd48b65104b83e"}, + {file = "ruff-0.0.262-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:24f989363e9bb5d0283490298102a5218682e49ebf300e445d69e24bee03ac83"}, + {file = "ruff-0.0.262-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:3c24e678e43ca4b67e29cc9a7a54eea05f31a5898cbf17bfec47b68f08d32a60"}, + {file = "ruff-0.0.262-py3-none-musllinux_1_2_i686.whl", hash = "sha256:0baff3c9a22227358ea109c165efe62dbdd0f2b9fd5256567dda8682b444fe23"}, + {file = "ruff-0.0.262-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:083bac6e238d8b7d5ac3618666ea63b7ac661cf94c5da160070a58e190082831"}, + {file = "ruff-0.0.262-py3-none-win32.whl", hash = "sha256:15bbfa2d15c137717627e0d56b0e535ae297b734551e34e03fcc25d7642cf43a"}, + {file = "ruff-0.0.262-py3-none-win_amd64.whl", hash = "sha256:973ac29193f718349cf5746b7d86dfeaf7d40e9651ed97790a9b9327305888b9"}, + {file = "ruff-0.0.262-py3-none-win_arm64.whl", hash = "sha256:f102904ebe395acd2a181d295b98120acd7a63f732b691672977fc688674f4af"}, + {file = "ruff-0.0.262.tar.gz", hash = "sha256:faea54231c265f5349975ba6f3d855b71881a01f391b2000c47740390c6d5f68"}, ] [[package]] @@ -3516,4 +3516,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "ece9e205daf1f2c8278fd2e9a8a91bc1b6e213f65a84aa3d898371ed55d567ef" +content-hash = "b5719b97b2f2588c2a668409d507f89390be714ac7c723987fb0cb42f3240eda" diff --git a/pyproject.toml b/pyproject.toml index 6aaaa004..87c3b05f 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -35,7 +35,7 @@ pyinstrument = "^4.4.0" pyright = "^1.1.303" watchfiles = "^0.19.0" jishaku = "^2.5.1" -ruff = "^0.0.261" +ruff = "^0.0.262" [tool.poetry.group.docs.dependencies] From 5d74e397cf2e6b7f9a1c57c552c2112782ac6bb0 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Thu, 20 Apr 2023 19:00:09 +0000 Subject: [PATCH 032/184] [Actions](deps): Bump actions/setup-python from 4.5.0 to 4.6.0 (#307) Bumps [actions/setup-python](https://github.com/actions/setup-python) from 4.5.0 to 4.6.0. - [Release notes](https://github.com/actions/setup-python/releases) - [Commits](https://github.com/actions/setup-python/compare/v4.5.0...v4.6.0) --- updated-dependencies: - dependency-name: actions/setup-python dependency-type: direct:production update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- .github/workflows/codeql-analysis.yml | 2 +- .github/workflows/lint.yml | 2 +- .github/workflows/snyk.yml | 2 +- .github/workflows/tests.yml | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) diff --git a/.github/workflows/codeql-analysis.yml b/.github/workflows/codeql-analysis.yml index 4f78d576..b1da4f35 100644 --- a/.github/workflows/codeql-analysis.yml +++ b/.github/workflows/codeql-analysis.yml @@ -26,7 +26,7 @@ jobs: uses: actions/checkout@v3 - name: Set up Python 3.11 id: setup-python - uses: actions/setup-python@v4.5.0 + uses: actions/setup-python@v4.6.0 with: python-version: '3.11' - name: Set up Poetry diff --git a/.github/workflows/lint.yml b/.github/workflows/lint.yml index 59c8b85d..87c7a988 100644 --- a/.github/workflows/lint.yml +++ b/.github/workflows/lint.yml @@ -41,7 +41,7 @@ jobs: - name: Set up Python ${{ matrix.version }} id: setup-python - uses: actions/setup-python@v4.5.0 + uses: actions/setup-python@v4.6.0 with: python-version: ${{ matrix.version }} diff --git a/.github/workflows/snyk.yml b/.github/workflows/snyk.yml index b1c0a75b..aab877b9 100644 --- a/.github/workflows/snyk.yml +++ b/.github/workflows/snyk.yml @@ -14,7 +14,7 @@ jobs: uses: actions/checkout@v3 - name: Set up Python 3.11 id: setup-python - uses: actions/setup-python@v4.5.0 + uses: actions/setup-python@v4.6.0 with: python-version: '3.11' - name: Set up Node.js 18 diff --git a/.github/workflows/tests.yml b/.github/workflows/tests.yml index ed4a8039..4737ee17 100644 --- a/.github/workflows/tests.yml +++ b/.github/workflows/tests.yml @@ -58,7 +58,7 @@ jobs: - name: Set up Python id: setup-python - uses: actions/setup-python@v4.5.0 + uses: actions/setup-python@v4.6.0 with: python-version: ${{ matrix.version }} From be63e745b4cc72e056fb49310f4b68089538c507 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Fri, 21 Apr 2023 18:59:15 +0000 Subject: [PATCH 033/184] [pip](deps-dev): Bump pyright from 1.1.303 to 1.1.304 (#308) Bumps [pyright](https://github.com/RobertCraigie/pyright-python) from 1.1.303 to 1.1.304. - [Release notes](https://github.com/RobertCraigie/pyright-python/releases) - [Commits](https://github.com/RobertCraigie/pyright-python/compare/v1.1.303...v1.1.304) --- updated-dependencies: - dependency-name: pyright dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index 6447d7bb..53120528 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2613,14 +2613,14 @@ diagrams = ["jinja2", "railroad-diagrams"] [[package]] name = "pyright" -version = "1.1.303" +version = "1.1.304" description = "Command line wrapper for pyright" category = "dev" optional = false python-versions = ">=3.7" files = [ - {file = "pyright-1.1.303-py3-none-any.whl", hash = "sha256:8fe3d122d7e965e2df2cef64e1ceb98cff8200f458e7892d92a4c21ee85689c7"}, - {file = "pyright-1.1.303.tar.gz", hash = "sha256:7daa516424555681e8974b21a95c108c5def791bf5381522b1410026d4da62c1"}, + {file = "pyright-1.1.304-py3-none-any.whl", hash = "sha256:70021bbae07fc28ed16e435f5efa65cd71e06a1888d9ca998798c283d4b3d010"}, + {file = "pyright-1.1.304.tar.gz", hash = "sha256:87adec38081904c939e3657ab23d5fc40b7ccc22709be0af1859fc785ae4ea61"}, ] [package.dependencies] @@ -3516,4 +3516,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "b5719b97b2f2588c2a668409d507f89390be714ac7c723987fb0cb42f3240eda" +content-hash = "2c6c5f3bcaa8b07dfefd062eadeba6fbb6cdebe244cb8db507ac8d77dcdbcdc8" diff --git a/pyproject.toml b/pyproject.toml index 87c3b05f..abf22da1 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -32,7 +32,7 @@ pytest-cov = "^4.0.0" [tool.poetry.group.dev.dependencies] pre-commit = "^3.2.2" pyinstrument = "^4.4.0" -pyright = "^1.1.303" +pyright = "^1.1.304" watchfiles = "^0.19.0" jishaku = "^2.5.1" ruff = "^0.0.262" From 8e04f83a53988aa975d979d6c192398c81eead57 Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Fri, 21 Apr 2023 23:48:45 -0700 Subject: [PATCH 034/184] Fix cache decos The cache decos were completely broken when debugged. Now should work --- Bot/Cogs/economy.py | 168 +++++++++++++++--------------- Bot/Cogs/ipc.py | 72 ++++++------- Bot/Libs/cache/__init__.py | 32 +++--- Bot/Libs/cache/decorators.py | 174 ++++++++++++++++---------------- Bot/Libs/economy/cache_utils.py | 52 +++++----- schema.prisma | 140 ++++++++++++------------- tests/redis/test_cache_deco.py | 76 +++++++------- 7 files changed, 352 insertions(+), 362 deletions(-) diff --git a/Bot/Cogs/economy.py b/Bot/Cogs/economy.py index b501c600..284b21b2 100644 --- a/Bot/Cogs/economy.py +++ b/Bot/Cogs/economy.py @@ -1,84 +1,84 @@ -from typing import Union - -import discord -from discord.ext import commands -from kumikocore import KumikoCore -from Libs.economy import getUser -from Libs.ui.economy import RegisterView -from Libs.utils import Embed -from prisma.models import User - - -class Economy(commands.Cog): - """Earn, sell, and interact with Kumiko's economy!""" - - def __init__(self, bot: KumikoCore) -> None: - self.bot = bot - super().__init__() - - @commands.hybrid_group(name="marketplace") - async def eco(self, ctx: commands.Context) -> None: - if ctx.invoked_subcommand is None: - await ctx.send_help(ctx.command) - - @eco.command(name="buy") - async def marketplaceBuy(self, ctx: commands.Context) -> None: - """Buy an item from the marketplace""" - await ctx.send("Buy") - - @eco.command(name="inventory", aliases=["inv"]) - async def marketplaceInv(self, ctx: commands.Context) -> None: - """View your marketplace inventory""" - currUser = await User.prisma().find_first( - where={"id": ctx.author.id}, include={"user_inv": True} - ) - if currUser is None: - await ctx.send( - embed=Embed( - title="No account!", - description="You don't even have an account yet!", - ) - ) - else: - if len() == 0: # type: ignore - await ctx.send( - embed=Embed( - title="No items!", - description="You don't have any items in your inventory!", - ) - ) - else: - await ctx.send( - embed=Embed(title="Inventory", description="Here are your items!") - ) - - @commands.hybrid_command(name="register") - async def register(self, ctx: commands.Context) -> None: - """Create an account for the economy""" - view = RegisterView() - embed = Embed( - title="Register", - description="Register for the economy! Before you do so, please make sure to follow the TOS. By registering, you are agreeing to use these services.", - ) - await ctx.send(embed=embed, view=view) - - @commands.hybrid_command(name="wallet") - async def wallet(self, ctx: commands.Context) -> Union[discord.Message, None]: - """Checks your wallet""" - user = await getUser(ctx.author.id) - if user is None: - return await ctx.send( - embed=Embed( - title="No Wallet", description="You don't have a wallet yet!" - ) - ) - userDesc = f"**Rank**: {user['rank']}\n\n**Balance**: {user['petals']}" - embed = Embed( - title=f"{ctx.author.name}'s Wallet", - description=userDesc, - ) - await ctx.send(embed=embed) - - -async def setup(bot: KumikoCore) -> None: - await bot.add_cog(Economy(bot)) +from discord.ext import commands +from kumikocore import KumikoCore +from Libs.economy import getUser +from Libs.ui.economy import RegisterView +from Libs.utils import Embed +from prisma.models import User + + +class Economy(commands.Cog): + """Earn, sell, and interact with Kumiko's economy!""" + + def __init__(self, bot: KumikoCore) -> None: + self.bot = bot + super().__init__() + + @commands.hybrid_group(name="marketplace") + async def eco(self, ctx: commands.Context) -> None: + if ctx.invoked_subcommand is None: + await ctx.send_help(ctx.command) + + @eco.command(name="buy") + async def marketplaceBuy(self, ctx: commands.Context) -> None: + """Buy an item from the marketplace""" + await ctx.send("Buy") + + @eco.command(name="inventory", aliases=["inv"]) + async def marketplaceInv(self, ctx: commands.Context) -> None: + """View your marketplace inventory""" + currUser = await User.prisma().find_first( + where={"id": ctx.author.id}, include={"user_inv": True} + ) + if currUser is None: + await ctx.send( + embed=Embed( + title="No account!", + description="You don't even have an account yet!", + ) + ) + else: + if len() == 0: # type: ignore + await ctx.send( + embed=Embed( + title="No items!", + description="You don't have any items in your inventory!", + ) + ) + else: + await ctx.send( + embed=Embed(title="Inventory", description="Here are your items!") + ) + + @commands.hybrid_command(name="register") + async def register(self, ctx: commands.Context) -> None: + """Create an account for the economy""" + view = RegisterView() + embed = Embed( + title="Register", + description="Register for the economy! Before you do so, please make sure to follow the TOS. By registering, you are agreeing to use these services.", + ) + await ctx.send(embed=embed, view=view) + + @commands.hybrid_command(name="wallet") + async def wallet(self, ctx: commands.Context) -> None: + """Checks your wallet""" + user = await getUser( + id=ctx.author.id, includes={"user_inv": False, "marketplace": False} + ) + if user is None: + await ctx.send( + embed=Embed( + title="No Wallet", description="You don't have a wallet yet!" + ) + ) + else: + userDesc = f"**Rank**: {user['rank']}\n\n**Balance**: {user['petals']}" # type: ignore + embed = Embed( + title=f"{ctx.author.name}'s Wallet", + description=userDesc, + ) + await ctx.send(embed=embed) + + +async def setup(bot: KumikoCore) -> None: + await bot.add_cog(Economy(bot)) diff --git a/Bot/Cogs/ipc.py b/Bot/Cogs/ipc.py index 84039150..a11372fa 100644 --- a/Bot/Cogs/ipc.py +++ b/Bot/Cogs/ipc.py @@ -1,36 +1,36 @@ -import os -from typing import Dict - -from discord.ext import commands, ipc -from discord.ext.ipc.objects import ClientPayload -from discord.ext.ipc.server import Server -from dotenv import load_dotenv -from kumikocore import KumikoCore - -load_dotenv() - -IPC_SECRET_KEY = os.getenv("IPC_SECRET_KEY") -IPC_HOST = os.environ["IPC_HOST"] - - -class IPCServer(commands.Cog): - def __init__(self, bot: KumikoCore): - self.bot = bot - self.ipc = ipc.Server( # type: ignore - self.bot, secret_key=IPC_SECRET_KEY, host=IPC_HOST - ) - - async def cog_load(self) -> None: - await self.ipc.start() - - async def cog_unload(self) -> None: - await self.ipc.stop() - - @Server.route() - async def get_user_data(self, data: ClientPayload) -> Dict: - user = self.bot.get_user(data.user_id) - return user._to_minimal_user_json() # type: ignore - - -async def setup(bot: KumikoCore): - await bot.add_cog(IPCServer(bot)) +import os +from typing import Dict + +from discord.ext import commands, ipc +from discord.ext.ipc.objects import ClientPayload +from discord.ext.ipc.server import Server +from dotenv import load_dotenv +from kumikocore import KumikoCore + +load_dotenv() + +IPC_SECRET_KEY = os.getenv("IPC_SECRET_KEY") +IPC_HOST = os.environ["IPC_HOST"] + + +class IPCServer(commands.Cog): + def __init__(self, bot: KumikoCore): + self.bot = bot + self.ipc = ipc.Server( # type: ignore + self.bot, secret_key=IPC_SECRET_KEY, host=IPC_HOST + ) + + async def cog_load(self) -> None: + await self.ipc.start() + + async def cog_unload(self) -> None: + await self.ipc.stop() + + @Server.route() + async def get_user_data(self, data: ClientPayload) -> Dict: + user = self.bot.get_user(data.user_id) + return user.to_minimal_user_json() # type: ignore + + +async def setup(bot: KumikoCore): + await bot.add_cog(IPCServer(bot)) diff --git a/Bot/Libs/cache/__init__.py b/Bot/Libs/cache/__init__.py index 071c22b2..5acb5fb7 100644 --- a/Bot/Libs/cache/__init__.py +++ b/Bot/Libs/cache/__init__.py @@ -1,16 +1,16 @@ -from .cp_manager import KumikoCPManager -from .decorators import cached, cachedJson -from .global_cp import kumikoCP -from .key_builder import CommandKeyBuilder -from .mem_cache import MemoryCache -from .redis_cache import KumikoCache - -__all__ = [ - "MemoryCache", - "CommandKeyBuilder", - "KumikoCache", - "cached", - "cachedJson", - "KumikoCPManager", - "kumikoCP", -] +from .cp_manager import KumikoCPManager +from .decorators import cache, cacheJson +from .global_cp import kumikoCP +from .key_builder import CommandKeyBuilder +from .mem_cache import MemoryCache +from .redis_cache import KumikoCache + +__all__ = [ + "MemoryCache", + "CommandKeyBuilder", + "KumikoCache", + "KumikoCPManager", + "kumikoCP", + "cache", + "cacheJson", +] diff --git a/Bot/Libs/cache/decorators.py b/Bot/Libs/cache/decorators.py index 95bd56b6..436722cc 100644 --- a/Bot/Libs/cache/decorators.py +++ b/Bot/Libs/cache/decorators.py @@ -1,87 +1,87 @@ -import uuid -from functools import wraps -from typing import Any, Callable, Optional - -from redis.asyncio.connection import ConnectionPool - -from .redis_cache import CommandKeyBuilder, KumikoCache - - -def cached( - connection_pool: ConnectionPool, - command_key: Optional[str], - ttl: int = 30, -) -> Callable[..., Any]: - """A decorator to cache the result of a function that returns a `str` to Redis. - - **Note**: The return type of the corountine used has to be `str` or `bytes` - - Args: - connection_pool (ConnectionPool): Redis connection pool to use - command_key (Optional[str]): Command key to use - ttl (int, optional): TTL (Time-To-Live). Defaults to 30. - - Returns: - Callable[..., Any]: The wrapper function - """ - - def wrapper(func: Callable[..., Any]) -> Any: - @wraps(func) - async def wrapped(*args: Any, **kwargs: Any) -> Any: - currFunc = await func(*args, **kwargs) - cache = KumikoCache(connection_pool=connection_pool) - key = ( - CommandKeyBuilder(id=uuid.uuid4(), command=cached.__name__) - if command_key is None - else command_key - ) - if await cache.cacheExists(key=key) is False: - await cache.setBasicCache(key=key, value=currFunc, ttl=ttl) - else: - return await cache.getBasicCache(key=key) - return currFunc - - return wrapped - - return wrapper - - -def cachedJson( - connection_pool: ConnectionPool, - command_key: Optional[str], - ttl: int = 30, -) -> Callable[..., Any]: - """A decorator to cache the result of a function that returns a `dict` to Redis. - - **Note**: The return type of the corountine used has to be `dict` - - Args: - connection_pool (ConnectionPool): Redis connection pool to use - command_key (Optional[str]): Command key to use - ttl (int, optional): TTL (Time-To-Live). Defaults to 30. - - Returns: - Callable[..., Any]: The wrapper function - """ - - def wrapper(func: Callable[..., Any]) -> Any: - @wraps(func) - async def wrapped(*args: Any, **kwargs: Any) -> Any: - currFunc = await func(*args, **kwargs) - if currFunc is None: - return None - cache = KumikoCache(connection_pool=connection_pool) - key = ( - CommandKeyBuilder(id=uuid.uuid4(), command=cachedJson.__name__) - if command_key is None - else command_key - ) - if await cache.cacheExists(key=key) is False: - await cache.setJSONCache(key=key, value=currFunc, ttl=ttl) - else: - return await cache.getJSONCache(key=key) - return currFunc - - return wrapped - - return wrapper +import uuid +from functools import wraps +from typing import Any, Callable, Union + +from redis.asyncio.connection import ConnectionPool + +from .redis_cache import CommandKeyBuilder, KumikoCache + + +class cache: + """A decorator to cache the result of a function that returns a `str` to Redis. + + **Note**: The return type of the coroutine used has to be `str` or `bytes` + + Args: + connection_pool (ConnectionPool): Redis connection pool to use + ttl (int, optional): TTL (Time-To-Live). Defaults to 30. + """ + + def __init__(self, connection_pool: ConnectionPool, ttl: int = 30): + self.connection_pool = connection_pool + self.ttl = ttl + + def __call__(self, func: Callable, *args: Any, **kwargs: Any): + @wraps(func) + async def wrapper(id: int, *args: Any, **kwargs: Any): + return await self.deco(func, id, *args, **kwargs) + + return wrapper + + async def deco(self, func: Callable, id: Union[int, None], *args, **kwargs): + res = await func(id, *args, **kwargs) + if res is None: + return None + cache = KumikoCache(connection_pool=self.connection_pool) + key = CommandKeyBuilder( + prefix="cache", + namespace="kumiko", + id=id if id is not None else uuid.uuid4(), + command=func.__name__, + ) + + if await cache.cacheExists(key=key) is False: + await cache.setBasicCache(key=key, value=res, ttl=self.ttl) + return res + return await cache.getBasicCache(key=key) + + +class cacheJson: + """ + A decorator to cache the result of a function that returns a `dict` to Redis. + + **Note**: The return type of the coroutine used has to be `dict` + + Args: + connection_pool (ConnectionPool): Redis connection pool to use + ttl (int, optional): TTL (Time-To-Live). + Defaults to 30. + """ + + def __init__(self, connection_pool: ConnectionPool, ttl: int = 30): + self.connection_pool = connection_pool + self.ttl = ttl + + def __call__(self, func: Callable, *args: Any, **kwargs: Any): + @wraps(func) + async def wrapper(id: int, *args: Any, **kwargs: Any): + return await self.deco(func, id, *args, **kwargs) + + return wrapper + + async def deco(self, func: Callable, id: Union[int, None], *args, **kwargs): + res = await func(id, *args, **kwargs) + if res is None: + return None + cache = KumikoCache(connection_pool=self.connection_pool) + key = CommandKeyBuilder( + prefix="cache", + namespace="kumiko", + id=id if id is not None else uuid.uuid4(), + command=func.__name__, + ) + + if await cache.cacheExists(key=key) is False: + await cache.setJSONCache(key=key, value=res, ttl=self.ttl) + return res + return await cache.getJSONCache(key=key) diff --git a/Bot/Libs/economy/cache_utils.py b/Bot/Libs/economy/cache_utils.py index 2382de60..06e7ca56 100644 --- a/Bot/Libs/economy/cache_utils.py +++ b/Bot/Libs/economy/cache_utils.py @@ -1,29 +1,23 @@ -import uuid -from typing import Dict, Union - -from prisma.models import User -from prisma.types import UserInclude - -from ..cache import CommandKeyBuilder, cachedJson, kumikoCP - - -@cachedJson( - connection_pool=kumikoCP.getConnPool(), - command_key=CommandKeyBuilder( - prefix="cache", namespace="kumiko", id=uuid.uuid4(), command="internal_get_user" - ), -) -async def getUser(user_id: int, includes: UserInclude) -> Union[Dict, None]: - """[Coroutine] Helper coroutine to obtain a user's profile from the database - - For reducing the latency for accessing the data, this helper coroutine is cached on Redis (w/ RedisJSON). Also note that this coroutine expects that the Prisma query engine and database are already connected. - - Args: - user_id (int): User ID to use to search up the user - includes (Dict[str, bool], optional): Which schemas to include (for 1-n relations) Note that it must be a dict containing the column, and to include it or not. Defaults to {"inv": False, "marketplace": False}. - - Returns: - Union[Dict, None]: The user's profile, or None if the user is not found - """ - user = await User.prisma().find_unique(where={"id": user_id}, include=includes) - return user.dict() if user is not None else None +from typing import Dict, Union + +from prisma.models import User +from prisma.types import UserInclude + +from ..cache import cacheJson, kumikoCP + + +@cacheJson(connection_pool=kumikoCP.getConnPool()) +async def getUser(id: int, includes: UserInclude) -> Union[Dict, None]: + """[Coroutine] Helper coroutine to obtain a user's profile from the database + + For reducing the latency for accessing the data, this helper coroutine is cached on Redis (w/ RedisJSON). Also note that this coroutine expects that the Prisma query engine and database are already connected. + + Args: + id (int): User ID to use to search up the user + includes (UserInclude, optional): Which schemas to include (for 1-n relations) Note that it must be a dict containing the column, and to include it or not. + + Returns: + Union[Dict, None]: The user's profile, or None if the user is not found + """ + user = await User.prisma().find_unique(where={"id": id}, include=includes) + return user.dict() if user is not None else None diff --git a/schema.prisma b/schema.prisma index 2ab24cb9..9d05c30e 100644 --- a/schema.prisma +++ b/schema.prisma @@ -1,74 +1,66 @@ -datasource db { - provider = "postgresql" - url = env("DATABASE_URL") -} - -generator client { - provider = "prisma-client-py" - recursive_type_depth = 5 -} - -model User { - id BigInt @id @unique - name String - rank Int @default(0) - petals Int @default(0) - date_joined DateTime @default(now()) - marketplace Marketplace? // A user can also optionally own a marketplace - user_inv UserInv[] // Give the user a default inventory that has one item that is worth 0 petals - // quests Quest[] // This default quest may be used to get the user to explore the marketplace - // QuestClaimer QuestClaimer? // A user can only claim one quest -} - -model UserInv { - id BigInt @id @unique - user User @relation(fields: [user_id], references: [id]) - items Item[] - user_id BigInt - amount Int -} - -model Item { - id String @id @default(uuid()) - marketplace Marketplace @relation(fields: [marketplace_id], references: [id]) - marketplace_id String - user_inv UserInv @relation(fields: [user_inv_id], references: [id]) - user_inv_id BigInt - name String - description String @db.Text - price Float -} - -model Marketplace { - id String @id @default(uuid()) - name String - description String @db.Text - date_created DateTime @default(now()) - owner User @relation(fields: [owner_id], references: [id]) - owner_id BigInt @unique - items Item[] -} - -// model QuestClaimer { -// id BigInt @id @unique -// user User @relation(fields: [user_id], references: [id]) -// user_id BigInt @unique -// claimed_at DateTime -// quest Quest[] -// } - -// model Quest { -// id String @id @default(uuid()) -// author User @relation(fields: [author_id], references: [id]) -// author_id BigInt -// claimer QuestClaimer @relation(fields: [claimer_id], references: [id]) -// claimer_id BigInt -// name String -// description String @db.Text -// reward Int @default(0) -// active Boolean @default(true) -// claimed Boolean @default(false) -// date_created DateTime @default(now()) -// date_completed DateTime? -// end_datetime DateTime? -// } +datasource db { + provider = "postgresql" + url = env("DATABASE_URL") +} + +generator client { + provider = "prisma-client-py" + recursive_type_depth = 5 +} + +model User { + id BigInt @id @unique + name String + rank Int @default(0) + petals Int @default(0) + date_joined DateTime @default(now()) + marketplace Marketplace? // A user can also optionally own a marketplace + user_inv MItem[] // Give the user a default inventory that has one item that is worth 0 petals + // quests Quest[] // This default quest may be used to get the user to explore the marketplace + // QuestClaimer QuestClaimer? // A user can only claim one quest +} + +model MItem { + id String @id @default(uuid()) + marketplace Marketplace @relation(fields: [marketplace_id], references: [id]) + marketplace_id String + user User? @relation(fields: [userId], references: [id]) + userId BigInt? + name String + description String @db.Text + price Float +} + +model Marketplace { + id String @id @default(uuid()) + name String + description String @db.Text + date_created DateTime @default(now()) + owner User @relation(fields: [owner_id], references: [id]) + owner_id BigInt @unique + items MItem[] +} + +// model QuestClaimer { +// id BigInt @id @unique +// user User @relation(fields: [user_id], references: [id]) +// user_id BigInt @unique +// claimed_at DateTime +// quest Quest[] +// } + +// model Quest { +// id String @id @default(uuid()) +// author User @relation(fields: [author_id], references: [id]) +// author_id BigInt +// claimer QuestClaimer @relation(fields: [claimer_id], references: [id]) +// claimer_id BigInt +// name String +// description String @db.Text +// reward Int @default(0) +// active Boolean @default(true) +// claimed Boolean @default(false) +// date_created DateTime @default(now()) +// date_completed DateTime? +// end_datetime DateTime? +// } diff --git a/tests/redis/test_cache_deco.py b/tests/redis/test_cache_deco.py index 4293935e..844b7864 100644 --- a/tests/redis/test_cache_deco.py +++ b/tests/redis/test_cache_deco.py @@ -1,36 +1,40 @@ -import sys -from pathlib import Path - -import pytest - -path = Path(__file__).parents[2].joinpath("Bot") -sys.path.append(str(path)) - -from Libs.cache import cached, cachedJson -from redis.asyncio.connection import ConnectionPool - - -@pytest.mark.asyncio -async def test_cache_deco(): - connPool = ConnectionPool(max_connections=25) - - @cached(connection_pool=connPool, command_key=None) - async def testFunc(): - return "Hello World" - - res = await testFunc() - assert (await testFunc() == "Hello World") and isinstance(res, str) # nosec - - -@pytest.mark.asyncio -async def test_cache_deco_json(): - connPool = ConnectionPool(max_connections=25) - - @cachedJson(connection_pool=connPool, command_key=None) - async def testFuncJSON(): - return {"message": "Hello World"} - - res = await testFuncJSON() - assert (await testFuncJSON() == {"message": "Hello World"}) and isinstance( # nosec - res, dict - ) +import sys +from pathlib import Path + +import pytest + +path = Path(__file__).parents[2].joinpath("Bot") +sys.path.append(str(path)) + +from Libs.cache import cache, cacheJson +from redis.asyncio.connection import ConnectionPool + + +@pytest.mark.asyncio +async def test_cache_deco(): + connPool = ConnectionPool(max_connections=25) + + @cache(connection_pool=connPool) + async def testFunc(id=1235): + return "Hello World" + + res = await testFunc(1235) + assert (await testFunc(1235) == "Hello World".encode("utf-8")) and isinstance( + res, str + ) # nosec + + +@pytest.mark.asyncio +async def test_cache_deco_json(): + connPool = ConnectionPool(max_connections=25) + + @cacheJson(connection_pool=connPool) + async def testFuncJSON(id=182348478): + return {"message": "Hello World"} + + res = await testFuncJSON(182348478) + assert ( + await testFuncJSON(182348478) == {"message": "Hello World"} + ) and isinstance( # nosec + res, dict + ) From b8aab35b5f48d78d158305358d90efffeef1748d Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Fri, 21 Apr 2023 23:57:03 -0700 Subject: [PATCH 035/184] Add tests for greedy formatter --- Bot/Libs/utils/greedy_formatter.py | 31 ++++++++++++++++++++-------- tests/utils/test_greedy_formatter.py | 25 ++++++++++++++++++++++ 2 files changed, 47 insertions(+), 9 deletions(-) create mode 100644 tests/utils/test_greedy_formatter.py diff --git a/Bot/Libs/utils/greedy_formatter.py b/Bot/Libs/utils/greedy_formatter.py index 2c70b2f6..c0601614 100644 --- a/Bot/Libs/utils/greedy_formatter.py +++ b/Bot/Libs/utils/greedy_formatter.py @@ -1,9 +1,22 @@ -from typing import List - - -def formatGreedy(list: List[str]) -> str: - if len(list) >= 3: - return f"{', '.join(list[:-1])}, and {list[-1]}" - elif len(list) == 2: - return " and ".join(list) - return "".join(list) +from typing import List + + +def formatGreedy(list: List[str]) -> str: + """Formats a Greedy list into a human-readable string + + For example, if we had a list of ["a", "b", "c"], it would return "a, b, and c". + If we had a list of ["a", "b"], it would return "a and b". + If we had a list of ["a"], it would return "a". + If we had a list of [], it would return "". + + Args: + list: The list of strings to format + + Returns: + str: The formatted string + """ + if len(list) >= 3: + return f"{', '.join(list[:-1])}, and {list[-1]}" + elif len(list) == 2: + return " and ".join(list) + return "".join(list) diff --git a/tests/utils/test_greedy_formatter.py b/tests/utils/test_greedy_formatter.py new file mode 100644 index 00000000..7241a280 --- /dev/null +++ b/tests/utils/test_greedy_formatter.py @@ -0,0 +1,25 @@ +import sys +from pathlib import Path + +path = Path(__file__).parents[2].joinpath("Bot") +sys.path.append(str(path)) + +from Libs.utils import formatGreedy + + +def test_format_greedy_3plus(): + assert (formatGreedy(["a", "b", "c"]) == "a, b, and c") and ( + formatGreedy(["a", "b", "c", "d"]) == "a, b, c, and d" + ) + + +def test_format_greedy_2(): + assert formatGreedy(["a", "b"]) == "a and b" + + +def test_format_greedy_1(): + assert formatGreedy(["a"]) == "a" + + +def test_format_greedy_empty(): + assert formatGreedy([]) == "" From 734da652009676256f7cbfdee11f3c611edb0868 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Mon, 24 Apr 2023 19:03:32 +0000 Subject: [PATCH 036/184] [pip](deps-dev): Bump sphinx from 6.1.3 to 6.2.0 (#310) Bumps [sphinx](https://github.com/sphinx-doc/sphinx) from 6.1.3 to 6.2.0. - [Release notes](https://github.com/sphinx-doc/sphinx/releases) - [Changelog](https://github.com/sphinx-doc/sphinx/blob/master/CHANGES) - [Commits](https://github.com/sphinx-doc/sphinx/compare/v6.1.3...v6.2.0) --- updated-dependencies: - dependency-name: sphinx dependency-type: direct:development update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 12 ++++++------ pyproject.toml | 2 +- 2 files changed, 7 insertions(+), 7 deletions(-) diff --git a/poetry.lock b/poetry.lock index 53120528..88198238 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2937,21 +2937,21 @@ files = [ [[package]] name = "sphinx" -version = "6.1.3" +version = "6.2.0" description = "Python documentation generator" category = "dev" optional = false python-versions = ">=3.8" files = [ - {file = "Sphinx-6.1.3.tar.gz", hash = "sha256:0dac3b698538ffef41716cf97ba26c1c7788dba73ce6f150c1ff5b4720786dd2"}, - {file = "sphinx-6.1.3-py3-none-any.whl", hash = "sha256:807d1cb3d6be87eb78a381c3e70ebd8d346b9a25f3753e9947e866b2786865fc"}, + {file = "Sphinx-6.2.0.tar.gz", hash = "sha256:9ef22c2941bc3d0ff080d25a797f7521fc317e857395c712ddde97a19d5bb440"}, + {file = "sphinx-6.2.0-py3-none-any.whl", hash = "sha256:ff1c2a1167bef9cdcd8ec71339e85fe10f26d4e9ef9382ef10b2687c876c936b"}, ] [package.dependencies] alabaster = ">=0.7,<0.8" babel = ">=2.9" colorama = {version = ">=0.4.5", markers = "sys_platform == \"win32\""} -docutils = ">=0.18,<0.20" +docutils = ">=0.18.1,<0.20" imagesize = ">=1.3" importlib-metadata = {version = ">=4.8", markers = "python_version < \"3.10\""} Jinja2 = ">=3.0" @@ -2969,7 +2969,7 @@ sphinxcontrib-serializinghtml = ">=1.1.5" [package.extras] docs = ["sphinxcontrib-websupport"] lint = ["docutils-stubs", "flake8 (>=3.5.0)", "flake8-simplify", "isort", "mypy (>=0.990)", "ruff", "sphinx-lint", "types-requests"] -test = ["cython", "html5lib", "pytest (>=4.6)"] +test = ["cython", "filelock", "html5lib", "pytest (>=4.6)"] [[package]] name = "sphinx-autobuild" @@ -3516,4 +3516,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "2c6c5f3bcaa8b07dfefd062eadeba6fbb6cdebe244cb8db507ac8d77dcdbcdc8" +content-hash = "df0f4038f57294d8cade728657e1c4e67fcb016ad783033672311712bc95f0f7" diff --git a/pyproject.toml b/pyproject.toml index abf22da1..52811399 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -39,7 +39,7 @@ ruff = "^0.0.262" [tool.poetry.group.docs.dependencies] -sphinx = "^6.1.3" +sphinx = "^6.2.0" myst-parser = "^1.0.0" sphinx-autobuild = "^2021.3.14" furo = "^2023.3.27" From 9a0a564765ab460888e326ec2aa9c96f8bf6d79d Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Mon, 24 Apr 2023 19:27:54 +0000 Subject: [PATCH 037/184] [pip](deps-dev): Bump nox from 2022.11.21 to 2023.4.22 Bumps [nox](https://github.com/wntrblm/nox) from 2022.11.21 to 2023.4.22. - [Release notes](https://github.com/wntrblm/nox/releases) - [Changelog](https://github.com/wntrblm/nox/blob/main/CHANGELOG.md) - [Commits](https://github.com/wntrblm/nox/compare/2022.11.21...2023.04.22) --- updated-dependencies: - dependency-name: nox dependency-type: direct:development update-type: version-update:semver-major ... Signed-off-by: dependabot[bot] --- poetry.lock | 12 ++++++------ pyproject.toml | 2 +- 2 files changed, 7 insertions(+), 7 deletions(-) diff --git a/poetry.lock b/poetry.lock index 88198238..88d33d6f 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2049,24 +2049,24 @@ setuptools = "*" [[package]] name = "nox" -version = "2022.11.21" +version = "2023.4.22" description = "Flexible test automation." category = "dev" optional = false python-versions = ">=3.7" files = [ - {file = "nox-2022.11.21-py3-none-any.whl", hash = "sha256:0e41a990e290e274cb205a976c4c97ee3c5234441a8132c8c3fd9ea3c22149eb"}, - {file = "nox-2022.11.21.tar.gz", hash = "sha256:e21c31de0711d1274ca585a2c5fde36b1aa962005ba8e9322bf5eeed16dcd684"}, + {file = "nox-2023.4.22-py3-none-any.whl", hash = "sha256:0b1adc619c58ab4fa57d6ab2e7823fe47a32e70202f287d78474adcc7bda1891"}, + {file = "nox-2023.4.22.tar.gz", hash = "sha256:46c0560b0dc609d7d967dc99e22cb463d3c4caf54a5fda735d6c11b5177e3a9f"}, ] [package.dependencies] -argcomplete = ">=1.9.4,<3.0" +argcomplete = ">=1.9.4,<4.0" colorlog = ">=2.6.1,<7.0.0" packaging = ">=20.9" virtualenv = ">=14" [package.extras] -tox-to-nox = ["jinja2", "tox"] +tox-to-nox = ["jinja2", "tox (<4)"] [[package]] name = "nox-poetry" @@ -3516,4 +3516,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "df0f4038f57294d8cade728657e1c4e67fcb016ad783033672311712bc95f0f7" +content-hash = "db5e08993686d6366518289e5f1867c3324e6ba8795ba3a3eef9d1ba3cad1448" diff --git a/pyproject.toml b/pyproject.toml index 52811399..411b90c5 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -25,7 +25,7 @@ discord-ext-menus = {git = "https://github.com/Rapptz/discord-ext-menus", rev = [tool.poetry.group.test.dependencies] pytest = "^7.3.1" pytest-asyncio = "^0.21.0" -nox = "^2022.11.21" +nox = "^2023.4.22" nox-poetry = "^1.0.2" pytest-cov = "^4.0.0" From 0c38a2f0a22ae5e1265e81ce6430eda69f17e821 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Mon, 24 Apr 2023 21:16:03 -0700 Subject: [PATCH 038/184] [skip ci] Update Docs --- Kumiko-Docs/source/guides/dev/requirements.rst | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/Kumiko-Docs/source/guides/dev/requirements.rst b/Kumiko-Docs/source/guides/dev/requirements.rst index c55d64d3..33d60477 100644 --- a/Kumiko-Docs/source/guides/dev/requirements.rst +++ b/Kumiko-Docs/source/guides/dev/requirements.rst @@ -41,27 +41,27 @@ Fedora 23+ .. code-block:: bash sudo dnf install make automake gcc gcc-c++ kernel-devel \ - libffi-devel python3-libnacl python3.11-devel openssl11-devel \ - openssl-devel opus opus-devel curl wget git + libffi-devel python3-libnacl python3.11-devel openssl-devel \ + opus-devel curl wget git OpenSUSE ^^^^^^^^ .. code-block:: bash - sudo zypper install gcc make automake openssl-devel openssl-1_1 openssl-1_1-devel \ - libffi-devel python311-devel python311-libnacl opus libopus0 wget git curl + sudo zypper install gcc make automake openssl-devel libffi-devel \ + python311-devel python311-libnacl libopus0 wget git curl Arch Linux ^^^^^^^^^^ .. code-block:: bash - sudo pacman -S --needed base-devel openssl openssl-1.1 libffi python python-libnacl opus + sudo pacman -S --needed base-devel openssl libffi python python-libnacl opus MacOS ^^^^^ .. code-block:: bash - brew install openssl openssl@1.1 libffi git curl make opus \ No newline at end of file + brew install openssl libffi git curl make opus From f63fd8594630846deea58e1edca94df6e5276ad6 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 25 Apr 2023 19:00:26 +0000 Subject: [PATCH 039/184] [pip](deps-dev): Bump sphinx from 6.2.0 to 6.2.1 (#312) Bumps [sphinx](https://github.com/sphinx-doc/sphinx) from 6.2.0 to 6.2.1. - [Release notes](https://github.com/sphinx-doc/sphinx/releases) - [Changelog](https://github.com/sphinx-doc/sphinx/blob/master/CHANGES) - [Commits](https://github.com/sphinx-doc/sphinx/compare/v6.2.0...v6.2.1) --- updated-dependencies: - dependency-name: sphinx dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index 88d33d6f..9b95745c 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2937,14 +2937,14 @@ files = [ [[package]] name = "sphinx" -version = "6.2.0" +version = "6.2.1" description = "Python documentation generator" category = "dev" optional = false python-versions = ">=3.8" files = [ - {file = "Sphinx-6.2.0.tar.gz", hash = "sha256:9ef22c2941bc3d0ff080d25a797f7521fc317e857395c712ddde97a19d5bb440"}, - {file = "sphinx-6.2.0-py3-none-any.whl", hash = "sha256:ff1c2a1167bef9cdcd8ec71339e85fe10f26d4e9ef9382ef10b2687c876c936b"}, + {file = "Sphinx-6.2.1.tar.gz", hash = "sha256:6d56a34697bb749ffa0152feafc4b19836c755d90a7c59b72bc7dfd371b9cc6b"}, + {file = "sphinx-6.2.1-py3-none-any.whl", hash = "sha256:97787ff1fa3256a3eef9eda523a63dbf299f7b47e053cfcf684a1c2a8380c912"}, ] [package.dependencies] @@ -3516,4 +3516,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "db5e08993686d6366518289e5f1867c3324e6ba8795ba3a3eef9d1ba3cad1448" +content-hash = "d293c8b1420fc40726633a9a9de08b810cc1e42e310b7ba147171ba6509cf0f6" diff --git a/pyproject.toml b/pyproject.toml index 411b90c5..ee3562f8 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -39,7 +39,7 @@ ruff = "^0.0.262" [tool.poetry.group.docs.dependencies] -sphinx = "^6.2.0" +sphinx = "^6.2.1" myst-parser = "^1.0.0" sphinx-autobuild = "^2021.3.14" furo = "^2023.3.27" From 0d6a7b31e16793067183ed9cb4f6d70b869842af Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 25 Apr 2023 19:11:56 +0000 Subject: [PATCH 040/184] [pip](deps-dev): Bump ruff from 0.0.262 to 0.0.263 (#313) Bumps [ruff](https://github.com/charliermarsh/ruff) from 0.0.262 to 0.0.263. - [Release notes](https://github.com/charliermarsh/ruff/releases) - [Changelog](https://github.com/charliermarsh/ruff/blob/main/BREAKING_CHANGES.md) - [Commits](https://github.com/charliermarsh/ruff/compare/v0.0.262...v0.0.263) --- updated-dependencies: - dependency-name: ruff dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 38 +++++++++++++++++++------------------- pyproject.toml | 2 +- 2 files changed, 20 insertions(+), 20 deletions(-) diff --git a/poetry.lock b/poetry.lock index 9b95745c..d5f877b9 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2845,29 +2845,29 @@ idna2008 = ["idna"] [[package]] name = "ruff" -version = "0.0.262" +version = "0.0.263" description = "An extremely fast Python linter, written in Rust." category = "dev" optional = false python-versions = ">=3.7" files = [ - {file = "ruff-0.0.262-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:c26c1abd420d041592d05d63aee8c6a18feb24aed4deb6e91129e9f2c7b4914a"}, - {file = "ruff-0.0.262-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:b379e9765afa679316e52288a942df085e590862f8945088936a7bce3116d8f3"}, - {file = "ruff-0.0.262-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:9b7e0ca6821aafbd2b059df3119fcd5881250721ca8e825789fd2c471f7c59be"}, - {file = "ruff-0.0.262-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:4cca35e2aeddff72bb4379a1dabc134e0c0d25ebc754a2cb733a1f8d4dbbb5e0"}, - {file = "ruff-0.0.262-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:15bf5533ce169aebbafa00017987f673e879f60a625d932b464b8cdaf32a4fce"}, - {file = "ruff-0.0.262-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:3909e249d984c4517194005a1c30eaa0c3a6d906c789d9fc0c9c7e007fb3e759"}, - {file = "ruff-0.0.262-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:4e2813013a19b3e147e840bdb2e42db5825b53b47364e58e7b467c5fa47ffda2"}, - {file = "ruff-0.0.262-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:d25a94996b2037e566c2a801c8b324c0a826194d5d4d90ad7c1ccb8cf06521fa"}, - {file = "ruff-0.0.262-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:85ca04348372efc59f6ee808d903d35e0d352cf2c78e487757cd48b65104b83e"}, - {file = "ruff-0.0.262-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:24f989363e9bb5d0283490298102a5218682e49ebf300e445d69e24bee03ac83"}, - {file = "ruff-0.0.262-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:3c24e678e43ca4b67e29cc9a7a54eea05f31a5898cbf17bfec47b68f08d32a60"}, - {file = "ruff-0.0.262-py3-none-musllinux_1_2_i686.whl", hash = "sha256:0baff3c9a22227358ea109c165efe62dbdd0f2b9fd5256567dda8682b444fe23"}, - {file = "ruff-0.0.262-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:083bac6e238d8b7d5ac3618666ea63b7ac661cf94c5da160070a58e190082831"}, - {file = "ruff-0.0.262-py3-none-win32.whl", hash = "sha256:15bbfa2d15c137717627e0d56b0e535ae297b734551e34e03fcc25d7642cf43a"}, - {file = "ruff-0.0.262-py3-none-win_amd64.whl", hash = "sha256:973ac29193f718349cf5746b7d86dfeaf7d40e9651ed97790a9b9327305888b9"}, - {file = "ruff-0.0.262-py3-none-win_arm64.whl", hash = "sha256:f102904ebe395acd2a181d295b98120acd7a63f732b691672977fc688674f4af"}, - {file = "ruff-0.0.262.tar.gz", hash = "sha256:faea54231c265f5349975ba6f3d855b71881a01f391b2000c47740390c6d5f68"}, + {file = "ruff-0.0.263-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:ee6c7a77f142c427fa73e1f5f603fc1a39413a36fe6966ed0fc55e97f6921d9c"}, + {file = "ruff-0.0.263-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:c3b7d4b365207f3e4c40d235127091478e595b31e35b6cd57d940920cdfae68b"}, + {file = "ruff-0.0.263-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ebc778d95f29c9917e6e7608b2b67815707e6ab8eb5af9341617beda479c3edf"}, + {file = "ruff-0.0.263-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:4f75fa1632ea065b8f10678e7b6ae9873f84d5046bdf146990112751e98af42a"}, + {file = "ruff-0.0.263-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:ddcee0d91629a4fa4bc9faebf5b94d4615d50d1cd76d1098fa71fbe1c54f4104"}, + {file = "ruff-0.0.263-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:4010b156f2e9fa6e74b5581098467f6ff68beac48945599b3a9239481e578ab4"}, + {file = "ruff-0.0.263-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:15386933dd8e03aafa3186f9e996d6823105492817311338fbcb64d0ecbcd95f"}, + {file = "ruff-0.0.263-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:04e0b280dd246448564c892bce5607d820ad1f14944f3d535db98692e2a7ac07"}, + {file = "ruff-0.0.263-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:82c41f276106017b6f075dd2f2cc68e1a0b434cc75488f816fc98bd41982628d"}, + {file = "ruff-0.0.263-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:3e9fcee3f81129eabc75da005d839235e32d7d374f2d4c0db0c708dad4703d6e"}, + {file = "ruff-0.0.263-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:981e3c4d773f7ff52479c4fd74a65e408f1e13fa5f889b72214d400cd1299ce4"}, + {file = "ruff-0.0.263-py3-none-musllinux_1_2_i686.whl", hash = "sha256:bed1d3fba306e3f7e13ce226927b84200350e25abd1e754e06ee361c6d41de15"}, + {file = "ruff-0.0.263-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:7890499c2c3dcb1e60de2a8b4c5f5775b2bfcdff7d3e68e38db5cb2d65b12006"}, + {file = "ruff-0.0.263-py3-none-win32.whl", hash = "sha256:c2b79919ebd93674b93dfc2c843e264bf8e52fbe737467e9b58521775c85f4ad"}, + {file = "ruff-0.0.263-py3-none-win_amd64.whl", hash = "sha256:9af932f665e177de62e172901704257fd6e5bfabb95893867ff7382a851459d3"}, + {file = "ruff-0.0.263-py3-none-win_arm64.whl", hash = "sha256:ddf4503595b560bfa5fae92fa2e4cb09ec465ee4cf88cc248f10ad2e956deec3"}, + {file = "ruff-0.0.263.tar.gz", hash = "sha256:1008f211ad8aa1d998517ac5bf3d68fbc68ec516d1da89b6081f25ff2f30b687"}, ] [[package]] @@ -3516,4 +3516,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "d293c8b1420fc40726633a9a9de08b810cc1e42e310b7ba147171ba6509cf0f6" +content-hash = "58d5ddf2e4ff24ca623995734c66006db8a624c49bb7ae3827a0a4e469f7e8f5" diff --git a/pyproject.toml b/pyproject.toml index ee3562f8..6ead4059 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -35,7 +35,7 @@ pyinstrument = "^4.4.0" pyright = "^1.1.304" watchfiles = "^0.19.0" jishaku = "^2.5.1" -ruff = "^0.0.262" +ruff = "^0.0.263" [tool.poetry.group.docs.dependencies] From 1fef3991ce535f1a0c02865f752399b43ba4ddeb Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Tue, 25 Apr 2023 19:07:36 -0700 Subject: [PATCH 041/184] [skip ci] Update Readme --- README.md | 15 ++++++--------- 1 file changed, 6 insertions(+), 9 deletions(-) diff --git a/README.md b/README.md index e22c4de3..94366f33 100644 --- a/README.md +++ b/README.md @@ -20,20 +20,17 @@ Kumiko is a multipurpose Discord bot built with freedom and choice in mind. Kumi ## Features -- An **Opt-In** Economy System with jobs system and marketplace (WIP, pinned for v1) - - Includes a marketplace - - Custom currency (Lavender Petals) - - Custom jobs (WIP) - - Rank system (WIP) - - Custom quests -- Basic Administration Commands -- Search memes, posts, anime, manga, and others! +- Customizable prefix module +- Global or guild economy with jobs and marketplaces +- Custom logging module +- Basic moderation commands +- Search for memes, posts, anime, manga, and others! And some ones that are planned: + - Complete Web Dashboard + Custom Embeds (WIP, pinned for v2) - Event Logging (Pinned for v1) - Annoucement releaser with support from GitHub (Pinned for v2) -- AI Driven GAN Anime Waifu Generator (Not implemented yet) - Selector Roles (pinned for v2) ## Prefix From a40ca05828df204fedff2cc4d411f7cf5aac5064 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Thu, 27 Apr 2023 19:03:24 +0000 Subject: [PATCH 042/184] [pip](deps-dev): Bump pyright from 1.1.304 to 1.1.305 (#314) Bumps [pyright](https://github.com/RobertCraigie/pyright-python) from 1.1.304 to 1.1.305. - [Release notes](https://github.com/RobertCraigie/pyright-python/releases) - [Commits](https://github.com/RobertCraigie/pyright-python/compare/v1.1.304...v1.1.305) --- updated-dependencies: - dependency-name: pyright dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index d5f877b9..abf2f20d 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2613,14 +2613,14 @@ diagrams = ["jinja2", "railroad-diagrams"] [[package]] name = "pyright" -version = "1.1.304" +version = "1.1.305" description = "Command line wrapper for pyright" category = "dev" optional = false python-versions = ">=3.7" files = [ - {file = "pyright-1.1.304-py3-none-any.whl", hash = "sha256:70021bbae07fc28ed16e435f5efa65cd71e06a1888d9ca998798c283d4b3d010"}, - {file = "pyright-1.1.304.tar.gz", hash = "sha256:87adec38081904c939e3657ab23d5fc40b7ccc22709be0af1859fc785ae4ea61"}, + {file = "pyright-1.1.305-py3-none-any.whl", hash = "sha256:147da3aac44ba0516423613cad5fbb7a0abba6b71c53718a1e151f456d4ab12e"}, + {file = "pyright-1.1.305.tar.gz", hash = "sha256:924d554253ecc4fafdfbfa76989d173cc15d426aa808630c0dd669fdc3227ef7"}, ] [package.dependencies] @@ -3516,4 +3516,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "58d5ddf2e4ff24ca623995734c66006db8a624c49bb7ae3827a0a4e469f7e8f5" +content-hash = "3f9be85073d4cd6f3219b867de2bff8a218e4a4170b0f3c4fa7411033e84aea1" diff --git a/pyproject.toml b/pyproject.toml index 6ead4059..cb21657b 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -32,7 +32,7 @@ pytest-cov = "^4.0.0" [tool.poetry.group.dev.dependencies] pre-commit = "^3.2.2" pyinstrument = "^4.4.0" -pyright = "^1.1.304" +pyright = "^1.1.305" watchfiles = "^0.19.0" jishaku = "^2.5.1" ruff = "^0.0.263" From 5bc917f65c97cc84c41d09121f352725ccf4c56f Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Fri, 28 Apr 2023 19:01:14 +0000 Subject: [PATCH 043/184] [pip](deps): Bump orjson from 3.8.10 to 3.8.11 (#315) Bumps [orjson](https://github.com/ijl/orjson) from 3.8.10 to 3.8.11. - [Release notes](https://github.com/ijl/orjson/releases) - [Changelog](https://github.com/ijl/orjson/blob/master/CHANGELOG.md) - [Commits](https://github.com/ijl/orjson/compare/3.8.10...3.8.11) --- updated-dependencies: - dependency-name: orjson dependency-type: direct:production update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 111 +++++++++++++++++++++++-------------------------- pyproject.toml | 2 +- 2 files changed, 54 insertions(+), 59 deletions(-) diff --git a/poetry.lock b/poetry.lock index abf2f20d..10414686 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2125,68 +2125,63 @@ files = [ [[package]] name = "orjson" -version = "3.8.10" +version = "3.8.11" description = "Fast, correct Python JSON library supporting dataclasses, datetimes, and numpy" category = "main" optional = false python-versions = ">= 3.7" files = [ - {file = "orjson-3.8.10-cp310-cp310-macosx_10_7_x86_64.whl", hash = "sha256:4dfe0651e26492d5d929bbf4322de9afbd1c51ac2e3947a7f78492b20359711d"}, - {file = "orjson-3.8.10-cp310-cp310-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:bc30de5c7b3a402eb59cc0656b8ee53ca36322fc52ab67739c92635174f88336"}, - {file = "orjson-3.8.10-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:c08b426fae7b9577b528f99af0f7e0ff3ce46858dd9a7d1bf86d30f18df89a4c"}, - {file = "orjson-3.8.10-cp310-cp310-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:bce970f293825e008dbf739268dfa41dfe583aa2a1b5ef4efe53a0e92e9671ea"}, - {file = "orjson-3.8.10-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:9b23fb0264bbdd7218aa685cb6fc71f0dcecf34182f0a8596a3a0dff010c06f9"}, - {file = "orjson-3.8.10-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:0826ad2dc1cea1547edff14ce580374f0061d853cbac088c71162dbfe2e52205"}, - {file = "orjson-3.8.10-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:a7bce6e61cea6426309259b04c6ee2295b3f823ea51a033749459fe2dd0423b2"}, - {file = "orjson-3.8.10-cp310-cp310-manylinux_2_28_x86_64.whl", hash = "sha256:0b470d31244a6f647e5402aac7d2abaf7bb4f52379acf67722a09d35a45c9417"}, - {file = "orjson-3.8.10-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:48824649019a25d3e52f6454435cf19fe1eb3d05ee697e65d257f58ae3aa94d9"}, - {file = "orjson-3.8.10-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:faee89e885796a9cc493c930013fa5cfcec9bfaee431ddf00f0fbfb57166a8b3"}, - {file = "orjson-3.8.10-cp310-none-win_amd64.whl", hash = "sha256:3cfe32b1227fe029a5ad989fbec0b453a34e5e6d9a977723f7c3046d062d3537"}, - {file = "orjson-3.8.10-cp311-cp311-macosx_10_7_x86_64.whl", hash = "sha256:2073b62822738d6740bd2492f6035af5c2fd34aa198322b803dc0e70559a17b7"}, - {file = "orjson-3.8.10-cp311-cp311-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:b2c4faf20b6bb5a2d7ac0c16f58eb1a3800abcef188c011296d1dc2bb2224d48"}, - {file = "orjson-3.8.10-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:8c1825997232a324911d11c75d91e1e0338c7b723c149cf53a5fc24496c048a4"}, - {file = "orjson-3.8.10-cp311-cp311-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:f7e85d4682f3ed7321d36846cad0503e944ea9579ef435d4c162e1b73ead8ac9"}, - {file = "orjson-3.8.10-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:2b8cdaacecb92997916603ab232bb096d0fa9e56b418ca956b9754187d65ca06"}, - {file = "orjson-3.8.10-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:ddabc5e44702d13137949adee3c60b7091e73a664f6e07c7b428eebb2dea7bbf"}, - {file = "orjson-3.8.10-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:27bb26e171e9cfdbec39c7ca4739b6bef8bd06c293d56d92d5e3a3fc017df17d"}, - {file = "orjson-3.8.10-cp311-cp311-manylinux_2_28_x86_64.whl", hash = "sha256:1810e5446fe68d61732e9743592da0ec807e63972eef076d09e02878c2f5958e"}, - {file = "orjson-3.8.10-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:61e2e51cefe7ef90c4fbbc9fd38ecc091575a3ea7751d56fad95cbebeae2a054"}, - {file = "orjson-3.8.10-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:f3e9ac9483c2b4cd794e760316966b7bd1e6afb52b0218f068a4e80c9b2db4f6"}, - {file = "orjson-3.8.10-cp311-none-win_amd64.whl", hash = "sha256:26aee557cf8c93b2a971b5a4a8e3cca19780573531493ce6573aa1002f5c4378"}, - {file = "orjson-3.8.10-cp37-cp37m-macosx_10_7_x86_64.whl", hash = "sha256:11ae68f995a50724032af297c92f20bcde31005e0bf3653b12bff9356394615b"}, - {file = "orjson-3.8.10-cp37-cp37m-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:35d879b46b8029e1e01e9f6067928b470a4efa1ca749b6d053232b873c2dcf66"}, - {file = "orjson-3.8.10-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:345e41abd1d9e3ecfb554e1e75ff818cf42e268bd06ad25a96c34e00f73a327e"}, - {file = "orjson-3.8.10-cp37-cp37m-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:45a5afc9cda6b8aac066dd50d8194432fbc33e71f7164f95402999b725232d78"}, - {file = "orjson-3.8.10-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:ad632dc330a7b39da42530c8d146f76f727d476c01b719dc6743c2b5701aaf6b"}, - {file = "orjson-3.8.10-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:4bf2556ba99292c4dc550560384dd22e88b5cdbe6d98fb4e202e902b5775cf9f"}, - {file = "orjson-3.8.10-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:b88afd662190f19c3bb5036a903589f88b1d2c2608fbb97281ce000db6b08897"}, - {file = "orjson-3.8.10-cp37-cp37m-manylinux_2_28_x86_64.whl", hash = "sha256:abce8d319aae800fd2d774db1106f926dee0e8a5ca85998fd76391fcb58ef94f"}, - {file = "orjson-3.8.10-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:e999abca892accada083f7079612307d94dd14cc105a699588a324f843216509"}, - {file = "orjson-3.8.10-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:a3fdee68c4bb3c5d6f89ed4560f1384b5d6260e48fbf868bae1a245a3c693d4d"}, - {file = "orjson-3.8.10-cp37-none-win_amd64.whl", hash = "sha256:e5d7f82506212e047b184c06e4bcd48c1483e101969013623cebcf51cf12cad9"}, - {file = "orjson-3.8.10-cp38-cp38-macosx_10_7_x86_64.whl", hash = "sha256:d953e6c2087dcd990e794f8405011369ee11cf13e9aaae3172ee762ee63947f2"}, - {file = "orjson-3.8.10-cp38-cp38-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:81aa3f321d201bff0bd0f4014ea44e51d58a9a02d8f2b0eeab2cee22611be8e1"}, - {file = "orjson-3.8.10-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:7d27b6182f75896dd8c10ea0f78b9265a3454be72d00632b97f84d7031900dd4"}, - {file = "orjson-3.8.10-cp38-cp38-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:1486600bc1dd1db26c588dd482689edba3d72d301accbe4301db4b2b28bd7aa4"}, - {file = "orjson-3.8.10-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:344ea91c556a2ce6423dc13401b83ab0392aa697a97fa4142c2c63a6fd0bbfef"}, - {file = "orjson-3.8.10-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:979f231e3bad1c835627eef1a30db12a8af58bfb475a6758868ea7e81897211f"}, - {file = "orjson-3.8.10-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:6fa3a26dcf0f5f2912a8ce8e87273e68b2a9526854d19fd09ea671b154418e88"}, - {file = "orjson-3.8.10-cp38-cp38-manylinux_2_28_x86_64.whl", hash = "sha256:b6e79d8864794635974b18821b49a7f27859d17b93413d4603efadf2e92da7a5"}, - {file = "orjson-3.8.10-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:ce49999bcbbc14791c61844bc8a69af44f5205d219be540e074660038adae6bf"}, - {file = "orjson-3.8.10-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:c2ef690335b24f9272dbf6639353c1ffc3f196623a92b851063e28e9515cf7dd"}, - {file = "orjson-3.8.10-cp38-none-win_amd64.whl", hash = "sha256:5a0b1f4e4fa75e26f814161196e365fc0e1a16e3c07428154505b680a17df02f"}, - {file = "orjson-3.8.10-cp39-cp39-macosx_10_7_x86_64.whl", hash = "sha256:af7601a78b99f0515af2f8ab12c955c0072ffcc1e437fb2556f4465783a4d813"}, - {file = "orjson-3.8.10-cp39-cp39-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:6bbd7b3a3e2030b03c68c4d4b19a2ef5b89081cbb43c05fe2010767ef5e408db"}, - {file = "orjson-3.8.10-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:4355c9aedfefe60904e8bd7901315ebbc8bb828f665e4c9bc94b1432e67cb6f7"}, - {file = "orjson-3.8.10-cp39-cp39-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:b7b0ba074375e25c1594e770e2215941e2017c3cd121889150737fa1123e8bfe"}, - {file = "orjson-3.8.10-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:34b6901c110c06ab9e8d7d0496db4bc9a0c162ca8d77f67539d22cb39e0a1ef4"}, - {file = "orjson-3.8.10-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:cb62ec16a1c26ad9487727b529103cb6a94a1d4969d5b32dd0eab5c3f4f5a6f2"}, - {file = "orjson-3.8.10-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:595e1e7d04aaaa3d41113e4eb9f765ab642173c4001182684ae9ddc621bb11c8"}, - {file = "orjson-3.8.10-cp39-cp39-manylinux_2_28_x86_64.whl", hash = "sha256:64ffd92328473a2f9af059410bd10c703206a4bbc7b70abb1bedcd8761e39eb8"}, - {file = "orjson-3.8.10-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:b1f648ec89c6a426098868460c0ef8c86b457ce1378d7569ff4acb6c0c454048"}, - {file = "orjson-3.8.10-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:6a286ad379972e4f46579e772f0477e6b505f1823aabcd64ef097dbb4549e1a4"}, - {file = "orjson-3.8.10-cp39-none-win_amd64.whl", hash = "sha256:d2874cee6856d7c386b596e50bc517d1973d73dc40b2bd6abec057b5e7c76b2f"}, - {file = "orjson-3.8.10.tar.gz", hash = "sha256:dcf6adb4471b69875034afab51a14b64f1026bc968175a2bb02c5f6b358bd413"}, + {file = "orjson-3.8.11-cp310-cp310-macosx_11_0_x86_64.macosx_11_0_arm64.macosx_11_0_universal2.whl", hash = "sha256:9fa900bdd84b4576c8dd6f3e2a00b35797f29283af328c6e3d70addfa4c2d599"}, + {file = "orjson-3.8.11-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:1103e597c16f82c241e1b02beadc9c91cecd93e60433ca73cb6464dcc235f37c"}, + {file = "orjson-3.8.11-cp310-cp310-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:d70b6db9d4e1e6057829cd7fe119c217cebaf989f88d14b2445fa69fc568d03e"}, + {file = "orjson-3.8.11-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:3afccf7f8684dca7f017837a315de0a1ab5c095de22a4eed206d079f9325ed72"}, + {file = "orjson-3.8.11-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:1fedcc428416e23a6c9de62a000c22ae33bbe0108302ad5d5935e29ea739bf37"}, + {file = "orjson-3.8.11-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:bf48ed8d4b6ab9f23b7ee642462369d7133412d72824bad89f9bf4311c06c6a1"}, + {file = "orjson-3.8.11-cp310-cp310-manylinux_2_28_x86_64.whl", hash = "sha256:3c55065bc2075a5ea6ffb30462d84fd3aa5bbb7ae600855c325ee5753feec715"}, + {file = "orjson-3.8.11-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:08729e339ff3146e6de56c1166f014c3d2ec3e79ffb76d6c55d52cc892e5e477"}, + {file = "orjson-3.8.11-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:358e515b8b19a275b259f5ee1e0efa2859b1d976b5ed5d016ac59f9e6c8788a3"}, + {file = "orjson-3.8.11-cp310-none-win_amd64.whl", hash = "sha256:62eb8bdcf6f4cdbe12743e88ad98696277a75f91a35e8fb93a7ea2b9f4a7000c"}, + {file = "orjson-3.8.11-cp311-cp311-macosx_11_0_x86_64.macosx_11_0_arm64.macosx_11_0_universal2.whl", hash = "sha256:982ab319b7a5ece4199caf2a2b3a28e62a8e289cb6418548ef98bced7e2a6cfe"}, + {file = "orjson-3.8.11-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:e14903bfeb591a9117b7d40d81e3ebca9700b4e77bd829d6f22ea57941bb0ebf"}, + {file = "orjson-3.8.11-cp311-cp311-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:58c068f93d701f9466f667bf3b5cb4e4946aee940df2b07ca5101f1cf1b60ce4"}, + {file = "orjson-3.8.11-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:9486963d2e65482c565dacb366adb36d22aa22acf7274b61490244c3d87fa631"}, + {file = "orjson-3.8.11-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:5c3b5405edc3a5f9e34516ee1a729f6c46aecf6de960ae07a7b3e95ebdd0e1d9"}, + {file = "orjson-3.8.11-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:3b65424ceee82b94e3613233b67ef110dc58f9d83b0076ec47a506289552a861"}, + {file = "orjson-3.8.11-cp311-cp311-manylinux_2_28_x86_64.whl", hash = "sha256:173b8f8c750590f432757292cfb197582e5c14347b913b4017561d47af0e759b"}, + {file = "orjson-3.8.11-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:37f38c8194ce086e6a9816b4b8dde5e7f383feeed92feec0385d99baf64f9b6e"}, + {file = "orjson-3.8.11-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:553fdaf9f4b5060a0dcc517ae0c511c289c184a83d6719d03c5602ed0eef0390"}, + {file = "orjson-3.8.11-cp311-none-win_amd64.whl", hash = "sha256:12f647d4da0aab1997e25bed4fa2b76782b5b9d2d1bf3066b5f0a57d34d833c4"}, + {file = "orjson-3.8.11-cp37-cp37m-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:71a656f1c62e84c69060093e20cedff6a92e472d53ff5b8b9026b1b298542a68"}, + {file = "orjson-3.8.11-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:176d742f53434541e50a5e659694073aa51dcbd8f29a1708a4fa1a320193c615"}, + {file = "orjson-3.8.11-cp37-cp37m-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:b369019e597b59c4b97e9f925a3b725321fa1481c129d76c74c6ea3823f5d1e8"}, + {file = "orjson-3.8.11-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:0a53b3c02a38aadc5302661c2ca18645093971488992df77ce14fef16f598b2e"}, + {file = "orjson-3.8.11-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:6d7b050135669d2335e40120215ad4120e29958c139f8bab68ce06a1cb1a1b2c"}, + {file = "orjson-3.8.11-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:66f0c9e4e8f6641497a7dc50591af3704b11468e9fc90cfb5874f28b0a61edb5"}, + {file = "orjson-3.8.11-cp37-cp37m-manylinux_2_28_x86_64.whl", hash = "sha256:235926b38ed9b76ab2bca99ff26ece79c1c46bc10079b06e660b087aecffbe69"}, + {file = "orjson-3.8.11-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:c2d3e6b65458ed71b6797f321d6e8bfeeadee9d3d31cac47806a608ea745edd7"}, + {file = "orjson-3.8.11-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:4118dcd2b5a27a22af5ad92414073f25d93bca1868f1f580056003c84841062f"}, + {file = "orjson-3.8.11-cp37-none-win_amd64.whl", hash = "sha256:b68a07794834b7bd53ae2a8b4fe4bf010734cae3f0917d434c83b97acf8e5bce"}, + {file = "orjson-3.8.11-cp38-cp38-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:98befa717efaab7ddb847ebe47d473f6bd6f0cb53e98e6c3d487c7c58ba2e174"}, + {file = "orjson-3.8.11-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:0f9415b86ef154bf247fa78a6918aac50089c296e26fb6cf15bc9d7e6402a1f8"}, + {file = "orjson-3.8.11-cp38-cp38-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:f7aeefac55848aeb29f20b91fa55f9e488f446201bb1bb31dc17480d113d8955"}, + {file = "orjson-3.8.11-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:d47f97b99beb9bcac6e288a76b559543a61e0187443d8089204b757726b1d000"}, + {file = "orjson-3.8.11-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:d7d5aecccfaf2052cd07ed5bec8efba9ddfea055682fcd346047b1a3e9da3034"}, + {file = "orjson-3.8.11-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:04b60dfc1251742e79bb075d7a7c4e37078b932a02e6f005c45761bd90c69189"}, + {file = "orjson-3.8.11-cp38-cp38-manylinux_2_28_x86_64.whl", hash = "sha256:ef52f1d5a2f89ef9049781c90ea35d5edf74374ed6ed515c286a706d1b290267"}, + {file = "orjson-3.8.11-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:7c7b4fae3b8fc69c8e76f1c0694f3decfe8a57f87e7ac7779ebb59cd71135438"}, + {file = "orjson-3.8.11-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:f4e4a1001933166fd1c257b920b241b35322bef99ed7329338bf266ac053abe7"}, + {file = "orjson-3.8.11-cp38-none-win_amd64.whl", hash = "sha256:5ff10789cbc08a9fd94507c907ba55b9315e99f20345ff8ef34fac432dacd948"}, + {file = "orjson-3.8.11-cp39-cp39-macosx_11_0_x86_64.macosx_11_0_arm64.macosx_11_0_universal2.whl", hash = "sha256:c67ac094a4dde914297543af19f22532d7124f3a35245580d8b756c4ff2f5884"}, + {file = "orjson-3.8.11-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:cdf201e77d3fac9d8d6f68d872ef45dccfe46f30b268bb88b6c5af5065b433aa"}, + {file = "orjson-3.8.11-cp39-cp39-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:3485c458670c0edb79ca149fe201f199dd9ccfe7ca3acbdef617e3c683e7b97f"}, + {file = "orjson-3.8.11-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:1e97fdbb779a3b8f5d9fc7dfddef5325f81ee45897eb7cb4638d5d9734d42514"}, + {file = "orjson-3.8.11-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:2fc050f8e7f2e4061c8c9968ad0be745b11b03913b77ffa8ceca65914696886c"}, + {file = "orjson-3.8.11-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f2ef933da50b31c112b252be03d1ef59e0d0552c1a08e48295bd529ce42aaab8"}, + {file = "orjson-3.8.11-cp39-cp39-manylinux_2_28_x86_64.whl", hash = "sha256:714c3e2be6ed7e4ff6e887926d6e171bfd94fdee76d7d3bfa74ee19237a2d49d"}, + {file = "orjson-3.8.11-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:7e4ded77ac7432a155d1d27a83bcadf722750aea3b9e6c4d47f2a92054ab71cb"}, + {file = "orjson-3.8.11-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:382f15861a4bf447ab9d07106010e61b217ef6d4245c6cf64af0c12c4c5e2346"}, + {file = "orjson-3.8.11-cp39-none-win_amd64.whl", hash = "sha256:0bc3d1b93a73b46a698c054697eb2d27bdedbc5ea0d11ec5f1a6bfbec36346b5"}, + {file = "orjson-3.8.11.tar.gz", hash = "sha256:882c77126c42dd93bb35288632d69b1e393863a2b752de3e5fe0112833609496"}, ] [[package]] @@ -3516,4 +3511,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "3f9be85073d4cd6f3219b867de2bff8a218e4a4170b0f3c4fa7411033e84aea1" +content-hash = "1f7d795b08b30bd9dc587ec2111f8e12d5f94164710bc9c6684be3c74bfba707" diff --git a/pyproject.toml b/pyproject.toml index cb21657b..43200c20 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -10,7 +10,7 @@ python = ">=3.8,<4.0" python-dotenv = "^1.0.0" aiodns = "^3.0.0" Brotli = "^1.0.9" -orjson = "^3.8.10" +orjson = "^3.8.11" asyncpraw = "^7.7.0" uvloop = "^0.17.0" gql = { extras = ["aiohttp"], version = "^3.4.0" } From 0a881d0b3915a2d9545c6478caf33b662f04c041 Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Sat, 29 Apr 2023 00:13:16 -0700 Subject: [PATCH 044/184] [skip ci] Update wallet footer --- Bot/Cogs/economy.py | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/Bot/Cogs/economy.py b/Bot/Cogs/economy.py index 284b21b2..77b5edc0 100644 --- a/Bot/Cogs/economy.py +++ b/Bot/Cogs/economy.py @@ -1,8 +1,9 @@ from discord.ext import commands +from discord.utils import format_dt from kumikocore import KumikoCore from Libs.economy import getUser from Libs.ui.economy import RegisterView -from Libs.utils import Embed +from Libs.utils import Embed, parseDatetime from prisma.models import User @@ -72,11 +73,12 @@ async def wallet(self, ctx: commands.Context) -> None: ) ) else: - userDesc = f"**Rank**: {user['rank']}\n\n**Balance**: {user['petals']}" # type: ignore + userDesc = f"**Rank**: {user['rank']}\n**Balance**: {user['petals']}\n**Date Joined**: {format_dt(parseDatetime(user['date_joined']))}" # type: ignore embed = Embed( title=f"{ctx.author.name}'s Wallet", description=userDesc, ) + embed.set_footer(text=f"User ID: {user['id']}") # type: ignore await ctx.send(embed=embed) From 173e57ec1eac0b78f622ece0ef8f84c0ba5c890f Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 2 May 2023 01:29:35 +0000 Subject: [PATCH 045/184] [pip](deps): Bump discord-py from 2.2.2 to 2.2.3 (#316) Bumps [discord-py](https://github.com/Rapptz/discord.py) from 2.2.2 to 2.2.3. - [Release notes](https://github.com/Rapptz/discord.py/releases) - [Commits](https://github.com/Rapptz/discord.py/compare/v2.2.2...v2.2.3) --- updated-dependencies: - dependency-name: discord-py dependency-type: direct:production update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index 10414686..c4ce4c6f 100644 --- a/poetry.lock +++ b/poetry.lock @@ -967,14 +967,14 @@ resolved_reference = "8686b5d1bbc1d3c862292eb436ab630d6e9c9b53" [[package]] name = "discord-py" -version = "2.2.2" +version = "2.2.3" description = "A Python wrapper for the Discord API" category = "main" optional = false python-versions = ">=3.8.0" files = [ - {file = "discord.py-2.2.2-py3-none-any.whl", hash = "sha256:38fc52a784727b8e5e5749267089400035b187a009028eddfabeb182abcc6d52"}, - {file = "discord.py-2.2.2.tar.gz", hash = "sha256:b9944056bcb5711b2d04088848fd004466cf117c15c84fa798bf55470f28275f"}, + {file = "discord.py-2.2.3-py3-none-any.whl", hash = "sha256:792bdcfe71cfe013c446cf379b2e83e08b5050604322ad6fb592864e63511abd"}, + {file = "discord.py-2.2.3.tar.gz", hash = "sha256:f9df95795c6f52c5db43b7ab43634993e12ef233288636a759166dd9c134d077"}, ] [package.dependencies] @@ -3511,4 +3511,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "1f7d795b08b30bd9dc587ec2111f8e12d5f94164710bc9c6684be3c74bfba707" +content-hash = "3f115f40085b2dbd3d6f0fbcbf59efdd4dd96a5c36521d280838a71bc4608272" diff --git a/pyproject.toml b/pyproject.toml index 43200c20..394cd4c3 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -19,7 +19,7 @@ prisma = "^0.8.2" redis = {extras = ["hiredis"], version = "^4.5.4"} ciso8601 = "^2.3.0" faust-cchardet = "^2.1.18" -discord-py = {extras = ["voice"], version = "^2.2.2"} +discord-py = {extras = ["voice"], version = "^2.2.3"} discord-ext-menus = {git = "https://github.com/Rapptz/discord-ext-menus", rev = "8686b5d1bbc1d3c862292eb436ab630d6e9c9b53"} [tool.poetry.group.test.dependencies] From 8cdc093e491ce1f9187e7185c40ca15d00a7b68d Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 2 May 2023 01:47:56 +0000 Subject: [PATCH 046/184] [pip](deps-dev): Bump pre-commit from 3.2.2 to 3.3.0 (#317) Bumps [pre-commit](https://github.com/pre-commit/pre-commit) from 3.2.2 to 3.3.0. - [Release notes](https://github.com/pre-commit/pre-commit/releases) - [Changelog](https://github.com/pre-commit/pre-commit/blob/main/CHANGELOG.md) - [Commits](https://github.com/pre-commit/pre-commit/compare/v3.2.2...v3.3.0) --- updated-dependencies: - dependency-name: pre-commit dependency-type: direct:development update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index c4ce4c6f..1c7b7c43 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2310,14 +2310,14 @@ testing = ["pytest", "pytest-benchmark"] [[package]] name = "pre-commit" -version = "3.2.2" +version = "3.3.0" description = "A framework for managing and maintaining multi-language pre-commit hooks." category = "dev" optional = false python-versions = ">=3.8" files = [ - {file = "pre_commit-3.2.2-py2.py3-none-any.whl", hash = "sha256:0b4210aea813fe81144e87c5a291f09ea66f199f367fa1df41b55e1d26e1e2b4"}, - {file = "pre_commit-3.2.2.tar.gz", hash = "sha256:5b808fcbda4afbccf6d6633a56663fed35b6c2bc08096fd3d47ce197ac351d9d"}, + {file = "pre_commit-3.3.0-py2.py3-none-any.whl", hash = "sha256:7577a012399334d9f001873b5553f9fabc1ccc5b3e2b29e0793f84ce18e9d042"}, + {file = "pre_commit-3.3.0.tar.gz", hash = "sha256:06acda43a7b6b63fdcc29aa90bf1228cf4d4029a4e4d70971347a9d2593c94d4"}, ] [package.dependencies] @@ -3511,4 +3511,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "3f115f40085b2dbd3d6f0fbcbf59efdd4dd96a5c36521d280838a71bc4608272" +content-hash = "026e5aba8cf2d1fe894e0b73a2561d98c82b16ff4fb508706a7819eca6379b04" diff --git a/pyproject.toml b/pyproject.toml index 394cd4c3..c7c43f15 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -30,7 +30,7 @@ nox-poetry = "^1.0.2" pytest-cov = "^4.0.0" [tool.poetry.group.dev.dependencies] -pre-commit = "^3.2.2" +pre-commit = "^3.3.0" pyinstrument = "^4.4.0" pyright = "^1.1.305" watchfiles = "^0.19.0" From 6dc653468e568f152ce5199ece2ce752349ae46e Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 2 May 2023 19:02:30 +0000 Subject: [PATCH 047/184] [pip](deps-dev): Bump pre-commit from 3.3.0 to 3.3.1 (#318) Bumps [pre-commit](https://github.com/pre-commit/pre-commit) from 3.3.0 to 3.3.1. - [Release notes](https://github.com/pre-commit/pre-commit/releases) - [Changelog](https://github.com/pre-commit/pre-commit/blob/main/CHANGELOG.md) - [Commits](https://github.com/pre-commit/pre-commit/compare/v3.3.0...v3.3.1) --- updated-dependencies: - dependency-name: pre-commit dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index 1c7b7c43..a848f318 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2310,14 +2310,14 @@ testing = ["pytest", "pytest-benchmark"] [[package]] name = "pre-commit" -version = "3.3.0" +version = "3.3.1" description = "A framework for managing and maintaining multi-language pre-commit hooks." category = "dev" optional = false python-versions = ">=3.8" files = [ - {file = "pre_commit-3.3.0-py2.py3-none-any.whl", hash = "sha256:7577a012399334d9f001873b5553f9fabc1ccc5b3e2b29e0793f84ce18e9d042"}, - {file = "pre_commit-3.3.0.tar.gz", hash = "sha256:06acda43a7b6b63fdcc29aa90bf1228cf4d4029a4e4d70971347a9d2593c94d4"}, + {file = "pre_commit-3.3.1-py2.py3-none-any.whl", hash = "sha256:218e9e3f7f7f3271ebc355a15598a4d3893ad9fc7b57fe446db75644543323b9"}, + {file = "pre_commit-3.3.1.tar.gz", hash = "sha256:733f78c9a056cdd169baa6cd4272d51ecfda95346ef8a89bf93712706021b907"}, ] [package.dependencies] @@ -3511,4 +3511,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "026e5aba8cf2d1fe894e0b73a2561d98c82b16ff4fb508706a7819eca6379b04" +content-hash = "1be23e44bc8af08fc34288cc6bc660cb2f92fc4ef5f1105bef2bdeb54a9734d1" diff --git a/pyproject.toml b/pyproject.toml index c7c43f15..d1e38fd7 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -30,7 +30,7 @@ nox-poetry = "^1.0.2" pytest-cov = "^4.0.0" [tool.poetry.group.dev.dependencies] -pre-commit = "^3.3.0" +pre-commit = "^3.3.1" pyinstrument = "^4.4.0" pyright = "^1.1.305" watchfiles = "^0.19.0" From 0c47c8a5fb14a532f925301815a01c2141f71d0d Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 2 May 2023 20:13:39 +0000 Subject: [PATCH 048/184] [pip](deps-dev): Bump ruff from 0.0.263 to 0.0.264 (#319) Bumps [ruff](https://github.com/charliermarsh/ruff) from 0.0.263 to 0.0.264. - [Release notes](https://github.com/charliermarsh/ruff/releases) - [Changelog](https://github.com/charliermarsh/ruff/blob/main/BREAKING_CHANGES.md) - [Commits](https://github.com/charliermarsh/ruff/compare/v0.0.263...v0.0.264) --- updated-dependencies: - dependency-name: ruff dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 38 +++++++++++++++++++------------------- pyproject.toml | 2 +- 2 files changed, 20 insertions(+), 20 deletions(-) diff --git a/poetry.lock b/poetry.lock index a848f318..9fb7bcdf 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2840,29 +2840,29 @@ idna2008 = ["idna"] [[package]] name = "ruff" -version = "0.0.263" +version = "0.0.264" description = "An extremely fast Python linter, written in Rust." category = "dev" optional = false python-versions = ">=3.7" files = [ - {file = "ruff-0.0.263-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:ee6c7a77f142c427fa73e1f5f603fc1a39413a36fe6966ed0fc55e97f6921d9c"}, - {file = "ruff-0.0.263-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:c3b7d4b365207f3e4c40d235127091478e595b31e35b6cd57d940920cdfae68b"}, - {file = "ruff-0.0.263-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ebc778d95f29c9917e6e7608b2b67815707e6ab8eb5af9341617beda479c3edf"}, - {file = "ruff-0.0.263-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:4f75fa1632ea065b8f10678e7b6ae9873f84d5046bdf146990112751e98af42a"}, - {file = "ruff-0.0.263-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:ddcee0d91629a4fa4bc9faebf5b94d4615d50d1cd76d1098fa71fbe1c54f4104"}, - {file = "ruff-0.0.263-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:4010b156f2e9fa6e74b5581098467f6ff68beac48945599b3a9239481e578ab4"}, - {file = "ruff-0.0.263-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:15386933dd8e03aafa3186f9e996d6823105492817311338fbcb64d0ecbcd95f"}, - {file = "ruff-0.0.263-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:04e0b280dd246448564c892bce5607d820ad1f14944f3d535db98692e2a7ac07"}, - {file = "ruff-0.0.263-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:82c41f276106017b6f075dd2f2cc68e1a0b434cc75488f816fc98bd41982628d"}, - {file = "ruff-0.0.263-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:3e9fcee3f81129eabc75da005d839235e32d7d374f2d4c0db0c708dad4703d6e"}, - {file = "ruff-0.0.263-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:981e3c4d773f7ff52479c4fd74a65e408f1e13fa5f889b72214d400cd1299ce4"}, - {file = "ruff-0.0.263-py3-none-musllinux_1_2_i686.whl", hash = "sha256:bed1d3fba306e3f7e13ce226927b84200350e25abd1e754e06ee361c6d41de15"}, - {file = "ruff-0.0.263-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:7890499c2c3dcb1e60de2a8b4c5f5775b2bfcdff7d3e68e38db5cb2d65b12006"}, - {file = "ruff-0.0.263-py3-none-win32.whl", hash = "sha256:c2b79919ebd93674b93dfc2c843e264bf8e52fbe737467e9b58521775c85f4ad"}, - {file = "ruff-0.0.263-py3-none-win_amd64.whl", hash = "sha256:9af932f665e177de62e172901704257fd6e5bfabb95893867ff7382a851459d3"}, - {file = "ruff-0.0.263-py3-none-win_arm64.whl", hash = "sha256:ddf4503595b560bfa5fae92fa2e4cb09ec465ee4cf88cc248f10ad2e956deec3"}, - {file = "ruff-0.0.263.tar.gz", hash = "sha256:1008f211ad8aa1d998517ac5bf3d68fbc68ec516d1da89b6081f25ff2f30b687"}, + {file = "ruff-0.0.264-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:ec2fa192c035b8b68cc2b91049c561cd69543e2b8c4d157d9aa7727320bedcca"}, + {file = "ruff-0.0.264-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:d97ba8db0fb601ffe9ee996ebb97c698e427a2fd4514fefbe7b803111354f783"}, + {file = "ruff-0.0.264-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:4564e0f245eb515c6ed63988c21e9c40bcfd485cd1ec63bdd790f9a81d301f15"}, + {file = "ruff-0.0.264-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:323ae6c1702b26c96d0fbf939c5959c37e79021f86b70f63634df918bc77f36e"}, + {file = "ruff-0.0.264-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:18a29ed37bf8cfe6dce8a2db56c313a64c0804095108753621f3c3321e0c9c5f"}, + {file = "ruff-0.0.264-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:d628de91e2be7a83128526636097d2dd890669a06143f826f6c591d79aeefbc4"}, + {file = "ruff-0.0.264-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:91c6eb4f979b661a2dd850d9ac803842bb7b66d4926de84f09c787af82590f73"}, + {file = "ruff-0.0.264-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:04ec5d75e4bca754cedd20d53e2ba4920d6259e7579abfb2e8e30c3c80e41b17"}, + {file = "ruff-0.0.264-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:71fd865ebacc1083259b3fb7e3eb45235a86e62e21830b8a6b067be0ec54aa2e"}, + {file = "ruff-0.0.264-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:cd4f60ffc3eb15802c554a9c8581bf2117c4d3d06fbc57e0ba58f04cb1aaa47f"}, + {file = "ruff-0.0.264-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:05ee163a046fc593d150179d23f4af447fb82f3e59cd34e031ea0868c65bb8e8"}, + {file = "ruff-0.0.264-py3-none-musllinux_1_2_i686.whl", hash = "sha256:484e395d1984ab9e1e66bd42e7a5192decfee86998d07d36ee50b2fadccc8734"}, + {file = "ruff-0.0.264-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:67326fdc9ac0a1b13e229c6e24e8d115863c52cd710faaaaa588851535281d6c"}, + {file = "ruff-0.0.264-py3-none-win32.whl", hash = "sha256:5a8658ebcc37d62f72840cbdf564171c1a2b6831db482b4d917962541a2f4a44"}, + {file = "ruff-0.0.264-py3-none-win_amd64.whl", hash = "sha256:068a82a29d80848a56e3d9d4308e6e0ca8b2ecdaf5ac342a292545a59b7f2c21"}, + {file = "ruff-0.0.264-py3-none-win_arm64.whl", hash = "sha256:3e2c38449548e122f2612843a7c04e22b4fd491656955c57b8cb05df11639ad6"}, + {file = "ruff-0.0.264.tar.gz", hash = "sha256:8fcd4b693ca1374eb7a5796581c90689f884f98f388740d94f0702fd30f8f78f"}, ] [[package]] @@ -3511,4 +3511,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "1be23e44bc8af08fc34288cc6bc660cb2f92fc4ef5f1105bef2bdeb54a9734d1" +content-hash = "5013ec36c64691489a3f3fc59dfcd8c3599e94382b9598a3e9adb6d406494707" diff --git a/pyproject.toml b/pyproject.toml index d1e38fd7..8a3bfeb5 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -35,7 +35,7 @@ pyinstrument = "^4.4.0" pyright = "^1.1.305" watchfiles = "^0.19.0" jishaku = "^2.5.1" -ruff = "^0.0.263" +ruff = "^0.0.264" [tool.poetry.group.docs.dependencies] From aa6e11a7fba6db13572bf00723b5aa4b9e605f23 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 3 May 2023 19:00:19 +0000 Subject: [PATCH 049/184] [pip](deps-dev): Bump pyright from 1.1.305 to 1.1.306 (#320) Bumps [pyright](https://github.com/RobertCraigie/pyright-python) from 1.1.305 to 1.1.306. - [Release notes](https://github.com/RobertCraigie/pyright-python/releases) - [Commits](https://github.com/RobertCraigie/pyright-python/compare/v1.1.305...v1.1.306) --- updated-dependencies: - dependency-name: pyright dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index 9fb7bcdf..3fb536c9 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2608,14 +2608,14 @@ diagrams = ["jinja2", "railroad-diagrams"] [[package]] name = "pyright" -version = "1.1.305" +version = "1.1.306" description = "Command line wrapper for pyright" category = "dev" optional = false python-versions = ">=3.7" files = [ - {file = "pyright-1.1.305-py3-none-any.whl", hash = "sha256:147da3aac44ba0516423613cad5fbb7a0abba6b71c53718a1e151f456d4ab12e"}, - {file = "pyright-1.1.305.tar.gz", hash = "sha256:924d554253ecc4fafdfbfa76989d173cc15d426aa808630c0dd669fdc3227ef7"}, + {file = "pyright-1.1.306-py3-none-any.whl", hash = "sha256:008eb2a29584ae274a154d749cf81476a3073fb562a462eac8d43a753378b9db"}, + {file = "pyright-1.1.306.tar.gz", hash = "sha256:16d5d198be64de497d5f9002000a271176c381e21b977ca5566cf779b643c9ed"}, ] [package.dependencies] @@ -3511,4 +3511,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "5013ec36c64691489a3f3fc59dfcd8c3599e94382b9598a3e9adb6d406494707" +content-hash = "88012da861fc41f1a8094fbe4ff6f20c13b5d3d897c9b0b934f14a6d939110cd" diff --git a/pyproject.toml b/pyproject.toml index 8a3bfeb5..4ef15e1e 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -32,7 +32,7 @@ pytest-cov = "^4.0.0" [tool.poetry.group.dev.dependencies] pre-commit = "^3.3.1" pyinstrument = "^4.4.0" -pyright = "^1.1.305" +pyright = "^1.1.306" watchfiles = "^0.19.0" jishaku = "^2.5.1" ruff = "^0.0.264" From 6fe720f06eae043cdf312e3831a192af6945d203 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Thu, 4 May 2023 00:04:26 -0700 Subject: [PATCH 050/184] Add an util for cog exts --- .pre-commit-config.yaml | 4 ++-- Bot/Cogs/cogs-ext.py | 36 ++++++++++++++++++++++++++++++++++++ Bot/Cogs/economy.py | 2 +- 3 files changed, 39 insertions(+), 3 deletions(-) create mode 100644 Bot/Cogs/cogs-ext.py diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index 5c0db1a5..a45f5427 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -1,5 +1,5 @@ default_language_version: - python: python3.10 + python: python3.11 files: '.py' exclude: ".env,.yml,.gitignore,.git,.md,.txt" default_stages: [push, commit] @@ -39,7 +39,7 @@ repos: stages: [commit] - repo: https://github.com/PyCQA/isort - rev: 5.10.1 + rev: 5.12.0 hooks: - id: isort name: ISort diff --git a/Bot/Cogs/cogs-ext.py b/Bot/Cogs/cogs-ext.py new file mode 100644 index 00000000..5780d9e9 --- /dev/null +++ b/Bot/Cogs/cogs-ext.py @@ -0,0 +1,36 @@ +from pathlib import Path + +import aiofiles +import discord +from discord import app_commands +from discord.ext import commands +from kumikocore import KumikoCore + + +class CogsExtensions(commands.Cog): + """Utility to add custom cogs for Kumiko""" + + def __init__(self, bot: KumikoCore) -> None: + self.bot = bot + self.session = bot.session + + @commands.hybrid_group(name="cogs-ext", alias=["cext"]) + async def cogsExt(self, ctx: commands.Context) -> None: + if ctx.invoked_subcommand is None: + await ctx.send_help(ctx.command) + + @cogsExt.command(name="add") + @app_commands.describe(cog="The cog to load. Can be from GitHub") + @commands.is_owner() + async def cogsExtAdd(self, ctx: commands.Context, cog: discord.Attachment) -> None: + """Adds and loads the given cog""" + async with self.session.get(cog.url) as r: + writeFile = Path(__file__).parent.joinpath(cog.filename) + async with aiofiles.open(writeFile, "w") as f: + await f.write(await r.text()) + await self.bot.load_extension(f"Cogs.{cog.filename[:-3]}") + await ctx.send("test") + + +async def setup(bot: KumikoCore) -> None: + await bot.add_cog(CogsExtensions(bot)) diff --git a/Bot/Cogs/economy.py b/Bot/Cogs/economy.py index 77b5edc0..2f6c0533 100644 --- a/Bot/Cogs/economy.py +++ b/Bot/Cogs/economy.py @@ -65,7 +65,7 @@ async def wallet(self, ctx: commands.Context) -> None: """Checks your wallet""" user = await getUser( id=ctx.author.id, includes={"user_inv": False, "marketplace": False} - ) + ) # type: ignore if user is None: await ctx.send( embed=Embed( From 58c62e664280f49489791a3d6aeae7d291b30d03 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Fri, 5 May 2023 19:00:50 +0000 Subject: [PATCH 051/184] [pip](deps-dev): Bump ruff from 0.0.264 to 0.0.265 (#321) Bumps [ruff](https://github.com/charliermarsh/ruff) from 0.0.264 to 0.0.265. - [Release notes](https://github.com/charliermarsh/ruff/releases) - [Changelog](https://github.com/charliermarsh/ruff/blob/main/BREAKING_CHANGES.md) - [Commits](https://github.com/charliermarsh/ruff/compare/v0.0.264...v0.0.265) --- updated-dependencies: - dependency-name: ruff dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 38 +++++++++++++++++++------------------- pyproject.toml | 2 +- 2 files changed, 20 insertions(+), 20 deletions(-) diff --git a/poetry.lock b/poetry.lock index 3fb536c9..2498a2f5 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2840,29 +2840,29 @@ idna2008 = ["idna"] [[package]] name = "ruff" -version = "0.0.264" +version = "0.0.265" description = "An extremely fast Python linter, written in Rust." category = "dev" optional = false python-versions = ">=3.7" files = [ - {file = "ruff-0.0.264-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:ec2fa192c035b8b68cc2b91049c561cd69543e2b8c4d157d9aa7727320bedcca"}, - {file = "ruff-0.0.264-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:d97ba8db0fb601ffe9ee996ebb97c698e427a2fd4514fefbe7b803111354f783"}, - {file = "ruff-0.0.264-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:4564e0f245eb515c6ed63988c21e9c40bcfd485cd1ec63bdd790f9a81d301f15"}, - {file = "ruff-0.0.264-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:323ae6c1702b26c96d0fbf939c5959c37e79021f86b70f63634df918bc77f36e"}, - {file = "ruff-0.0.264-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:18a29ed37bf8cfe6dce8a2db56c313a64c0804095108753621f3c3321e0c9c5f"}, - {file = "ruff-0.0.264-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:d628de91e2be7a83128526636097d2dd890669a06143f826f6c591d79aeefbc4"}, - {file = "ruff-0.0.264-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:91c6eb4f979b661a2dd850d9ac803842bb7b66d4926de84f09c787af82590f73"}, - {file = "ruff-0.0.264-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:04ec5d75e4bca754cedd20d53e2ba4920d6259e7579abfb2e8e30c3c80e41b17"}, - {file = "ruff-0.0.264-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:71fd865ebacc1083259b3fb7e3eb45235a86e62e21830b8a6b067be0ec54aa2e"}, - {file = "ruff-0.0.264-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:cd4f60ffc3eb15802c554a9c8581bf2117c4d3d06fbc57e0ba58f04cb1aaa47f"}, - {file = "ruff-0.0.264-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:05ee163a046fc593d150179d23f4af447fb82f3e59cd34e031ea0868c65bb8e8"}, - {file = "ruff-0.0.264-py3-none-musllinux_1_2_i686.whl", hash = "sha256:484e395d1984ab9e1e66bd42e7a5192decfee86998d07d36ee50b2fadccc8734"}, - {file = "ruff-0.0.264-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:67326fdc9ac0a1b13e229c6e24e8d115863c52cd710faaaaa588851535281d6c"}, - {file = "ruff-0.0.264-py3-none-win32.whl", hash = "sha256:5a8658ebcc37d62f72840cbdf564171c1a2b6831db482b4d917962541a2f4a44"}, - {file = "ruff-0.0.264-py3-none-win_amd64.whl", hash = "sha256:068a82a29d80848a56e3d9d4308e6e0ca8b2ecdaf5ac342a292545a59b7f2c21"}, - {file = "ruff-0.0.264-py3-none-win_arm64.whl", hash = "sha256:3e2c38449548e122f2612843a7c04e22b4fd491656955c57b8cb05df11639ad6"}, - {file = "ruff-0.0.264.tar.gz", hash = "sha256:8fcd4b693ca1374eb7a5796581c90689f884f98f388740d94f0702fd30f8f78f"}, + {file = "ruff-0.0.265-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:30ddfe22de6ce4eb1260408f4480bbbce998f954dbf470228a21a9b2c45955e4"}, + {file = "ruff-0.0.265-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:a11bd0889e88d3342e7bc514554bb4461bf6cc30ec115821c2425cfaac0b1b6a"}, + {file = "ruff-0.0.265-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:2a9b38bdb40a998cbc677db55b6225a6c4fadcf8819eb30695e1b8470942426b"}, + {file = "ruff-0.0.265-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:a8b44a245b60512403a6a03a5b5212da274d33862225c5eed3bcf12037eb19bb"}, + {file = "ruff-0.0.265-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:b279fa55ea175ef953208a6d8bfbcdcffac1c39b38cdb8c2bfafe9222add70bb"}, + {file = "ruff-0.0.265-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:5028950f7af9b119d43d91b215d5044976e43b96a0d1458d193ef0dd3c587bf8"}, + {file = "ruff-0.0.265-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:4057eb539a1d88eb84e9f6a36e0a999e0f261ed850ae5d5817e68968e7b89ed9"}, + {file = "ruff-0.0.265-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:d586e69ab5cbf521a1910b733412a5735936f6a610d805b89d35b6647e2a66aa"}, + {file = "ruff-0.0.265-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:aa17b13cd3f29fc57d06bf34c31f21d043735cc9a681203d634549b0e41047d1"}, + {file = "ruff-0.0.265-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:9ac13b11d9ad3001de9d637974ec5402a67cefdf9fffc3929ab44c2fcbb850a1"}, + {file = "ruff-0.0.265-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:62a9578b48cfd292c64ea3d28681dc16b1aa7445b7a7709a2884510fc0822118"}, + {file = "ruff-0.0.265-py3-none-musllinux_1_2_i686.whl", hash = "sha256:d0f9967f84da42d28e3d9d9354cc1575f96ed69e6e40a7d4b780a7a0418d9409"}, + {file = "ruff-0.0.265-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:1d5a8de2fbaf91ea5699451a06f4074e7a312accfa774ad9327cde3e4fda2081"}, + {file = "ruff-0.0.265-py3-none-win32.whl", hash = "sha256:9e9db5ccb810742d621f93272e3cc23b5f277d8d00c4a79668835d26ccbe48dd"}, + {file = "ruff-0.0.265-py3-none-win_amd64.whl", hash = "sha256:f54facf286103006171a00ce20388d88ed1d6732db3b49c11feb9bf3d46f90e9"}, + {file = "ruff-0.0.265-py3-none-win_arm64.whl", hash = "sha256:c78470656e33d32ddc54e8482b1b0fc6de58f1195586731e5ff1405d74421499"}, + {file = "ruff-0.0.265.tar.gz", hash = "sha256:53c17f0dab19ddc22b254b087d1381b601b155acfa8feed514f0d6a413d0ab3a"}, ] [[package]] @@ -3511,4 +3511,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "88012da861fc41f1a8094fbe4ff6f20c13b5d3d897c9b0b934f14a6d939110cd" +content-hash = "19e7f02f366d5a92ba6935a9a619af6bb6bfb8606bbb8401ac5683c3c380a824" diff --git a/pyproject.toml b/pyproject.toml index 4ef15e1e..bd972b35 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -35,7 +35,7 @@ pyinstrument = "^4.4.0" pyright = "^1.1.306" watchfiles = "^0.19.0" jishaku = "^2.5.1" -ruff = "^0.0.264" +ruff = "^0.0.265" [tool.poetry.group.docs.dependencies] From 627ee94c14aa47d5f63b6b1313bcb15c45b8d1b7 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Sat, 6 May 2023 01:09:00 -0700 Subject: [PATCH 052/184] Reduce the amount of ctx in mem + Prisma ctx --- Bot/Cogs/db.py | 49 ---- Bot/Cogs/reddit.py | 225 ++++++++++-------- Bot/Cogs/search.py | 316 +++++++++++++------------- Bot/Libs/utils/postgresql/__init__.py | 4 +- Bot/Libs/utils/postgresql/ctx.py | 43 ++-- Bot/kumikobot.py | 46 ++-- Bot/kumikocore.py | 27 --- tests/db/test_db_conn.py | 6 +- 8 files changed, 337 insertions(+), 379 deletions(-) delete mode 100644 Bot/Cogs/db.py diff --git a/Bot/Cogs/db.py b/Bot/Cogs/db.py deleted file mode 100644 index 32a2e2b3..00000000 --- a/Bot/Cogs/db.py +++ /dev/null @@ -1,49 +0,0 @@ -import asyncio -import logging - -from discord.ext import commands, tasks -from kumikocore import KumikoCore -from Libs.utils import backoff -from prisma import Prisma # type: ignore -from prisma.engine.errors import EngineConnectionError # type: ignore - - -class PrismaClientSession(commands.Cog): - def __init__(self, bot: KumikoCore): - self.bot = bot - self.backoffSec = 10 - self.backoffSecIndex = 0 - self.db = Prisma(auto_register=True) - self.logger = logging.getLogger("discord") - - async def cog_load(self) -> None: - self.connect.start() - - async def cog_unload(self) -> None: - try: - await self.db.disconnect() - except EngineConnectionError as e: - self.logger.error( - f"Failed to disconnect from PostgreSQL database - {str(e)}" - ) - - @tasks.loop(count=1) - async def connect(self) -> None: - await self.db.connect() - self.logger.info("Successfully connected to PostgreSQL database") - - @connect.error # type: ignore - async def connError(self, exc: Exception) -> None: - backoffTime = backoff( - backoff_sec=self.backoffSec, backoff_sec_index=self.backoffSecIndex - ) - self.backoffSecIndex += 1 - self.logger.error( - f"({str(exc.__class__.__name__)}) Failed to connect to PostgreSQL database - Reconnecting in {int(backoffTime)} seconds" - ) - await asyncio.sleep(backoffTime) - self.connect.restart() - - -async def setup(bot: KumikoCore): - await bot.add_cog(PrismaClientSession(bot)) diff --git a/Bot/Cogs/reddit.py b/Bot/Cogs/reddit.py index e413eb0d..8ed92bc7 100644 --- a/Bot/Cogs/reddit.py +++ b/Bot/Cogs/reddit.py @@ -1,21 +1,30 @@ +import os from datetime import datetime from typing import Literal, Optional +import asyncpraw import orjson from discord import app_commands from discord.ext import commands from discord.utils import format_dt +from dotenv import load_dotenv from kumikocore import KumikoCore from Libs.utils import parseSubreddit from Libs.utils.pages import EmbedListSource, KumikoPages +load_dotenv() + + +REDDIT_ID = os.environ["REDDIT_ID"] +REDDIT_SECRET = os.environ["REDDIT_SECRET"] + class Reddit(commands.Cog): """Search, and view posts and memes from Reddit""" def __init__(self, bot: KumikoCore) -> None: self.bot = bot - self.prawReddit = self.bot.reddit_session + self.session = self.bot.session @commands.hybrid_group(name="reddit") async def reddit(self, ctx: commands.Context) -> None: @@ -32,33 +41,41 @@ async def redditSearch( self, ctx: commands.Context, *, search: str, subreddit: Optional[str] = "all" ) -> None: """Searches for posts on Reddit""" - sub = await self.prawReddit.subreddit(parseSubreddit(subreddit)) - data = [ - { - "title": post.title, - "description": post.selftext, - "image": post.url, - "fields": [ - {"name": "Author", "value": post.author}, - {"name": "Upvotes", "value": post.score}, - {"name": "NSFW", "value": post.over_18}, - {"name": "Flair", "value": post.link_flair_text}, - {"name": "Number of Comments", "value": post.num_comments}, - { - "name": "Reddit URL", - "value": f"https://reddit.com{post.permalink}", - }, - { - "name": "Created At", - "value": format_dt(datetime.fromtimestamp(post.created_utc)), - }, - ], - } - async for post in sub.search(search) - ] - embedSource = EmbedListSource(data, per_page=1) - pages = KumikoPages(source=embedSource, ctx=ctx) - await pages.start() + async with asyncpraw.Reddit( + client_id=REDDIT_ID, + client_secret=REDDIT_SECRET, + user_agent="Kumiko (by /u/No767)", + requestor_kwargs={"session": self.bot.session}, + ) as reddit: + sub = await reddit.subreddit(parseSubreddit(subreddit)) + data = [ + { + "title": post.title, + "description": post.selftext, + "image": post.url, + "fields": [ + {"name": "Author", "value": post.author}, + {"name": "Upvotes", "value": post.score}, + {"name": "NSFW", "value": post.over_18}, + {"name": "Flair", "value": post.link_flair_text}, + {"name": "Number of Comments", "value": post.num_comments}, + { + "name": "Reddit URL", + "value": f"https://reddit.com{post.permalink}", + }, + { + "name": "Created At", + "value": format_dt( + datetime.fromtimestamp(post.created_utc) + ), + }, + ], + } + async for post in sub.search(search) + ] + embedSource = EmbedListSource(data, per_page=1) + pages = KumikoPages(source=embedSource, ctx=ctx) + await pages.start() @reddit.command(name="eggirl") @app_commands.describe(filter="Sort filters. Defaults to New") @@ -68,40 +85,48 @@ async def redditEggIRL( filter: Optional[Literal["New", "Hot", "Rising"]] = "New", ) -> None: """Literally just shows you r/egg_irl posts. No comment.""" - sub = await self.prawReddit.subreddit(parseSubreddit("egg_irl")) - subGen = ( - sub.new(limit=10) - if filter == "New" - else sub.hot(limit=10) - if filter == "Hot" - else sub.rising(limit=10) - ) - data = [ - { - "title": post.title, - "description": post.selftext, - "image": post.url, - "fields": [ - {"name": "Author", "value": post.author}, - {"name": "Upvotes", "value": post.score}, - {"name": "NSFW", "value": post.over_18}, - {"name": "Flair", "value": post.link_flair_text}, - {"name": "Number of Comments", "value": post.num_comments}, - { - "name": "Reddit URL", - "value": f"https://reddit.com{post.permalink}", - }, - { - "name": "Created At", - "value": format_dt(datetime.fromtimestamp(post.created_utc)), - }, - ], - } - async for post in subGen - ] - embedSource = EmbedListSource(data, per_page=1) - pages = KumikoPages(source=embedSource, ctx=ctx) - await pages.start() + async with asyncpraw.Reddit( + client_id=REDDIT_ID, + client_secret=REDDIT_SECRET, + user_agent="Kumiko (by /u/No767)", + requestor_kwargs={"session": self.bot.session}, + ) as reddit: + sub = await reddit.subreddit(parseSubreddit("egg_irl")) + subGen = ( + sub.new(limit=10) + if filter == "New" + else sub.hot(limit=10) + if filter == "Hot" + else sub.rising(limit=10) + ) + data = [ + { + "title": post.title, + "description": post.selftext, + "image": post.url, + "fields": [ + {"name": "Author", "value": post.author}, + {"name": "Upvotes", "value": post.score}, + {"name": "NSFW", "value": post.over_18}, + {"name": "Flair", "value": post.link_flair_text}, + {"name": "Number of Comments", "value": post.num_comments}, + { + "name": "Reddit URL", + "value": f"https://reddit.com{post.permalink}", + }, + { + "name": "Created At", + "value": format_dt( + datetime.fromtimestamp(post.created_utc) + ), + }, + ], + } + async for post in subGen + ] + embedSource = EmbedListSource(data, per_page=1) + pages = KumikoPages(source=embedSource, ctx=ctx) + await pages.start() @reddit.command(name="feed") @app_commands.describe( @@ -114,40 +139,48 @@ async def redditFeed( filter: Optional[Literal["New", "Hot", "Rising"]] = "New", ) -> None: """Gets a feed of posts from a subreddit""" - sub = await self.prawReddit.subreddit(parseSubreddit(subreddit)) - subGen = ( - sub.new(limit=10) - if filter == "New" - else sub.hot(limit=10) - if filter == "Hot" - else sub.rising(limit=10) - ) - data = [ - { - "title": post.title, - "description": post.selftext, - "image": post.url, - "fields": [ - {"name": "Author", "value": post.author}, - {"name": "Upvotes", "value": post.score}, - {"name": "NSFW", "value": post.over_18}, - {"name": "Flair", "value": post.link_flair_text}, - {"name": "Number of Comments", "value": post.num_comments}, - { - "name": "Reddit URL", - "value": f"https://reddit.com{post.permalink}", - }, - { - "name": "Created At", - "value": format_dt(datetime.fromtimestamp(post.created_utc)), - }, - ], - } - async for post in subGen - ] - embedSource = EmbedListSource(data, per_page=1) - pages = KumikoPages(source=embedSource, ctx=ctx) - await pages.start() + async with asyncpraw.Reddit( + client_id=REDDIT_ID, + client_secret=REDDIT_SECRET, + user_agent="Kumiko (by /u/No767)", + requestor_kwargs={"session": self.bot.session}, + ) as reddit: + sub = await reddit.subreddit(parseSubreddit(subreddit)) + subGen = ( + sub.new(limit=10) + if filter == "New" + else sub.hot(limit=10) + if filter == "Hot" + else sub.rising(limit=10) + ) + data = [ + { + "title": post.title, + "description": post.selftext, + "image": post.url, + "fields": [ + {"name": "Author", "value": post.author}, + {"name": "Upvotes", "value": post.score}, + {"name": "NSFW", "value": post.over_18}, + {"name": "Flair", "value": post.link_flair_text}, + {"name": "Number of Comments", "value": post.num_comments}, + { + "name": "Reddit URL", + "value": f"https://reddit.com{post.permalink}", + }, + { + "name": "Created At", + "value": format_dt( + datetime.fromtimestamp(post.created_utc) + ), + }, + ], + } + async for post in subGen + ] + embedSource = EmbedListSource(data, per_page=1) + pages = KumikoPages(source=embedSource, ctx=ctx) + await pages.start() @reddit.command(name="memes") @app_commands.describe( diff --git a/Bot/Cogs/search.py b/Bot/Cogs/search.py index 42134730..98c986a4 100644 --- a/Bot/Cogs/search.py +++ b/Bot/Cogs/search.py @@ -7,7 +7,8 @@ from discord.ext import commands from discord.utils import format_dt from dotenv import load_dotenv -from gql import gql +from gql import Client, gql +from gql.transport.aiohttp import AIOHTTPTransport from kumikocore import KumikoCore from Libs.errors import NoItemsError from Libs.utils.pages import EmbedListSource, KumikoPages @@ -23,7 +24,6 @@ class Searches(commands.Cog): def __init__(self, bot: KumikoCore) -> None: self.bot = bot self.session = self.bot.session - self.gql_session = self.bot.gql_session @commands.hybrid_group(name="search") async def search(self, ctx: commands.Context) -> None: @@ -35,172 +35,180 @@ async def search(self, ctx: commands.Context) -> None: @app_commands.describe(name="The name of the anime to search") async def searchAnime(self, ctx: commands.Context, *, name: str) -> None: """Searches up animes""" - query = gql( - """ - query ($animeName: String!, $perPage: Int, $isAdult: Boolean!) { - Page (perPage: $perPage){ - media(search: $animeName, isAdult: $isAdult, type: ANIME) { - title { - native - english - romaji - } - description - format - status - seasonYear - startDate { - day - month - year - } - endDate { - day - month - year - } - coverImage { - extraLarge - } - genres - tags { - name + async with Client( + transport=AIOHTTPTransport(url="https://graphql.anilist.co/"), + fetch_schema_from_transport=True, + ) as gql_session: + query = gql( + """ + query ($animeName: String!, $perPage: Int, $isAdult: Boolean!) { + Page (perPage: $perPage){ + media(search: $animeName, isAdult: $isAdult, type: ANIME) { + title { + native + english + romaji + } + description + format + status + seasonYear + startDate { + day + month + year + } + endDate { + day + month + year + } + coverImage { + extraLarge + } + genres + tags { + name + } + synonyms + id + } - synonyms - id - } } - } - """ - ) + """ + ) - params = {"animeName": name, "perPage": 25, "isAdult": False} - data = await self.gql_session.execute(query, variable_values=params) + params = {"animeName": name, "perPage": 25, "isAdult": False} + data = await gql_session.execute(query, variable_values=params) - if len(data["Page"]["media"]) == 0: - raise NoItemsError - else: - mainData = [ - { - "title": item["title"]["romaji"], - "description": str(item["description"]).replace("
", ""), - "image": item["coverImage"]["extraLarge"], - "fields": [ - {"name": "Native Name", "value": item["title"]["native"]}, - {"name": "English Name", "value": item["title"]["english"]}, - {"name": "Status", "value": item["status"]}, - { - "name": "Start Date", - "value": f'{item["startDate"]["year"]}-{item["startDate"]["month"]}-{item["startDate"]["day"]}', - }, - { - "name": "End Date", - "value": f'{item["endDate"]["year"]}-{item["endDate"]["month"]}-{item["endDate"]["day"]}', - }, - {"name": "Genres", "value": item["genres"]}, - {"name": "Synonyms", "value": item["synonyms"]}, - {"name": "Format", "value": item["format"]}, - {"name": "Season Year", "value": item["seasonYear"]}, - { - "name": "Tags", - "value": [tagItem["name"] for tagItem in item["tags"]], - }, - { - "name": "AniList URL", - "value": f"https://anilist.co/anime/{item['id']}", - }, - ], - } - for item in data["Page"]["media"] - ] - embedSource = EmbedListSource(mainData, per_page=1) - pages = KumikoPages(source=embedSource, ctx=ctx) - await pages.start() + if len(data["Page"]["media"]) == 0: + raise NoItemsError + else: + mainData = [ + { + "title": item["title"]["romaji"], + "description": str(item["description"]).replace("
", ""), + "image": item["coverImage"]["extraLarge"], + "fields": [ + {"name": "Native Name", "value": item["title"]["native"]}, + {"name": "English Name", "value": item["title"]["english"]}, + {"name": "Status", "value": item["status"]}, + { + "name": "Start Date", + "value": f'{item["startDate"]["year"]}-{item["startDate"]["month"]}-{item["startDate"]["day"]}', + }, + { + "name": "End Date", + "value": f'{item["endDate"]["year"]}-{item["endDate"]["month"]}-{item["endDate"]["day"]}', + }, + {"name": "Genres", "value": item["genres"]}, + {"name": "Synonyms", "value": item["synonyms"]}, + {"name": "Format", "value": item["format"]}, + {"name": "Season Year", "value": item["seasonYear"]}, + { + "name": "Tags", + "value": [tagItem["name"] for tagItem in item["tags"]], + }, + { + "name": "AniList URL", + "value": f"https://anilist.co/anime/{item['id']}", + }, + ], + } + for item in data["Page"]["media"] + ] + embedSource = EmbedListSource(mainData, per_page=1) + pages = KumikoPages(source=embedSource, ctx=ctx) + await pages.start() @search.command(name="manga") @app_commands.describe(name="The name of the manga to search") async def searchManga(self, ctx: commands.Context, *, name: str): """Searches for manga on AniList""" - query = gql( - """ - query ($mangaName: String!, $perPage: Int, $isAdult: Boolean!) { - Page (perPage: $perPage){ - media(search: $mangaName, isAdult: $isAdult, type: MANGA) { - title { - native - english - romaji - } - description - format - status - startDate { - day - month - year - } - endDate { - day - month - year - } - coverImage { - extraLarge - } - genres - tags { - name + async with Client( + transport=AIOHTTPTransport(url="https://graphql.anilist.co/"), + fetch_schema_from_transport=True, + ) as gql_session: + query = gql( + """ + query ($mangaName: String!, $perPage: Int, $isAdult: Boolean!) { + Page (perPage: $perPage){ + media(search: $mangaName, isAdult: $isAdult, type: MANGA) { + title { + native + english + romaji + } + description + format + status + startDate { + day + month + year + } + endDate { + day + month + year + } + coverImage { + extraLarge + } + genres + tags { + name + } + synonyms + id + } - synonyms - id - } } - } - """ - ) + """ + ) - params = {"mangaName": name, "perPage": 25, "isAdult": False} - data = await self.gql_session.execute(query, variable_values=params) - if len(data["Page"]["media"]) == 0: - raise NoItemsError - else: - mainData = [ - { - "title": item["title"]["romaji"], - "description": str(item["description"]).replace("
", ""), - "image": item["coverImage"]["extraLarge"], - "fields": [ - {"name": "Native Name", "value": item["title"]["native"]}, - {"name": "English Name", "value": item["title"]["english"]}, - {"name": "Status", "value": item["status"]}, - { - "name": "Start Date", - "value": f'{item["startDate"]["year"]}-{item["startDate"]["month"]}-{item["startDate"]["day"]}', - }, - { - "name": "End Date", - "value": f'{item["endDate"]["year"]}-{item["endDate"]["month"]}-{item["endDate"]["day"]}', - }, - {"name": "Genres", "value": item["genres"]}, - {"name": "Synonyms", "value": item["synonyms"]}, - {"name": "Format", "value": item["format"]}, - { - "name": "Tags", - "value": [tagItem["name"] for tagItem in item["tags"]], - }, - { - "name": "AniList URL", - "value": f"https://anilist.co/anime/{item['id']}", - }, - ], - } - for item in data["Page"]["media"] - ] - embedSource = EmbedListSource(mainData, per_page=1) - pages = KumikoPages(source=embedSource, ctx=ctx) - await pages.start() + params = {"mangaName": name, "perPage": 25, "isAdult": False} + data = await gql_session.execute(query, variable_values=params) + if len(data["Page"]["media"]) == 0: + raise NoItemsError + else: + mainData = [ + { + "title": item["title"]["romaji"], + "description": str(item["description"]).replace("
", ""), + "image": item["coverImage"]["extraLarge"], + "fields": [ + {"name": "Native Name", "value": item["title"]["native"]}, + {"name": "English Name", "value": item["title"]["english"]}, + {"name": "Status", "value": item["status"]}, + { + "name": "Start Date", + "value": f'{item["startDate"]["year"]}-{item["startDate"]["month"]}-{item["startDate"]["day"]}', + }, + { + "name": "End Date", + "value": f'{item["endDate"]["year"]}-{item["endDate"]["month"]}-{item["endDate"]["day"]}', + }, + {"name": "Genres", "value": item["genres"]}, + {"name": "Synonyms", "value": item["synonyms"]}, + {"name": "Format", "value": item["format"]}, + { + "name": "Tags", + "value": [tagItem["name"] for tagItem in item["tags"]], + }, + { + "name": "AniList URL", + "value": f"https://anilist.co/anime/{item['id']}", + }, + ], + } + for item in data["Page"]["media"] + ] + embedSource = EmbedListSource(mainData, per_page=1) + pages = KumikoPages(source=embedSource, ctx=ctx) + await pages.start() @search.command(name="gifs") @app_commands.describe(search="The search term to use") diff --git a/Bot/Libs/utils/postgresql/__init__.py b/Bot/Libs/utils/postgresql/__init__.py index 37600a57..06a7c635 100644 --- a/Bot/Libs/utils/postgresql/__init__.py +++ b/Bot/Libs/utils/postgresql/__init__.py @@ -1,3 +1,3 @@ -from .ctx import PrismaClientSession +from .ctx import PrismaSessionManager -__all__ = ["PrismaClientSession"] +__all__ = ["PrismaSessionManager"] diff --git a/Bot/Libs/utils/postgresql/ctx.py b/Bot/Libs/utils/postgresql/ctx.py index fcde37a4..d05ce611 100644 --- a/Bot/Libs/utils/postgresql/ctx.py +++ b/Bot/Libs/utils/postgresql/ctx.py @@ -1,29 +1,34 @@ import logging -from contextlib import asynccontextmanager +from types import TracebackType +from typing import Optional, Type, TypeVar from prisma import Prisma # type: ignore from prisma.engine.errors import EngineConnectionError # type: ignore +BE = TypeVar("BE", bound=BaseException) + logger = logging.getLogger("discord") or logging.getLogger(__name__) -# This will only really be kept around for either test scripts or for other purposes -@asynccontextmanager -async def PrismaClientSession(): - """Implements an asynchronous context manager for Prisma client sessions - Raises: - EngineConnectionError: Raised when the PostgreSQL server or DB server is unreachable +class PrismaSessionManager: + """Context manager for managing Prisma Sessions""" + + def __init__(self) -> None: + self.self = self + self.db = Prisma(auto_register=True) - Returns: - AsyncIterator[None]: Returns an asynchronous context manager for Prisma client sessions - """ - try: - db = Prisma(auto_register=True) - conn = await db.connect() + async def __aenter__(self) -> None: + await self.db.connect() logger.info("Successfully connected to PostgreSQL database") - yield conn - except EngineConnectionError: - logger.error("Failed to connect to PostgreSQL database") - raise EngineConnectionError - finally: - await db.disconnect() + + async def __aexit__( + self, + exc_type: Optional[Type[BE]], + exc: Optional[BE], + traceback: Optional[TracebackType], + ) -> None: + if isinstance(exc, EngineConnectionError): + logging.error(f"Failed to connect to PostgreSQL database - {str(exc)}") + elif self.db.is_connected() is True: + await self.db.disconnect() + logging.info("Safely disconnected from PostgreSQL database") diff --git a/Bot/kumikobot.py b/Bot/kumikobot.py index 7d5c63b3..fdd6ea5b 100644 --- a/Bot/kumikobot.py +++ b/Bot/kumikobot.py @@ -1,21 +1,17 @@ +import asyncio +import contextlib import logging import os -import asyncpraw import discord from aiohttp import ClientSession from anyio import run from dotenv import load_dotenv -from gql import Client -from gql.transport.aiohttp import AIOHTTPTransport from kumikocore import KumikoCore +from Libs.utils.postgresql import PrismaSessionManager load_dotenv() - -REDDIT_ID = os.environ["REDDIT_ID"] -REDDIT_SECRET = os.environ["REDDIT_SECRET"] - KUMIKO_TOKEN = os.environ["DEV_BOT_TOKEN"] DEV_MODE = os.getenv("DEV_MODE") in ("True", "TRUE") intents = discord.Intents.default() @@ -31,28 +27,20 @@ async def main() -> None: - async with ClientSession() as session: - async with Client( - transport=AIOHTTPTransport(url="https://graphql.anilist.co/"), - fetch_schema_from_transport=True, - ) as gql_session: - async with asyncpraw.Reddit( - client_id=REDDIT_ID, - client_secret=REDDIT_SECRET, - user_agent="Kumiko (by /u/No767)", - ) as reddit: - async with KumikoCore( - intents=intents, - session=session, - gql_session=gql_session, - reddit_session=reddit, - dev_mode=DEV_MODE, - ) as bot: - await bot.start(KUMIKO_TOKEN) + async with PrismaSessionManager(): + async with ClientSession() as session: + async with KumikoCore( + intents=intents, + session=session, + dev_mode=DEV_MODE, + ) as bot: + await bot.start(KUMIKO_TOKEN) if __name__ == "__main__": - try: - run(main, backend_options={"use_uvloop": True}) - except KeyboardInterrupt: - logger.info("Shutting down...") + # I hate having to do this, but it's the only way to not get AIOHTTP to throw an cancellederror on me + with contextlib.suppress(asyncio.CancelledError): + try: + run(main, backend_options={"use_uvloop": True}) + except KeyboardInterrupt: + logger.info("Shutting down...") diff --git a/Bot/kumikocore.py b/Bot/kumikocore.py index 61798711..23698667 100644 --- a/Bot/kumikocore.py +++ b/Bot/kumikocore.py @@ -1,13 +1,10 @@ import logging from pathlib import Path as SyncPath -from typing import Union import discord from aiohttp import ClientSession from anyio import Path -from asyncpraw import Reddit from discord.ext import commands -from gql.client import AsyncClientSession, ReconnectingAsyncClientSession from Libs.utils.help import KumikoHelpPaginated from Libs.utils.redis import redisCheck @@ -26,8 +23,6 @@ def __init__( self, intents: discord.Intents, session: ClientSession, - gql_session: Union[ReconnectingAsyncClientSession, AsyncClientSession], - reddit_session: Reddit, dev_mode: bool = False, *args, **kwargs, @@ -42,8 +37,6 @@ def __init__( ) self.dev_mode = dev_mode self._session = session - self._gql_session = gql_session - self._reddit_session = reddit_session self.logger: logging.Logger = logging.getLogger("kumikobot") @property @@ -55,26 +48,6 @@ def session(self) -> ClientSession: """ return self._session - @property - def gql_session(self) -> Union[ReconnectingAsyncClientSession, AsyncClientSession]: - """A global GraphQL session used throughout the lifetime of the bot - - This is exclusively used for the AniList integration, thus the URL is set to the AniList GraphQL endpoints. - - Returns: - Union[ReconnectingAsyncClientSession, AsyncClientSession]: The current GQL session - """ - return self._gql_session - - @property - def reddit_session(self) -> Reddit: - """A global Reddit session used throughout the lifetime of the bot - - Returns: - Reddit: The current Reddit session - """ - return self._reddit_session - async def fsWatcher(self) -> None: cogsPath = SyncPath(__file__).parent.joinpath("Cogs") async for changes in awatch(cogsPath): diff --git a/tests/db/test_db_conn.py b/tests/db/test_db_conn.py index 4b123ffd..d465e9c3 100644 --- a/tests/db/test_db_conn.py +++ b/tests/db/test_db_conn.py @@ -7,12 +7,12 @@ sys.path.append(str(path)) -from Libs.utils.postgresql import PrismaClientSession +from Libs.utils.postgresql import PrismaSessionManager from prisma.models import User @pytest.mark.asyncio -async def test_prisma_client_session(): - async with PrismaClientSession(): +async def test_prisma_client_session_manager(): + async with PrismaSessionManager(): res = await User.prisma().find_first(where={"id": 454357482102587393}) assert (res is None) or (isinstance(res, User)) # nosec From 2dc43456011e7a93c949dcd50f1377f5b5ddb550 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Sat, 6 May 2023 11:47:11 -0700 Subject: [PATCH 053/184] Include Ruff for linting --- .github/workflows/lint.yml | 4 ++++ Bot/Libs/utils/help/kumiko_help.py | 4 ++-- Bot/Libs/utils/help/kumiko_help_paginated.py | 4 ++-- pyproject.toml | 3 +++ 4 files changed, 11 insertions(+), 4 deletions(-) diff --git a/.github/workflows/lint.yml b/.github/workflows/lint.yml index 87c7a988..a44f809c 100644 --- a/.github/workflows/lint.yml +++ b/.github/workflows/lint.yml @@ -67,3 +67,7 @@ jobs: - name: Run Pyright run: | poetry run pyright Bot + + - name: Run Ruff + run: | + poetry run ruff Bot diff --git a/Bot/Libs/utils/help/kumiko_help.py b/Bot/Libs/utils/help/kumiko_help.py index 7550d69d..b111c3f6 100644 --- a/Bot/Libs/utils/help/kumiko_help.py +++ b/Bot/Libs/utils/help/kumiko_help.py @@ -29,9 +29,9 @@ async def send_bot_help(self, mapping): for ( cog, - commands, + cmds, ) in mapping.items(): # iterating through our mapping of cog: commands - if filtered_commands := await self.filter_commands(commands): + if filtered_commands := await self.filter_commands(cmds): # if no commands are usable in this category, we don't want to display it amount_commands = len(filtered_commands) usable += amount_commands diff --git a/Bot/Libs/utils/help/kumiko_help_paginated.py b/Bot/Libs/utils/help/kumiko_help_paginated.py index a5f7cc7e..4381d59f 100644 --- a/Bot/Libs/utils/help/kumiko_help_paginated.py +++ b/Bot/Libs/utils/help/kumiko_help_paginated.py @@ -66,9 +66,9 @@ async def send_bot_help( for ( cog, - commands, + cmds, ) in mapping.items(): # iterating through our mapping of cog: commands - if filtered_commands := await self.filter_commands(commands): + if filtered_commands := await self.filter_commands(cmds): # if no commands are usable in this category, we don't want to display it amount_commands = len(filtered_commands) usable += amount_commands diff --git a/pyproject.toml b/pyproject.toml index bd972b35..944f4bad 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -58,6 +58,9 @@ reportMissingTypeStubs = false [tool.bandit] skips = ["B311", "B101"] +[tool.ruff] +ignore = ["E501"] + [build-system] requires = ["poetry-core>=1.0.0"] build-backend = "poetry.core.masonry.api" From 0bd55b67219503d769573b0436e3ff38bfa8106a Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Mon, 8 May 2023 19:03:33 +0000 Subject: [PATCH 054/184] [pip](deps): Bump orjson from 3.8.11 to 3.8.12 (#322) Bumps [orjson](https://github.com/ijl/orjson) from 3.8.11 to 3.8.12. - [Release notes](https://github.com/ijl/orjson/releases) - [Changelog](https://github.com/ijl/orjson/blob/master/CHANGELOG.md) - [Commits](https://github.com/ijl/orjson/compare/3.8.11...3.8.12) --- updated-dependencies: - dependency-name: orjson dependency-type: direct:production update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 103 +++++++++++++++++++++++-------------------------- pyproject.toml | 2 +- 2 files changed, 50 insertions(+), 55 deletions(-) diff --git a/poetry.lock b/poetry.lock index 2498a2f5..b3923c16 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2125,63 +2125,58 @@ files = [ [[package]] name = "orjson" -version = "3.8.11" +version = "3.8.12" description = "Fast, correct Python JSON library supporting dataclasses, datetimes, and numpy" category = "main" optional = false -python-versions = ">= 3.7" +python-versions = ">=3.7" files = [ - {file = "orjson-3.8.11-cp310-cp310-macosx_11_0_x86_64.macosx_11_0_arm64.macosx_11_0_universal2.whl", hash = "sha256:9fa900bdd84b4576c8dd6f3e2a00b35797f29283af328c6e3d70addfa4c2d599"}, - {file = "orjson-3.8.11-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:1103e597c16f82c241e1b02beadc9c91cecd93e60433ca73cb6464dcc235f37c"}, - {file = "orjson-3.8.11-cp310-cp310-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:d70b6db9d4e1e6057829cd7fe119c217cebaf989f88d14b2445fa69fc568d03e"}, - {file = "orjson-3.8.11-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:3afccf7f8684dca7f017837a315de0a1ab5c095de22a4eed206d079f9325ed72"}, - {file = "orjson-3.8.11-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:1fedcc428416e23a6c9de62a000c22ae33bbe0108302ad5d5935e29ea739bf37"}, - {file = "orjson-3.8.11-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:bf48ed8d4b6ab9f23b7ee642462369d7133412d72824bad89f9bf4311c06c6a1"}, - {file = "orjson-3.8.11-cp310-cp310-manylinux_2_28_x86_64.whl", hash = "sha256:3c55065bc2075a5ea6ffb30462d84fd3aa5bbb7ae600855c325ee5753feec715"}, - {file = "orjson-3.8.11-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:08729e339ff3146e6de56c1166f014c3d2ec3e79ffb76d6c55d52cc892e5e477"}, - {file = "orjson-3.8.11-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:358e515b8b19a275b259f5ee1e0efa2859b1d976b5ed5d016ac59f9e6c8788a3"}, - {file = "orjson-3.8.11-cp310-none-win_amd64.whl", hash = "sha256:62eb8bdcf6f4cdbe12743e88ad98696277a75f91a35e8fb93a7ea2b9f4a7000c"}, - {file = "orjson-3.8.11-cp311-cp311-macosx_11_0_x86_64.macosx_11_0_arm64.macosx_11_0_universal2.whl", hash = "sha256:982ab319b7a5ece4199caf2a2b3a28e62a8e289cb6418548ef98bced7e2a6cfe"}, - {file = "orjson-3.8.11-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:e14903bfeb591a9117b7d40d81e3ebca9700b4e77bd829d6f22ea57941bb0ebf"}, - {file = "orjson-3.8.11-cp311-cp311-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:58c068f93d701f9466f667bf3b5cb4e4946aee940df2b07ca5101f1cf1b60ce4"}, - {file = "orjson-3.8.11-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:9486963d2e65482c565dacb366adb36d22aa22acf7274b61490244c3d87fa631"}, - {file = "orjson-3.8.11-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:5c3b5405edc3a5f9e34516ee1a729f6c46aecf6de960ae07a7b3e95ebdd0e1d9"}, - {file = "orjson-3.8.11-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:3b65424ceee82b94e3613233b67ef110dc58f9d83b0076ec47a506289552a861"}, - {file = "orjson-3.8.11-cp311-cp311-manylinux_2_28_x86_64.whl", hash = "sha256:173b8f8c750590f432757292cfb197582e5c14347b913b4017561d47af0e759b"}, - {file = "orjson-3.8.11-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:37f38c8194ce086e6a9816b4b8dde5e7f383feeed92feec0385d99baf64f9b6e"}, - {file = "orjson-3.8.11-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:553fdaf9f4b5060a0dcc517ae0c511c289c184a83d6719d03c5602ed0eef0390"}, - {file = "orjson-3.8.11-cp311-none-win_amd64.whl", hash = "sha256:12f647d4da0aab1997e25bed4fa2b76782b5b9d2d1bf3066b5f0a57d34d833c4"}, - {file = "orjson-3.8.11-cp37-cp37m-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:71a656f1c62e84c69060093e20cedff6a92e472d53ff5b8b9026b1b298542a68"}, - {file = "orjson-3.8.11-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:176d742f53434541e50a5e659694073aa51dcbd8f29a1708a4fa1a320193c615"}, - {file = "orjson-3.8.11-cp37-cp37m-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:b369019e597b59c4b97e9f925a3b725321fa1481c129d76c74c6ea3823f5d1e8"}, - {file = "orjson-3.8.11-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:0a53b3c02a38aadc5302661c2ca18645093971488992df77ce14fef16f598b2e"}, - {file = "orjson-3.8.11-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:6d7b050135669d2335e40120215ad4120e29958c139f8bab68ce06a1cb1a1b2c"}, - {file = "orjson-3.8.11-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:66f0c9e4e8f6641497a7dc50591af3704b11468e9fc90cfb5874f28b0a61edb5"}, - {file = "orjson-3.8.11-cp37-cp37m-manylinux_2_28_x86_64.whl", hash = "sha256:235926b38ed9b76ab2bca99ff26ece79c1c46bc10079b06e660b087aecffbe69"}, - {file = "orjson-3.8.11-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:c2d3e6b65458ed71b6797f321d6e8bfeeadee9d3d31cac47806a608ea745edd7"}, - {file = "orjson-3.8.11-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:4118dcd2b5a27a22af5ad92414073f25d93bca1868f1f580056003c84841062f"}, - {file = "orjson-3.8.11-cp37-none-win_amd64.whl", hash = "sha256:b68a07794834b7bd53ae2a8b4fe4bf010734cae3f0917d434c83b97acf8e5bce"}, - {file = "orjson-3.8.11-cp38-cp38-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:98befa717efaab7ddb847ebe47d473f6bd6f0cb53e98e6c3d487c7c58ba2e174"}, - {file = "orjson-3.8.11-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:0f9415b86ef154bf247fa78a6918aac50089c296e26fb6cf15bc9d7e6402a1f8"}, - {file = "orjson-3.8.11-cp38-cp38-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:f7aeefac55848aeb29f20b91fa55f9e488f446201bb1bb31dc17480d113d8955"}, - {file = "orjson-3.8.11-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:d47f97b99beb9bcac6e288a76b559543a61e0187443d8089204b757726b1d000"}, - {file = "orjson-3.8.11-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:d7d5aecccfaf2052cd07ed5bec8efba9ddfea055682fcd346047b1a3e9da3034"}, - {file = "orjson-3.8.11-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:04b60dfc1251742e79bb075d7a7c4e37078b932a02e6f005c45761bd90c69189"}, - {file = "orjson-3.8.11-cp38-cp38-manylinux_2_28_x86_64.whl", hash = "sha256:ef52f1d5a2f89ef9049781c90ea35d5edf74374ed6ed515c286a706d1b290267"}, - {file = "orjson-3.8.11-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:7c7b4fae3b8fc69c8e76f1c0694f3decfe8a57f87e7ac7779ebb59cd71135438"}, - {file = "orjson-3.8.11-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:f4e4a1001933166fd1c257b920b241b35322bef99ed7329338bf266ac053abe7"}, - {file = "orjson-3.8.11-cp38-none-win_amd64.whl", hash = "sha256:5ff10789cbc08a9fd94507c907ba55b9315e99f20345ff8ef34fac432dacd948"}, - {file = "orjson-3.8.11-cp39-cp39-macosx_11_0_x86_64.macosx_11_0_arm64.macosx_11_0_universal2.whl", hash = "sha256:c67ac094a4dde914297543af19f22532d7124f3a35245580d8b756c4ff2f5884"}, - {file = "orjson-3.8.11-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:cdf201e77d3fac9d8d6f68d872ef45dccfe46f30b268bb88b6c5af5065b433aa"}, - {file = "orjson-3.8.11-cp39-cp39-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:3485c458670c0edb79ca149fe201f199dd9ccfe7ca3acbdef617e3c683e7b97f"}, - {file = "orjson-3.8.11-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:1e97fdbb779a3b8f5d9fc7dfddef5325f81ee45897eb7cb4638d5d9734d42514"}, - {file = "orjson-3.8.11-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:2fc050f8e7f2e4061c8c9968ad0be745b11b03913b77ffa8ceca65914696886c"}, - {file = "orjson-3.8.11-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f2ef933da50b31c112b252be03d1ef59e0d0552c1a08e48295bd529ce42aaab8"}, - {file = "orjson-3.8.11-cp39-cp39-manylinux_2_28_x86_64.whl", hash = "sha256:714c3e2be6ed7e4ff6e887926d6e171bfd94fdee76d7d3bfa74ee19237a2d49d"}, - {file = "orjson-3.8.11-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:7e4ded77ac7432a155d1d27a83bcadf722750aea3b9e6c4d47f2a92054ab71cb"}, - {file = "orjson-3.8.11-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:382f15861a4bf447ab9d07106010e61b217ef6d4245c6cf64af0c12c4c5e2346"}, - {file = "orjson-3.8.11-cp39-none-win_amd64.whl", hash = "sha256:0bc3d1b93a73b46a698c054697eb2d27bdedbc5ea0d11ec5f1a6bfbec36346b5"}, - {file = "orjson-3.8.11.tar.gz", hash = "sha256:882c77126c42dd93bb35288632d69b1e393863a2b752de3e5fe0112833609496"}, + {file = "orjson-3.8.12-cp310-cp310-macosx_11_0_x86_64.macosx_11_0_arm64.macosx_11_0_universal2.whl", hash = "sha256:c84046e890e13a119404a83f2e09e622509ed4692846ff94c4ca03654fbc7fb5"}, + {file = "orjson-3.8.12-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:29706dd8189835bcf1781faed286e99ae54fd6165437d364dfdbf0276bf39b19"}, + {file = "orjson-3.8.12-cp310-cp310-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:f4e22b0aa70c963ac01fcd620de15be21a5027711b0e5d4b96debcdeea43e3ae"}, + {file = "orjson-3.8.12-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:6d1acf52d3a4b9384af09a5c2658c3a7a472a4d62a0ad1fe2c8fab8ef460c9b4"}, + {file = "orjson-3.8.12-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:a72b50719bdd6bb0acfca3d4d1c841aa4b191f3ff37268e7aba04e5d6be44ccd"}, + {file = "orjson-3.8.12-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:83e8c740a718fa6d511a82e463adc7ab17631c6eea81a716b723e127a9c51d57"}, + {file = "orjson-3.8.12-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:ebb03e4c7648f7bb299872002a6120082da018f41ba7a9ebf4ceae8d765443d2"}, + {file = "orjson-3.8.12-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:44f7bb4c995652106276442de1147c9993716d1e2d79b7fd435afa154ff236b9"}, + {file = "orjson-3.8.12-cp310-none-win_amd64.whl", hash = "sha256:06e528f9a84fbb4000fd0eee573b5db543ee70ae586fdbc53e740b0ac981701c"}, + {file = "orjson-3.8.12-cp311-cp311-macosx_11_0_x86_64.macosx_11_0_arm64.macosx_11_0_universal2.whl", hash = "sha256:9a6c1594d5a9ff56e5babc4a87ac372af38d37adef9e06744e9f158431e33f43"}, + {file = "orjson-3.8.12-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:c6390ce0bce24c107fc275736aa8a4f768ef7eb5df935d7dca0cc99815eb5d99"}, + {file = "orjson-3.8.12-cp311-cp311-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:efb3a10030462a22c731682434df5c137a67632a8339f821cd501920b169007e"}, + {file = "orjson-3.8.12-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:7e405d54c84c30d9b1c918c290bcf4ef484a45c69d5583a95db81ffffba40b44"}, + {file = "orjson-3.8.12-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:cd6fbd1413559572e81b5ac64c45388147c3ba85cc3df2eaa11002945e0dbd1f"}, + {file = "orjson-3.8.12-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f480ae7b84369b1860d8867f0baf8d885fede400fda390ce088bfa8edf97ffdc"}, + {file = "orjson-3.8.12-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:355055e0977c43b0e5325b9312b7208c696fe20cd54eed1d6fc80b0a4d6721f5"}, + {file = "orjson-3.8.12-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:d937503e4dfba5edc8d5e0426d3cc97ed55716e93212b2e12a198664487b9965"}, + {file = "orjson-3.8.12-cp311-none-win_amd64.whl", hash = "sha256:eb16e0195febd24b44f4db1ab3be85ecf6038f92fd511370cebc004b3d422294"}, + {file = "orjson-3.8.12-cp37-cp37m-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:dc27a8ec13f28e92dc1ea89bf1232d77e7d3ebfd5c1ccf4f3729a70561cb63bd"}, + {file = "orjson-3.8.12-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:77710774faed337ac4ad919dadc5f3b655b0cd40518e5386e6f1f116de9c6c25"}, + {file = "orjson-3.8.12-cp37-cp37m-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:7e549468867991f6f9cfbd9c5bbc977330173bd8f6ceb79973bbd4634e13e1b9"}, + {file = "orjson-3.8.12-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:96fb1eb82b578eb6c0e53e3cf950839fe98ea210626f87c8204bd4fc2cc6ba02"}, + {file = "orjson-3.8.12-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:8d153b228b6e24f8bccf732a51e01e8e938eef59efed9030c5c257778fbe0804"}, + {file = "orjson-3.8.12-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:becbd5af6d035a7ec2ee3239d4700929d52d8517806b97dd04efcc37289403f7"}, + {file = "orjson-3.8.12-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:7d63f524048825e05950db3b6998c756d5377a5e8c469b2e3bdb9f3217523d74"}, + {file = "orjson-3.8.12-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:ec4f0130d9a27cb400423e09e0f9e46480e9e977f05fdcf663a7a2c68735513e"}, + {file = "orjson-3.8.12-cp37-none-win_amd64.whl", hash = "sha256:6f1b01f641f5e87168b819ac1cbd81aa6278e7572c326f3d27e92dea442a2c0d"}, + {file = "orjson-3.8.12-cp38-cp38-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:062e67108c218fdb9475edd5272b1629c05b56c66416fa915de5656adde30e73"}, + {file = "orjson-3.8.12-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:0ba645c92801417933fa74448622ba614a275ea82df05e888095c7742d913bb4"}, + {file = "orjson-3.8.12-cp38-cp38-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:7d50d9b1ae409ea15534365fec0ce8a5a5f7dc94aa790aacfb8cfec87ab51aa4"}, + {file = "orjson-3.8.12-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:8f00038bf5d07439d13c0c2c5cd6ad48eb86df7dbd7a484013ce6a113c421b14"}, + {file = "orjson-3.8.12-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:397670665f94cf5cff779054781d80395084ba97191d82f7b3a86f0a20e6102b"}, + {file = "orjson-3.8.12-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:6f568205519bb0197ca91915c5da6058cfbb59993e557b02dfc3b2718b34770a"}, + {file = "orjson-3.8.12-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:4fd240e736ce52cd757d74142d9933fd35a3184396be887c435f0574e0388654"}, + {file = "orjson-3.8.12-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:6cae2ff288a80e81ce30313e735c5436495ab58cf8d4fbe84900e616d0ee7a78"}, + {file = "orjson-3.8.12-cp38-none-win_amd64.whl", hash = "sha256:710c40c214b753392e46f9275fd795e9630dd737a5ab4ac6e4ee1a02fe83cc0d"}, + {file = "orjson-3.8.12-cp39-cp39-macosx_11_0_x86_64.macosx_11_0_arm64.macosx_11_0_universal2.whl", hash = "sha256:aff761de5ed5543a0a51e9f703668624749aa2239de5d7d37d9c9693daeaf5dc"}, + {file = "orjson-3.8.12-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:135f29cf936283a0cd1b8bce86540ca181108f2a4d4483eedad6b8026865d2a9"}, + {file = "orjson-3.8.12-cp39-cp39-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:62f999798f2fa55e567d483864ebfc30120fb055c2696a255979439323a5b15c"}, + {file = "orjson-3.8.12-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:3fa58ca064c640fa9d823f98fbbc8e71940ecb78cea3ac2507da1cbf49d60b51"}, + {file = "orjson-3.8.12-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:8682f752c19f6a7d9fc727fd98588b4c8b0dce791b5794bb814c7379ccd64a79"}, + {file = "orjson-3.8.12-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:de3d096dde3e46d01841abc1982b906694ab3c92f338d37a2e6184739dc8a958"}, + {file = "orjson-3.8.12-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:834b50df79f1fe89bbaced3a1c1d8c8c92cc99e84cdcd374d8da4974b3560d2a"}, + {file = "orjson-3.8.12-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:2ad149ed76dce2bbdfbadd61c35959305e77141badf364a158beb4ef3d88ec37"}, + {file = "orjson-3.8.12-cp39-none-win_amd64.whl", hash = "sha256:82d65e478a21f98107b4eb8390104746bb3024c27084b57edab7d427385f1f70"}, + {file = "orjson-3.8.12.tar.gz", hash = "sha256:9f0f042cf002a474a6aea006dd9f8d7a5497e35e5fb190ec78eb4d232ec19955"}, ] [[package]] @@ -3511,4 +3506,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "19e7f02f366d5a92ba6935a9a619af6bb6bfb8606bbb8401ac5683c3c380a824" +content-hash = "11d8991a762945d61e751fcdbd8745d2320bd2de84b18869953b54b13d394eaf" diff --git a/pyproject.toml b/pyproject.toml index 944f4bad..db402e95 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -10,7 +10,7 @@ python = ">=3.8,<4.0" python-dotenv = "^1.0.0" aiodns = "^3.0.0" Brotli = "^1.0.9" -orjson = "^3.8.11" +orjson = "^3.8.12" asyncpraw = "^7.7.0" uvloop = "^0.17.0" gql = { extras = ["aiohttp"], version = "^3.4.0" } From 173504300afc920ffad71533b4a693d096384c37 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 9 May 2023 01:15:25 +0000 Subject: [PATCH 055/184] [pip](deps): Bump redis from 4.5.4 to 4.5.5 (#324) Bumps [redis](https://github.com/redis/redis-py) from 4.5.4 to 4.5.5. - [Release notes](https://github.com/redis/redis-py/releases) - [Changelog](https://github.com/redis/redis-py/blob/master/CHANGES) - [Commits](https://github.com/redis/redis-py/compare/v4.5.4...v4.5.5) --- updated-dependencies: - dependency-name: redis dependency-type: direct:production update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 10 +++++----- pyproject.toml | 2 +- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/poetry.lock b/poetry.lock index b3923c16..ba431106 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2775,18 +2775,18 @@ files = [ [[package]] name = "redis" -version = "4.5.4" +version = "4.5.5" description = "Python client for Redis database and key-value store" category = "main" optional = false python-versions = ">=3.7" files = [ - {file = "redis-4.5.4-py3-none-any.whl", hash = "sha256:2c19e6767c474f2e85167909061d525ed65bea9301c0770bb151e041b7ac89a2"}, - {file = "redis-4.5.4.tar.gz", hash = "sha256:73ec35da4da267d6847e47f68730fdd5f62e2ca69e3ef5885c6a78a9374c3893"}, + {file = "redis-4.5.5-py3-none-any.whl", hash = "sha256:77929bc7f5dab9adf3acba2d3bb7d7658f1e0c2f1cafe7eb36434e751c471119"}, + {file = "redis-4.5.5.tar.gz", hash = "sha256:dc87a0bdef6c8bfe1ef1e1c40be7034390c2ae02d92dcd0c7ca1729443899880"}, ] [package.dependencies] -async-timeout = {version = ">=4.0.2", markers = "python_version <= \"3.11.2\""} +async-timeout = {version = ">=4.0.2", markers = "python_full_version <= \"3.11.2\""} hiredis = {version = ">=1.0.0", optional = true, markers = "extra == \"hiredis\""} [package.extras] @@ -3506,4 +3506,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "11d8991a762945d61e751fcdbd8745d2320bd2de84b18869953b54b13d394eaf" +content-hash = "2ebb786d48ab9a8e9453e745244c11a10787d02c5f9be0bd757788b63449a458" diff --git a/pyproject.toml b/pyproject.toml index db402e95..17b9547e 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -16,7 +16,7 @@ uvloop = "^0.17.0" gql = { extras = ["aiohttp"], version = "^3.4.0" } better-ipc = "^2.0.3" prisma = "^0.8.2" -redis = {extras = ["hiredis"], version = "^4.5.4"} +redis = {extras = ["hiredis"], version = "^4.5.5"} ciso8601 = "^2.3.0" faust-cchardet = "^2.1.18" discord-py = {extras = ["voice"], version = "^2.2.3"} From b9cce3efaafc79e1066bde6506523cab3ae9f6f0 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 9 May 2023 01:17:58 +0000 Subject: [PATCH 056/184] [pip](deps): Bump gql from 3.4.0 to 3.4.1 (#323) Bumps [gql](https://github.com/graphql-python/gql) from 3.4.0 to 3.4.1. - [Release notes](https://github.com/graphql-python/gql/releases) - [Commits](https://github.com/graphql-python/gql/compare/v3.4.0...v3.4.1) --- updated-dependencies: - dependency-name: gql dependency-type: direct:production update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 16 ++++++++-------- pyproject.toml | 2 +- 2 files changed, 9 insertions(+), 9 deletions(-) diff --git a/poetry.lock b/poetry.lock index ba431106..ddb8dd07 100644 --- a/poetry.lock +++ b/poetry.lock @@ -1235,14 +1235,14 @@ sphinx-basic-ng = "*" [[package]] name = "gql" -version = "3.4.0" +version = "3.4.1" description = "GraphQL client for Python" category = "main" optional = false python-versions = "*" files = [ - {file = "gql-3.4.0-py2.py3-none-any.whl", hash = "sha256:59c8a0b8f0a2f3b0b2ff970c94de86f82f65cb1da3340bfe57143e5f7ea82f71"}, - {file = "gql-3.4.0.tar.gz", hash = "sha256:ca81aa8314fa88a8c57dd1ce34941278e0c352d762eb721edcba0387829ea7c0"}, + {file = "gql-3.4.1-py2.py3-none-any.whl", hash = "sha256:315624ca0f4d571ef149d455033ebd35e45c1a13f18a059596aeddcea99135cf"}, + {file = "gql-3.4.1.tar.gz", hash = "sha256:11dc5d8715a827f2c2899593439a4f36449db4f0eafa5b1ea63948f8a2f8c545"}, ] [package.dependencies] @@ -1253,11 +1253,11 @@ yarl = ">=1.6,<2.0" [package.extras] aiohttp = ["aiohttp (>=3.7.1,<3.9.0)"] -all = ["aiohttp (>=3.7.1,<3.9.0)", "botocore (>=1.21,<2)", "requests (>=2.26,<3)", "requests-toolbelt (>=0.9.1,<1)", "urllib3 (>=1.26)", "websockets (>=10,<11)", "websockets (>=9,<10)"] +all = ["aiohttp (>=3.7.1,<3.9.0)", "botocore (>=1.21,<2)", "requests (>=2.26,<3)", "requests-toolbelt (>=0.9.1,<1)", "urllib3 (>=1.26,<2)", "websockets (>=10,<11)", "websockets (>=9,<10)"] botocore = ["botocore (>=1.21,<2)"] -dev = ["aiofiles", "aiohttp (>=3.7.1,<3.9.0)", "black (==22.3.0)", "botocore (>=1.21,<2)", "check-manifest (>=0.42,<1)", "flake8 (==3.8.1)", "isort (==4.3.21)", "mock (==4.0.2)", "mypy (==0.910)", "parse (==1.15.0)", "pytest (==6.2.5)", "pytest-asyncio (==0.16.0)", "pytest-console-scripts (==1.3.1)", "pytest-cov (==3.0.0)", "requests (>=2.26,<3)", "requests-toolbelt (>=0.9.1,<1)", "sphinx (>=3.0.0,<4)", "sphinx-argparse (==0.2.5)", "sphinx-rtd-theme (>=0.4,<1)", "types-aiofiles", "types-mock", "types-requests", "urllib3 (>=1.26)", "vcrpy (==4.0.2)", "websockets (>=10,<11)", "websockets (>=9,<10)"] -requests = ["requests (>=2.26,<3)", "requests-toolbelt (>=0.9.1,<1)", "urllib3 (>=1.26)"] -test = ["aiofiles", "aiohttp (>=3.7.1,<3.9.0)", "botocore (>=1.21,<2)", "mock (==4.0.2)", "parse (==1.15.0)", "pytest (==6.2.5)", "pytest-asyncio (==0.16.0)", "pytest-console-scripts (==1.3.1)", "pytest-cov (==3.0.0)", "requests (>=2.26,<3)", "requests-toolbelt (>=0.9.1,<1)", "urllib3 (>=1.26)", "vcrpy (==4.0.2)", "websockets (>=10,<11)", "websockets (>=9,<10)"] +dev = ["aiofiles", "aiohttp (>=3.7.1,<3.9.0)", "black (==22.3.0)", "botocore (>=1.21,<2)", "check-manifest (>=0.42,<1)", "flake8 (==3.8.1)", "isort (==4.3.21)", "mock (==4.0.2)", "mypy (==0.910)", "parse (==1.15.0)", "pytest (==6.2.5)", "pytest-asyncio (==0.16.0)", "pytest-console-scripts (==1.3.1)", "pytest-cov (==3.0.0)", "requests (>=2.26,<3)", "requests-toolbelt (>=0.9.1,<1)", "sphinx (>=3.0.0,<4)", "sphinx-argparse (==0.2.5)", "sphinx-rtd-theme (>=0.4,<1)", "types-aiofiles", "types-mock", "types-requests", "urllib3 (>=1.26,<2)", "vcrpy (==4.0.2)", "websockets (>=10,<11)", "websockets (>=9,<10)"] +requests = ["requests (>=2.26,<3)", "requests-toolbelt (>=0.9.1,<1)", "urllib3 (>=1.26,<2)"] +test = ["aiofiles", "aiohttp (>=3.7.1,<3.9.0)", "botocore (>=1.21,<2)", "mock (==4.0.2)", "parse (==1.15.0)", "pytest (==6.2.5)", "pytest-asyncio (==0.16.0)", "pytest-console-scripts (==1.3.1)", "pytest-cov (==3.0.0)", "requests (>=2.26,<3)", "requests-toolbelt (>=0.9.1,<1)", "urllib3 (>=1.26,<2)", "vcrpy (==4.0.2)", "websockets (>=10,<11)", "websockets (>=9,<10)"] test-no-transport = ["aiofiles", "mock (==4.0.2)", "parse (==1.15.0)", "pytest (==6.2.5)", "pytest-asyncio (==0.16.0)", "pytest-console-scripts (==1.3.1)", "pytest-cov (==3.0.0)", "vcrpy (==4.0.2)"] websockets = ["websockets (>=10,<11)", "websockets (>=9,<10)"] @@ -3506,4 +3506,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "2ebb786d48ab9a8e9453e745244c11a10787d02c5f9be0bd757788b63449a458" +content-hash = "478eb5acf43db82f0333116b66b6916535346add1702451c3ad05052deb470ba" diff --git a/pyproject.toml b/pyproject.toml index 17b9547e..953f3991 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -13,7 +13,7 @@ Brotli = "^1.0.9" orjson = "^3.8.12" asyncpraw = "^7.7.0" uvloop = "^0.17.0" -gql = { extras = ["aiohttp"], version = "^3.4.0" } +gql = { extras = ["aiohttp"], version = "^3.4.1" } better-ipc = "^2.0.3" prisma = "^0.8.2" redis = {extras = ["hiredis"], version = "^4.5.5"} From 642be378f689e8e08101489d679a3a608c7a0c21 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 10 May 2023 19:05:12 +0000 Subject: [PATCH 057/184] [pip](deps-dev): Bump pyright from 1.1.306 to 1.1.307 (#325) Bumps [pyright](https://github.com/RobertCraigie/pyright-python) from 1.1.306 to 1.1.307. - [Release notes](https://github.com/RobertCraigie/pyright-python/releases) - [Commits](https://github.com/RobertCraigie/pyright-python/compare/v1.1.306...v1.1.307) --- updated-dependencies: - dependency-name: pyright dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index ddb8dd07..e6ee3f57 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2603,14 +2603,14 @@ diagrams = ["jinja2", "railroad-diagrams"] [[package]] name = "pyright" -version = "1.1.306" +version = "1.1.307" description = "Command line wrapper for pyright" category = "dev" optional = false python-versions = ">=3.7" files = [ - {file = "pyright-1.1.306-py3-none-any.whl", hash = "sha256:008eb2a29584ae274a154d749cf81476a3073fb562a462eac8d43a753378b9db"}, - {file = "pyright-1.1.306.tar.gz", hash = "sha256:16d5d198be64de497d5f9002000a271176c381e21b977ca5566cf779b643c9ed"}, + {file = "pyright-1.1.307-py3-none-any.whl", hash = "sha256:6b360d2e018311bdf8acea73ef1f21bf0b5b502345aa94bc6763cf197b2e75b3"}, + {file = "pyright-1.1.307.tar.gz", hash = "sha256:b7a8734fad4a2438b8bb0dfbe462f529c9d4eb31947bdae85b9b4e7a97ff6a49"}, ] [package.dependencies] @@ -3506,4 +3506,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "478eb5acf43db82f0333116b66b6916535346add1702451c3ad05052deb470ba" +content-hash = "337a9d2f506255865403632919de3114c92152d10289708c5c43f0d683ccbe22" diff --git a/pyproject.toml b/pyproject.toml index 953f3991..930a0b47 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -32,7 +32,7 @@ pytest-cov = "^4.0.0" [tool.poetry.group.dev.dependencies] pre-commit = "^3.3.1" pyinstrument = "^4.4.0" -pyright = "^1.1.306" +pyright = "^1.1.307" watchfiles = "^0.19.0" jishaku = "^2.5.1" ruff = "^0.0.265" From 0787f00d910f145b5e770aa539f6208369395839 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Fri, 12 May 2023 01:33:30 -0700 Subject: [PATCH 058/184] [skip ci] Possible logo changes? --- README.md | 5 +++-- .../logos/kumiko_possible-transformed (1).png | Bin 0 -> 130686 bytes assets/logos/kumiko_possible-transformed.png | Bin 0 -> 471373 bytes assets/logos/kumiko_possible_rounded.png | Bin 0 -> 370590 bytes 4 files changed, 3 insertions(+), 2 deletions(-) create mode 100644 assets/logos/kumiko_possible-transformed (1).png create mode 100644 assets/logos/kumiko_possible-transformed.png create mode 100644 assets/logos/kumiko_possible_rounded.png diff --git a/README.md b/README.md index 94366f33..3020089f 100644 --- a/README.md +++ b/README.md @@ -4,7 +4,8 @@ # Kumiko (久美子) -![Kumiko](./assets/kumiko-resized-round.svg) + +![Kumiko](./assets/logos/kumiko_possible_rounded.png) [![Required Python Version](https://img.shields.io/badge/Python-3.8%20|%203.9%20|%203.10%20|%203.11-blue?logo=python&logoColor=white)](https://github.com/No767/Kumiko/blob/dev/pyproject.toml) [![CodeQL](https://github.com/No767/Kumiko/actions/workflows/codeql-analysis.yml/badge.svg?branch=dev)](https://github.com/No767/Kumiko/actions/workflows/codeql-analysis.yml) [![Snyk](https://github.com/No767/Kumiko/actions/workflows/snyk.yml/badge.svg?branch=dev)](https://github.com/No767/Kumiko/actions/workflows/snyk.yml) [![Lint](https://github.com/No767/Kumiko/actions/workflows/lint.yml/badge.svg)](https://github.com/No767/Kumiko/actions/workflows/lint.yml) [![Docker Build](https://github.com/No767/Kumiko/actions/workflows/docker-build.yml/badge.svg)](https://github.com/No767/Kumiko/actions/workflows/docker-build.yml) [![Tests](https://github.com/No767/Kumiko/actions/workflows/tests.yml/badge.svg)](https://github.com/No767/Kumiko/actions/workflows/tests.yml) ![Read the Docs](https://img.shields.io/readthedocs/kumiko?label=Docs&logo=readthedocs&logoColor=white) [![Codacy Badge](https://app.codacy.com/project/badge/Grade/950cd812f1e04f0d813bb0298fdaa225)](https://www.codacy.com/gh/No767/Kumiko/dashboard?utm_source=github.com&utm_medium=referral&utm_content=No767/Kumiko&utm_campaign=Badge_Grade) [![codecov](https://codecov.io/gh/No767/Kumiko/branch/dev/graph/badge.svg?token=CwcMp3LIFx)](https://codecov.io/gh/No767/Kumiko) [![GitHub release (latest SemVer)](https://img.shields.io/github/v/release/No767/Kumiko?label=Release&logo=github&sort=semver)](https://github.com/No767/Kumiko/releases) ![Docker Image Version (latest semver)](https://img.shields.io/docker/v/no767/kumiko?label=Docker%20Release&logo=docker&logoColor=white&sort=semver) [![GitHub License](https://img.shields.io/github/license/No767/Rin?label=License&logo=github)](https://github.com/No767/Kumiko/blob/dev/LICENSE) [![Kumiko](https://img.shields.io/badge/Kumiko-Oumae-white)](https://hibike-euphonium.fandom.com/wiki/Kumiko_Oumae) @@ -67,4 +68,4 @@ Kumiko and any software that is a part of Kumiko is licensed under [Apache-2.0]( ## Name Inspiration -Kumiko's name comes from the anime character [Kumiko Oumae](https://hibike-euphonium.fandom.com/wiki/Kumiko_Oumae) from the anime [Hibike! Euphonium](https://anilist.co/anime/20912/Hibike-Euphonium/). +Kumiko's name comes from the anime character [Kumiko Oumae](https://hibike-euphonium.fandom.com/wiki/Kumiko_Oumae) from the anime [Hibike! Euphonium](https://anilist.co/anime/20912/Hibike-Euphonium/). \ No newline at end of file diff --git a/assets/logos/kumiko_possible-transformed (1).png b/assets/logos/kumiko_possible-transformed (1).png new file mode 100644 index 0000000000000000000000000000000000000000..82485b96f5b9d800423251f8c24c0cd8621863cd GIT binary patch literal 130686 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%0AqZkUiyeOI4CF_u6=l; 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 o~k6iJ)L5kn+IoR-&t$rXa=?lyHP}hQBO= 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 D#bxS8 literal 0 HcmV?d00001 diff --git a/assets/logos/kumiko_possible-transformed.png b/assets/logos/kumiko_possible-transformed.png new file mode 100644 index 0000000000000000000000000000000000000000..733d4cd2c569850175d7814e3964417d1ea2f6be GIT binary patch literal 471373 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

  • 31FJJS15peF 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%0D^x(PqS9l6#pReAS8B=UNvE^7-g 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

    |)hV5B=Ee{q_G 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�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 Date: Fri, 12 May 2023 01:37:39 -0700 Subject: [PATCH 059/184] [skip ci] Possible logo changes? --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 3020089f..b79474af 100644 --- a/README.md +++ b/README.md @@ -5,7 +5,7 @@ # Kumiko (久美子) -![Kumiko](./assets/logos/kumiko_possible_rounded.png) +![Kumiko](./assets/logos/kumiko_possible_final`.png) [![Required Python Version](https://img.shields.io/badge/Python-3.8%20|%203.9%20|%203.10%20|%203.11-blue?logo=python&logoColor=white)](https://github.com/No767/Kumiko/blob/dev/pyproject.toml) [![CodeQL](https://github.com/No767/Kumiko/actions/workflows/codeql-analysis.yml/badge.svg?branch=dev)](https://github.com/No767/Kumiko/actions/workflows/codeql-analysis.yml) [![Snyk](https://github.com/No767/Kumiko/actions/workflows/snyk.yml/badge.svg?branch=dev)](https://github.com/No767/Kumiko/actions/workflows/snyk.yml) [![Lint](https://github.com/No767/Kumiko/actions/workflows/lint.yml/badge.svg)](https://github.com/No767/Kumiko/actions/workflows/lint.yml) [![Docker Build](https://github.com/No767/Kumiko/actions/workflows/docker-build.yml/badge.svg)](https://github.com/No767/Kumiko/actions/workflows/docker-build.yml) [![Tests](https://github.com/No767/Kumiko/actions/workflows/tests.yml/badge.svg)](https://github.com/No767/Kumiko/actions/workflows/tests.yml) ![Read the Docs](https://img.shields.io/readthedocs/kumiko?label=Docs&logo=readthedocs&logoColor=white) [![Codacy Badge](https://app.codacy.com/project/badge/Grade/950cd812f1e04f0d813bb0298fdaa225)](https://www.codacy.com/gh/No767/Kumiko/dashboard?utm_source=github.com&utm_medium=referral&utm_content=No767/Kumiko&utm_campaign=Badge_Grade) [![codecov](https://codecov.io/gh/No767/Kumiko/branch/dev/graph/badge.svg?token=CwcMp3LIFx)](https://codecov.io/gh/No767/Kumiko) [![GitHub release (latest SemVer)](https://img.shields.io/github/v/release/No767/Kumiko?label=Release&logo=github&sort=semver)](https://github.com/No767/Kumiko/releases) ![Docker Image Version (latest semver)](https://img.shields.io/docker/v/no767/kumiko?label=Docker%20Release&logo=docker&logoColor=white&sort=semver) [![GitHub License](https://img.shields.io/github/license/No767/Rin?label=License&logo=github)](https://github.com/No767/Kumiko/blob/dev/LICENSE) [![Kumiko](https://img.shields.io/badge/Kumiko-Oumae-white)](https://hibike-euphonium.fandom.com/wiki/Kumiko_Oumae) From f7ba0542903bafb917efdc58bab4c777e0fa6eb2 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Fri, 12 May 2023 01:38:47 -0700 Subject: [PATCH 060/184] [skip ci] fix readme --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index b79474af..676cbdd9 100644 --- a/README.md +++ b/README.md @@ -5,7 +5,7 @@ # Kumiko (久美子) -![Kumiko](./assets/logos/kumiko_possible_final`.png) +![Kumiko](./assets/logos/kumiko_possible_final.png) [![Required Python Version](https://img.shields.io/badge/Python-3.8%20|%203.9%20|%203.10%20|%203.11-blue?logo=python&logoColor=white)](https://github.com/No767/Kumiko/blob/dev/pyproject.toml) [![CodeQL](https://github.com/No767/Kumiko/actions/workflows/codeql-analysis.yml/badge.svg?branch=dev)](https://github.com/No767/Kumiko/actions/workflows/codeql-analysis.yml) [![Snyk](https://github.com/No767/Kumiko/actions/workflows/snyk.yml/badge.svg?branch=dev)](https://github.com/No767/Kumiko/actions/workflows/snyk.yml) [![Lint](https://github.com/No767/Kumiko/actions/workflows/lint.yml/badge.svg)](https://github.com/No767/Kumiko/actions/workflows/lint.yml) [![Docker Build](https://github.com/No767/Kumiko/actions/workflows/docker-build.yml/badge.svg)](https://github.com/No767/Kumiko/actions/workflows/docker-build.yml) [![Tests](https://github.com/No767/Kumiko/actions/workflows/tests.yml/badge.svg)](https://github.com/No767/Kumiko/actions/workflows/tests.yml) ![Read the Docs](https://img.shields.io/readthedocs/kumiko?label=Docs&logo=readthedocs&logoColor=white) [![Codacy Badge](https://app.codacy.com/project/badge/Grade/950cd812f1e04f0d813bb0298fdaa225)](https://www.codacy.com/gh/No767/Kumiko/dashboard?utm_source=github.com&utm_medium=referral&utm_content=No767/Kumiko&utm_campaign=Badge_Grade) [![codecov](https://codecov.io/gh/No767/Kumiko/branch/dev/graph/badge.svg?token=CwcMp3LIFx)](https://codecov.io/gh/No767/Kumiko) [![GitHub release (latest SemVer)](https://img.shields.io/github/v/release/No767/Kumiko?label=Release&logo=github&sort=semver)](https://github.com/No767/Kumiko/releases) ![Docker Image Version (latest semver)](https://img.shields.io/docker/v/no767/kumiko?label=Docker%20Release&logo=docker&logoColor=white&sort=semver) [![GitHub License](https://img.shields.io/github/license/No767/Rin?label=License&logo=github)](https://github.com/No767/Kumiko/blob/dev/LICENSE) [![Kumiko](https://img.shields.io/badge/Kumiko-Oumae-white)](https://hibike-euphonium.fandom.com/wiki/Kumiko_Oumae) From 81b40ed0af7b3481c5a47f173f5661dcf6ce32ec Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Fri, 12 May 2023 01:39:54 -0700 Subject: [PATCH 061/184] [skip ci] It's already 2am and i forgot --- assets/logos/kumiko_possible_final.png | Bin 0 -> 105344 bytes 1 file changed, 0 insertions(+), 0 deletions(-) create mode 100644 assets/logos/kumiko_possible_final.png diff --git a/assets/logos/kumiko_possible_final.png b/assets/logos/kumiko_possible_final.png new file mode 100644 index 0000000000000000000000000000000000000000..a76bd0b75b6bdbc37c16d7c54c0b839a351d5395 GIT binary patch literal 105344 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

    xnkuwMpI1bAc2BaV% zRtUA8MTVNsLi1;W6+dkxfMDJ$8FdZfOJRbi`Y^{cT{H1G_(q9iOQ?FJR;hiGz11~9 z5DgFYhiNB}fMa$;VE)Ol=?Q?*)#z$%$Kj5k!7Ibd?EUG79EaHlL0T_)PQvtEAjM&Z zYH(YcqqRWfwYgas8_5mKopJG&UzqPYaXb?Y9AKbU&_uE?c5HeYNd!ZH3(FB<70GW| zc+9mGDNc9DzZzp>73S_6qgrqudPmCa>Tda0Kltyi)yM<l!2C2jE}{Q}Vlb-8$bwvI-_9kILC24MwOtYH-> zhwhs+;}lP=7K2@K*^9vVHXf74F2dA4@DATuU!B>8eb9Xu*L&2B?SR|3PTO02hr-I% zORZ*DRBYV07ZN>74uK(Z29373T;lzuR2ma&0RU3o<5}4;Uc~hD$UynR7r&?+Agvdke75v~11AP(#?Bl+fmu8hKXq$)tz5tK9KufKwv7BI z?F`%HyaO@pO-`0w4!pcDRZL0B{>0-?mMa&pQPv5^(7?RQ<;lk{mk)j5(ekhVw;wD2 z{wLmDp1U}U_TD7lVQ{MOvzMc`2gtB>iljKVtH(avMg|kT@Sz7ojLu97hlp{@r|_}T z`~%Pk_XLSpatF4pp3++0E`0|ODH`8hJssk?FuxG(;s`v=MQ61=^W5dESN7VszPY#n z>kt2%e_g)po4yLIb5Pb7u0ik$7iC3PnL2&G?DtQVCqMca`SgP`;O3jKk1)a9Va$|G z=&M#%bA@`q{lv7b)WgwYjg^%$F*On93Ho_Id;NyU_jA$#KhTN|UYguTW)4TNxptdo zbA&-~(S^^wQl<{gq$kHVblZ!@rzh?#*4UOZp^e7vyW$NUSvW&2B09L1wIGavL z@6cjg1PDrA+Hwwsyaf$8?Yi<6JO^WE?=-mA9a-!i)|!axDxXllX79i<-G}fkX)5H@ z;;shk7TPj;&-Z-&cYG%W8WM3v@-UMe?F67gqqp2A3owfr)4(YtkUDX8DNP8IxSitfn5-JePrO1RQAl z-$@f8;9eY3r2-i3wL^1%;3T7Kc@KTv-C*FILBe&TAmc6EVDwzp#( zcyy!0r&^#*G*o=(jdD8RD0`BH5foD0-;4<=BzQSRzutc(0UN+1L<+!|Du^ zQy+Y*|G)3_>vb%aF7k#6@_C@-LUg z^_BAFU-#wZ`o*WQp0?Y5`T*L0uiRK@mWSW`mE|M9_`cF=R>2c}3m`J6-DeaJC}nw7 zLOTR_H8qCNaDQ=;1k=5F<8nEE{Fntu90kMe>o;R9)(56(+sQy#URWqIlhZJc%%O!< z{c$s~{O-{`LAqgZ-e-&7ovm`u1%wiXuVys)KvynlcJbEr(lb6*7FSj?^3vWS-2k)B zW)h@pS`PeLgYMQ40*?J~%{b3~6DwhBqikXByOE~DyQ7gEyhXj5hBy#6>6J?RRTUEU zOu5rem|LOI+F63Hy5}vm+@H!78h}?~+_C8)+B*N+do_Gpn%E^0Mn8ZMU?>k5>yD|6 zMzi_fh2%7;T_|p1bcDmDiR#iab?M~3;_|T0AI}m@FxCJXG>b&=&a)=CW27^rR{t9_ zyknk^DFApb<2ydmz8u<1)XIp^b9%vYZ za(%$9eZ41798KfR=HgPi;?#C^#1R;Tu`+cOsok+?Y9nN5DsfaI0DvjmSGs{+|K5Bg zlK68m%Lkwre5@Wf!9RjlQNxS@=P2pwle=2T2yrNjzCIf6fHeKyb<1OFqs=vG5Afl8 zdIrhDC837PkG|`t%lftiiEz+G0M7~sU5DD(1`BbmAd~xpMW!VtMy3{95^vKlRlRV1N1GuYR-)jh`$-6DP{S@KiaN zm?;YlC+oDzoB!fBmG$18((KtQ4Se)Q*G}2!L3?#Uz+IZUc2?>$%hpwMscCKNXsoTL zRb11zxs7FGT~G$gQ(MR_ODAwmML3^-ux}{kFj0GjoXurT#meLxcR;DjH?=E~{N`8I z%BFP;?zEJ&A~f-+(e&b6eC|rQy|_^3R+q}{m8CMbw8F8P^KH)atLtTPt%1;MmIcz9 zC(i9<4ruD;>|D8VbGF>LHDBfzmdXm2U?bL7GumFktsY8mjAetqGI0xG;N+MM1d`WV z(5myh6bwCEB!F)=Bin!CT6 z%o!aALuq2$pZIAli#ZK}r%?pL0Zn1R_~|@zD6HLbcGxQ@9RBA*im?QEre9r`sUqn+m=)3y#p;Z4D$r z>_If!AZ#7{^kNCD!7D9=X@r6CWOkWO%fXgaOjZ~-ecQmO=24JjWtuhttMBrhv%;u0 z%qWzk$SPP2nzFVOU%Psxe8J0J3~aWANV7E+g$#dHAaNn_<~=``o7%X&UV3-I^*#rJ z$bRt+haImpu$pYmMbLqh4?OyKdHVWddG7~4QhxdUA1><<<;Oq%@$$3(;b+S;n8fe- z&~KIxeDss$*=x7Ub2rx@bhPgE6@=&6a?isrDt$APWgog(+E^`(-3^41gly|Qz*rx^ zW|^#KwW!6k4)4GJKAsCE86xU z{cX=GU0guVd>2=GclSd*fAeeq%8QX=U!*y1Vg1PdUL*REjIMd!@d2W_Iil??n~36& z0oAse&e>iCiRv0rZfM}z=W1SOf&N?hX}hu)Zn)0TjpKN&POj^EDIoX z7h&W+UQ(5UK$04wqF?{YmuD4^g~y+P!C`g$B=dA+(fHI9lm?Ed(3QD`vT)nU3E>u) zO-4i0alK8Mwjhv$!_#FQg0Q9Dt#hO8D?-V)3Im5FRxRao&M6%4iFlxi+~zp}jai{DT#y!eqULv`%_3+3KdytKUdO|L1h_|tDIlc$c97IitlI9oPavQIFY z!bo>&bQ{#R_qNLUyUvu+iShFE<4=?qxH6B$0#{N-V--z^AhNAQJhr7p8N-}zZf;Q_SJW=fmajdWHdU>C`a;a=UE30VK zI(@kgqjq|<^DS0j?uC_=F!daDvAnzz=5~m-qdgtv zibvzgR3u1T4=Ru}_cVuj?j*-b;QTi(Fh&!#uOmbR8Mq9VEv#;uNf*5J4VOJk{Ga~C zUx&apusqzB7&E_q!8e{vMCS2Z1q_yob3%5(uP#I)@s4PyXBTjoDG}{5P@emV5Tg0_ONq z|4vyQIVi2k{_@aQzM*{e-}|oeo&WX+%8S4G%gg$Be_1SBWxX3e7GJ)0`Qb_dkE7Tu z`;ZNo3co;U(Ve@Gu;E6A40BLN+c4h{?xTLPxQe2JuH*r=WTlN>?p*;!`^b9gj%J+0 zcXxHDI&w@ALVW7V{&44JJJ+I#S-pzYCo|8^V}4`RUB?8!etWLmn#UA}=5C{G=2lm+ zVl>&;%L+`sw&Cz?v_7zI#T~XJ2pr%R_41~cg;Sz!{H~Ta2Rv-cy+gM}U5PINSnxW^$~m$!wcSwdR%?!7kgK-UR~~l2JEo1MdNjFO z7)c*3%(d|xY~Z98%_7rD!x_@wEqat*;Ja$~keg&E(F$9IE6)R)!3*AV628ta!7}mA zIkx7#M_FZX6LH-3)oV8}uUgTlnSV{W&B^{=tr_z^?hr@_!<|U7WU_g;HOT-3Bo}KH zh|5hXSQtB?#jGN}9;6Lwy%1I!)+mgX=6jJI#wNapU%PokUAWA0QX1egM2hD_?>mY3 zhIk^4o66Yyal|@+!S@j|eFLMIJfr2`yz6I6-!SH|IvQ(40VJ{3Z^)f{p%9Lp^%fQy zX1H~a4yObpYQvIZ2gShI?RjVMCA+BmHMH$QbEOPS4VQ2Io^LJx-M{&PZpY7vb248QY5n?B9dw_eygD7v+h( z{4)ME=hgK!G`x%qEyA#N9kx7RR2kF;?X)A1rgSRpsAdJ-*^OCOfg@`rkXL3^QU{s9 zh4rwN2Dcqo>e<8kmf-cPW$M6FIV-PR#P!P-f$m15lik zsvqrucc0tvRT z*2>WEIPcA)Pb$bLBbfnlAAw+Fjl^VohCw2+f--OhqL2w}^-lU!UiBpvLB=D#ABEY0 zgtE!9DTDvi=tk%;a-N9`;+v7z4o2YXtS>H;icAq9)1t9^VDe|LE|d>__A-}f`$ zSKj!wZ!QOeJ!o8r5jsQfa!^jb+ao{wwf9262w?tiV$`<~YMQ%Ete`b)mu0?Pf$4is zO_gu?hyQK)y1)PbDjQS%Wqu#C79p^Cuv4zh-$H=xmC>;=%-+@DGYkSgYzS3rJGe)` zR@{iE(W%KYJX)97QkmHmtH!qOJFVntMCBW`WP~)&97g@@<;$Q`Aq;-ui{Oi7&zv|} zcF@9(sH=;h)P45Xx75(9_~1>L(b1gHiaJYZNYho19IBnkTEHVdWMH319s!>;<9Z9x z?zo2=9P2Q(3!SVsHZ%5MWo;wvNlPnhWnp=BuN&!mMW&HzfEyq~G761IFwNdfMbixD zEaPTudK$~@Yu2x>N1x`k_h?@mxH@~0^&%7$4B2T!6Pv_+SGOr@=K?lOvKm(AKTQG6Krg3vfV(RmP!D0g$WE^iH~~+7*Vgi z#07_0IvU1Z>)I&`dz+$|{X$V6TXYX&ms|{chjD;a(@-T=vF;)8|xuz1W#_7HT0hQUSxh>LSg0*v~2-gy*3~1Si7>l>URr9-a=`zGV0&$=}c&0BY z<)-T>0>oWMyRry9H}SECM#kEC5EWw2;uqA88s0Uv?1MD#+9+ar9Hi?mCH<4*XevMn ztOjAzUmBR0%9ic@R$1BJDEp&h<&ihO zru@Bs`9GB}c-4Bnvv%Y||hOJ=GN z483#h#s{a*+?6#6M0Nad@UOx%zUWnhM|<;KohpqG0B#o~xjnxKj95P$2J2dDb(DkD z$VWX~t$|u9U?OkXS(3>Pq`pUAcj~(1?&$tB5SYu2^|G|ufPuHT-k{E!+^@sPn*EJ3 zhqbb}w!*U&G&W~k6`6c)X?bs9b>V&8kNmkWx{~?9xg6C*%&T8rSKc-=Oqq4^S%>l@eqocag~U%4a_+(H z-eBHuk*B+P7#u5~;f6-GkCFtpH)_`z8P)`-bctDG-DRJ8Mn}WoHGl`BC{D#0zdOM+ zJ%u=|6PSQ!5|K~5Hny0|`v?Zp)7SQrGj9w)mb2j4L!tlUkVz*&eBeXB#hZSf50NGj zOqcgExKQuz@d0ou7Tp%gVR@4}YsnoIYHd))hWr3moV# zntSwFgoo5suVYbA@0ATmS9*zL@y1r-YO2Pn;@J*NzN4Ss-9mF?DNPQQZ~Y(t-{oar z@y2qyY?Mojv)S!)le$QogZPGiGYs2w4JMx~NE0~SHcI-E@x`(2MJf&jo(PkUR3=dh z(1LYod1U&Vw`K#Y&og_CpZwxnZ(V}qBMc@*#=fs01OP6i)7n@aml2Cb`V}6T+XlDA zhT6DM<`G(RFz{`x6Z_ZgV!OGp$TR!U7qjc_0?!s#R?70~YFTMC4*uu=@IT*_+e8F^ z06-?@o0jSRYAV~9mO&yiuqJx^WtiK0eQJ)ZIzcHa0a$@DG{B1u?xkY2A%D@zBHqJa z2v){K0%zb1CX5KS`M=$l*KQH4E5J06Vy^Du+HSj=DK;>;=3Dz-gvFLbSfuepM(3IF zwJbz$6*BwyLye3*zipaS(7r^GHzdKQmPcW8?9dEpU><>VnIp^mXbq5#Q}oO;vwDc{ zJa7p`mp~%6oNA-A_>K(Y=Q|`8EkNA#fBSP~2H@2Vk;$U5IfpFxPAr;EVB*>flIB`H zRm+}{FU91V9 zUR)$p8i+4Wk+>=s&YY?1suSb}`9OtP7w8}-V6bLVj~wZpF&_Aoc2rm{LAJEEhBjU; zw^tX-t>uMsZGN^~nY~f2;a1+FoVQmN!r)7dwXzH?yKkP0syI87@`+$lBap|0=7^zeZ-i7$0~wX?A%VoN zmZ?Er-XRtBcYK#7e{4ginYs#$Os#pox#iHljVz(lY;K0JchJD86w=GcBynfKAfAd; z2nCuc-eDL&NfK@@SG*otFF7TTQZ4++}-V5^?qXXQ-58hF~3p< zda+(=awP2dXxtD|SiUHrL2{4{Sg#2me1?_7aq?k?DHOV z$_E4TNUiO+3P**LuEib?)$BGpwR#WADvDu!u)DnRo4>le>Cb;n`K6D2s0Ovme5nf#eY%_?znqe4KLfaAs{=6OTSy;yF} z&zD;ZF!a(Q+M6@X?O++1y0O))g4H%E4#6K9?7v}ZNt1&8u!ZY121#g|93GkM!O@vF z?ldD($9vLM^ybKfoAREt=UYg~u2%^@^z?!yD zP}1s`*!7Tw8Jim!zSmsmz-+fqP;IZ~kgW0-Mz(BLhU<1aDynKJ%`q*BC!c=04B`{p z8d-_S!?MU#ltls|UAJ%DClA*i8yIS9Y#H0MWlAefjR1TKoS56Z6Bo&gG`A^J@Az14 zrRNjjNCS(X-w6r?Eg@m2!hPwV!X$BJPRZ?gAGOOE{O7OpuAZaeD^?P;1R`J*G-|ls z{_?4(E|%_o=d;7eHWBT?>;SrQW2N+EGK-_TCp0dF$73nWC)Qtz>bNYA~)RY>P9+>^#Eg`!#OUl_}H4?9?NA7v)ys>8we#EJEeVlY@`hpZd~Vq!GCS)VQ>;$ zHD80$H`)or=wD{Sx(DWYTFyCac<@|Tb!ihGz~umVySB2O5N9P=G;|oYns#As-X}iS z&c#-``YcQh<16u_>1AGyI-;%~Y6=TyKcfO9i!mZVG9oSciL^@Uol0`PZ-*(BkWJEV zG@7^~&I<;?K>)GCum*^LOY=E;+#N@21KJ=0PPi?57^@SXEVpqL%&UVBiGfq{bCOB7 z-D5;mTSvpTiPlJWa`l5iUEif1gu5L>63RF2VE*~WJb9dSea?N3c6#-p#;(un`@~1+ z*;sSq`YmZp`ZAGnu)SAqU%6E#MkhlP4##!GoyXidejfNf^w53fEathR*j(Y%S!E`! zAV`SO*VuIr#Og3!;3)dGeT&@i=^v=PWrYutI5G9Fxd^a0UU4p)^8{c zT%N0Fxjh$>(1jvhSDA@vEEwQZdt!BEHOxMGXeusNx}?a&k!`iROk{v_aAd=p5UI?h zalNWxgyY=JS!mPIZB76}F%T5?LtLxqqybCRS*tEpZW)0oUArdAIcqAQi7GBEse(v_ zhvEv2yEuwgtk$Zu&O73X3zINiU24})w2cfGdWFZ8!7(Z8mYIYOb9Y9KWra)%@9GpT zz}R7UnY-ZcPN4(!<5@Wll9~eO4L3!pih%5F<~eTLc65c_7G~Gk=^4$QWA+ z6y`=tI$OrI-O}KO*{*M{FP?mO9s&TK6r98EE9cy*HLI!ERjyyVS`HmOme$ZZo68K% zny)~#)&%4bS7U5^Jla^lYH&a^-$mxF%r>L@E%;enSfsAF17?LxhJ|RFlV<v26NmW@g{`p-ev>Aj$!m(@}=J4DRKt4BJlv@2B zJSaG9fEt^aDZlo<59P4}M4xbHW4AOGS0I)#;-Zx`kNIYEcRRbCURqf!ulU+8D_s-# ztZ58wMF>=K;|PfDYi|I*!`z<^V$L7f=biXS-TArq#PD8Ct@~v#+4KaY%)mq%cD>oR z-r#O`Y_NRApa16a%>0eAy1jv5rM?}vf%TLwy5welU7;i0HWyBqK6*F}x*cCz=Im^9 zB=FK^@X4Ku$We^_-F;=&VZ)%CEJTHP(O$SwtFj zB2@Or^F2&1KdFV|dJ%-zQp-0UsekciS>Pi}W5qjs+i@ntz%e>BaxgVIkw$<}P1o@L zk0aF(<}!B&Ab{cC0qz+Z3PUTQ;+J!HUA0&x^e`+1kG7Sm+mfbZmdku?KHPM z6-B@GTfbFKo1mIWz$FOJnUZv?RB z@;W$}U2Bxd2QHK&51uOr{b)i2UpK;EOT3oJ9K}hY=q(d@6t2K09ZHj-ND}A)m~Kq6=bm|v;^NZUJqAGH z^!{__vnz>~A0MY)qjgBfmiBBhH0U5Nr!+ec15A;({Vk#|-JQTK(^t*T$phFF7HL~D zFJP0owXhu->axw_BV*fR6B9p0V%9<_4}8;WZ%F_q!XF8dNSlE@I~=c`y{`<|Swl*I zI@o%N);^L$6Q3H zSh0@m>Gj<`Lj@I(YUYVz@cpe@qTi`f-!aUQL4Ur}$ zfjq>A_f=DHC7vuJIPJI{KB_7EuExC+lAiVWyk~^K&xbzF9^O2=GujQ91aG~u1|Iq< z$3T-?i_J1V=-hM5qvd0(_(56S*($TmM)~5e{YuKzQ?^L2iKV8N^ivPvGDxq_ho|QF z>1*LKq}*PUN8*r=XVda*=-{iKYwNngbC*nf=G5C=s$vrcaRl7UUiX@Eb8V%p=vxn> zI7SgbFp?v|bdzNCI+lWZg`-b2$uP={XxLx6CjzHJuh){reUYS>a-fd>Yb_<_atdRvP+q?ea;iVSFms zMxH$zcZLVbHhI?-W0PY9iFqc!;9huhN8S*uRuORoDe1Q3)fk-H*MZqv|H&lnGIT<| z<#6y&ob0{L(zUx$`daH{Xm_)W6in=8d{**2aA3+xvrOZAXXO@2gnXdivV|41gxNcK z_px%~zOyh?SGJdOgdUVxnG_h3dm9G-J1n)MaZ@P?o$^pux%0gdIP`^bZJ%_sFx$_Ce zrY1t8`r<0EFgSHv@hJ}KSvL$77u>k_{p#Wp0)8!Kx_qK(FXKLR$I&9 z16hG)!u1TuH=5irCK*&_s<=;-Npl`h5x^=!gbwA(9^)L+fxP3WQaAi}bz~XbV|-|6 z6+jdCyoRp*uD>q;azKs0;9*)m))e$w4O*Gegw@{ln!i+z*QpQ)(IX6v1Pfwnw^fJD}Kt?xz3mV@|&JG;aRY+YB zl$^~qv^4oiNW%CmmHxm(FDmYivLn%04h2Am_&C{;X&DYpPbMGd!IL^npo|9xz@7eD z%4b8>?dvzHKndfEL$v|K#znuYf{?z`4KoH?!jw=H0yz_zPz9`Mm8(1i(duGcEaMz}~)=L*!e7~_# z4w^e?hJjiR$<2C&d75bN>r2b!)nE1YQighpd&IdfoWj)llmW#~>Vq%EYZz2u1E{o8 z;jQq?y!C9T?CZJ1+~!;3Bu(xW6v2egQ(xrUj-%;r-+T6w>+ddSU-nSBwzN<-dDaab z$$V9bof;#(bFq%J> z1~8>0Z9r-X{BgyjtkePH@h=S@k3IHSIdtMkHZOFEAsZ5{KP96@3w*%pRjQ7w-+SafKjRz6Z|Yfr<)-_09qB7?f7RLYWv{%e9PhnVP7TbL ziJjSU;pj-|#$7pR?qYi4l0m*{UjZ-nirCM(>QX{5&Y2fIP@Hqs#FDWG!a*_4PnQYv z1Bq(mfYgTj&cXAP=?=WY#y7z!dF7Sg`XdB(1%uBx+W7DrU)DR{*Lbmb(AF+ob1*hk z9)8^`%ahlylwBCRZ*;h9fd{W!6m3_NeY44T&?pHUKXszwA6gCmps$RyGfnPoi;$)q z;b|*6wxrC2X6-G{J^d_c)O7?Q68!Una+ga-L2ub*G!0;N;+5a1$z@>8_DqR}c0B6z zXx(46w^~{zm-niW?hFNYx$u7A@A%*Hj=Um+!#|Q&f^3n{y}$EbPVl70k0|38q;*gT zG5Q(zF-vn~m;3_;O~M+d)>G%db@R-nTjkdL zN*SH#FOR(V-g5fHbh$lyIXLdx!rq7@YWZvaGObe>S7C$&H2g!aeo5(@7_1XWD6=q$ zH|eGW|DB_KA=3z;_nqgSO+QwP^uy1R)T;_HG3tL$_3}=foVD5#+thNII(F9HCTVV= z@y@;Cp>lJ19){m5y%WPQH(I`ry6L4{eFtS_6UzmG;N%n6bUS?PNZNEvr!z||(6oiI zR1(e2*}B$L_q>W_<5&&164J`tMflx);$(Zvto|%v<~j&tSfcKYmxW09wl{4Y)LCc; zu}WbTBhrV=uchE>NG@ZBuBh}Wy;D9L<}z^$zN!s(j!Ws??CtA*zaSebl@ZQ<%d0<5 z0iX+!C8jt9vz|CV@48;L<0aH{h$_tQ_b`Imj!NiMnBS!VPhbTs%t;|5g$L$fajQlKETTa`Fo)Z`jyZFT`*nP5H+74a*Y~D;5gL?lJ=+&iA(X2V1jEG+sMWGf zg=~|C+NrMI(mu$`bDMpWUarM)p43q5qy}NjIsZFno^e5n!ExeqL}+nu9Eru7#kIZi z@yD-~UWB6#%GlwFa`Mcn@~YRqu`&#Q3Mjvl=rws=R;sbP#j#h;zvLw_i`u(Ic`OI< zDW8HM)*px8TDHK|4z&!QK71{_H6DR;hfzDR0(`FTJV{7717{U>^io^p#8cnx@1Z^p$|l-x8!fo7;eeR#%;Itt)EBnLY^Wvxrn#j;vzTJUAhOf`t^$UE^=k^=F_bVO`G6cVB;n$*E$q%eKl;FhvWknbwzpkY_IAn!%)J4VZw>U6o2!duPfg8X)8`QG)cB$4 z2)9}`(-jU~5g1Ijg*?0tLy}KiP3q^FC!WgO1~(_zvlnS&tK4(yR5>wyxEz^uo1(hY z=s1j?#YWo=ZVm+=Br-l13wJnFQLQ#`A0Ax5un+UgUkW0p4Hf%$&NUQ&bczUz}Eh} zG$tU9a?L{v=@e8C$HL3VGJSSGbBe4du7zIb>z5}nwbrn@41fN1EnDZ{Srw|i9yF$dl&PEIE-iV1M%rd^3 z&DLGlRqw{{Teq8w%22C^=!tWu#n^vbdX|vHecQ)zEk3lE^d;T=ZhGceIr7q1l@qV{lCp7t>3HN^*=)2Z8ibCNNxljdzOmna zd1DiIqozL=8{kUKQ-DS49 zRyMoQ`oxjKU1afvFMR|TWIN@Hz$IZvVaiSpZZX#gOrBfk9$JZ4o_;3oTR-$^Pg8TP zQ7+tdcR4mQ1A|YMnemCbr7#+O9F0CYJeG!J=aAQZ`8#VF4yF}eI<#&(OzvS>g(K}V zz~@{Jd#N0|?nt-w#`^yOcz435u}VN{U)kN=J;;zx%#}Jhq#l~uyvv{w3!4EQ5CM6D zSy3$jXkrT-28Bt`h)N^RkvPVY>6JX(=hOTbi4nZDAUuodVOnr%8WK!LU&O8im@xi2 zX1rZ!YIaR}cZ-lgYs*SXpU2=&0p3x!vZeZYn8l@u3KzZ9l=|7o0 z*M8{9XJQ6CS=K|-Gv(y*#1|JIcCAUGIVK6Zc&xTiC{}{hcs& zx}3<$5o{??J5*+tIk=WaNTWWh8dl3Bhxh!*2H5J6Yj7M!HndNMN-LzvNlR&;Iy6_G zcH)aW6;z%9Rt5>VqwKM%vOUyWHu1lkXzy*b_a^9T9JI=fg?VVUH^SAq4o8n4DgD%) ze4wzFSv$Q!(xyJI`AO%VExPouxzQ}m##+XUxIdXn!Cs-mXm1BhjSr8akZe452hmX& z+nq%x$^=aBlw21B9U)E{nA^QZuEUVQUZfu!Dz@Z3aF@kVv81*TM$OG;SzB+k);1cq zf{1qbZ47?lTVC}a_-J1#l!ewUpowtrpnzS+z;c~#FP>9-$<#h!0mwiVnC6Za^~iG> zy2fdfZt|;UdPR=sypP1>nsXWypiT(4gpGgEZVvq)J~UC*5h|{$B_l}AhWM#rhzeP!;v`&QGn&tQtyFiNv9ssSmGk#r zC?_%breXMOHo#8;^W2f};?D2#9MBcC8Gk_f3avN1`HRc&;j!Z0*Yj7G%K2A(DHU7MTFz`o-0ifX+a;G z(m;Q2y3-ze=84jS*6o7nH?}s*9vc0ghwiT?I`wLffsOJ~=m^XREp9tza{9)3zHsv< zLZz<^Lr)Iwa(zDgsOu_6C=Y10t`=-#vI~^jkc@RUfe?V%W%4nZ90B0FG2*z)cV~y7 zP90n8!4=n9+A1=beDyE>z<1hMekc4k2Im9nV(&NOgM%1}T84J9LJ#|7-TTOK-F7!+ zqKF75lW2-|CF#S~QC@0u8D3_uLpy^EYlEN^N(-uIvBe=k9%)SSIcSDuNWT(mm>q#p zg$M@{T5~%6g6TS_R)c=9dF^duVw1GQ(ZFQN02ksm@sB1ZCenRj1=u>DRbV}kzFH8P zOM#QT572IKO6l6QAw$gxRGT|xdEQ+{{Sik}po|&VL7Dro4jPohp_I-dyEDX6HxBqJ zv0735_mW_Vy$r4toLEH;haH4q+|D_>lk&`bB2Wn8-gMd=;MZmVz8tJ!TAJyly!K6B zRIXjSQVyLsjJDY>U4s*)cl>Z!ynKrb!CX>s-1$TQ*?o0~sFLcX{Kx&YdYe z&O0CvhqT%?X6K=($Wmn4z;WT#Pl`e%~wQIpX8Eal8u|edEL$T z%X9N(#8z?Qt~WQz2&TCbbrh{X22;z}YH)`Sk~t>S2;bTUQO#S`a4MJlOnY^1x$L{+ zrd7pzO~aViz_pJnvDeq1(QEdF+rTCPN{Cehl7RQ^P-~@DPX-*d?E)q9^72}_d26m* zzk0jO-kd9IYwJ{~HbVWTQ`x3!`U(g8u+?Od_&h(@-7K$u>#NGr@_d<^o-Vg9UoU50 z_;A@;S}P5gKc=oKK;$ce0ng#TtN3*TXz!^rN6U`=#%M+J@h3yaVxznP!m^WshyPN) z)~$H)o+FCGQI6EB^9eGf*+bV4bJL-kj?EtE>ng)A*eG}$9deWx0uvCO&LSP;@Mrm` z&s>`UA+7p?Ksg){*V@@H1Jvcf_()mDg4hHmhYasf+!miS_O{E-l?D8D1Or8pHf(e| zdirE~J>q^5PrQ&^=+65NZe?HvfOLQB%GJ#Na*yyKEI=0tQOQUnT2k_jbI%sV=yqMV_wWO|qTww=j5tR@BKt~irdRJ>03+1&m=gMjA+ApPwD zW&eJFzyeo;%ivBHQFBuXYIB&|XC`iCInLX~94u;O=IV!cO!UA*0pfd$m}E)GtN|+C zLk3r(cT6fRh*Wqg-J!2uD|G5n=aH)cs`ex4AW0$(!jc!c*wPC#`CjvCX>svRU-sJC zY8k>Lcg31C;=$x~543?aZz@Ah{ z6M@hoFP~W{pZ2Y}d0t34f)}6rp7cZw3ED`wys}g-KlfaD_SuW&%C+ldeqk|nA_Gft z9sG8ZwJu^7CoSKVf~>(r?=3^)qh;BxelQFBhR4d)$Db-kT@pHwRRJnIR?jxpO4lH; zz{E$-o-P{@Q5q0Un?LJC_lOU@O_0et8oSdQ14g1S-1&23b0cn(iUZ0=Kpa5WePwcF zuuS3iPL2$enepLrbaJH3jOjAL2h?Ad6i14$Ko>3|Iz2hf)2_0-xEx^__si(Pkq$t+cLRFztcw}{9F09=t2>N7 ziRnHA+*9K+xtiPtI5aslqB4l~jyt`#R=T!6A!yGJQq^w@4}JSvKY=9OwDQy*GMf95 zd4$m+=rCaz57MO)JCf6Ct_)TgEySfc5@2LB(LfnNNXML$SnMwc&M>*-ugz1TQTIWU znV-kxN`K(6VD+e;lGrxCFb}u<=cv|z@Pybndhykvx6B0}K*HLHWrLN-wGq#2r~U0w zb{Sqqw-4Nw%@kA9jP!(S{`MR~B)S7)L70%K4#h4NIW#pIEtQ(3AsaMs-rQ=HspE%A6UH9K-LPxS{^F!d-tKB* z+lTd9LrowSnXS9vaBX$9%+Jl0B{by5#yU{$qLoI=nbSwgJ?Bo9bEl7%lSik@k*Sd~ zJq{C(4d6C8@~bD>dt#)YGxdU^a4?5MJKaFiom-_T1(~@AyB#<<#YK||`8jY!nsRBS zm%s80b1eVEY_WwD9-%JA z?M`bmwpx4==AM~`*~e?EyS+t&(5P-{XIunTzxe-q_rH2NH_r?I8G{=r{QoyYPWd)k zngZKecV}dp6$o=lRstQ2ig2#0CaK8v@Y>fhdFr1d+J%By$Y^2?893V$!#K8H%G|z7 zIMnZ*8mS4MS>=>d+sBbzZYF6j ziW4rhxZIzvS9?97V$9H?KMO4`YwJF#Kv%B(y{zoEo@>J6I9BeFz5fY7u_}xVJgGbkh)~`NgN6 zDSI0TMHq1mD`|UUBf@DM&Fn5dwycLg$X6>wZLB3^SDWKLY*-t0duf=@L!uz07Am9lG#eE+5?^<$k3I6V>WOT zKiM;f%wQZp3tdV;oOfF=B%-q}%LIc$Ow|O3c_C&8{ku54!y(-kRqMgSEoZjTU>#SX zHvT#7uUZ$vY}-Ks4R&j~#=5(RINQty#y+&NbH8Qr%!i7XplRX8wKzMzeakvictDFQnB`g#GNePQwF1Yn z2**d-qcCA&88q!wYITKJ7`)D&9EQ2Qmg()n)oic3^xC>E!)M-i?OGcd*+vL{G6num z!tco7FF&>QbKn>*kqBk*igc0Z$}za=_vg@6cn0CF}XoV zv_kt`7}bj7+h}VT(A`bd+6n@hT1NL?AJrK_uIRFXc9QU1sly;~bbL{}du*B1taBSy zVc%23IxLa=Hc4k=V~aFgrL{e;yItN5%z4eGpn>#AwanePMFvP;Dp4OQWrxA^zp0t5 zdSdsInvleNoA1TuX`|dwirlv-tamBy9rYmDykGOR_3`6HoT4K895^#M!wQX*;4UmZ@$e;v9>< zX#I@tMA6t7Y(IMKFCWKrpDM?W94^O?94W^R9htp0vG5x~&VLfb&wm!W-ti6{tsekm z^ggcicn+lSL$a8d9vJ z_P1#ZKwIlq+vw+>$*#v{BT5*4t3I>k+##njul>Ci(>_UOrRlS{kFvyMye*h{o%;qp z*IHveyFIS0HUI@6sAPkdf(>$MO~s_$X>61h!oUF!=}Dj>pw%?$*kay0F;Z3$TnLlARS7Ol1B_4(cgC?wqOJKR!)r;ZuEL__B)**>M}(|JIXFQ10=p^3yDdM_z=W!=mI1wRxj&zs&dTmD&Eia)qZ) z!QdZTn=hYiER-iWKeaYj-v7j-*@479aa+V)FJQf~ZmpF*n0O4vpP0l)$K1{a4;0gq zO8nwa1(Wd}90~y4$1LoCsXoQGhw#mhOdl#Ijvh1p?|;|3-lfO!p9OLKI|fXzUxP9C zqsc_DNV`)RzV|Fr16G31B29T7U)^hQ4|7_{RYODgGI#uW-a|O4G~>!8B**Jinx?Wo zuxZ5%L>NS)gSafK9E}2@!GQYIE==d*4r+8|yINm{7DDsO=JvoSL)#kK+}MV(H(+ec zv9(5+++&?*ep5@PRyfGmVH>OL4_}>MiCNnvV?sgE%2W){M}v1EnHy?67*g#MB9nkE zBT*|ve!>fr$i3HUsrn16+12HHm_y?HG_I@QFn;Erx6`Siqvwpf53_8ewR+0a7oRN; zzW8At^BnDb>#0lSuEU2FCpA8}w{O=BO<`?&Gwl_<5FnByc<)$ME?sT?tT$H6(IZpk z!i7_10->gx;@6+9d&_H`3cEU^x-!X7h8GsW^u$YXwX(iluH0BCH*PPL`K7hA_!~cr zPkn|)2(`_mGJpw3Kbu}~!g~dRh4bS);J_--?K^hjP#MI%$YdHaSF^hSgp-0k@$56D z9|m^HHq+c*sGf!+UVw}IETD?Zg5_2-?xT(%iJc)0zs&&*^l)! zH9l3A78XOt3ag>vq0Ak3Y(vI1h&kZz@KBJ_23;-g5LpMv$mEXOa7=qz+9xJkM`orz zU`c)FQ%R*$xrVBpD`7~on#3}D zT`E~k4#TR^L4xLAw7!~x?_*vey*WV(_90e+u@6~uYX^T&>7K1|AXpcmcb}&9=4NqY zdSOdE@-T1VcYureudX)BF7Ue%+)ATSR@c$sXk<5Qw=t&C+`!^M%79ogtRG~0p)yiy zF0Ph-zSpu)lL%upDLB}N=v-2Ghv$k^$+2oNE~qRCMR+=zH|%Joa<8bX43UTxj~;nX z_QvNrbCh|W{k44UO9St`iVu3QgC-W|lKxJ4#j9Tt-%X9Zjb_}Y3_WT`kECH%BD*Ut zN*TgTrHrGQcu|FhTQhYwSKQy(E-!rHxiUWCwntTXRd7AmgQV)g`)F${3Ms)1{U5>P zJMguI#q;##+vU=&rLu-4)-WZ-z8d!LZVwgPqK;LwhDGKE+1z z(cfbuUN_ps!hk`#fyY7!8_iQv(YGI% zT#9>$v!=U^X5vLUl^?8^SSy(9Sr-9;P+QVDtI>x>uYPFz@!!!rH~g*)-t|t5$DV`l zuMCb90q7t#hYaoWdanryX8B6wRwnl_D7hut0Bj|AEmOnDN;jEXUo0CVBo0T;R!t?8 zEMLS~Yumor9T?4iMF(BD0o*2%b`wI_Z0+MqSASeMc6p|$>mJLt4y%PUHRl$W(QE~Q zu#>}0*WK(*hIfS$8D5h<(v))6!5oy4{2d|XaKr=hwB!c+KQ+B%a5olgN}POW16!!8 zjb@5bZ%tQR@Re9fNrOKL^V8bdN0O=EwO@zPlML^3@blYz4>g!#2ptpsz#arl%CG&V zuPT4$>%XSP1qW9j$2@nPaLV8^ACAVVwME|iU&Df#IC?mK_tddNA;^qrpx*7WYi(_o zmw&;FAY6y-RyYmyRN*pig^#imr#9gES{S+JeeD70Dyz+{^2BrVWqn(Lq|6Z>+cmn& zC?>xG#=$CT-^Ti81h;}-+OuoPA;dO*cJN@n(r4gkYjS4|_TgI(jt-Xjh2`?PH@-=8 zBJf983cZX<{eAEgpC}{vxNarAio3S4wpJdv?*&mZYJ1^!08E4vM`e2acocDqG#m!I zjW7P8M}I3cZd8SYg=?&?MKD=T=bsy7YM0}7F%!|HOQmXc<-0R)s3jfiTciH(I)4PMJR16o)x>jnJq>Q|in5BU*M+usz|8fVx5^9d zxj+;#QE~3sx)*1n(7F<4$3WPUu7f+Z*rF)?YavUz%qThRt(Kx9h1>MWPf6b8;)<4s_Y#Z+w@l(EALa&! z+i0Y{mG#n%wsdm?qAJNr*c>sH#i{YB*B%G=hz5wtx^Lpn96Np}4Qev9%pq^o{40zy zbLJN)UfSK2GIf}iG;9Ynt$o~w8*_{0($$-78c>Mi(s`!dIwrsMJ-671VAdY9?Zolr z&U`bT0x+}*16h=grC4cBrDHn=Gz-&ZQ3uMW!stO$-~Yf1Vl|30txDg+QfV>&^^g8$ z85|#{^83q;+1u%!nsN^_%4`tVR#ocMdx7=Lk@gelZX4n9mDY69aCH~==J)dDNMze097+c*oK@_${MN<}HFWL5 zvK2M^Nprs;!EwI{lZVlHzDcELk7Tc@pazI(!klg}pIt2>cJp@G98DZsx?Pw*>EW+$ zr~!y)T=!jeqc`uf)e`Br|CKa<(C<9*g85`iClZ!2HZbojt1l#+XbQ_mdDEz77Yn#S z>{@JIfD@xD9NUi)_^2{@C5#XxhjfxwbvfZqt2&2{W7HABIOg9WWYVr#DCxoH-VWwy zZ~4}5`^F5xt*()lYIk|=6Hk<*lT-NL6p#ZxgHWu9{AFv}i6b*;ul_OuLA$z%?HZbk zANlBq%Y_Sfk!PUbgZfczW6(7Kr^J2Y$xG!|fAu%Z&;Q5wm1i$qOS%1q+RtIQd2P1b zxN-{%Lcs%3w;Z|(qd5r3i~#M_!IX)AiD2GI2GzWpr<} zjtMW$74*R?zuG2)03hOx8?)u%M;-@ z=_pgJfjz6TLO?RPl%_Vfo^h+7hW-C08U7wYy7)cA!A|$jA%WK=QjeHjWLnGOS?D2b zGPi4{Lv*pqIM-Mbrq?{=uS#c$4#t+bWoj5NepZ{2JK8xK9H!f%VzU7{XAiY>Omd{e zh8j2;xjw5Bv^NuEdV2b)JcI>I>{dq`j(!7X3B}6Z=DT{X%q~1)C8i~2kiiBH)7wXy zFV8JhlT_8g*?3lT^rt=?l|rp3-zh)%0TeZ3TEW}+kdU6w@X=^$J@2KK9F=joO1%2c zKdTI(nJ6`ZO1?Y*pIfaBe7vsm=V9(chbCZl$`1a-xdm(7xK&1a1~Sjxg#+s>KK?jt z@N{qKel(3UtDKx++1Btu|NZ~<6I|`q0Y9lfz9V=}T|)FvJ$|YD^iRE~T)K2MTRy3| zuUx*Gx-|q|;@;%h!u6Y_+X+qXbB1NmW0xkdckOPW1kn7r30+RLMOfMLZkJdsEw89A z>wlYX(*3G{$s6i`cMhR7PUw(t{Vq&L9Xn9Sk$-bHm&?6bx~tNrG!k>2Z(JsOhkE># zkNgJ0?r>RYu9v5uyHqZmJqv@8N35mJ&s^KNlSg1APc042{n^G!xw?o80-dNJR5;{P zW-mUO{U4J;Q_F@w!={ zes|s0)h8A~NhfntG@f-TS%lU&cq_c`1c|c#?5pKlWKZG&r#`orHk^flAqGw5O|**F z%{#{qrnPfkVd`9?b!G6xZ3}`hDuMuk;nF$!(zejrBA$f{_@>!}!Qnm?n9XEvRIfm= zJXX9t1WrhC5JFX)yi+6dt_wKU78V1y7K|nxALft&ZB#Q|@le|tC>!64GRv4a96qSU z=Rar?1K#^mizY^y-&&E0?>p1=oezN6w1}fL&)^OT4`C=8Mpye5I6i9=$|RZg@fGIUpeb=!UE?12#+nGZUO0#MLb915xe zUFO$Q7%Yw6#g|BG+Bv;O(-7XFJ2Zh)}glO|S6zP>UW3^B? zKI#YouPunabk?V)a&QSVjnCCjG`lw_gg&=NQ)Y)NH<9M+AYmOs^u23?*?KNRhp~CL zg@)F@13MX5KvGC^^T79ppf_!V<61XhS2uyOR4YX0cG+7brvnj2N31a*_f=}KY%Z^q zjr9!(Y&TL?MH_}wm|3}epG6f_3J^(1D=0Azf8vci%`V?b9qoZG4tS~2{nc|K3V`2v zDgMmUL);osZ4!LC66kJu@WuC)*T41Efy3@YyYeImP4bH$f23v z2-8rzeDLcbWI^pA{K3xpL(_KUW_A z>35Y6|M(A=Prc{eW#!_h%4lo7O!e(zb%6738C0#OMpIj3{mC5EhnierBdTo^Nsoyz z5(2Z@TVW1P9nY}7SuLFtCy%DbM8tN()Dc$H7V!^0_VLmME>KYb8~ijk13}rk>whNfKUQ(@M~%LNasKB;zKGlva8UCyJyD zJd5`C%t;;>m!|2peq*FLaCO1hlGNd2hsxJ~>(}5~^x)#?g6LP0Cb;h2IVda7-6~UK zQ>BkYb{kt|uZaNIgc%$WxUo^5xp=vpJa@MA4G))YaG>jA-*aoDRsQR5`(_vzSVDAy z;x!e>U&Xd|(0;l5#8DlHFu5z`PU7z$Idq6(f=9IR+_R6CnXc9H;uFK=B`1c;i;nb` zmmVK1FXj5BCkD&w?>kn$;$`Q{tM3{vqjML_qyOPY%X@zKUzO{Rez=V8ZF8Fyrj)rSi~=9|FI%Tp2+I{;jiY zgUqo;8qdwmmR{=p^6lB$ot4H{>wwo=$QyU~%9GJXbZ+1N(evKKnPUCQUc8`md5z`#3PaGx9yQ}DjT2$CjTj8q#=Y5>1JFG2dDsR8q;hnlTmFjv-MlX z-Qqsln!|39CaS%5i5a){dAB^cx8cPs)X?dpO#U#MdwBD6gqzw?2J@RWB;>Q#ZxoGI zyJ#d!E7oA6hFuV8GNVitF{VOg!|Ylf4FrbFsk4#qJa}$J0#0u2Gxs8`#=J`^Fj>uo z{CFfW$PTd_IBG*3*Tzr8`km&t`S{rUlNU$Ezmul&LBH4rqM^~g@-2V)8`ID0G*3tQ zsllv+4CUl+0Kv1nzNLyQJ7I3{zP173;AcZ%w^x=+56lf`W+zmUumR%_4iA;7Lo?JV z__dx1DL7MeImz*tM{mKVQ-_57Wd;a%-UVh`J z{%z@5oh$wL>k|XrWyHDx7PX$HwvBG$NHj{PwnS$GO^_u%#H@bp*w}bkm|H53Jo1wG zAnSCD#`1rF=q0kUc z;MH&Y(d1XJ-Yl!6xrox4TUai0ODkn*b+ydm2ClXTVA*KdM8MWDA{F;td;8y(i{D51 zeKYtA|MHi-8#CypjTzsS z5LkTgv~IVmUyUi9fhgM@Q(P0A_`G+*zRX>_(-bDMVcRq#j>{yIJLb-IkdlECWa@B4 zCmy(PBeIoRK&x=FK~NTR7Mk}i+w6gWj&?}54;8((xEN+hU7`ijKX0UVrP}2*ingcl zNz;J|YETz=G+{|0#K-%5!Q-T5ntmUR-F_D4?ZlU0#i<}mR9=%Be(F9)?_gK?+Hd}< za`ePB-k`G61dyLF6ds>4Dxdy4x!Ks|)3!BV*;OUh%^6l8N5( z=>PSD-tGE**J+BOSifv1l@_85%1 z5qxU_P7IHiiG6@dx1Wj(MKGM2JC#w`>-VH!)i~ecI3+&os$xDVMQr6_?3t zKlT=cs6So%ylX4E-)W*K3}oI25)jH|C3X_54R)0vYnNOX+H8n#t50U7NvMu`>m3{l z3~IM*ItSBL=?|mutRKR5d8%I0UIW3A=mO5S*4M`JYVA@Y%}8j8hMbks`gIBoCHSBk zme)1~hzwynK=W5qkmq5bfXbi$>JhWsPox-MOFTJ@N9vT*SLuTnzqT;8r~F zkGvoz^$x;NArQgq2n>moGTeOTVp?WVoH5TG@Z$Sj;C6S=k3aQfdD&~fsPw=n3M7(% z_?%urkf#C6x;CWj2$;w%UMd{>cDKrtA9`%sXYGXRAE%!JjYh`^g_Fjpf^A zAB}tYqrXvx6@cxac2)Cf&S#fXj&4m*wFeBBb?N@b{)EEs&$=)HO{FgB1e<+*J*q-9ce>FcM0opGcH0Y zZjP|Lv|8ro7NfNnR#(bAjD2$+=EkzPd2698LT`?)+z?*iIB?KbPw#h=mtg(A!XJpi zdk+SFuC=>!I}KWGjjATCLqMyUBV*Yj&TY(aeIXlge5RkBmU6BgsImbEYlf?>HPvlk z+v1%>9F9So1ZSD3-xC=~7h? zkqtnkW=-%FQl2#SAgX>U>)vx`vi=;Y*`QH+F{iqK)2)nZR!Vj*tXT6Pjk>=XYzL47 zoNZ7_+ME;!{8b|0P=iDfa;Ow#rYJ|sLn4%^9?~0RRiA}WG|&B>bSbyZ1n2I#tGw>5 zuZ94?8A7TORuzmL|KIiKRxV#FGtM#Y?JHZW>$n~L8B1*!@WI_V2Ej5B>Cy zmtXle{}KzLnfj}{ks_vm!9@}r2kxvZpJiw!<;>deq-|Fj?12?P9dSJjv-fVVlo);OpAG4B87vGwVd>owFs@73`XLacySqLM>RSQKD`?pv0jabHS(!T z&mc^qX%4hCOZ!#4+STDQBcy^r^Ho%n4V z8~m4oIQ)HwNB;WjR?yu4U{@)K*3%ESyCTeJK_KpEObYA~Lc{!4BRib5(>m^<#>V<4 zjRI454w)Ju5#mJCaO{BQSOBKWnLjXJ30@%*<4#E(2&n;%p~2ypL-t?W_bE&{>|)`4 z-QWO1Lz;GB;&zkJ_C_;}Loa&p{_?;B_mn1*({b8cYwH=dtL4>)9U zO@HjbDyboyQPNi%36%{{R<<-PkTSf2C|r~?r-XVD!6B3Js|{|X0xt6&;tbJo*4!MO z7%E@?t$zl8*}b)D8%Jj-a7K5v(}#s%G*WJ&c_^h;SZrC!;+kWRU3#{>{Pka4_J{h> zFz5=(XAg(l6RjZ(hB0Bmemw#M@SxQ!Q!j#M`PRj7@^q$Z#IlZkXtgX9NQy!?qdEjy;CbQX=&f#$J8EH ziwj2g?{AlpgY9x+XurJV^mG|qzfpevhyIuH==d;O!D^|0{R~$bZ_tf=+5rmT&I!kjv4HkYLdt@2_)urHNPbywZ3L|G&IlZ zU=}nv&ogj^I0^|@xwOZVS2<+f;7sNO(=zBD&pN{%CATmEuz9V2~%SOs+(-&#Vq z!p)z|M<&K$gpurcGJ+=PrkwI+bptqi4UEDcHmv~XA;saoYTLB7bC4_7zSOi=vlw5Z zK}#c)ToCeWzWyuA_@S{_Qm(dQViH^xXxtM&`(|xymLA^kuWchmsU>h?i>$6vlk{d` z3 z<*xf)SWcclUrwI6yPPqpCTXiMu_ zMpmF}?J4|PyW3@IYN8xEa;S_=jFnZG=L^5+Rnfkt9nBj?u5Bm|4;{qX%MLpz1((@Y zIav18B=M?y20W<&;nScNR^FQsG+-B53*273c|F}@PEa~``g8_ht*kc6!U|^k+FDl7 zUE+EfCSSm0SDUXiFy$8)KlSAG+4qp>A1Fw3f1vQn@BQ-I5aIu97fo8Pl~N!(=6Q#? zB?uXqYX_}JfN3!Yabai(EPFU3nf1fd07lwG&yk%#xYvb@nQ6xSYoipXIV0`WKvlfT z2>i8~#0BX#F{9kW+df7cn_>Zwm&}|67GZcBU(}9W5b|qZ{e|TvuYNIR(e3iy_x@@b z8N!@H1{|R6ocrBaSxXn1GTF9(_+Fgrbl06SHa=d7gFMuCSy3H41ZqI$kH9y=YZ0t? z0@-uR&u=*@f7dcqVSsKUAJa)>&OJT*<)vTnaJlbA_n_&jYoyzui1mHaCT@>EXwAhP z`bc;PfwzaL=lE>#Vau>xKwt2tS7%$`4b#yIAwSza6avlWdTC-NK6mj7AelDsDsY6b zYqvc8*ayo{?{3COr#*xGkHE+?cb$bpG{O5zH`=Oye4-2s{KY-IcIB z={<4fVyp^bn4X$0Q>05(#Nu>Wsd{X2zgfG_up|{ibMwo8@0DPp+IAn6Qs@+TWGj`kJEg^uwUZk!4jPth_csCHsLID!NKylL$*UrZ-FBc5> z_P_e)%Rp~e`RO0|$@1}!JW3_k_bQBTZp>>F6J5T^P{Y81#3nD{a)GELM~`Lg>H$|) z+1x2p{rzPGrU`RGh-sK2C=Amo?qlwApT!){&a)xPEt z{BpHv7dSnA_9S_!s9;9$4mD*_$gv@paULzx<74H>#6&qdJyB+0%1QDV9~dl?xPylg z?#FOFjvt=M5=w`#N=C6r($E^gtpzH5qvUor%QM%n=34k4ID3vdsjKA1x}+}S-cpt* z&(!VSC%SiU|7;5X2Mm8G27le({IZ4CUf1`ktu=u=-BmV@xz2RVan4&Xmknz6ZD%aG z4QdJifX+7{!0xj-XsW-19a+ys`YpQxN0A6_@-8Nu4M?WG?aLOrX5H_h}xw3 z?i|2DmZVGCBxGY00j|&)tn0?K= zl;1RLN40^eZ@;|b8@{p(xIM0d6!>1w6$&nTQBv{ z!XI2K4}S5>N^7{cZ0v299^lW;9%wrS@u~B7rA{3YXp67Y7lm01!GSB6pZyf3Ip(Ux z0riLP#{52d0vy5cJgAUx09$QG;29@}!PbF5d_;LQ$6YAH_1C+HhRX>4^VGS!5ELg$ zH;jIupa6klA#Z;lj?Xo*#v%9=Bnwjsy3sR+fpK08$CXQE5)) zl+o*Gwe~@L8C}Coyw#Ft-=s^hsj}P=}9K3jAAuQPL**SXyURq&iR$F zBqS{igWJT!eC3(_x>?VfigOWxC5U}(b1UwFjZApw-t^vQ?NvqY^6*>>uUxFl+i@iEoR!LJpPX zmt_wEee2s_Uyh$S47>BwG9eLhrKT4>ognsl#pC97>1vVlMx7g6;P6T#)yX1VW+ zURrjCy299M4vBBm@dISsH;fhnPb=VNbZorbo?WPn#kYIg8|BKgPi4%xKL6Ovp)z^= zG_WXufi`87S*povd8>sXGTYabJ;K>syA4LkY(}jn z%4Hcnn-QfoHC|@ur)${Tpf-dRH9G3HK={r0@Cu@t>B-cQVhOIa_yb>IM@ z?Hplt>dp`g!FuFun~Y}oVKn+(M-G>BCr*@mf$;%^+XH9M!q|70`|mzm?mu(B+<*2$ zxeLo~+|4d2uZ?h9;M~n0?54F5_}pEmOE-j{#yNs+L@%z*$S4Bj@Zoaw=+R$1yL0?yFNh5dbiCwu_;lw$RFQnqO)_ zucaHcxS>{_hZ>thg3r@hsg>C~abynP*K>x%DomVAL437$%vgxmbC{lM8}&5*?Ew8-k z5m(c(I+K=W21xC}99p=1qgn+px#_2+9ZKDzP=iON>QX}rKyd6JqNSA;KJ3n3Xr|@F z8~xy;Cytfpuu{@31fe!pmyAXna1KKqfvD3@OIfQm;$fa0YoxkWS}?94BdqBTq@W&& zsm~3A%jo+uy^KCRU53$+{S(vWpl`74liTRVneW2n=0^N#!En#D%OpAIspU! zhG2A;Aa=pb)n(VUw=TNy!#B$DlgANaBT)v@iRQ9nJ)G0-GTm8b3^zc5@7idt(0dAV zTn0V?qo3gV@YG~EIx~r>K3z^6K2$E;b*kKR*WKmx(W5c<6&fm(W4I(M4O`O>%GCG- zrvD^#CT-Q>vij%lM>jGyb}%|L`fcxc*E?j9KUAQK{_x@EmAMb0wSPH2wM-nw_U!Oe zv~-)%Gr0rQYnH3A)ed#q0Hkj1D_RwgGBWSdT_G`WsBvXPNupL}<$x$PpMsRimAz%(TNi8vr+bXemn|oCYm{ny}<$8Mp<`^q*F` zmE4nY59&j0JUug3zWVFlUU~-Wy4w;*OjCYds{pEoq^xRx&b`2W^O;L!6zye0qTOp* zgn{&L;j5l{@O){JpR@8@CRm}T_H*J!A0}cC_&Ee|Vxw|&mjz7SNFcQG%EBCvNf%&` zpF3N+VW^0)luJ^()-+Wh{IXh$T$b^tO-xGkoG_soS7>9Fwi~% zXFrmq(n-=u*?Y=H(;Zl*p_|&?pg^wcpzUWLy56qdvT$pm+`M{2f`~QXl27Js1M%rI zXVR#fHYISsv+sz?ZM1D&5Jb8%Ylk$C4G))TcOID>FO&G_qr+~i!>!5pclxZ=M-_=2{B*hYS@%f5`9` z|HWV2+1}mxu8p1DrVA-JI!(q7qsTBaK9skO2FzM&5PF^TSAAJEERR#MZE{EmBS;t$ z00;;nDD~Bbz7Me&$7?G)j}ylQ-tGZc+{h=a8E-t)+CU-@(2^3`Sf=s5XmjZ~Aj6LKX!$RQI; zAa;ql$7~Qx6u#n%h?>}H68-Pv8>Z=>7%lzyq!Ab?FKPO%Ttj{f3ybC4eJ|wGzR*HrwV4S*?%e4z*?Zf2 z<=Vx|n7v2JOJ4etGC4IKCLSCf%u-zszvQ7XmzYoEtc}75#C34th%%X73&lZF4yGEi zj``N*mNFX8lJdRqXBMAQmmtkZ-=?L|ah(ANztsDKauh$ltpaLW5oy3nE4!PU-~D^7 zxAyx9eQ+zbw@*{QN;@JOx;vzPsJc@HI3u* zTDd@Ei8`f{9}{?92OapJ9-UVrCPDxL(F9v>u5)j_^AXRCmpo0M7ioOs-j@3ogs??~ zY-!{HOtu3k)t497Yz4$V-zqy)a!kwkj0y-ULF|o>lx?(1lM3EIO3%SCi#uDmCe@sq z85l03T@ZlMOhy;rP$h8Jo51c1`^>$UII7%&utC6E-|{8p!hLt8QLW-d!j>^ihgiAJ zr@@z`k~pM0F*sUwAl?Kc@yrH78?y!=a2qvMfgKGyHa+Hp#8Z<^ADIrb>#L4oPF}lm z6FB=YYnRgZf9TXn@*!RS5K;tJrL90V4_qL0|)3p9rwH1Z}1K;z*-!sRfKT;62f22SK z9BgfM{VlZibs1T++!1Orj@@5X4_N_LH1|A{NF^v+FY1DPmB>@YBDgK#KOOwC7CxHX z*M63F1fIvNCry`?bzwV;mall8zH}q=UW-91B9;O7GP1<7*JkW6HwYK;b)pIRAhfgq zOwPH-)<>89ro`F7G~L21+veD!vNy2^X8CU38C|3`jmB~RuiC;-$t{D4271xot^#iB z;1uGLK^8bbQ$P5^^X1iVco|j&xQq6!625*@g;mv@rpJHrLNZw?6)U5^x4-Ph`T)NY z7--VSbaR}*+N?{{dy?rTY5Z~X?;k9) z^NXdwe}uSo0!^c_R)$CF29vf_M@S)*Tqxq1XP+z2UAtECM_R%-Xty1V8ywXfsc)}q z)hVEyI$SrX?9J*cF3M;cn@&dAgt29AXPt4q;`s8p`Eu*#%_xYhZAU%Y5U2>thLzBu zGburR=vP0#wcC1nXL;eBWcx=BZR+}?h41|SKQj+=|AprM-ho>VC~MsSAoUbHRb+*L z(5e}4%=@|&jV4T2{5dsGw;^lQ2Nr0OKGA2RrPzD<b#=Xb?9oqUowY$Uy9}!K6+YKazvte2pp~eAT1TAi`gHc$*yvaq*Cw%K z#@d2IxYIC48k*^v?E3q|qpov~89#uV2D}cI!v0PJoudO|jdH}#->VB^=#ErE+yB~k zJ^n76g8s-scKM8i&B>nk;A8(xhL;Mi6-Mfv%F8BeNLxqwI3Piz&8>gzr_DiO9WmsV zL&gcyOANdVnmJp!ZHZCS&x4wNeTolG#Wx^6HFG6iO(8We8klDip+w}T`HJ)^lh~gN z!ErCaDt!7g;z&q&MpTIw!0_1-K2*9J47wzbdyqNBa!*Z88k>}($#)H+Ux$#Kt>r=x z8RHzdYaYTE+(1Z5BznGW&tM(F4HoKO%8`e;@gLXimrizZ zfQQpp_wn0Z@J|677f9R=>KB3^@)tLO$0w0t2W4q~Ib-kF*P0Mxe_26jUb}HCjgrqi z{Y=crVTe8TKoHO3CLl#*)KD3@ebubEYRj-*lhQKaCnOiqdX12xK!t_E1Bcr%tHnxGE>^;Wy z7){#(^~PF0w5d3^Vu%t*`s``4maH1O1G9<)kr832iXNTLS*pTeo|6GupN{azUZFv z&==eX0aTyNB0AJIWzUCb|AY!RPZHF+UUzeDuB?<{2y1(DGs`JC@-Mz6U#Q6)9~}`$ zdPxJIWcJ~)k+O=GUYMOP(=$^%+bJiGA1hZcU(LR4F5_feTihjnuhV~@oRfR5D<=Jy z|DO)rDnzO<^|td}eHY|_eM7|#_cEe&;J2h7SE`TvIr_&Y%gP2O`0#jHYi^Z`xDn$p znA`8VDMCMZpQS7x`}m`!MH+*+O^$)kl99<{9YG(W_rZrA$}TGRo;g<@zW;%8^4RgT zmJc9A3<~L3VZdScqYF4lbK?k%8E`dWtNPRg_Y+*Zf&X}!7#%NDV-smzcWdB27-4Y0 z9(8O}ifJ7Plz^J#TUDFTKf;3IY0i@&_k~&>3 z`9wj{W^g`^znbT@k_<_Y5Mmd%JkbBP&)2RI6Os_L3iRjGJ54-yv%q`G1_5b9BcIwx z159dlm~)>pxe1|T@3)cIcF$#LpybmAz_OSJUpfSIWVFA$^()>00h2z=?J797eBTLv z2EiLYGufms-jhN7mCi|JXbrqM2+ z0H((zZ%C86(EsOOmR>r3{=Txbx>+85^oio?xyMhQC=)Q5g5c`a>*di;e$s{on0q9% z@9Y+HdTzQ+$x{3(#NFE0_K#^8?vWQhSYGVX+E!?YMHymnF+aPqoC9zF|2~4uuD6WS z->D5(9cwiHGTGV&!C%V#n%93pnK|Zm#V{l0b%)SBxC|aFYiD+qJdx*w#N(YlbU)1P zI~m+Au;7emstwm%Gx(j_SF<;3yeVjirxtSK{Z^*P0wBO1nmL?F5lhRvNW4@ff z|KakH-+Ht>_3S0I@QcdSw0o+R^2Dc}Do;OivGhWBy>@3I*sNiIPkPQWw9za$M1}8f zwaTG!EP<89a_Z>Oa^HmuD_RKdRH|j>5MVXDZk=cA z)ESJ@&SBuW=j^%if^+A~-6u|l!QFGMxzWVzA1lX>9)8z9{iT2UZcF-^3}Wpw8Z_0Z zlyC3pK3MNVgAGF5!!Y)UehSh~#vVsXj_Z@)XHM{J0_4l&YV*MXm>Y)f55dl&{n8gywgM(C+Gsr6 z5TfyTCPTYnywe$7Ia3Ly<`$c3FiF#t97#oOr_Ws&vXGzGQWJ;m4QXuQ+992e?>>BF zyu9wsuOuz31c*H8@>PX3H%UWw@R^Jm;goyM9JX2LcRO!gedlVN5}dEANlNm-QsDqD z(**}ER^fKbyW2P(%*qBoaJY6oP50L zggkHG=iFv;!S-AJ2Nptx!g}_l!iJOA9%`4 zDDZBVkACz~nEz%P(j1YeudIO3`m)Z%g~_PJRYZoR+qcS@6UWOY){3(d9g%hhYvBCp zQ{^tsyI4hT$dDcem^}N2k#4?EfmAZkO_UpD<(WMhQ&|S!`gd(*!YVeG4_oATd9=O&1`{srGgrvBc&|9+5i`O|MJ(B{vm}4mH}p?+Fq$u8N#yF@;U1)k$7(KSq(ntTg*te zru9Zb>}+&rEOS%)*rlbQb3sCJB@P_OV&j_23?Du`Q+77D%lysRvXy6869_vuD z&mO`jTpi)5sLbP>6ECoK;@8jypGRIOn!p<-GG+zOD66hg7@NE)hXSPzo>6Fbm2Hr_ z0kRhxo8>jHdwn@^@-#m9mGZ&g_-I*cY{1mDaT9LB<)OSD&{t*!g8Wz^(1qr|qyL_J z`k8Xi-Dk>RcYm3?c{9^&$MKsFp@ENJT01gL7c1rL2xv=4yiSjfMO7$@2btgT@H1%t z;|Pmm9B#F2YkROkQlrDeU-@VM`CnZW4WH>CK0hnr{u_NiH_+Gf9|l0?Fec16T6zK# zd<-TZRg-I$quIw00HeO=nI^n`xl=bYa|h&c36O1qfEq#%RT<{PKp*E5M9ZjZGPOiY@7DYRxZ)2K^G0M#9 zK?O;O#*c{G+-gEp2nOEQ`P#zFdk$Nz!w|r$&@%OVA2?ecdg;9aL0U3qJ3jewm0%jV zHVeX?YvNUHU*qgz#dHWU!c1YubBY8lDo%*(U;9v2QpA{z5`4xIz+4YKaBsPC@ltvE z@h8g1Kl-r<0<~haDP>5%cLz9vW$)Yv-~Q#n9pLz;Ubj!t(lylh=_$%#9z387o-5wC z<-P~)4d%)kf@k{J>2l$o`_QVTyzkdOSe|+2GH(=$_JUx=$j}@S4Au?Sn21OtF1U_A zO~Nwx?VGpCaZK}*$BvcNh54-2*G+yy{R3qR)BW_xQ@E2OfyJM~NV?02I|N{sE|U;Q zQe4}6GKwOboE*zS6RvXOn0H6P=_&O0_5H-#|Nhs%H^u)f1VH%g1P92UetPdu4|I1u zIs|fu`ntmCGW9S-G>l~PaM{~o-n)CnAOxxQ9#Aq;>yeIV$Zjxi9fTgJgiZ(nq?&V= zMF&>bR-sD~3=vBWRHlTVEs5F{X%Zb`(KhhjLq?F5kTK;DCa4lwjbTNFNPtT=%~FI| zB=`|w`bw}J7)jr})HdGnQ07nnuUek>h6tCSpYO<{momQn%U@5WSBA79tPZ-7f$BFE zPQT;aA$lJA+EU$N0?O|m-cC6*EelYG-;y2&r3y~AHeIx_nwOfInz930To9x^8jY3J zG7d35@}dW$fnN26UzkM-nlOLer@KOAu#^=KxoL;adtkHdJ{P`}i<|!>zU2^~KImw} zJoj1s%Qr4pW%nM^s4Olw%FL0w%11EA-}iwJXC+=|V|DPMZ)_u$dw`_@5qe02DRo(w zt2R}w4)S!&g6<>!@zlg<1kD!ywzcFj$h#>glpHyn-U+|4STeSIsoDDO=7D?rPXBD@ zts(=5X?PnMidAKMNS|ZsyAMA8MSttd-(j&nTS2%#Ye6O->h1atTg(Sh#h=#9@CS!X zZ{wQ{YiN7k+Xt@J_OM3nHcE8|Vb-Zfs#*dt_{KyU^X}GW>BkI9 z%bD-gZ2Sb&pISMlEO}^tzV6MhD92CFkOO)6jB_o65Y_)avux()bv<`}ojCmX-p%b? z>PR7%2^HYh2%74dT}Np?^q~)z55504%EgP%DUZ^fB%>>g2C%q>M+VB~MzhSId0aAj zWoeQzN0=HqfF;yO-daDM=YAuc9VV~vi(TFuhr=ni8Ou#svNTxx zTZMXcFYs~E;`2*u*`ai~(aa1uw+K#F9O;tu!0M=rgE&1{%}urly0qDFlW_>7zl%_G zZC08f$CWgh01%Qd9fb5d^?^6iVDegt1+b+fE=M4dbd96e!sSYk0T} z3=d^`sEWe6-`;5*^!0XsM+)^>3{uc%HGI?e{#Wno?cV=0GVB1_$%eN+7~NS?W)7Zn z$k_3HdFU20QiS8MWl>EetE`%{wW32DR--4Lsh7gw5O%H5DxoDHwN=NDuR)^nzZIPS z?a|UavvRjv<>=Hn(is5*T$$!a#mKDAy4oS#76QV_E2dvl0~)W*hqJz{ds5rFuGX(Y z$GDvN&e=nId+z_dQzmCd%a^?6i_k7Ulb~VnBpHaj$SIFVBPM08Wq9$zL3*-C@B+a) z-7%C*P+TMq#~|9-mhb_X^yuj$W#;hVtjql?zx>|v%kO<}xrh&{*08_L-!8em<-CP7QVOl52MEnQ2vU32Sv2kU zAfsb~iYY4q6mji42^US-Hg^-3?<4{j#&fkxP0cjGS#f+U!^EWXK?tp;>(B2}!920< zW$Lb-RymB%WChyQp|51$siW88cjIQXkVI;5?So1nl}Pp96*iljF7ae!1yv&E-m=Fn zpd7oqF7~uj{uHM9@VIM*s=Y0re`Lx7L6tcytr=CE5Il7*IfpMi^Dw_Qqe#FCyu{;h zml9{&x%$lT#6;py1a^fiF=Tw=yeY^b3PybZ;6`1|%<;y_PT~3}nQ672ei^|u$ z<4>12y#5X4#PQ>3Bhq|6JZ)j(UGnF-xc7DEx&{kZuX)RV-+3}(t<#*nw+u460vsF| z+hEyD&mpN>y9jc$wByl@UbiR$hm@%Y|5sY5vPHqbg$xbTn^x}Ic{_S?e)eYBYBXSO zXYdV$k!_Q(Xu=rl0UC(1@Lu}W_lBYEirhkjyB47H&G*pa(w5^nBA_US3oHurPHXo^ z4}H~(|6L06Sq`;UJ_q3qf9*|wnu7hh5^*;^3+J7kDj_MjKBEY5hs*3f0rG4$%>j0z zy+h_!jbvP}CH+buc5C%z6q}OUST$x>W?^;ipC7FF5S|3cTStF&BaKha9Kzb5V%lHX zuN}sL=Qh!1`?waaY!>296u*xg0HHoZ%kRj%T=K&1uH?-*pxUN>kl`}r>^-N;OJ4B+ z*9y5doarR5n&nR5MOu*gsSP@qs5s%;V&vy{SR@d32KPXno$q?pI#?BIWc}`|XulS^ z@DZNF~#^C zgwGj+6Arew_r7j>yVY>|p^WVsU#=puvALZI_1UB!q}j!j(OYVDDqSrfO>5kLgbourq~wLpYr9|jmhd`nO@uP6_gN%uo>vA1ty&_VgiKm8^c527Pq zzZI0gB1jfb;wHY#RAN%VD(ieGflW-tgu(mACz=KUGegI9+CE=gP1C+OL(z z9{qS3Ll77&_nij6c3GbvI=BgN6>=WtCUM0^C!{tkjCjbwwdL|zjlefBtwM`Bo?C1n zu*R}NP=q+RQIlsQ1$}SvFO!QWm`trM3e8uzOxCou+;-NRWu&h^41W5qQ{~9f!|BRW z)<)j)Ettj3ZYw8E?e-K>2O~LlK;PT7{@gfl&u7qbiX0((Ag$lp-)Mac7-<*ivmXTg za~9tAciwh=Yq#~4>l<4KHik7}Mz_alVA8<#n2tPClgsEJs$*`Yf|cM@WHp7u;kj;; zZlt~by9{n)Mp`&ILh!sZ36X6>i5DHBkuBoWLG-!+Hs&2aG*zgJqnO~m14HG>r!JMp zpLmKiy2}h2-DQqOC&$YW+Wf@n6XoF-KV07O<~NrIA9!II8W^s5w{ak@4L<9H%G?$3 zxGRLb_mlR0{&&9dWv<)s5^_s263rp+3DlVu$3(dRu++l2M%R|3fSM2h$Pp1Xl*6tIhkC$U7kCmyJsf;x@Yw;SG`OZD*;!A@+m66tG z*1F?fbKSv0`N(YfCN5g(+T3gHebw1-dBvOuvsGBS1KNEsTPK%+lbe&fR*El)i4blIdX>~^wy zXJDWnPMWD*OwS9#(1!E*2KyaBnlm_;;5~cGvrf#ED8 zuu{83m5dxVtT~i844$Jm=P*4?oV?q#A;xS#Rp9G?-@b7zTQE7#y9Z4%JTX!xrYFk8 z#8{pQYf509a;;S;sIf4)P-u2GhTPw!9$|8|x%;4Du5Y$BcHi`(zx=un)dGC(!snd9 z4PW!$f6cp_+uPs0+H4-I!`uy5B!!S%Y0{N5WN>FS*}~jed?ls8v|*lvdL8DYa*`eb<8a8`KAzQYAAjaj`HkQDM0xz_XS1!X@f;bZ`Kv{sFimJPpZ|sB`3&qU1z>`3 z2G;gHA#o^NwOAB@mb>1kJmTAH(^E)MCksn!lnWDD?Jf*zNz2H)j5jBqoB`RkR7|b-E>h++(ZM0J*TmK7>{I$=1i}~*q+O_k!4`a^_eSdR%>nGN>HnN1xI)`g@yAD=% zI*IQqk;~+@(M=9W!;5FBUFj|JLlkzgS$S&wPM^8D-y@n-MwBJ2Tmc}BFqeb}BSwSo zZI>6`ca~()Xb_0=pzUH&E2z15s8HAM&L$0f*BRp;p%J3p$E+LA=r#LaePX`pb2T5{ zyIG>V@m92VPd|jmcQLCiQ=3^NYtytxApwfiZ11#;he$bFHqCR1H_=RsvvBE7IMmgV zcQSZjN!vtEnVg!=Qo#z-E-Z;z+Eec0iV(my(021duq=3ZC1Ik#MX z^J9-@EVfH9%T&VQ5eS~gkcR3`aSi+xN}&_yKC9oR|Z==1BAxv#q2r!EDxw77CGzp(WG|Jk*V{75qU zV+en24DKM9k?rnpSl`i7`Gre8zwr^I+bqaSVa8jK}h&6yMP}4JGLZo*N?|dpV?Pgf)*}G4|Xf;h6@hX90322_?=<0Ja=|p zFIwFppK5LQ^RmCWnz?NbG?019Ac*-FVDdI^tP`KKqyP3mjC^0?M3{qSd<(=+Lx&(vldIT4KO`Mp~YTwii`4LYOefjoWCW3hFk^R+UL0T`> zr1!9gXKk&S#VUj&&@%?IEk)8%EE89x5W+Xz6>UWE9apj?`t_6^c^s%-v>0Jn~4hyXs&LOH+ zj&-h3sK%OU*L-3IA~5XMdgS4U%jn=Rsv3Q*kEKxI8;QhL^Yz_U=^sI>4{Cl(KqO-t z>J{D(596O=qD>#33GoPH@&bmm3X_*Q=+&=zc^MpTPuKKUfxDxnh|1F{Ai})dMf-5? z#Fbzmu=}+z__<}Q)oG)X<<3-9nREct9KSNADNH(Z;#gT;T#j#^EWx!x(Z%+Uo;ndG z4@@>6d-A&7G96;)*8bs6LuM_j8FO%L{E8pTU*C29--(;ozW3~3#f>=kSTmTaf zO$v;;Lg2Wsw#q&hR=(gl?=zSM9*^nGWAhiRPuI0MK{wD#-V^`kwHxKw(c@)i=1}(S z)Bf#VQmu&qy!h*ir9InBD~(_F)oD-kW0$FUpC2e7jATrj($NFv*g~DM#QP3wd6MslQNId@!>LcXa**+ zADw(nv>mAk%a>E0be?)qQ{mG1{6(vphh=T2n{)7311yZ0 zyo>hK+*a67F25rawQon@_(j~dc3M)4W!EsNB;&VLV=pf)m$8A-(%&~g^&{*zG0(RV zk6cS4S_*Y!9M%j+22$y&Ap~rbkfB%H4vFvV4Qg(+er&Duf8*=k`MN(=<~Dp9bAOEC zo&WkAaoX-PMC@`y%~pvYGZ=+Zy8@o(J< zNdM2H<|&*z<=j1|GGW1on!=KQeJ9Ln@3vraun%Xi>qHsjny3GB!IvgnzY%4AZ@Owv zEsm}M8_zb&(Bv3y1>fdC%%l; zzUHl?wa_crk;zorC0yTFuu!oKsU%mRZ zUkKJ~e8IP9cCXa#FU}^Oh)0s-|fxyJ(5i}&KJGCq01#4f5hdwaPI437b~%uU{W z)5FgoO(+~{{g}Q&t1_tqM?s*Fvj5x3BF^_-UtLN6x7!^#z-g=5ENjavWp#0>G?rE} z4Ao4W-8e|uot@@L!OSb?$kNTWp7-|rc+cecH@)Ls@A!>39Yqf&PBQ4qC%wCxV4VA$H6aTYn4Z-!nC#I(}i6ir<$$-A19D5Xnm#oI8S#$YJhidj!-F7FsXwY;Rebn=6aAXUj$d?Y-VC>np1~ zn=kXTvt?<1iRVr@5z}Urq`-NF$(3Sy2l{{fLT~psz2lvqKg@0DpyTrXXV|}1G z_*N?T*JI#;Knb8te&RODJg>xXo+U!In6Y~ZN{QlE^VZ0DO;Qp~eb#BAb*|SdU-qIh zJ~{w%Z^BW|M8Y?-0m_ds%hu4QE4J`M*jdE|fa>HG5D4Swhs%^TKOah{<|kZjM&RAq z^QW`AhcNppW#F(FG1oiKI63rE^Djgc!k4r@oo;@9<4*+f%(x1-bmQ?{W?0$U$k=(| zt>&w~YHvAx@>p58F<*L2S9}p)_rfx#dyTXP$3|iDsdWF?79n26;o-y6VepviL=0{@ zVr+TUen9M8W{7Pkm~i_xas6)^9CdoA_neK#bx4ZktR(H0(>A}x4<~DrZF}UHK@A{7Q=ElI6Lagu8+ z>st#8S!B`utKGfDE->@&nA)9?T`;)K2r>vs;;Wj71I_oU*Ss84j_(1*XPS=6aR8A% z=nUF*jhqFo@& zEOX3DwW~}Q_{lTZd~2?rvtB#T(=Y3pRJL(LPQ2iJxqNFjn=?4gwSb>aegl}65kSck zI7x%YFr0$Ja)>+rL+lQHb@2knaF36>;wupeF{?TAI9j-B()zN#Ga=IOIe!sud2c+P zn-K8E=LYw|KLxsjQlA+QlYDP`x7@fsTL#d$;zRt{xY@(ISQDK*#ic?M4eo#_7mw&{ zq|uLX_81_ZE7q-Inx8y$7#M`ge0bMCfTcB7Ca0##^r4wDf+gehTDKFRn&(7#KyzDQ&?DL{Q?RN^Fw+wF3Cm$Q!_^Yq70y+z8%UtG&Wo&uzaSD9x78u4wtd12`oB-yN%_Me3iz6Zo^TlbapARIWgF8ly-b5>(Z zR$&AxHw{Wg4CO*R5);HfIW|(x-+ih)c+c5#6e-=UpSHPKy3hy_7!s_eKF5>Suawr1 z8w}!qYY|F~A!q~z`9nVh(I_{!^CQUU@hge%&LD@6&SaGoHD*SMsowS92!2Dhl|jR7 zkSO^z?T;nhFto>>0s-Lz2)YU`f4sxJ!zMMo?U${SbuiIkmJJehYvV)roiB5(&GOvh zVp&B_-fXOw+4Ze*_TdN1GL}n=?}f?MYEjkZ-ry^ZQZRo{2;JZHGncMJr&)|l4zU!T>fAT~B%|AIf=>A%m*L`z%S_x2^Fob82 z$~FdBSq@Rfkj?wh4iyclmP0V~k*Uej3&WpwV*mJ9)!h1~YG==A>w~`D(&WP@u3s+) z4&T&=O@0zvn^@K4A<)jzfyVqg!p26g-E!u_UBR}nBsOW)QG0#`ikR!+}PnMG=Lemy|C|&1K#T2RN(o)Y5e@i}Tl8_};q+BsFy(j9Qso2Ctf0AtkftIOxsR zydG-qewca~OJK-vg+To7v`C{T0?u{}SGRHOzI3EEuZ@!xOeD)DG2ZkA-}ROs?)qaK ze)G-#OC%eGZUj_ zyU{2!LnCDmO*W`jMtj2@AvBNF9L(^kOP9(jlXzHT*?WmwZN z1~5se+#jI9?>=)n&updDKa4L8Q_5IXbMqEr(h8A@sz!wIiL0flc`Bo8etX0u_snyW z36uKFaw`m6JFZ0*-x$$Dsy{IiR(q4r?gz;X?;h~baqBvWqHH%>yY@KWi%0zAc<-j znV^k?SXq?2AB~(%DtViYEfGN3?uvVbg_>K2c6XP$QZME?jI9QDkZ>1B+QEu(WSR?& zct|(drwrh?Z2tg+UGUJ|H{|f$Tm1vQuYdVpd&?iotgt_9_>;uo3IF(q{+plc-S2z( z{{F$QN)*cM4spnAYK&bfCp;#Vakv14qsQC~e(v^M+1_lH8MMJ5=3Lp{cBz?|gm#rw z$=zGFNb{plJ|4eyAHvpTmgx)~(le;3%s&_HpkH3u!W(`5{W39G7f6VtL!tJNboFyj>j?!)fjSQn1cRBv#-iDufH z7%n|WC(GoSW2FbzqXlf$G7(i^5V+!Mq)a^Hmtnhr>Xtm)+goM8b_(MAO}>PRo-h3J zEPs_TYbgN^8S&=p|JsJZPi7|6yN+PwEG`r@Fk%oEMz7YviX-pr8UqIkY}-p@>V7nB zA3~>UabVS)_ZqkcVc-G286e(}t>;|hXp{r2faZD=OQ1W8P&N_ru1C;>7FK!gdh2dv zs8%PlpFim8eaQpg@|w^2eC|JL_!GzAhJW-U-*aVZd;85?{)Bp`qeWy4ThV23nMTsF zVaUz$wzisOeSIwi>YQ=g!bb-O(B3e(4LcB7RtJF~_7MnA+_+wDQRxS2I44$QYG)-% zGn4G}|086~A2TsTT$_H4#1GZVbzkoR8lal^ewb4TSKqoD#+FIdzz&#!`PInWt6f&{ zIW_S=ZHB|lIY>Ri{9!{9!m9JX#REv}aS!Ex~7f)lm_h;Cp*C_B~DGMJ}z>(r3`F3s|8%yND1-Y~h1 zaSDNh9q>urd++>j$CR&cWRghsA6v!B9-63b^Q{E1|6gMRt< z{m|ce2h#rQ_EBA$!`Y&S%G-d62hqHf`MmVwC}mClS|EzLP~_ zhD+x>lexFHVc@nou6DMo%xQ-mtuHfm7&we8{2X?T1tt+=K0K>1R36dfR}0&%w?oc# zyW{Ry1rE_Pr0a<}g}<(UZ(C=S7=^*@;6OnUsctVsvh z{UvcilJZ3!2{T9F;01YSr#A)wn*a%n9FBI|M0>9_8)a!_r7W+k95mKezvhv@^tx{lL}C4t z82-dExIsPe{r~2Bf4qBd_qBVwJC8X&SRb@I-8y}xwY8mPl#$g`VD*t51kppBnenmq zLiMhQSy$v#OZH;A|I!D3qpXqsE)4HteHpnH>NH5;nvh&UjQXmbHPX^A?sG|+dr4dZ zb_-u`Wn>xJL*fsE!kn7rn%s8tb$o4~nUFZ ztx4oPWYi~ zx0)p@q~h~Fb@fL1*u^Vle{iVmI)DN~3DL<72{I7>A(XWI<_1J^l29{`oe-MOHP0Zz zFf7+$6o0(yXy7_(&Bn8X%p!C35QR-x61eJ~R|FZ(y^-%MKv7g8EhN=y7)jn$Q zz2>fuRHB{u!k=rIq;oB!aqo0V8PJIsBSRyx25REU_!}gZDi_|(Xjk<7RO)t17ri^Z@`XIvIvzoh40g!k8 z2ZxyB3W6t}d@{76HAar$a0gI#-}P<(;_p22E#LPy{zNsV{cfR_`2Qi{|MS0p_m?4o z-@XBNJ279Tmb7A4O8}lB606&d+?|}_yln@2l%BrQfVqC|SAMOO;i2?{tC7`w`gamU zhz`1xfTKVpEI1?kr|~{?FJZR{UW)V5E~ce<{9VzVbd2Xbb2T;jBXrWeMgB5Ev@P#! zOd1^>3y*5_Q_d7l6`cZAZX8Mg`+wI?T@ z`;5GR=h%s3bs`N<@|6kZq~}XM9Cz{{)c>TBcfhDd77h{RTVal%vgE?wIfOO2bM#_T zBg9-&ihC_0+b107&{^0a_$N8bQukU{dsjh_i810p0m9)*sK#xqH^8ZkjX>RLVYD5* z@xT6G|ITN1udvT`5M%$33jgB|{q3JyJLtN5=V1Sr99k&BL9QVf2g9i;T(!j|ceXIk z8)$GBQ*RkOl{}W^+FMP*gn*7zYWq_D}0lVuqz|x#+ z2?xU~m9=&}nrjWABmD@?clDK_bKm;UzUQ;H%jX|g_yQ22H$xj= zyN7)%@rCe0Opat54I?>_1j{(u`qzHzx5~wZ#j=a(#C9GnqGZ!aPd3Wey@)|W3|lhi_hj_p=ON@&#w_nS6B!|-+BiHzbL5KEyxNR#Poll^SECF|`d?X;lUIfOQ`FV5GB^(!=sxXs6AKj}aUIRGwQ%xkl++GeVR<7Uy zlKx7i`uWRlyY}J_>-*dvH|>-FcZ$*l_up`TQcou6wmvFQ%4jgi=F2PxD>eHfMm%a% zc{n z9+VHoME{xYs#ya8zhqg%l9iziB0q2Vv=vpVxA9quaSmH=&WUj=(g+U&6wMZoS!njT z+M7HtgYyM_W-UFNGHx%QzhW^Gzz6NKw^=Ux^&LOR_Ct%x<%pcqdAN4g_Ru(GjUa2r zho{O!bPe1+7wKX()Q8^E#|IO~2+&w!Ph;mUxUVD6U$~i%rgO~owkO26ZaP2ir$CI#wswMjQfdkaWGl87sbps6cfN?e}K-cJXcprMqj$3zCW)| zGTiA$?S**|i~*qQCPzuq!4a}0Q(^ZW056iA>=|d$m4GX4fR&zZ&nr$L-WwofW*H56 z!+|UfegYl``S;NP2{{-!Z-&0U4ScX(iH=^ZE*Wuz;rB+w(`Xc|4k8=j<``MxvxdaV zlzQMmRtSD=6z@O33qvkjw-FY&Hjjn~7!5cu+PP2IgBC#OdF> zCG>9YH4p+*mVIKeX-H5)l$izvt#n{h12r(}KJcbihPA{Za^UzhQ3ezp=5@>oUSvQ9 zyv#_!=kC3q1Eu&N+xB#mh0BjuqPjC(RW237#_pal8f!^DRXVq_$fFD^lf1(<$&T=5 z9MRhF62wcRsSOw1-@%sEUwfd7Y699gDur!ZhXmL%se&}+xeS2L_=XL(>3aIxPl>h^Dr^fULNp;|;i8Bv;UitlmcXHY#0G`wQ$L0^s`_=WA?>1`pDc$|mN1u6R zRa)T*FTgD&0AMz4CB*}L_JpeTC@pKCO+n2M1_Xc_b+sQeYN(72HW@H@P(=M}@iAHs z*t)vjF-8DEdGx)LW@3GA?}M|)PU}y?a<{!rT?fD}M0mN>L}|7MEE%AP%Qp|(&dKUF zGJ-sw6P%h$uXMmg{c-{afC}G+6<BvRJ>{@z;Yg5Hk-h1++2Yiy838s7tBY6r^>4FlMIN5LdU?EG#>?M#txTq)f;aod9cK5!m*lfBBFamO`0NV(HCo9KD ze0g2)g6!oEInX)gTH-kvLMb$pDDdJ#*7Wueomj!rE3l=O$e*M6Yepf9Fo*-i~SJwD-Qx=rk`k^QvR$L&~o+&VM z-2t+cl188|OJt3KOs^}d_WC2;K7_#QqjcQ6adTL|cAbs*ngOz6#0kHF3Vflg)Xc#R z02x!NRtAM5DYjw8d7O_BmW%^Mn7+Fec25;1HbH`T9ohgnz_Sa zy*?Bs9(s`aximzM7XzB{QZIoG**bP2em3dhi#In6K@LK zg}BXt&68s$H=`WXBla&B(&(b{wsh*WuO0W)oH=tOc-N*~9^g4GT=?^C_dRse9mQ(x zgs72zRXX!BifqaQ0JTRc-KuL-8prvDi*75;vOM|2Ck}p;nguOM_|qSkTA#LEeSbi1 zfJX1hBju$ygB9`GaMu|;4|~4c!rLpQNOl&HALO!~jh~!>Jwmm& zD8MTvQ9YANH5_=r1ZpOhEI(V8Yx^MrL#drdZT;MGm9@c5k;#jq=|IQc2d5PKr&*`EjtG2tV}caI#*n6Hs~W4GmeVkFH4t&N~I#V zJF<~!WN{aOl7Rt45vR?;kE}G5%S;tHP>gJ+x?t(ZMEx?#y#bR2;U%aQp@{%pR%T9y zayHHb#~15QZD95C2`80pVcaR)6KCfwWbAoD22N z&q;(d@-sF;QC)9#g|T~$x3%cV%17?WBfh1@LOd-VHDT&$mrq?h>)W#iJh4SNwE+Gv z=$^-K9=PwppFFwnp_FEu_UP{m4>PJ1tpA?jBnL3R23Fl= zTdVESUY2$SCHt4PWV(sk%j+fR7+q5B!ZsRqDSs@|=ta9ZsmPPXHTnXtK z&;U>#a?PFRymTJCQN_S*xqP#0s4b6Y$0M}Gw$Zv?`8&{~L7mHzxKWt=*>9Y3@@ZF0 zfBN)GCsviAMeji^fd5B|(nX7JUb$%TPp3Bvjbmj^Z>u*OUHNntD$WZZ8Hh9MW=fBe zqSSyKi>`)1@l2PoD(iuTzYhh4Su$($+u}pHL6p?mi&fC=o&(69rmEEi)_31BafrbI zo8=W5#zqix-8dW6%Y>6BJG3}EHna!9PkWW4MuEnqDC0R)-5T0iVXJytEv>#T!}`q} zTf^d;nj#aKN7;_+!^k;PVgk8LxjR5?G%#Xzv7B>3*Q+Q`XRPX=oN0J7Dim*y;^wge z_4L!On)(WyE&BJ=0{H(xix>a$)dwG$|IK1jIWBG1XG{5C(l+RWaRRfn(80>F_t8CG z3M|d#bx^EJU-9C~ux{P@FnUzMrp#EdVarvO-`sh49Y03o#e!`c7|amkaXHAmu~FH> z9spnhCV*dY0Ne7p3yu2=!8+_xQ>JznVlH1YQ4X>(O~&*Y%Tgh;cHHS#&A9f|xu?G7 z(p&W3(DpmjqW4AToPFid($MqNr@TaZIx)%~I(CcvZjuETSZYZnoOSl8;p%T)5#Cz6 zIdrbs6zWoH!0&U*VnzA09kLpV?tZ5`?7#nh3JYXriJeI24{(kwH$U_^-|Th5l7)r! z{`+=d#|#q20;9^b`DLXQqedvz2SZd{A7;)tQJnHr1Wp$U=L6cE;3i2L)F!+ zHsIzR?5wNjHCaP77USFZ;Oq^moP$KDuC+KSuZ}|dt(~14pE&yJOIMk|7QHX>yV0Wm zn=ZQOqC#cs_~`=0ECs(JU7a9xFBouL*=_OX74 z8@K@3!UamtpQ1PSZVu!2+A{|NKgL5EVamZ{7`B{}Wx%txLV&d_$WqPND-0|Ba|+@+ zZA}51Z=E*;yt3*Or?rr7>kX49?HLaJ)Of4EH85lrWv!Xj0bwHn&Qoc&PC%Qv<&xQ` zR2|$b+)X!>Gs0z8UK&<)c8B$ww)&D;tSXi~0}$@Ffmp{wHu_$& z_34IAfJH)f7Y)4H3~PX!Fvsi_3BYLpII!0uXL*fZ$M%XOS!f=?K49bc|t8(82BXbC;j||75`}ou0hP5zqlQK(@EnV!^9wG^(}!X05R)YBq1IHybbg zVX*K_Yu@^UC+ZcD3Yzw>ZF*XBH1~l>Jz$S6zW|GvJ)#{c|t^GBw zCwHX-wHMlFUeM}Kf5_x_w?!Wr&6x4s;+VF#&rE8yeVff>?!{j|fAR$vU)Z+n`PWAc zr9}fc{cS*P)>a^)uPmq-V0t(8+DjK4I|4sx*@#>|FlQE3cW$Fe3|1(j>IUjj-;Gm&1kUpAp(id{M+39S1p5D8~Wr4}vH_U%pwdNam2b z^v^Ytp*sce_3cMYdr}QRR?8NB6x0Iv4nSMCHji5NLg#1tt4+Zvz9Eg`-GsqdE_S=! zpd7f`s)Lo#Hj0n(E1-Te;Dq=k3TOjtv+Neen&xTz;t^;s0lp`VMu7QmV6MKiei?8p z;;uI;q0+Z5oPFlhz{g1eFKhK7vRgkuK-OB}`U=u@{9~o2T zK6`3r!F7yLWv#sdTwX&dj^v)pmuOZ)V_ Date: Fri, 12 May 2023 18:59:59 +0000 Subject: [PATCH 062/184] [pip](deps-dev): Bump pyright from 1.1.307 to 1.1.308 (#326) Bumps [pyright](https://github.com/RobertCraigie/pyright-python) from 1.1.307 to 1.1.308. - [Release notes](https://github.com/RobertCraigie/pyright-python/releases) - [Commits](https://github.com/RobertCraigie/pyright-python/compare/v1.1.307...v1.1.308) --- updated-dependencies: - dependency-name: pyright dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index e6ee3f57..be80c5b9 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2603,14 +2603,14 @@ diagrams = ["jinja2", "railroad-diagrams"] [[package]] name = "pyright" -version = "1.1.307" +version = "1.1.308" description = "Command line wrapper for pyright" category = "dev" optional = false python-versions = ">=3.7" files = [ - {file = "pyright-1.1.307-py3-none-any.whl", hash = "sha256:6b360d2e018311bdf8acea73ef1f21bf0b5b502345aa94bc6763cf197b2e75b3"}, - {file = "pyright-1.1.307.tar.gz", hash = "sha256:b7a8734fad4a2438b8bb0dfbe462f529c9d4eb31947bdae85b9b4e7a97ff6a49"}, + {file = "pyright-1.1.308-py3-none-any.whl", hash = "sha256:40a541d21000d256bbd076f4337fc93d4265a92c63f06e5bedf893d77afb234d"}, + {file = "pyright-1.1.308.tar.gz", hash = "sha256:7858a32d08555f8894931e2dc9571126cdc417e78e096f5be13e9418d8aed1e9"}, ] [package.dependencies] @@ -3506,4 +3506,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "337a9d2f506255865403632919de3114c92152d10289708c5c43f0d683ccbe22" +content-hash = "d530c2ba448191434715620d4814d9f15629e10ae317025ccd900e54a4b0c9ed" diff --git a/pyproject.toml b/pyproject.toml index 930a0b47..ce6d20a2 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -32,7 +32,7 @@ pytest-cov = "^4.0.0" [tool.poetry.group.dev.dependencies] pre-commit = "^3.3.1" pyinstrument = "^4.4.0" -pyright = "^1.1.307" +pyright = "^1.1.308" watchfiles = "^0.19.0" jishaku = "^2.5.1" ruff = "^0.0.265" From c56c6f774c2eef7809582094800ff6f095efe569 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Mon, 15 May 2023 01:10:22 -0700 Subject: [PATCH 063/184] Finally fix the cursed cancelerror --- Bot/Libs/utils/postgresql/ctx.py | 13 ++++++------- Bot/kumikobot.py | 32 ++++++++++++++++---------------- tests/db/test_db_conn.py | 9 ++++----- 3 files changed, 26 insertions(+), 28 deletions(-) diff --git a/Bot/Libs/utils/postgresql/ctx.py b/Bot/Libs/utils/postgresql/ctx.py index d05ce611..288d2663 100644 --- a/Bot/Libs/utils/postgresql/ctx.py +++ b/Bot/Libs/utils/postgresql/ctx.py @@ -4,6 +4,7 @@ from prisma import Prisma # type: ignore from prisma.engine.errors import EngineConnectionError # type: ignore +from prisma.utils import async_run BE = TypeVar("BE", bound=BaseException) @@ -17,18 +18,16 @@ def __init__(self) -> None: self.self = self self.db = Prisma(auto_register=True) - async def __aenter__(self) -> None: - await self.db.connect() + def __enter__(self) -> None: + async_run(self.db.connect()) logger.info("Successfully connected to PostgreSQL database") - async def __aexit__( + def __exit__( self, exc_type: Optional[Type[BE]], exc: Optional[BE], traceback: Optional[TracebackType], ) -> None: - if isinstance(exc, EngineConnectionError): - logging.error(f"Failed to connect to PostgreSQL database - {str(exc)}") - elif self.db.is_connected() is True: - await self.db.disconnect() + if self.db.is_connected() is True: + async_run(self.db.disconnect()) logging.info("Safely disconnected from PostgreSQL database") diff --git a/Bot/kumikobot.py b/Bot/kumikobot.py index fdd6ea5b..ef30731a 100644 --- a/Bot/kumikobot.py +++ b/Bot/kumikobot.py @@ -1,5 +1,3 @@ -import asyncio -import contextlib import logging import os @@ -27,20 +25,22 @@ async def main() -> None: - async with PrismaSessionManager(): - async with ClientSession() as session: - async with KumikoCore( - intents=intents, - session=session, - dev_mode=DEV_MODE, - ) as bot: - await bot.start(KUMIKO_TOKEN) + async with ClientSession() as session: + async with KumikoCore( + intents=intents, + session=session, + dev_mode=DEV_MODE, + ) as bot: + await bot.start(KUMIKO_TOKEN) + + +def launch() -> None: + with PrismaSessionManager(): + run(main, backend_options={"use_uvloop": True}) if __name__ == "__main__": - # I hate having to do this, but it's the only way to not get AIOHTTP to throw an cancellederror on me - with contextlib.suppress(asyncio.CancelledError): - try: - run(main, backend_options={"use_uvloop": True}) - except KeyboardInterrupt: - logger.info("Shutting down...") + try: + launch() + except KeyboardInterrupt: + logger.info("Shutting down...") diff --git a/tests/db/test_db_conn.py b/tests/db/test_db_conn.py index d465e9c3..bc2e54df 100644 --- a/tests/db/test_db_conn.py +++ b/tests/db/test_db_conn.py @@ -1,7 +1,7 @@ import sys from pathlib import Path -import pytest +from prisma.utils import async_run path = Path(__file__).parents[2].joinpath("Bot") sys.path.append(str(path)) @@ -11,8 +11,7 @@ from prisma.models import User -@pytest.mark.asyncio -async def test_prisma_client_session_manager(): - async with PrismaSessionManager(): - res = await User.prisma().find_first(where={"id": 454357482102587393}) +def test_prisma_client_session_manager(): + with PrismaSessionManager(): + res = async_run(User.prisma().find_first(where={"id": 454357482102587393})) assert (res is None) or (isinstance(res, User)) # nosec From dd443f78f77ac05afd5c2eee27de7cfda1229420 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Mon, 15 May 2023 01:15:51 -0700 Subject: [PATCH 064/184] Fix linting issues --- Bot/Libs/utils/postgresql/ctx.py | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/Bot/Libs/utils/postgresql/ctx.py b/Bot/Libs/utils/postgresql/ctx.py index 288d2663..1037e2db 100644 --- a/Bot/Libs/utils/postgresql/ctx.py +++ b/Bot/Libs/utils/postgresql/ctx.py @@ -2,8 +2,7 @@ from types import TracebackType from typing import Optional, Type, TypeVar -from prisma import Prisma # type: ignore -from prisma.engine.errors import EngineConnectionError # type: ignore +from prisma import Prisma from prisma.utils import async_run BE = TypeVar("BE", bound=BaseException) From 247391806dcde31861a355b6a1804c2243b7879e Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Mon, 15 May 2023 01:17:25 -0700 Subject: [PATCH 065/184] [skip ci] Go back to old pfp --- README.md | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 676cbdd9..40bce3b0 100644 --- a/README.md +++ b/README.md @@ -4,8 +4,9 @@ # Kumiko (久美子) - -![Kumiko](./assets/logos/kumiko_possible_final.png) +![Kumiko](./assets/kumiko-resized-round.svg) + + [![Required Python Version](https://img.shields.io/badge/Python-3.8%20|%203.9%20|%203.10%20|%203.11-blue?logo=python&logoColor=white)](https://github.com/No767/Kumiko/blob/dev/pyproject.toml) [![CodeQL](https://github.com/No767/Kumiko/actions/workflows/codeql-analysis.yml/badge.svg?branch=dev)](https://github.com/No767/Kumiko/actions/workflows/codeql-analysis.yml) [![Snyk](https://github.com/No767/Kumiko/actions/workflows/snyk.yml/badge.svg?branch=dev)](https://github.com/No767/Kumiko/actions/workflows/snyk.yml) [![Lint](https://github.com/No767/Kumiko/actions/workflows/lint.yml/badge.svg)](https://github.com/No767/Kumiko/actions/workflows/lint.yml) [![Docker Build](https://github.com/No767/Kumiko/actions/workflows/docker-build.yml/badge.svg)](https://github.com/No767/Kumiko/actions/workflows/docker-build.yml) [![Tests](https://github.com/No767/Kumiko/actions/workflows/tests.yml/badge.svg)](https://github.com/No767/Kumiko/actions/workflows/tests.yml) ![Read the Docs](https://img.shields.io/readthedocs/kumiko?label=Docs&logo=readthedocs&logoColor=white) [![Codacy Badge](https://app.codacy.com/project/badge/Grade/950cd812f1e04f0d813bb0298fdaa225)](https://www.codacy.com/gh/No767/Kumiko/dashboard?utm_source=github.com&utm_medium=referral&utm_content=No767/Kumiko&utm_campaign=Badge_Grade) [![codecov](https://codecov.io/gh/No767/Kumiko/branch/dev/graph/badge.svg?token=CwcMp3LIFx)](https://codecov.io/gh/No767/Kumiko) [![GitHub release (latest SemVer)](https://img.shields.io/github/v/release/No767/Kumiko?label=Release&logo=github&sort=semver)](https://github.com/No767/Kumiko/releases) ![Docker Image Version (latest semver)](https://img.shields.io/docker/v/no767/kumiko?label=Docker%20Release&logo=docker&logoColor=white&sort=semver) [![GitHub License](https://img.shields.io/github/license/No767/Rin?label=License&logo=github)](https://github.com/No767/Kumiko/blob/dev/LICENSE) [![Kumiko](https://img.shields.io/badge/Kumiko-Oumae-white)](https://hibike-euphonium.fandom.com/wiki/Kumiko_Oumae) From 2941e390aa9fff7746952b873b9f55b89445d15a Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Mon, 15 May 2023 01:53:55 -0700 Subject: [PATCH 066/184] Add Socket Events cog --- Bot/Cogs/socket-events.py | 22 ++++++ schema.prisma | 140 ++++++++++++++++++++------------------ 2 files changed, 96 insertions(+), 66 deletions(-) create mode 100644 Bot/Cogs/socket-events.py diff --git a/Bot/Cogs/socket-events.py b/Bot/Cogs/socket-events.py new file mode 100644 index 00000000..657ece2d --- /dev/null +++ b/Bot/Cogs/socket-events.py @@ -0,0 +1,22 @@ +import discord +from discord.ext import commands +from kumikocore import KumikoCore +from prisma.models import Guild + + +class SocketEvents(commands.Cog): + """Cog for handling socket events from Discord""" + + def __init__(self, bot: KumikoCore) -> None: + self.bot = bot + + @commands.Cog.listener(name="on_guild_join") + async def serverInit(guild: discord.Guild) -> None: # type: ignore + """Initializes the server in the database""" + findGuild = await Guild.prisma().find_unique(where={"id": guild.id}) + if findGuild is None: + await Guild.prisma().create({"id": guild.id}) + + +async def setup(bot: KumikoCore) -> None: + await bot.add_cog(SocketEvents(bot)) diff --git a/schema.prisma b/schema.prisma index 9d05c30e..c0b68735 100644 --- a/schema.prisma +++ b/schema.prisma @@ -1,66 +1,74 @@ -datasource db { - provider = "postgresql" - url = env("DATABASE_URL") -} - -generator client { - provider = "prisma-client-py" - recursive_type_depth = 5 -} - -model User { - id BigInt @id @unique - name String - rank Int @default(0) - petals Int @default(0) - date_joined DateTime @default(now()) - marketplace Marketplace? // A user can also optionally own a marketplace - user_inv MItem[] // Give the user a default inventory that has one item that is worth 0 petals - // quests Quest[] // This default quest may be used to get the user to explore the marketplace - // QuestClaimer QuestClaimer? // A user can only claim one quest -} - -model MItem { - id String @id @default(uuid()) - marketplace Marketplace @relation(fields: [marketplace_id], references: [id]) - marketplace_id String - user User? @relation(fields: [userId], references: [id]) - userId BigInt? - name String - description String @db.Text - price Float -} - -model Marketplace { - id String @id @default(uuid()) - name String - description String @db.Text - date_created DateTime @default(now()) - owner User @relation(fields: [owner_id], references: [id]) - owner_id BigInt @unique - items MItem[] -} - -// model QuestClaimer { -// id BigInt @id @unique -// user User @relation(fields: [user_id], references: [id]) -// user_id BigInt @unique -// claimed_at DateTime -// quest Quest[] -// } - -// model Quest { -// id String @id @default(uuid()) -// author User @relation(fields: [author_id], references: [id]) -// author_id BigInt -// claimer QuestClaimer @relation(fields: [claimer_id], references: [id]) -// claimer_id BigInt -// name String -// description String @db.Text -// reward Int @default(0) -// active Boolean @default(true) -// claimed Boolean @default(false) -// date_created DateTime @default(now()) -// date_completed DateTime? -// end_datetime DateTime? -// } +datasource db { + provider = "postgresql" + url = env("DATABASE_URL") +} + +generator client { + provider = "prisma-client-py" + recursive_type_depth = 5 +} + +model Guild { + id BigInt @id @unique + prefix String @default(">") + logs Boolean @default(false) + birthday Boolean @default(false) + local_economy Boolean @default(false) +} + +model User { + id BigInt @id @unique + name String + rank Int @default(0) + petals Int @default(0) + date_joined DateTime @default(now()) + marketplace Marketplace? // A user can also optionally own a marketplace + user_inv MItem[] // Give the user a default inventory that has one item that is worth 0 petals + // quests Quest[] // This default quest may be used to get the user to explore the marketplace + // QuestClaimer QuestClaimer? // A user can only claim one quest +} + +model MItem { + id String @id @default(uuid()) + marketplace Marketplace @relation(fields: [marketplace_id], references: [id]) + marketplace_id String + user User? @relation(fields: [userId], references: [id]) + userId BigInt? + name String + description String @db.Text + price Float +} + +model Marketplace { + id String @id @default(uuid()) + name String + description String @db.Text + date_created DateTime @default(now()) + owner User @relation(fields: [owner_id], references: [id]) + owner_id BigInt @unique + items MItem[] +} + +// model QuestClaimer { +// id BigInt @id @unique +// user User @relation(fields: [user_id], references: [id]) +// user_id BigInt @unique +// claimed_at DateTime +// quest Quest[] +// } + +// model Quest { +// id String @id @default(uuid()) +// author User @relation(fields: [author_id], references: [id]) +// author_id BigInt +// claimer QuestClaimer @relation(fields: [claimer_id], references: [id]) +// claimer_id BigInt +// name String +// description String @db.Text +// reward Int @default(0) +// active Boolean @default(true) +// claimed Boolean @default(false) +// date_created DateTime @default(now()) +// date_completed DateTime? +// end_datetime DateTime? +// } From ea065e92d5208357874c8a0a0570a0dd9d5ab973 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Mon, 15 May 2023 19:05:07 +0000 Subject: [PATCH 067/184] [pip](deps-dev): Bump ruff from 0.0.265 to 0.0.267 (#327) Bumps [ruff](https://github.com/charliermarsh/ruff) from 0.0.265 to 0.0.267. - [Release notes](https://github.com/charliermarsh/ruff/releases) - [Changelog](https://github.com/charliermarsh/ruff/blob/main/BREAKING_CHANGES.md) - [Commits](https://github.com/charliermarsh/ruff/compare/v0.0.265...v0.0.267) --- updated-dependencies: - dependency-name: ruff dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 38 +++++++++++++++++++------------------- pyproject.toml | 2 +- 2 files changed, 20 insertions(+), 20 deletions(-) diff --git a/poetry.lock b/poetry.lock index be80c5b9..53efaba4 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2835,29 +2835,29 @@ idna2008 = ["idna"] [[package]] name = "ruff" -version = "0.0.265" +version = "0.0.267" description = "An extremely fast Python linter, written in Rust." category = "dev" optional = false python-versions = ">=3.7" files = [ - {file = "ruff-0.0.265-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:30ddfe22de6ce4eb1260408f4480bbbce998f954dbf470228a21a9b2c45955e4"}, - {file = "ruff-0.0.265-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:a11bd0889e88d3342e7bc514554bb4461bf6cc30ec115821c2425cfaac0b1b6a"}, - {file = "ruff-0.0.265-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:2a9b38bdb40a998cbc677db55b6225a6c4fadcf8819eb30695e1b8470942426b"}, - {file = "ruff-0.0.265-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:a8b44a245b60512403a6a03a5b5212da274d33862225c5eed3bcf12037eb19bb"}, - {file = "ruff-0.0.265-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:b279fa55ea175ef953208a6d8bfbcdcffac1c39b38cdb8c2bfafe9222add70bb"}, - {file = "ruff-0.0.265-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:5028950f7af9b119d43d91b215d5044976e43b96a0d1458d193ef0dd3c587bf8"}, - {file = "ruff-0.0.265-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:4057eb539a1d88eb84e9f6a36e0a999e0f261ed850ae5d5817e68968e7b89ed9"}, - {file = "ruff-0.0.265-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:d586e69ab5cbf521a1910b733412a5735936f6a610d805b89d35b6647e2a66aa"}, - {file = "ruff-0.0.265-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:aa17b13cd3f29fc57d06bf34c31f21d043735cc9a681203d634549b0e41047d1"}, - {file = "ruff-0.0.265-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:9ac13b11d9ad3001de9d637974ec5402a67cefdf9fffc3929ab44c2fcbb850a1"}, - {file = "ruff-0.0.265-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:62a9578b48cfd292c64ea3d28681dc16b1aa7445b7a7709a2884510fc0822118"}, - {file = "ruff-0.0.265-py3-none-musllinux_1_2_i686.whl", hash = "sha256:d0f9967f84da42d28e3d9d9354cc1575f96ed69e6e40a7d4b780a7a0418d9409"}, - {file = "ruff-0.0.265-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:1d5a8de2fbaf91ea5699451a06f4074e7a312accfa774ad9327cde3e4fda2081"}, - {file = "ruff-0.0.265-py3-none-win32.whl", hash = "sha256:9e9db5ccb810742d621f93272e3cc23b5f277d8d00c4a79668835d26ccbe48dd"}, - {file = "ruff-0.0.265-py3-none-win_amd64.whl", hash = "sha256:f54facf286103006171a00ce20388d88ed1d6732db3b49c11feb9bf3d46f90e9"}, - {file = "ruff-0.0.265-py3-none-win_arm64.whl", hash = "sha256:c78470656e33d32ddc54e8482b1b0fc6de58f1195586731e5ff1405d74421499"}, - {file = "ruff-0.0.265.tar.gz", hash = "sha256:53c17f0dab19ddc22b254b087d1381b601b155acfa8feed514f0d6a413d0ab3a"}, + {file = "ruff-0.0.267-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:4adbbbe314d8fcc539a245065bad89446a3cef2e0c9cf70bf7bb9ed6fe31856d"}, + {file = "ruff-0.0.267-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:67254ae34c38cba109fdc52e4a70887de1f850fb3971e5eeef343db67305d1c1"}, + {file = "ruff-0.0.267-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:bbe104f21a429b77eb5ac276bd5352fd8c0e1fbb580b4c772f77ee8c76825654"}, + {file = "ruff-0.0.267-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:db33deef2a5e1cf528ca51cc59dd764122a48a19a6c776283b223d147041153f"}, + {file = "ruff-0.0.267-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:9adf1307fa9d840d1acaa477eb04f9702032a483214c409fca9dc46f5f157fe3"}, + {file = "ruff-0.0.267-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:0afca3633c8e2b6c0a48ad0061180b641b3b404d68d7e6736aab301c8024c424"}, + {file = "ruff-0.0.267-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:2972241065b1c911bce3db808837ed10f4f6f8a8e15520a4242d291083605ab6"}, + {file = "ruff-0.0.267-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:f731d81cb939e757b0335b0090f18ca2e9ff8bcc8e6a1cf909245958949b6e11"}, + {file = "ruff-0.0.267-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:20c594eb56c19063ef5a57f89340e64c6550e169d6a29408a45130a8c3068adc"}, + {file = "ruff-0.0.267-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:45d61a2b01bdf61581a2ee039503a08aa603dc74a6bbe6fb5d1ce3052f5370e5"}, + {file = "ruff-0.0.267-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:2107cec3699ca4d7bd41543dc1d475c97ae3a21ea9212238b5c2088fa8ee7722"}, + {file = "ruff-0.0.267-py3-none-musllinux_1_2_i686.whl", hash = "sha256:786de30723c71fc46b80a173c3313fc0dbe73c96bd9da8dd1212cbc2f84cdfb2"}, + {file = "ruff-0.0.267-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:5a898953949e37c109dd242cfcf9841e065319995ebb7cdfd213b446094a942f"}, + {file = "ruff-0.0.267-py3-none-win32.whl", hash = "sha256:d12ab329474c46b96d962e2bdb92e3ad2144981fe41b89c7770f370646c0101f"}, + {file = "ruff-0.0.267-py3-none-win_amd64.whl", hash = "sha256:d09aecc9f5845586ba90911d815f9772c5a6dcf2e34be58c6017ecb124534ac4"}, + {file = "ruff-0.0.267-py3-none-win_arm64.whl", hash = "sha256:7df7eb5f8d791566ba97cc0b144981b9c080a5b861abaf4bb35a26c8a77b83e9"}, + {file = "ruff-0.0.267.tar.gz", hash = "sha256:632cec7bbaf3c06fcf0a72a1dd029b7d8b7f424ba95a574aaa135f5d20a00af7"}, ] [[package]] @@ -3506,4 +3506,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "d530c2ba448191434715620d4814d9f15629e10ae317025ccd900e54a4b0c9ed" +content-hash = "35c5c4646f6aa0209a930fa842bfbc5ca509d433100b7c7d4ab68714bdec61a1" diff --git a/pyproject.toml b/pyproject.toml index ce6d20a2..465ca320 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -35,7 +35,7 @@ pyinstrument = "^4.4.0" pyright = "^1.1.308" watchfiles = "^0.19.0" jishaku = "^2.5.1" -ruff = "^0.0.265" +ruff = "^0.0.267" [tool.poetry.group.docs.dependencies] From 2427bbb3ba52b5ce0c6f8c4bb4ceecb9f6cdb591 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Thu, 18 May 2023 19:01:07 +0000 Subject: [PATCH 068/184] [pip](deps-dev): Bump pyright from 1.1.308 to 1.1.309 (#328) Bumps [pyright](https://github.com/RobertCraigie/pyright-python) from 1.1.308 to 1.1.309. - [Release notes](https://github.com/RobertCraigie/pyright-python/releases) - [Commits](https://github.com/RobertCraigie/pyright-python/compare/v1.1.308...v1.1.309) --- updated-dependencies: - dependency-name: pyright dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index 53efaba4..dba8f2b8 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2603,14 +2603,14 @@ diagrams = ["jinja2", "railroad-diagrams"] [[package]] name = "pyright" -version = "1.1.308" +version = "1.1.309" description = "Command line wrapper for pyright" category = "dev" optional = false python-versions = ">=3.7" files = [ - {file = "pyright-1.1.308-py3-none-any.whl", hash = "sha256:40a541d21000d256bbd076f4337fc93d4265a92c63f06e5bedf893d77afb234d"}, - {file = "pyright-1.1.308.tar.gz", hash = "sha256:7858a32d08555f8894931e2dc9571126cdc417e78e096f5be13e9418d8aed1e9"}, + {file = "pyright-1.1.309-py3-none-any.whl", hash = "sha256:a8b052c1997f7334e80074998ea0f93bd149550e8cf27ccb5481d3b2e1aad161"}, + {file = "pyright-1.1.309.tar.gz", hash = "sha256:1abcfa83814d792a5d70b38621cc6489acfade94ebb2279e55ba1f394d54296c"}, ] [package.dependencies] @@ -3506,4 +3506,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "35c5c4646f6aa0209a930fa842bfbc5ca509d433100b7c7d4ab68714bdec61a1" +content-hash = "f99f7f88972d5e1b8eb9ad82efb23e0f33451b93cfed6a6ba8ece7c8b72e8800" diff --git a/pyproject.toml b/pyproject.toml index 465ca320..60686949 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -32,7 +32,7 @@ pytest-cov = "^4.0.0" [tool.poetry.group.dev.dependencies] pre-commit = "^3.3.1" pyinstrument = "^4.4.0" -pyright = "^1.1.308" +pyright = "^1.1.309" watchfiles = "^0.19.0" jishaku = "^2.5.1" ruff = "^0.0.267" From 0a6ab81ea9e763b571f94b3e36cb9738b7b7d158 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Thu, 18 May 2023 19:37:28 +0000 Subject: [PATCH 069/184] [pip](deps-dev): Bump pre-commit from 3.3.1 to 3.3.2 (#329) Bumps [pre-commit](https://github.com/pre-commit/pre-commit) from 3.3.1 to 3.3.2. - [Release notes](https://github.com/pre-commit/pre-commit/releases) - [Changelog](https://github.com/pre-commit/pre-commit/blob/main/CHANGELOG.md) - [Commits](https://github.com/pre-commit/pre-commit/compare/v3.3.1...v3.3.2) --- updated-dependencies: - dependency-name: pre-commit dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index dba8f2b8..f97905bb 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2305,14 +2305,14 @@ testing = ["pytest", "pytest-benchmark"] [[package]] name = "pre-commit" -version = "3.3.1" +version = "3.3.2" description = "A framework for managing and maintaining multi-language pre-commit hooks." category = "dev" optional = false python-versions = ">=3.8" files = [ - {file = "pre_commit-3.3.1-py2.py3-none-any.whl", hash = "sha256:218e9e3f7f7f3271ebc355a15598a4d3893ad9fc7b57fe446db75644543323b9"}, - {file = "pre_commit-3.3.1.tar.gz", hash = "sha256:733f78c9a056cdd169baa6cd4272d51ecfda95346ef8a89bf93712706021b907"}, + {file = "pre_commit-3.3.2-py2.py3-none-any.whl", hash = "sha256:8056bc52181efadf4aac792b1f4f255dfd2fb5a350ded7335d251a68561e8cb6"}, + {file = "pre_commit-3.3.2.tar.gz", hash = "sha256:66e37bec2d882de1f17f88075047ef8962581f83c234ac08da21a0c58953d1f0"}, ] [package.dependencies] @@ -3506,4 +3506,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "f99f7f88972d5e1b8eb9ad82efb23e0f33451b93cfed6a6ba8ece7c8b72e8800" +content-hash = "ae6097dbf19727db7bcae6a5de405097259988c5ab55aeceffbeede9dfc0af9e" diff --git a/pyproject.toml b/pyproject.toml index 60686949..e7044cc2 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -30,7 +30,7 @@ nox-poetry = "^1.0.2" pytest-cov = "^4.0.0" [tool.poetry.group.dev.dependencies] -pre-commit = "^3.3.1" +pre-commit = "^3.3.2" pyinstrument = "^4.4.0" pyright = "^1.1.309" watchfiles = "^0.19.0" From c559750ce0245fa9464601c00234dd1988717567 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Fri, 19 May 2023 19:01:52 +0000 Subject: [PATCH 070/184] [pip](deps-dev): Bump ruff from 0.0.267 to 0.0.269 (#330) Bumps [ruff](https://github.com/charliermarsh/ruff) from 0.0.267 to 0.0.269. - [Release notes](https://github.com/charliermarsh/ruff/releases) - [Changelog](https://github.com/charliermarsh/ruff/blob/main/BREAKING_CHANGES.md) - [Commits](https://github.com/charliermarsh/ruff/compare/v0.0.267...v0.0.269) --- updated-dependencies: - dependency-name: ruff dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 38 +++++++++++++++++++------------------- pyproject.toml | 2 +- 2 files changed, 20 insertions(+), 20 deletions(-) diff --git a/poetry.lock b/poetry.lock index f97905bb..4853e05f 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2835,29 +2835,29 @@ idna2008 = ["idna"] [[package]] name = "ruff" -version = "0.0.267" +version = "0.0.269" description = "An extremely fast Python linter, written in Rust." category = "dev" optional = false python-versions = ">=3.7" files = [ - {file = "ruff-0.0.267-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:4adbbbe314d8fcc539a245065bad89446a3cef2e0c9cf70bf7bb9ed6fe31856d"}, - {file = "ruff-0.0.267-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:67254ae34c38cba109fdc52e4a70887de1f850fb3971e5eeef343db67305d1c1"}, - {file = "ruff-0.0.267-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:bbe104f21a429b77eb5ac276bd5352fd8c0e1fbb580b4c772f77ee8c76825654"}, - {file = "ruff-0.0.267-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:db33deef2a5e1cf528ca51cc59dd764122a48a19a6c776283b223d147041153f"}, - {file = "ruff-0.0.267-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:9adf1307fa9d840d1acaa477eb04f9702032a483214c409fca9dc46f5f157fe3"}, - {file = "ruff-0.0.267-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:0afca3633c8e2b6c0a48ad0061180b641b3b404d68d7e6736aab301c8024c424"}, - {file = "ruff-0.0.267-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:2972241065b1c911bce3db808837ed10f4f6f8a8e15520a4242d291083605ab6"}, - {file = "ruff-0.0.267-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:f731d81cb939e757b0335b0090f18ca2e9ff8bcc8e6a1cf909245958949b6e11"}, - {file = "ruff-0.0.267-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:20c594eb56c19063ef5a57f89340e64c6550e169d6a29408a45130a8c3068adc"}, - {file = "ruff-0.0.267-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:45d61a2b01bdf61581a2ee039503a08aa603dc74a6bbe6fb5d1ce3052f5370e5"}, - {file = "ruff-0.0.267-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:2107cec3699ca4d7bd41543dc1d475c97ae3a21ea9212238b5c2088fa8ee7722"}, - {file = "ruff-0.0.267-py3-none-musllinux_1_2_i686.whl", hash = "sha256:786de30723c71fc46b80a173c3313fc0dbe73c96bd9da8dd1212cbc2f84cdfb2"}, - {file = "ruff-0.0.267-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:5a898953949e37c109dd242cfcf9841e065319995ebb7cdfd213b446094a942f"}, - {file = "ruff-0.0.267-py3-none-win32.whl", hash = "sha256:d12ab329474c46b96d962e2bdb92e3ad2144981fe41b89c7770f370646c0101f"}, - {file = "ruff-0.0.267-py3-none-win_amd64.whl", hash = "sha256:d09aecc9f5845586ba90911d815f9772c5a6dcf2e34be58c6017ecb124534ac4"}, - {file = "ruff-0.0.267-py3-none-win_arm64.whl", hash = "sha256:7df7eb5f8d791566ba97cc0b144981b9c080a5b861abaf4bb35a26c8a77b83e9"}, - {file = "ruff-0.0.267.tar.gz", hash = "sha256:632cec7bbaf3c06fcf0a72a1dd029b7d8b7f424ba95a574aaa135f5d20a00af7"}, + {file = "ruff-0.0.269-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:3569bcdee679045c09c0161fabc057599759c49219a08d9a4aad2cc3982ccba3"}, + {file = "ruff-0.0.269-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:56347da63757a56cbce7d4b3d6044ca4f1941cd1bbff3714f7554360c3361f83"}, + {file = "ruff-0.0.269-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:6da8ee25ef2f0cc6cc8e6e20942c1d44d25a36dce35070d7184655bc14f63f63"}, + {file = "ruff-0.0.269-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:bd81b8e681b9eaa6cf15484f3985bd8bd97c3d114e95bff3e8ea283bf8865062"}, + {file = "ruff-0.0.269-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:1f19f59ca3c28742955241fb452f3346241ddbd34e72ac5cb3d84fadebcf6bc8"}, + {file = "ruff-0.0.269-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:f062059b8289a4fab7f6064601b811d447c2f9d3d432a17f689efe4d68988450"}, + {file = "ruff-0.0.269-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:3f5dc7aac52c58e82510217e3c7efd80765c134c097c2815d59e40face0d1fe6"}, + {file = "ruff-0.0.269-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:e131b4dbe798c391090c6407641d6ab12c0fa1bb952379dde45e5000e208dabb"}, + {file = "ruff-0.0.269-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:a374434e588e06550df0f8dcb74777290f285678de991fda4e1063c367ab2eb2"}, + {file = "ruff-0.0.269-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:cec2f4b84a14b87f1b121488649eb5b4eaa06467a2387373f750da74bdcb5679"}, + {file = "ruff-0.0.269-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:374b161753a247904aec7a32d45e165302b76b6e83d22d099bf3ff7c232c888f"}, + {file = "ruff-0.0.269-py3-none-musllinux_1_2_i686.whl", hash = "sha256:9ca0a1ddb1d835b5f742db9711c6cf59f213a1ad0088cb1e924a005fd399e7d8"}, + {file = "ruff-0.0.269-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:5a20658f0b97d207c7841c13d528f36d666bf445b00b01139f28a8ccb80093bb"}, + {file = "ruff-0.0.269-py3-none-win32.whl", hash = "sha256:03ff42bc91ceca58e0f0f072cb3f9286a9208f609812753474e799a997cdad1a"}, + {file = "ruff-0.0.269-py3-none-win_amd64.whl", hash = "sha256:f3b59ccff57b21ef0967ea8021fd187ec14c528ec65507d8bcbe035912050776"}, + {file = "ruff-0.0.269-py3-none-win_arm64.whl", hash = "sha256:bbeb857b1e508a4487bdb02ca1e6d41dd8d5ac5335a5246e25de8a3dff38c1ff"}, + {file = "ruff-0.0.269.tar.gz", hash = "sha256:11ddcfbab32cf5c420ea9dd5531170ace5a3e59c16d9251c7bd2581f7b16f602"}, ] [[package]] @@ -3506,4 +3506,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "ae6097dbf19727db7bcae6a5de405097259988c5ab55aeceffbeede9dfc0af9e" +content-hash = "956594157a92f626911dbe6fbf934420d2401e8246ea07b8de8f4090c0418f71" diff --git a/pyproject.toml b/pyproject.toml index e7044cc2..5d0a9504 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -35,7 +35,7 @@ pyinstrument = "^4.4.0" pyright = "^1.1.309" watchfiles = "^0.19.0" jishaku = "^2.5.1" -ruff = "^0.0.267" +ruff = "^0.0.269" [tool.poetry.group.docs.dependencies] From e68dd2641c6df7c85a00c6f416141f39fe0e33cf Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Mon, 22 May 2023 19:04:30 +0000 Subject: [PATCH 071/184] [pip](deps-dev): Bump furo from 2023.3.27 to 2023.5.20 (#331) Bumps [furo](https://github.com/pradyunsg/furo) from 2023.3.27 to 2023.5.20. - [Release notes](https://github.com/pradyunsg/furo/releases) - [Changelog](https://github.com/pradyunsg/furo/blob/main/docs/changelog.md) - [Commits](https://github.com/pradyunsg/furo/compare/2023.03.27...2023.05.20) --- updated-dependencies: - dependency-name: furo dependency-type: direct:development update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 10 +++++----- pyproject.toml | 2 +- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/poetry.lock b/poetry.lock index 4853e05f..9073c6f8 100644 --- a/poetry.lock +++ b/poetry.lock @@ -1217,20 +1217,20 @@ files = [ [[package]] name = "furo" -version = "2023.3.27" +version = "2023.5.20" description = "A clean customisable Sphinx documentation theme." category = "dev" optional = false python-versions = ">=3.7" files = [ - {file = "furo-2023.3.27-py3-none-any.whl", hash = "sha256:4ab2be254a2d5e52792d0ca793a12c35582dd09897228a6dd47885dabd5c9521"}, - {file = "furo-2023.3.27.tar.gz", hash = "sha256:b99e7867a5cc833b2b34d7230631dd6558c7a29f93071fdbb5709634bb33c5a5"}, + {file = "furo-2023.5.20-py3-none-any.whl", hash = "sha256:594a8436ddfe0c071f3a9e9a209c314a219d8341f3f1af33fdf7c69544fab9e6"}, + {file = "furo-2023.5.20.tar.gz", hash = "sha256:40e09fa17c6f4b22419d122e933089226dcdb59747b5b6c79363089827dea16f"}, ] [package.dependencies] beautifulsoup4 = "*" pygments = ">=2.7" -sphinx = ">=5.0,<7.0" +sphinx = ">=6.0,<8.0" sphinx-basic-ng = "*" [[package]] @@ -3506,4 +3506,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "956594157a92f626911dbe6fbf934420d2401e8246ea07b8de8f4090c0418f71" +content-hash = "589d6c1b4ec28036e0503a1295e98bff7035c5b59e9f5721ccd13fb6677808e2" diff --git a/pyproject.toml b/pyproject.toml index 5d0a9504..9c5f0395 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -42,7 +42,7 @@ ruff = "^0.0.269" sphinx = "^6.2.1" myst-parser = "^1.0.0" sphinx-autobuild = "^2021.3.14" -furo = "^2023.3.27" +furo = "^2023.5.20" sphinxext-opengraph = "^0.8.2" [tool.isort] From e3e326add2772e317294c582cc1084694d3a820c Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 23 May 2023 06:00:20 +0000 Subject: [PATCH 072/184] Bump requests from 2.28.2 to 2.31.0 (#332) Bumps [requests](https://github.com/psf/requests) from 2.28.2 to 2.31.0. - [Release notes](https://github.com/psf/requests/releases) - [Changelog](https://github.com/psf/requests/blob/main/HISTORY.md) - [Commits](https://github.com/psf/requests/compare/v2.28.2...v2.31.0) --- updated-dependencies: - dependency-name: requests dependency-type: indirect ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index 9073c6f8..bfffa71b 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2795,21 +2795,21 @@ ocsp = ["cryptography (>=36.0.1)", "pyopenssl (==20.0.1)", "requests (>=2.26.0)" [[package]] name = "requests" -version = "2.28.2" +version = "2.31.0" description = "Python HTTP for Humans." category = "main" optional = false -python-versions = ">=3.7, <4" +python-versions = ">=3.7" files = [ - {file = "requests-2.28.2-py3-none-any.whl", hash = "sha256:64299f4909223da747622c030b781c0d7811e359c37124b4bd368fb8c6518baa"}, - {file = "requests-2.28.2.tar.gz", hash = "sha256:98b1b2782e3c6c4904938b84c0eb932721069dfdb9134313beff7c83c2df24bf"}, + {file = "requests-2.31.0-py3-none-any.whl", hash = "sha256:58cd2187c01e70e6e26505bca751777aa9f2ee0b7f4300988b709f44e013003f"}, + {file = "requests-2.31.0.tar.gz", hash = "sha256:942c5a758f98d790eaed1a29cb6eefc7ffb0d1cf7af05c3d2791656dbd6ad1e1"}, ] [package.dependencies] certifi = ">=2017.4.17" charset-normalizer = ">=2,<4" idna = ">=2.5,<4" -urllib3 = ">=1.21.1,<1.27" +urllib3 = ">=1.21.1,<3" [package.extras] socks = ["PySocks (>=1.5.6,!=1.5.7)"] From 2af5a8b143d9d3f917d1c904d40c69f14a18bbce Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 24 May 2023 18:58:57 +0000 Subject: [PATCH 073/184] [Actions](deps): Bump actions/setup-python from 4.6.0 to 4.6.1 (#333) Bumps [actions/setup-python](https://github.com/actions/setup-python) from 4.6.0 to 4.6.1. - [Release notes](https://github.com/actions/setup-python/releases) - [Commits](https://github.com/actions/setup-python/compare/v4.6.0...v4.6.1) --- updated-dependencies: - dependency-name: actions/setup-python dependency-type: direct:production update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- .github/workflows/codeql-analysis.yml | 2 +- .github/workflows/lint.yml | 2 +- .github/workflows/snyk.yml | 2 +- .github/workflows/tests.yml | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) diff --git a/.github/workflows/codeql-analysis.yml b/.github/workflows/codeql-analysis.yml index b1da4f35..e5e8247c 100644 --- a/.github/workflows/codeql-analysis.yml +++ b/.github/workflows/codeql-analysis.yml @@ -26,7 +26,7 @@ jobs: uses: actions/checkout@v3 - name: Set up Python 3.11 id: setup-python - uses: actions/setup-python@v4.6.0 + uses: actions/setup-python@v4.6.1 with: python-version: '3.11' - name: Set up Poetry diff --git a/.github/workflows/lint.yml b/.github/workflows/lint.yml index a44f809c..e18ecae5 100644 --- a/.github/workflows/lint.yml +++ b/.github/workflows/lint.yml @@ -41,7 +41,7 @@ jobs: - name: Set up Python ${{ matrix.version }} id: setup-python - uses: actions/setup-python@v4.6.0 + uses: actions/setup-python@v4.6.1 with: python-version: ${{ matrix.version }} diff --git a/.github/workflows/snyk.yml b/.github/workflows/snyk.yml index aab877b9..14543e32 100644 --- a/.github/workflows/snyk.yml +++ b/.github/workflows/snyk.yml @@ -14,7 +14,7 @@ jobs: uses: actions/checkout@v3 - name: Set up Python 3.11 id: setup-python - uses: actions/setup-python@v4.6.0 + uses: actions/setup-python@v4.6.1 with: python-version: '3.11' - name: Set up Node.js 18 diff --git a/.github/workflows/tests.yml b/.github/workflows/tests.yml index 4737ee17..82a5aa81 100644 --- a/.github/workflows/tests.yml +++ b/.github/workflows/tests.yml @@ -58,7 +58,7 @@ jobs: - name: Set up Python id: setup-python - uses: actions/setup-python@v4.6.0 + uses: actions/setup-python@v4.6.1 with: python-version: ${{ matrix.version }} From cb4ecd1799cb86b2cc3bf9c2565d0f6cb780f9f5 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 24 May 2023 19:01:48 +0000 Subject: [PATCH 074/184] [pip](deps): Bump orjson from 3.8.12 to 3.8.13 (#334) Bumps [orjson](https://github.com/ijl/orjson) from 3.8.12 to 3.8.13. - [Release notes](https://github.com/ijl/orjson/releases) - [Changelog](https://github.com/ijl/orjson/blob/master/CHANGELOG.md) - [Commits](https://github.com/ijl/orjson/compare/3.8.12...3.8.13) --- updated-dependencies: - dependency-name: orjson dependency-type: direct:production update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 96 +++++++++++++++++++++++++------------------------- pyproject.toml | 2 +- 2 files changed, 49 insertions(+), 49 deletions(-) diff --git a/poetry.lock b/poetry.lock index bfffa71b..de3c4d20 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2125,58 +2125,58 @@ files = [ [[package]] name = "orjson" -version = "3.8.12" +version = "3.8.13" description = "Fast, correct Python JSON library supporting dataclasses, datetimes, and numpy" category = "main" optional = false python-versions = ">=3.7" files = [ - {file = "orjson-3.8.12-cp310-cp310-macosx_11_0_x86_64.macosx_11_0_arm64.macosx_11_0_universal2.whl", hash = "sha256:c84046e890e13a119404a83f2e09e622509ed4692846ff94c4ca03654fbc7fb5"}, - {file = "orjson-3.8.12-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:29706dd8189835bcf1781faed286e99ae54fd6165437d364dfdbf0276bf39b19"}, - {file = "orjson-3.8.12-cp310-cp310-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:f4e22b0aa70c963ac01fcd620de15be21a5027711b0e5d4b96debcdeea43e3ae"}, - {file = "orjson-3.8.12-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:6d1acf52d3a4b9384af09a5c2658c3a7a472a4d62a0ad1fe2c8fab8ef460c9b4"}, - {file = "orjson-3.8.12-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:a72b50719bdd6bb0acfca3d4d1c841aa4b191f3ff37268e7aba04e5d6be44ccd"}, - {file = "orjson-3.8.12-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:83e8c740a718fa6d511a82e463adc7ab17631c6eea81a716b723e127a9c51d57"}, - {file = "orjson-3.8.12-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:ebb03e4c7648f7bb299872002a6120082da018f41ba7a9ebf4ceae8d765443d2"}, - {file = "orjson-3.8.12-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:44f7bb4c995652106276442de1147c9993716d1e2d79b7fd435afa154ff236b9"}, - {file = "orjson-3.8.12-cp310-none-win_amd64.whl", hash = "sha256:06e528f9a84fbb4000fd0eee573b5db543ee70ae586fdbc53e740b0ac981701c"}, - {file = "orjson-3.8.12-cp311-cp311-macosx_11_0_x86_64.macosx_11_0_arm64.macosx_11_0_universal2.whl", hash = "sha256:9a6c1594d5a9ff56e5babc4a87ac372af38d37adef9e06744e9f158431e33f43"}, - {file = "orjson-3.8.12-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:c6390ce0bce24c107fc275736aa8a4f768ef7eb5df935d7dca0cc99815eb5d99"}, - {file = "orjson-3.8.12-cp311-cp311-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:efb3a10030462a22c731682434df5c137a67632a8339f821cd501920b169007e"}, - {file = "orjson-3.8.12-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:7e405d54c84c30d9b1c918c290bcf4ef484a45c69d5583a95db81ffffba40b44"}, - {file = "orjson-3.8.12-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:cd6fbd1413559572e81b5ac64c45388147c3ba85cc3df2eaa11002945e0dbd1f"}, - {file = "orjson-3.8.12-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f480ae7b84369b1860d8867f0baf8d885fede400fda390ce088bfa8edf97ffdc"}, - {file = "orjson-3.8.12-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:355055e0977c43b0e5325b9312b7208c696fe20cd54eed1d6fc80b0a4d6721f5"}, - {file = "orjson-3.8.12-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:d937503e4dfba5edc8d5e0426d3cc97ed55716e93212b2e12a198664487b9965"}, - {file = "orjson-3.8.12-cp311-none-win_amd64.whl", hash = "sha256:eb16e0195febd24b44f4db1ab3be85ecf6038f92fd511370cebc004b3d422294"}, - {file = "orjson-3.8.12-cp37-cp37m-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:dc27a8ec13f28e92dc1ea89bf1232d77e7d3ebfd5c1ccf4f3729a70561cb63bd"}, - {file = "orjson-3.8.12-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:77710774faed337ac4ad919dadc5f3b655b0cd40518e5386e6f1f116de9c6c25"}, - {file = "orjson-3.8.12-cp37-cp37m-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:7e549468867991f6f9cfbd9c5bbc977330173bd8f6ceb79973bbd4634e13e1b9"}, - {file = "orjson-3.8.12-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:96fb1eb82b578eb6c0e53e3cf950839fe98ea210626f87c8204bd4fc2cc6ba02"}, - {file = "orjson-3.8.12-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:8d153b228b6e24f8bccf732a51e01e8e938eef59efed9030c5c257778fbe0804"}, - {file = "orjson-3.8.12-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:becbd5af6d035a7ec2ee3239d4700929d52d8517806b97dd04efcc37289403f7"}, - {file = "orjson-3.8.12-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:7d63f524048825e05950db3b6998c756d5377a5e8c469b2e3bdb9f3217523d74"}, - {file = "orjson-3.8.12-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:ec4f0130d9a27cb400423e09e0f9e46480e9e977f05fdcf663a7a2c68735513e"}, - {file = "orjson-3.8.12-cp37-none-win_amd64.whl", hash = "sha256:6f1b01f641f5e87168b819ac1cbd81aa6278e7572c326f3d27e92dea442a2c0d"}, - {file = "orjson-3.8.12-cp38-cp38-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:062e67108c218fdb9475edd5272b1629c05b56c66416fa915de5656adde30e73"}, - {file = "orjson-3.8.12-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:0ba645c92801417933fa74448622ba614a275ea82df05e888095c7742d913bb4"}, - {file = "orjson-3.8.12-cp38-cp38-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:7d50d9b1ae409ea15534365fec0ce8a5a5f7dc94aa790aacfb8cfec87ab51aa4"}, - {file = "orjson-3.8.12-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:8f00038bf5d07439d13c0c2c5cd6ad48eb86df7dbd7a484013ce6a113c421b14"}, - {file = "orjson-3.8.12-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:397670665f94cf5cff779054781d80395084ba97191d82f7b3a86f0a20e6102b"}, - {file = "orjson-3.8.12-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:6f568205519bb0197ca91915c5da6058cfbb59993e557b02dfc3b2718b34770a"}, - {file = "orjson-3.8.12-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:4fd240e736ce52cd757d74142d9933fd35a3184396be887c435f0574e0388654"}, - {file = "orjson-3.8.12-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:6cae2ff288a80e81ce30313e735c5436495ab58cf8d4fbe84900e616d0ee7a78"}, - {file = "orjson-3.8.12-cp38-none-win_amd64.whl", hash = "sha256:710c40c214b753392e46f9275fd795e9630dd737a5ab4ac6e4ee1a02fe83cc0d"}, - {file = "orjson-3.8.12-cp39-cp39-macosx_11_0_x86_64.macosx_11_0_arm64.macosx_11_0_universal2.whl", hash = "sha256:aff761de5ed5543a0a51e9f703668624749aa2239de5d7d37d9c9693daeaf5dc"}, - {file = "orjson-3.8.12-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:135f29cf936283a0cd1b8bce86540ca181108f2a4d4483eedad6b8026865d2a9"}, - {file = "orjson-3.8.12-cp39-cp39-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:62f999798f2fa55e567d483864ebfc30120fb055c2696a255979439323a5b15c"}, - {file = "orjson-3.8.12-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:3fa58ca064c640fa9d823f98fbbc8e71940ecb78cea3ac2507da1cbf49d60b51"}, - {file = "orjson-3.8.12-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:8682f752c19f6a7d9fc727fd98588b4c8b0dce791b5794bb814c7379ccd64a79"}, - {file = "orjson-3.8.12-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:de3d096dde3e46d01841abc1982b906694ab3c92f338d37a2e6184739dc8a958"}, - {file = "orjson-3.8.12-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:834b50df79f1fe89bbaced3a1c1d8c8c92cc99e84cdcd374d8da4974b3560d2a"}, - {file = "orjson-3.8.12-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:2ad149ed76dce2bbdfbadd61c35959305e77141badf364a158beb4ef3d88ec37"}, - {file = "orjson-3.8.12-cp39-none-win_amd64.whl", hash = "sha256:82d65e478a21f98107b4eb8390104746bb3024c27084b57edab7d427385f1f70"}, - {file = "orjson-3.8.12.tar.gz", hash = "sha256:9f0f042cf002a474a6aea006dd9f8d7a5497e35e5fb190ec78eb4d232ec19955"}, + {file = "orjson-3.8.13-cp310-cp310-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:bf934a036dafe63c3b1d630efaf996b85554e7ab03754019a18cc0fe2bdcc3a9"}, + {file = "orjson-3.8.13-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:1316c60c0f55440e765b0211e94d171ab2c11d00fe8dcf0ac70c9bd1d9818e6b"}, + {file = "orjson-3.8.13-cp310-cp310-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:4b98fbca0ea0f5e56b3c1d050b78460ca9708419780ec218cef1eca424db2ee5"}, + {file = "orjson-3.8.13-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:c97be6a6ff4d546579f08f1d67aad92715313a06b214e3f2df9bb9f1b45765c2"}, + {file = "orjson-3.8.13-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:e62f14f3eabccdd2108e3d5884fb66197255accc42b9ffa7f04d9dbf7336b479"}, + {file = "orjson-3.8.13-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:0d2e9a8ea45db847864868f7a566bece7d425c06627e5dbdd5fc8399a9c3330b"}, + {file = "orjson-3.8.13-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:637d55ba6b48b698973d7e647b9de6bb2b424c445f51c86df4e976e672300b21"}, + {file = "orjson-3.8.13-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:6b323bb4af76c16636ac1fec403331208f978ae8a2c6bcab904ee1683c05ad7a"}, + {file = "orjson-3.8.13-cp310-none-win_amd64.whl", hash = "sha256:246e22d167ede9ebf09685587187bde9e2440a515bd5eab2e97f029b9de57677"}, + {file = "orjson-3.8.13-cp311-cp311-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:156bd6325a4f4a0c88556b7d774e3e18713c8134b6f807571a3eec14dfcafff6"}, + {file = "orjson-3.8.13-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:8d2ce41c5992dbe9962ef75db1e70ed33636959f2f4b929f9d8cbb2e30472a08"}, + {file = "orjson-3.8.13-cp311-cp311-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:50cfa3449157c4a4ad017a041dbb5fe37091800220fd5e651c0e5fff63bdac61"}, + {file = "orjson-3.8.13-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:59d81f5b9e280ac3ced615e726bfba722785cc5f7fc3aa1e0ea304c5a4114e94"}, + {file = "orjson-3.8.13-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:59d79e5de4a1de246517b4c92dcf6a7ef1fb12e3ce4bbfc6c0f99d1d905405fd"}, + {file = "orjson-3.8.13-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:97d8444cf48f8fe2718fd3b99484906c29a909dc3a8177e8751170a9a28bcf33"}, + {file = "orjson-3.8.13-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:f084ce58b3fd496429deb3435aa7295ab57e349a33cdb99b3cb5f0a66a610a84"}, + {file = "orjson-3.8.13-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:ce737ddf9d5f960996b63c12dbcc82ae2315c45f19165b2fe14a5b33ab8705bb"}, + {file = "orjson-3.8.13-cp311-none-win_amd64.whl", hash = "sha256:305ffd227857cede7318c056020d1a3f3295e8adf8e7f2cbd78c26c530a0f234"}, + {file = "orjson-3.8.13-cp37-cp37m-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:0055168bc38c9caf7211e66e7c06d7f127d2c1dd1cd1d806c58f3a81d6074a6c"}, + {file = "orjson-3.8.13-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:fc42b2006abaa4fb72c9193931a9236dd85ce0483cc74079c315ce8529568ca1"}, + {file = "orjson-3.8.13-cp37-cp37m-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:6dcccda35f11f12ebb36db0ebdca9854327530e1fffe02331cde78177851ae7f"}, + {file = "orjson-3.8.13-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:1234110f782af5e81893b5419b9374ca2559dbd976cbd515e6c3afc292cdfb6a"}, + {file = "orjson-3.8.13-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:d30b8b9fe1ff56fb6ff64d2c2e227d49819b58ae8dac51089f393e31b39a4080"}, + {file = "orjson-3.8.13-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:24f923cf8d7e2e9a975f4507f93e93c262f26b4a1a4f72e4d6e75eda45de8f40"}, + {file = "orjson-3.8.13-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:17788155c50f47d9fd037e12ac82a57381c157ea4de50e8946df8519da0f7f02"}, + {file = "orjson-3.8.13-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:05bfef2719d68b44ab38061f9cd2b3a58d9994f7230734ba6d3c16db97c5e94a"}, + {file = "orjson-3.8.13-cp37-none-win_amd64.whl", hash = "sha256:6fe2981bd0f6959d821253604e9ba2c5ffa03c6202d11f0e3c190e5712b6835b"}, + {file = "orjson-3.8.13-cp38-cp38-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:2e362090bdd4261608eceefd8ed127cd2bfc48643601f9c0cf5d162ca6a7c4cd"}, + {file = "orjson-3.8.13-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:0a3bc7e12f69f7bcefe522c4e4dac33a9b3b450aae0b3170ab61fbce0a6e1b37"}, + {file = "orjson-3.8.13-cp38-cp38-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:5e56ca7bd82b25f40955184df21c977369debe51c4b83fc3113b6427726312f3"}, + {file = "orjson-3.8.13-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:e792d286ad175d36f6b77b7ba77f1654a13f705a7ccfef7819e9b6d49277120d"}, + {file = "orjson-3.8.13-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:cf79f51a7ca59ac322a1e65430142ab1cb9c9a845e893e0e3958deaefe1c9873"}, + {file = "orjson-3.8.13-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:41585f90cfe24d0ae7d5bc96968617b8bcebb618e19db5b0bbadce6bc82f3455"}, + {file = "orjson-3.8.13-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:9b5b005841394e563f1ca3314a6884101a1b1f1dd30c569b4a0335e1ebf49fbf"}, + {file = "orjson-3.8.13-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:8075487b7b2e7cc2c44d8ee7950845b6854cd08a04df80b36055cc0236c28edd"}, + {file = "orjson-3.8.13-cp38-none-win_amd64.whl", hash = "sha256:0ca2aced3fa6ce6d440a2a2e55bb7618fd24fce146068523472f349598e992ee"}, + {file = "orjson-3.8.13-cp39-cp39-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:f8aa77df01c60b7d8b0ff5501d6b8583a4acb06c4373c59bf769025ff8b8b4cb"}, + {file = "orjson-3.8.13-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ea6899624661d2258a71bde33266c3c08c8d9596865acf0ac19a9552c08fa1a6"}, + {file = "orjson-3.8.13-cp39-cp39-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:11a457fafdd207f361986750a5229fc36911fc9fdfc274d078fdf1654845ef45"}, + {file = "orjson-3.8.13-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:386e60a09585b2b5db84879ebad6d49427ae5a9677f86a90bff9cbbec42b03be"}, + {file = "orjson-3.8.13-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:b05ef096362c8a96fdcd85392c68156c9b680271aea350b490c2d0f3ef1b6b6a"}, + {file = "orjson-3.8.13-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5492a1d9eea5a1cb33ae6d225091c69dc79f16d952885625c00070388489d412"}, + {file = "orjson-3.8.13-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:47cb98386a7ff79d0ace6a7c9d5c49ca2b4ea42e4339c565f5efe7757790dd04"}, + {file = "orjson-3.8.13-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:a4a182e7a58114a81d52d67bdc034eb83571690158c4b8d3f1bf5c5f772f77b1"}, + {file = "orjson-3.8.13-cp39-none-win_amd64.whl", hash = "sha256:b2325d8471867c99c432c96861d72d8b7336293860ebb17c9d70e1d377cc2b32"}, + {file = "orjson-3.8.13.tar.gz", hash = "sha256:14e54713703d5436a7be54ff50d780b6b09358f1a0be6107a3ea4f3537a4f6d8"}, ] [[package]] @@ -3506,4 +3506,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "589d6c1b4ec28036e0503a1295e98bff7035c5b59e9f5721ccd13fb6677808e2" +content-hash = "f6d937a913c02f7791fb6161540c4ce6efd344c079ab40da43802d0dd051817e" diff --git a/pyproject.toml b/pyproject.toml index 9c5f0395..da06f480 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -10,7 +10,7 @@ python = ">=3.8,<4.0" python-dotenv = "^1.0.0" aiodns = "^3.0.0" Brotli = "^1.0.9" -orjson = "^3.8.12" +orjson = "^3.8.13" asyncpraw = "^7.7.0" uvloop = "^0.17.0" gql = { extras = ["aiohttp"], version = "^3.4.1" } From d196c5e80b840d219eb365e200992331bf5d7d52 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Thu, 25 May 2023 18:55:17 +0000 Subject: [PATCH 075/184] Bump tornado from 6.2 to 6.3.2 (#336) Bumps [tornado](https://github.com/tornadoweb/tornado) from 6.2 to 6.3.2. - [Changelog](https://github.com/tornadoweb/tornado/blob/master/docs/releases.rst) - [Commits](https://github.com/tornadoweb/tornado/compare/v6.2.0...v6.3.2) --- updated-dependencies: - dependency-name: tornado dependency-type: indirect ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 26 +++++++++++++------------- 1 file changed, 13 insertions(+), 13 deletions(-) diff --git a/poetry.lock b/poetry.lock index de3c4d20..52a31667 100644 --- a/poetry.lock +++ b/poetry.lock @@ -3136,23 +3136,23 @@ files = [ [[package]] name = "tornado" -version = "6.2" +version = "6.3.2" description = "Tornado is a Python web framework and asynchronous networking library, originally developed at FriendFeed." category = "dev" optional = false -python-versions = ">= 3.7" +python-versions = ">= 3.8" files = [ - {file = "tornado-6.2-cp37-abi3-macosx_10_9_universal2.whl", hash = "sha256:20f638fd8cc85f3cbae3c732326e96addff0a15e22d80f049e00121651e82e72"}, - {file = "tornado-6.2-cp37-abi3-macosx_10_9_x86_64.whl", hash = "sha256:87dcafae3e884462f90c90ecc200defe5e580a7fbbb4365eda7c7c1eb809ebc9"}, - {file = "tornado-6.2-cp37-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ba09ef14ca9893954244fd872798b4ccb2367c165946ce2dd7376aebdde8e3ac"}, - {file = "tornado-6.2-cp37-abi3-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:b8150f721c101abdef99073bf66d3903e292d851bee51910839831caba341a75"}, - {file = "tornado-6.2-cp37-abi3-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:d3a2f5999215a3a06a4fc218026cd84c61b8b2b40ac5296a6db1f1451ef04c1e"}, - {file = "tornado-6.2-cp37-abi3-musllinux_1_1_aarch64.whl", hash = "sha256:5f8c52d219d4995388119af7ccaa0bcec289535747620116a58d830e7c25d8a8"}, - {file = "tornado-6.2-cp37-abi3-musllinux_1_1_i686.whl", hash = "sha256:6fdfabffd8dfcb6cf887428849d30cf19a3ea34c2c248461e1f7d718ad30b66b"}, - {file = "tornado-6.2-cp37-abi3-musllinux_1_1_x86_64.whl", hash = "sha256:1d54d13ab8414ed44de07efecb97d4ef7c39f7438cf5e976ccd356bebb1b5fca"}, - {file = "tornado-6.2-cp37-abi3-win32.whl", hash = "sha256:5c87076709343557ef8032934ce5f637dbb552efa7b21d08e89ae7619ed0eb23"}, - {file = "tornado-6.2-cp37-abi3-win_amd64.whl", hash = "sha256:e5f923aa6a47e133d1cf87d60700889d7eae68988704e20c75fb2d65677a8e4b"}, - {file = "tornado-6.2.tar.gz", hash = "sha256:9b630419bde84ec666bfd7ea0a4cb2a8a651c2d5cccdbdd1972a0c859dfc3c13"}, + {file = "tornado-6.3.2-cp38-abi3-macosx_10_9_universal2.whl", hash = "sha256:c367ab6c0393d71171123ca5515c61ff62fe09024fa6bf299cd1339dc9456829"}, + {file = "tornado-6.3.2-cp38-abi3-macosx_10_9_x86_64.whl", hash = "sha256:b46a6ab20f5c7c1cb949c72c1994a4585d2eaa0be4853f50a03b5031e964fc7c"}, + {file = "tornado-6.3.2-cp38-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:c2de14066c4a38b4ecbbcd55c5cc4b5340eb04f1c5e81da7451ef555859c833f"}, + {file = "tornado-6.3.2-cp38-abi3-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:05615096845cf50a895026f749195bf0b10b8909f9be672f50b0fe69cba368e4"}, + {file = "tornado-6.3.2-cp38-abi3-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5b17b1cf5f8354efa3d37c6e28fdfd9c1c1e5122f2cb56dac121ac61baa47cbe"}, + {file = "tornado-6.3.2-cp38-abi3-musllinux_1_1_aarch64.whl", hash = "sha256:29e71c847a35f6e10ca3b5c2990a52ce38b233019d8e858b755ea6ce4dcdd19d"}, + {file = "tornado-6.3.2-cp38-abi3-musllinux_1_1_i686.whl", hash = "sha256:834ae7540ad3a83199a8da8f9f2d383e3c3d5130a328889e4cc991acc81e87a0"}, + {file = "tornado-6.3.2-cp38-abi3-musllinux_1_1_x86_64.whl", hash = "sha256:6a0848f1aea0d196a7c4f6772197cbe2abc4266f836b0aac76947872cd29b411"}, + {file = "tornado-6.3.2-cp38-abi3-win32.whl", hash = "sha256:7efcbcc30b7c654eb6a8c9c9da787a851c18f8ccd4a5a3a95b05c7accfa068d2"}, + {file = "tornado-6.3.2-cp38-abi3-win_amd64.whl", hash = "sha256:0c325e66c8123c606eea33084976c832aa4e766b7dff8aedd7587ea44a604cdf"}, + {file = "tornado-6.3.2.tar.gz", hash = "sha256:4b927c4f19b71e627b13f3db2324e4ae660527143f9e1f2e2fb404f3a187e2ba"}, ] [[package]] From e33ec9eb079bbd55a97a322fc94989471d8cd8c5 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Thu, 25 May 2023 19:01:15 +0000 Subject: [PATCH 076/184] [pip](deps-dev): Bump pyright from 1.1.309 to 1.1.310 (#337) Bumps [pyright](https://github.com/RobertCraigie/pyright-python) from 1.1.309 to 1.1.310. - [Release notes](https://github.com/RobertCraigie/pyright-python/releases) - [Commits](https://github.com/RobertCraigie/pyright-python/compare/v1.1.309...v1.1.310) --- updated-dependencies: - dependency-name: pyright dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index 52a31667..4673520c 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2603,14 +2603,14 @@ diagrams = ["jinja2", "railroad-diagrams"] [[package]] name = "pyright" -version = "1.1.309" +version = "1.1.310" description = "Command line wrapper for pyright" category = "dev" optional = false python-versions = ">=3.7" files = [ - {file = "pyright-1.1.309-py3-none-any.whl", hash = "sha256:a8b052c1997f7334e80074998ea0f93bd149550e8cf27ccb5481d3b2e1aad161"}, - {file = "pyright-1.1.309.tar.gz", hash = "sha256:1abcfa83814d792a5d70b38621cc6489acfade94ebb2279e55ba1f394d54296c"}, + {file = "pyright-1.1.310-py3-none-any.whl", hash = "sha256:55995ac76bf56cb7a44193b7b1ffafc573abab1f1dbc9f62d327f2a1768b3bda"}, + {file = "pyright-1.1.310.tar.gz", hash = "sha256:9e95335a678db2717eaa0c867d61f9399e916289f4a9f47d993e0df74e7d7391"}, ] [package.dependencies] @@ -3506,4 +3506,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "f6d937a913c02f7791fb6161540c4ce6efd344c079ab40da43802d0dd051817e" +content-hash = "1ac75ed3c0d7234817875f4ff046920020933f8e041eb6e7a6fd1ff870d2e0bc" diff --git a/pyproject.toml b/pyproject.toml index da06f480..9b7666d9 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -32,7 +32,7 @@ pytest-cov = "^4.0.0" [tool.poetry.group.dev.dependencies] pre-commit = "^3.3.2" pyinstrument = "^4.4.0" -pyright = "^1.1.309" +pyright = "^1.1.310" watchfiles = "^0.19.0" jishaku = "^2.5.1" ruff = "^0.0.269" From c27d9465eb854de8f478463a659767db342127ac Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Thu, 25 May 2023 19:06:31 +0000 Subject: [PATCH 077/184] [pip](deps-dev): Bump pytest-cov from 4.0.0 to 4.1.0 (#335) Bumps [pytest-cov](https://github.com/pytest-dev/pytest-cov) from 4.0.0 to 4.1.0. - [Changelog](https://github.com/pytest-dev/pytest-cov/blob/master/CHANGELOG.rst) - [Commits](https://github.com/pytest-dev/pytest-cov/compare/v4.0.0...v4.1.0) --- updated-dependencies: - dependency-name: pytest-cov dependency-type: direct:development update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 10 +++++----- pyproject.toml | 2 +- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/poetry.lock b/poetry.lock index 4673520c..9a416bce 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2664,14 +2664,14 @@ testing = ["coverage (>=6.2)", "flaky (>=3.5.0)", "hypothesis (>=5.7.1)", "mypy [[package]] name = "pytest-cov" -version = "4.0.0" +version = "4.1.0" description = "Pytest plugin for measuring coverage." category = "dev" optional = false -python-versions = ">=3.6" +python-versions = ">=3.7" files = [ - {file = "pytest-cov-4.0.0.tar.gz", hash = "sha256:996b79efde6433cdbd0088872dbc5fb3ed7fe1578b68cdbba634f14bb8dd0470"}, - {file = "pytest_cov-4.0.0-py3-none-any.whl", hash = "sha256:2feb1b751d66a8bd934e5edfa2e961d11309dc37b73b0eabe73b5945fee20f6b"}, + {file = "pytest-cov-4.1.0.tar.gz", hash = "sha256:3904b13dfbfec47f003b8e77fd5b589cd11904a21ddf1ab38a64f204d6a10ef6"}, + {file = "pytest_cov-4.1.0-py3-none-any.whl", hash = "sha256:6ba70b9e97e69fcc3fb45bfeab2d0a138fb65c4d0d6a41ef33983ad114be8c3a"}, ] [package.dependencies] @@ -3506,4 +3506,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "1ac75ed3c0d7234817875f4ff046920020933f8e041eb6e7a6fd1ff870d2e0bc" +content-hash = "7b1e7955b6bd0f82b32e9370cc5301c50a8c0f0097ce6fbc48e070ab656c28b4" diff --git a/pyproject.toml b/pyproject.toml index 9b7666d9..81c48ead 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -27,7 +27,7 @@ pytest = "^7.3.1" pytest-asyncio = "^0.21.0" nox = "^2023.4.22" nox-poetry = "^1.0.2" -pytest-cov = "^4.0.0" +pytest-cov = "^4.1.0" [tool.poetry.group.dev.dependencies] pre-commit = "^3.3.2" From 8d14c09e34a9cda9e11872c947ee2952920bf7a1 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Thu, 25 May 2023 19:11:15 +0000 Subject: [PATCH 078/184] [pip](deps-dev): Bump ruff from 0.0.269 to 0.0.270 (#338) Bumps [ruff](https://github.com/charliermarsh/ruff) from 0.0.269 to 0.0.270. - [Release notes](https://github.com/charliermarsh/ruff/releases) - [Changelog](https://github.com/charliermarsh/ruff/blob/main/BREAKING_CHANGES.md) - [Commits](https://github.com/charliermarsh/ruff/compare/v0.0.269...v0.0.270) --- updated-dependencies: - dependency-name: ruff dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 38 +++++++++++++++++++------------------- pyproject.toml | 2 +- 2 files changed, 20 insertions(+), 20 deletions(-) diff --git a/poetry.lock b/poetry.lock index 9a416bce..226518dc 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2835,29 +2835,29 @@ idna2008 = ["idna"] [[package]] name = "ruff" -version = "0.0.269" +version = "0.0.270" description = "An extremely fast Python linter, written in Rust." category = "dev" optional = false python-versions = ">=3.7" files = [ - {file = "ruff-0.0.269-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:3569bcdee679045c09c0161fabc057599759c49219a08d9a4aad2cc3982ccba3"}, - {file = "ruff-0.0.269-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:56347da63757a56cbce7d4b3d6044ca4f1941cd1bbff3714f7554360c3361f83"}, - {file = "ruff-0.0.269-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:6da8ee25ef2f0cc6cc8e6e20942c1d44d25a36dce35070d7184655bc14f63f63"}, - {file = "ruff-0.0.269-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:bd81b8e681b9eaa6cf15484f3985bd8bd97c3d114e95bff3e8ea283bf8865062"}, - {file = "ruff-0.0.269-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:1f19f59ca3c28742955241fb452f3346241ddbd34e72ac5cb3d84fadebcf6bc8"}, - {file = "ruff-0.0.269-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:f062059b8289a4fab7f6064601b811d447c2f9d3d432a17f689efe4d68988450"}, - {file = "ruff-0.0.269-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:3f5dc7aac52c58e82510217e3c7efd80765c134c097c2815d59e40face0d1fe6"}, - {file = "ruff-0.0.269-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:e131b4dbe798c391090c6407641d6ab12c0fa1bb952379dde45e5000e208dabb"}, - {file = "ruff-0.0.269-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:a374434e588e06550df0f8dcb74777290f285678de991fda4e1063c367ab2eb2"}, - {file = "ruff-0.0.269-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:cec2f4b84a14b87f1b121488649eb5b4eaa06467a2387373f750da74bdcb5679"}, - {file = "ruff-0.0.269-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:374b161753a247904aec7a32d45e165302b76b6e83d22d099bf3ff7c232c888f"}, - {file = "ruff-0.0.269-py3-none-musllinux_1_2_i686.whl", hash = "sha256:9ca0a1ddb1d835b5f742db9711c6cf59f213a1ad0088cb1e924a005fd399e7d8"}, - {file = "ruff-0.0.269-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:5a20658f0b97d207c7841c13d528f36d666bf445b00b01139f28a8ccb80093bb"}, - {file = "ruff-0.0.269-py3-none-win32.whl", hash = "sha256:03ff42bc91ceca58e0f0f072cb3f9286a9208f609812753474e799a997cdad1a"}, - {file = "ruff-0.0.269-py3-none-win_amd64.whl", hash = "sha256:f3b59ccff57b21ef0967ea8021fd187ec14c528ec65507d8bcbe035912050776"}, - {file = "ruff-0.0.269-py3-none-win_arm64.whl", hash = "sha256:bbeb857b1e508a4487bdb02ca1e6d41dd8d5ac5335a5246e25de8a3dff38c1ff"}, - {file = "ruff-0.0.269.tar.gz", hash = "sha256:11ddcfbab32cf5c420ea9dd5531170ace5a3e59c16d9251c7bd2581f7b16f602"}, + {file = "ruff-0.0.270-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:f74c4d550f7b8e808455ac77bbce38daafc458434815ba0bc21ae4bdb276509b"}, + {file = "ruff-0.0.270-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:643de865fd35cb76c4f0739aea5afe7b8e4d40d623df7e9e6ea99054e5cead0a"}, + {file = "ruff-0.0.270-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:eca02e709b3308eb7255b5f74e779be23b5980fca3862eae28bb23069cd61ae4"}, + {file = "ruff-0.0.270-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:3ed3b198768d2b3a2300fb18f730cd39948a5cc36ba29ae9d4639a11040880be"}, + {file = "ruff-0.0.270-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:739495d2dbde87cf4e3110c8d27bc20febf93112539a968a4e02c26f0deccd1d"}, + {file = "ruff-0.0.270-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:08188f8351f4c0b6216e8463df0a76eb57894ca59a3da65e4ed205db980fd3ae"}, + {file = "ruff-0.0.270-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:0827b074635d37984fc98d99316bfab5c8b1231bb83e60dacc83bd92883eedb4"}, + {file = "ruff-0.0.270-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:0d61ae4841313f6eeb8292dc349bef27b4ce426e62c36e80ceedc3824e408734"}, + {file = "ruff-0.0.270-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:0eb412f20e77529a01fb94d578b19dcb8331b56f93632aa0cce4a2ea27b7aeba"}, + {file = "ruff-0.0.270-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:b775e2c5fc869359daf8c8b8aa0fd67240201ab2e8d536d14a0edf279af18786"}, + {file = "ruff-0.0.270-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:21f00e47ab2308617c44435c8dfd9e2e03897461c9e647ec942deb2a235b4cfd"}, + {file = "ruff-0.0.270-py3-none-musllinux_1_2_i686.whl", hash = "sha256:0bbfbf6fd2436165566ca85f6e57be03ed2f0a994faf40180cfbb3604c9232ef"}, + {file = "ruff-0.0.270-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:8af391ef81f7be960be10886a3c1aac0b298bde7cb9a86ec2b05faeb2081ce6b"}, + {file = "ruff-0.0.270-py3-none-win32.whl", hash = "sha256:b4c037fe2f75bcd9aed0c89c7c507cb7fa59abae2bd4c8b6fc331a28178655a4"}, + {file = "ruff-0.0.270-py3-none-win_amd64.whl", hash = "sha256:0012f9b7dc137ab7f1f0355e3c4ca49b562baf6c9fa1180948deeb6648c52957"}, + {file = "ruff-0.0.270-py3-none-win_arm64.whl", hash = "sha256:9613456b0b375766244c25045e353bc8890c856431cd97893c97b10cc93bd28d"}, + {file = "ruff-0.0.270.tar.gz", hash = "sha256:95db07b7850b30ebf32b27fe98bc39e0ab99db3985edbbf0754d399eb2f0e690"}, ] [[package]] @@ -3506,4 +3506,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "7b1e7955b6bd0f82b32e9370cc5301c50a8c0f0097ce6fbc48e070ab656c28b4" +content-hash = "cc085da29b10ec691783b01b6cccce8c97b7e890b91d67a98cd95d1aaa43931b" diff --git a/pyproject.toml b/pyproject.toml index 81c48ead..3e298afc 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -35,7 +35,7 @@ pyinstrument = "^4.4.0" pyright = "^1.1.310" watchfiles = "^0.19.0" jishaku = "^2.5.1" -ruff = "^0.0.269" +ruff = "^0.0.270" [tool.poetry.group.docs.dependencies] From a91f52f6a57ca4269861da7a2a2b38e6ddccd450 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Fri, 26 May 2023 18:59:46 +0000 Subject: [PATCH 079/184] [pip](deps): Bump orjson from 3.8.13 to 3.8.14 (#339) Bumps [orjson](https://github.com/ijl/orjson) from 3.8.13 to 3.8.14. - [Release notes](https://github.com/ijl/orjson/releases) - [Changelog](https://github.com/ijl/orjson/blob/master/CHANGELOG.md) - [Commits](https://github.com/ijl/orjson/compare/3.8.13...3.8.14) --- updated-dependencies: - dependency-name: orjson dependency-type: direct:production update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 96 +++++++++++++++++++++++++------------------------- pyproject.toml | 2 +- 2 files changed, 49 insertions(+), 49 deletions(-) diff --git a/poetry.lock b/poetry.lock index 226518dc..00df0311 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2125,58 +2125,58 @@ files = [ [[package]] name = "orjson" -version = "3.8.13" +version = "3.8.14" description = "Fast, correct Python JSON library supporting dataclasses, datetimes, and numpy" category = "main" optional = false python-versions = ">=3.7" files = [ - {file = "orjson-3.8.13-cp310-cp310-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:bf934a036dafe63c3b1d630efaf996b85554e7ab03754019a18cc0fe2bdcc3a9"}, - {file = "orjson-3.8.13-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:1316c60c0f55440e765b0211e94d171ab2c11d00fe8dcf0ac70c9bd1d9818e6b"}, - {file = "orjson-3.8.13-cp310-cp310-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:4b98fbca0ea0f5e56b3c1d050b78460ca9708419780ec218cef1eca424db2ee5"}, - {file = "orjson-3.8.13-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:c97be6a6ff4d546579f08f1d67aad92715313a06b214e3f2df9bb9f1b45765c2"}, - {file = "orjson-3.8.13-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:e62f14f3eabccdd2108e3d5884fb66197255accc42b9ffa7f04d9dbf7336b479"}, - {file = "orjson-3.8.13-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:0d2e9a8ea45db847864868f7a566bece7d425c06627e5dbdd5fc8399a9c3330b"}, - {file = "orjson-3.8.13-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:637d55ba6b48b698973d7e647b9de6bb2b424c445f51c86df4e976e672300b21"}, - {file = "orjson-3.8.13-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:6b323bb4af76c16636ac1fec403331208f978ae8a2c6bcab904ee1683c05ad7a"}, - {file = "orjson-3.8.13-cp310-none-win_amd64.whl", hash = "sha256:246e22d167ede9ebf09685587187bde9e2440a515bd5eab2e97f029b9de57677"}, - {file = "orjson-3.8.13-cp311-cp311-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:156bd6325a4f4a0c88556b7d774e3e18713c8134b6f807571a3eec14dfcafff6"}, - {file = "orjson-3.8.13-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:8d2ce41c5992dbe9962ef75db1e70ed33636959f2f4b929f9d8cbb2e30472a08"}, - {file = "orjson-3.8.13-cp311-cp311-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:50cfa3449157c4a4ad017a041dbb5fe37091800220fd5e651c0e5fff63bdac61"}, - {file = "orjson-3.8.13-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:59d81f5b9e280ac3ced615e726bfba722785cc5f7fc3aa1e0ea304c5a4114e94"}, - {file = "orjson-3.8.13-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:59d79e5de4a1de246517b4c92dcf6a7ef1fb12e3ce4bbfc6c0f99d1d905405fd"}, - {file = "orjson-3.8.13-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:97d8444cf48f8fe2718fd3b99484906c29a909dc3a8177e8751170a9a28bcf33"}, - {file = "orjson-3.8.13-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:f084ce58b3fd496429deb3435aa7295ab57e349a33cdb99b3cb5f0a66a610a84"}, - {file = "orjson-3.8.13-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:ce737ddf9d5f960996b63c12dbcc82ae2315c45f19165b2fe14a5b33ab8705bb"}, - {file = "orjson-3.8.13-cp311-none-win_amd64.whl", hash = "sha256:305ffd227857cede7318c056020d1a3f3295e8adf8e7f2cbd78c26c530a0f234"}, - {file = "orjson-3.8.13-cp37-cp37m-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:0055168bc38c9caf7211e66e7c06d7f127d2c1dd1cd1d806c58f3a81d6074a6c"}, - {file = "orjson-3.8.13-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:fc42b2006abaa4fb72c9193931a9236dd85ce0483cc74079c315ce8529568ca1"}, - {file = "orjson-3.8.13-cp37-cp37m-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:6dcccda35f11f12ebb36db0ebdca9854327530e1fffe02331cde78177851ae7f"}, - {file = "orjson-3.8.13-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:1234110f782af5e81893b5419b9374ca2559dbd976cbd515e6c3afc292cdfb6a"}, - {file = "orjson-3.8.13-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:d30b8b9fe1ff56fb6ff64d2c2e227d49819b58ae8dac51089f393e31b39a4080"}, - {file = "orjson-3.8.13-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:24f923cf8d7e2e9a975f4507f93e93c262f26b4a1a4f72e4d6e75eda45de8f40"}, - {file = "orjson-3.8.13-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:17788155c50f47d9fd037e12ac82a57381c157ea4de50e8946df8519da0f7f02"}, - {file = "orjson-3.8.13-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:05bfef2719d68b44ab38061f9cd2b3a58d9994f7230734ba6d3c16db97c5e94a"}, - {file = "orjson-3.8.13-cp37-none-win_amd64.whl", hash = "sha256:6fe2981bd0f6959d821253604e9ba2c5ffa03c6202d11f0e3c190e5712b6835b"}, - {file = "orjson-3.8.13-cp38-cp38-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:2e362090bdd4261608eceefd8ed127cd2bfc48643601f9c0cf5d162ca6a7c4cd"}, - {file = "orjson-3.8.13-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:0a3bc7e12f69f7bcefe522c4e4dac33a9b3b450aae0b3170ab61fbce0a6e1b37"}, - {file = "orjson-3.8.13-cp38-cp38-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:5e56ca7bd82b25f40955184df21c977369debe51c4b83fc3113b6427726312f3"}, - {file = "orjson-3.8.13-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:e792d286ad175d36f6b77b7ba77f1654a13f705a7ccfef7819e9b6d49277120d"}, - {file = "orjson-3.8.13-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:cf79f51a7ca59ac322a1e65430142ab1cb9c9a845e893e0e3958deaefe1c9873"}, - {file = "orjson-3.8.13-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:41585f90cfe24d0ae7d5bc96968617b8bcebb618e19db5b0bbadce6bc82f3455"}, - {file = "orjson-3.8.13-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:9b5b005841394e563f1ca3314a6884101a1b1f1dd30c569b4a0335e1ebf49fbf"}, - {file = "orjson-3.8.13-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:8075487b7b2e7cc2c44d8ee7950845b6854cd08a04df80b36055cc0236c28edd"}, - {file = "orjson-3.8.13-cp38-none-win_amd64.whl", hash = "sha256:0ca2aced3fa6ce6d440a2a2e55bb7618fd24fce146068523472f349598e992ee"}, - {file = "orjson-3.8.13-cp39-cp39-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:f8aa77df01c60b7d8b0ff5501d6b8583a4acb06c4373c59bf769025ff8b8b4cb"}, - {file = "orjson-3.8.13-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ea6899624661d2258a71bde33266c3c08c8d9596865acf0ac19a9552c08fa1a6"}, - {file = "orjson-3.8.13-cp39-cp39-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:11a457fafdd207f361986750a5229fc36911fc9fdfc274d078fdf1654845ef45"}, - {file = "orjson-3.8.13-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:386e60a09585b2b5db84879ebad6d49427ae5a9677f86a90bff9cbbec42b03be"}, - {file = "orjson-3.8.13-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:b05ef096362c8a96fdcd85392c68156c9b680271aea350b490c2d0f3ef1b6b6a"}, - {file = "orjson-3.8.13-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5492a1d9eea5a1cb33ae6d225091c69dc79f16d952885625c00070388489d412"}, - {file = "orjson-3.8.13-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:47cb98386a7ff79d0ace6a7c9d5c49ca2b4ea42e4339c565f5efe7757790dd04"}, - {file = "orjson-3.8.13-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:a4a182e7a58114a81d52d67bdc034eb83571690158c4b8d3f1bf5c5f772f77b1"}, - {file = "orjson-3.8.13-cp39-none-win_amd64.whl", hash = "sha256:b2325d8471867c99c432c96861d72d8b7336293860ebb17c9d70e1d377cc2b32"}, - {file = "orjson-3.8.13.tar.gz", hash = "sha256:14e54713703d5436a7be54ff50d780b6b09358f1a0be6107a3ea4f3537a4f6d8"}, + {file = "orjson-3.8.14-cp310-cp310-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:7a7b0fead2d0115ef927fa46ad005d7a3988a77187500bf895af67b365c10d1f"}, + {file = "orjson-3.8.14-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ca90db8f551b8960da95b0d4cad6c0489df52ea03585b6979595be7b31a3f946"}, + {file = "orjson-3.8.14-cp310-cp310-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:f4ac01a3db4e6a98a8ad1bb1a3e8bfc777928939e87c04e93e0d5006df574a4b"}, + {file = "orjson-3.8.14-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:bf6825e160e4eb0ef65ce37d8c221edcab96ff2ffba65e5da2437a60a12b3ad1"}, + {file = "orjson-3.8.14-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:f80e62afe49e6bfc706e041faa351d7520b5f86572b8e31455802251ea989613"}, + {file = "orjson-3.8.14-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:6112194c11e611596eed72f46efb0e6b4812682eff3c7b48473d1146c3fa0efb"}, + {file = "orjson-3.8.14-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:739f9f633e1544f2a477fa3bef380f488c8dca6e2521c8dc36424b12554ee31e"}, + {file = "orjson-3.8.14-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:7d3d8faded5a514b80b56d0429eb38b429d7a810f8749d25dc10a0cc15b8a3c8"}, + {file = "orjson-3.8.14-cp310-none-win_amd64.whl", hash = "sha256:0bf00c42333412a9338297bf888d7428c99e281e20322070bde8c2314775508b"}, + {file = "orjson-3.8.14-cp311-cp311-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:d66966fd94719beb84e8ed84833bc59c3c005d3d2d0c42f11d7552d3267c6de7"}, + {file = "orjson-3.8.14-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:087c0dc93379e8ba2d59e9f586fab8de8c137d164fccf8afd5523a2137570917"}, + {file = "orjson-3.8.14-cp311-cp311-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:04c70dc8ca79b0072a16d82f94b9d9dd6598a43dd753ab20039e9f7d2b14f017"}, + {file = "orjson-3.8.14-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:aedba48264fe87e5060c0e9c2b28909f1e60626e46dc2f77e0c8c16939e2e1f7"}, + {file = "orjson-3.8.14-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:01640ab79111dd97515cba9fab7c66cb3b0967b0892cc74756a801ff681a01b6"}, + {file = "orjson-3.8.14-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:8b206cca6836a4c6683bcaa523ab467627b5f03902e5e1082dc59cd010e6925f"}, + {file = "orjson-3.8.14-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:ee0299b2dda9afce351a5e8c148ea7a886de213f955aa0288fb874fb44829c36"}, + {file = "orjson-3.8.14-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:31a2a29be559e92dcc5c278787b4166da6f0d45675b59a11c4867f5d1455ebf4"}, + {file = "orjson-3.8.14-cp311-none-win_amd64.whl", hash = "sha256:20b7ffc7736000ea205f9143df322b03961f287b4057606291c62c842ff3c5b5"}, + {file = "orjson-3.8.14-cp37-cp37m-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:de1ee13d6b6727ee1db38722695250984bae81b8fc9d05f1176c74d14b1322d9"}, + {file = "orjson-3.8.14-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:3ee09bfbf1d54c127d3061f6721a1a11d2ce502b50597c3d0d2e1bd2d235b764"}, + {file = "orjson-3.8.14-cp37-cp37m-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:97ebb7fab5f1ae212a6501f17cb7750a6838ffc2f1cebbaa5dec1a90038ca3c6"}, + {file = "orjson-3.8.14-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:38ca39bae7fbc050332a374062d4cdec28095540fa8bb245eada467897a3a0bb"}, + {file = "orjson-3.8.14-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:92374bc35b6da344a927d5a850f7db80a91c7b837de2f0ea90fc870314b1ff44"}, + {file = "orjson-3.8.14-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:9393a63cb0424515ec5e434078b3198de6ec9e057f1d33bad268683935f0a5d5"}, + {file = "orjson-3.8.14-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:5fb66f0ac23e861b817c858515ac1f74d1cd9e72e3f82a5b2c9bae9f92286adc"}, + {file = "orjson-3.8.14-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:19415aaf30525a5baff0d72a089fcdd68f19a3674998263c885c3908228c1086"}, + {file = "orjson-3.8.14-cp37-none-win_amd64.whl", hash = "sha256:87ba7882e146e24a7d8b4a7971c20212c2af75ead8096fc3d55330babb1015fb"}, + {file = "orjson-3.8.14-cp38-cp38-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:9f5cf61b6db68f213c805c55bf0aab9b4cb75a4e9c7f5bfbd4deb3a0aef0ec53"}, + {file = "orjson-3.8.14-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:33bc310da4ad2ffe8f7f1c9e89692146d9ec5aec2d1c9ef6b67f8dc5e2d63241"}, + {file = "orjson-3.8.14-cp38-cp38-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:67a7e883b6f782b106683979ccc43d89b98c28a1f4a33fe3a22e253577499bb1"}, + {file = "orjson-3.8.14-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:9df820e6c8c84c52ec39ea2cc9c79f7999c839c7d1481a056908dce3b90ce9f9"}, + {file = "orjson-3.8.14-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:ebca14ae80814219ea3327e3dfa7ff618621ff335e45781fac26f5cd0b48f2b4"}, + {file = "orjson-3.8.14-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:27967be4c16bd09f4aeff8896d9be9cbd00fd72f5815d5980e4776f821e2f77c"}, + {file = "orjson-3.8.14-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:062829b5e20cd8648bf4c11c3a5ee7cf196fa138e573407b5312c849b0cf354d"}, + {file = "orjson-3.8.14-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:e53bc5beb612df8ddddb065f079d3fd30b5b4e73053518524423549d61177f3f"}, + {file = "orjson-3.8.14-cp38-none-win_amd64.whl", hash = "sha256:d03f29b0369bb1ab55c8a67103eb3a9675daaf92f04388568034fe16be48fa5d"}, + {file = "orjson-3.8.14-cp39-cp39-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:716a3994e039203f0a59056efa28185d4cac51b922cc5bf27ab9182cfa20e12e"}, + {file = "orjson-3.8.14-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:7cb35dd3ba062c1d984d57e6477768ed7b62ed9260f31362b2d69106f9c60ebd"}, + {file = "orjson-3.8.14-cp39-cp39-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:0bc6b7abf27f1dc192dadad249df9b513912506dd420ce50fd18864a33789b71"}, + {file = "orjson-3.8.14-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:7e2f75b7d9285e35c3d4dff9811185535ff2ea637f06b2b242cb84385f8ffe63"}, + {file = "orjson-3.8.14-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:017de5ba22e58dfa6f41914f5edb8cd052d23f171000684c26b2d2ab219db31e"}, + {file = "orjson-3.8.14-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:09a3bf3154f40299b8bc95e9fb8da47436a59a2106fc22cae15f76d649e062da"}, + {file = "orjson-3.8.14-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:64b4fca0531030040e611c6037aaf05359e296877ab0a8e744c26ef9c32738b9"}, + {file = "orjson-3.8.14-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:8a896a12b38fe201a72593810abc1f4f1597e65b8c869d5fc83bbcf75d93398f"}, + {file = "orjson-3.8.14-cp39-none-win_amd64.whl", hash = "sha256:9725226478d1dafe46d26f758eadecc6cf98dcbb985445e14a9c74aaed6ccfea"}, + {file = "orjson-3.8.14.tar.gz", hash = "sha256:5ea93fd3ef7be7386f2516d728c877156de1559cda09453fc7dd7b696d0439b3"}, ] [[package]] @@ -3506,4 +3506,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "cc085da29b10ec691783b01b6cccce8c97b7e890b91d67a98cd95d1aaa43931b" +content-hash = "daa326263ecc68a43c2f02ed2de3b6b55596cbb6b79555620a5cf72ca7d4a614" diff --git a/pyproject.toml b/pyproject.toml index 3e298afc..c80f43d5 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -10,7 +10,7 @@ python = ">=3.8,<4.0" python-dotenv = "^1.0.0" aiodns = "^3.0.0" Brotli = "^1.0.9" -orjson = "^3.8.13" +orjson = "^3.8.14" asyncpraw = "^7.7.0" uvloop = "^0.17.0" gql = { extras = ["aiohttp"], version = "^3.4.1" } From bc71446639872c99b982020185f17a582b3579e3 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Sun, 28 May 2023 02:53:27 -0700 Subject: [PATCH 080/184] The start of another rewrite --- poetry.lock | 205 +++++++++++++++++-------------------------------- pyproject.toml | 2 + 2 files changed, 74 insertions(+), 133 deletions(-) diff --git a/poetry.lock b/poetry.lock index 00df0311..06690d02 100644 --- a/poetry.lock +++ b/poetry.lock @@ -1,10 +1,9 @@ -# This file is automatically @generated by Poetry and should not be changed by hand. +# This file is automatically @generated by Poetry 1.5.0 and should not be changed by hand. [[package]] name = "aiodns" version = "3.0.0" description = "Simple DNS resolver for asyncio" -category = "main" optional = false python-versions = "*" files = [ @@ -19,7 +18,6 @@ pycares = ">=4.0.0" name = "aiofiles" version = "0.8.0" description = "File support for asyncio." -category = "main" optional = false python-versions = ">=3.6,<4.0" files = [ @@ -31,7 +29,6 @@ files = [ name = "aiohttp" version = "3.8.4" description = "Async http client/server framework (asyncio)" -category = "main" optional = false python-versions = ">=3.6" files = [ @@ -140,7 +137,6 @@ speedups = ["Brotli", "aiodns", "cchardet"] name = "aiosignal" version = "1.3.1" description = "aiosignal: a list of registered asynchronous callbacks" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -155,7 +151,6 @@ frozenlist = ">=1.1.0" name = "aiosqlite" version = "0.17.0" description = "asyncio bridge to the standard sqlite3 module" -category = "main" optional = false python-versions = ">=3.6" files = [ @@ -170,7 +165,6 @@ typing_extensions = ">=3.7.2" name = "alabaster" version = "0.7.13" description = "A configurable sidebar-enabled Sphinx theme" -category = "dev" optional = false python-versions = ">=3.6" files = [ @@ -182,7 +176,6 @@ files = [ name = "anyio" version = "3.6.2" description = "High level compatibility layer for multiple asynchronous event loop implementations" -category = "main" optional = false python-versions = ">=3.6.2" files = [ @@ -203,7 +196,6 @@ trio = ["trio (>=0.16,<0.22)"] name = "argcomplete" version = "2.0.0" description = "Bash tab completion for argparse" -category = "dev" optional = false python-versions = ">=3.6" files = [ @@ -218,7 +210,6 @@ test = ["coverage", "flake8", "pexpect", "wheel"] name = "astunparse" version = "1.6.3" description = "An AST unparser for Python" -category = "dev" optional = false python-versions = "*" files = [ @@ -234,7 +225,6 @@ wheel = ">=0.23.0,<1.0" name = "async-generator" version = "1.10" description = "Async generators and context managers for Python 3.5+" -category = "main" optional = false python-versions = ">=3.5" files = [ @@ -246,7 +236,6 @@ files = [ name = "async-timeout" version = "4.0.2" description = "Timeout context manager for asyncio programs" -category = "main" optional = false python-versions = ">=3.6" files = [ @@ -258,7 +247,6 @@ files = [ name = "asyncio-extras" version = "1.3.2" description = "Asynchronous generators, context managers and more for asyncio" -category = "main" optional = false python-versions = "*" files = [ @@ -273,11 +261,74 @@ async-generator = ">=1.3" doc = ["sphinx-autodoc-typehints"] test = ["pytest", "pytest-asyncio", "pytest-cov"] +[[package]] +name = "asyncpg" +version = "0.27.0" +description = "An asyncio PostgreSQL driver" +optional = false +python-versions = ">=3.7.0" +files = [ + {file = "asyncpg-0.27.0-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:fca608d199ffed4903dce1bcd97ad0fe8260f405c1c225bdf0002709132171c2"}, + {file = "asyncpg-0.27.0-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:20b596d8d074f6f695c13ffb8646d0b6bb1ab570ba7b0cfd349b921ff03cfc1e"}, + {file = "asyncpg-0.27.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:7a6206210c869ebd3f4eb9e89bea132aefb56ff3d1b7dd7e26b102b17e27bbb1"}, + {file = "asyncpg-0.27.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:a7a94c03386bb95456b12c66026b3a87d1b965f0f1e5733c36e7229f8f137747"}, + {file = "asyncpg-0.27.0-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:bfc3980b4ba6f97138b04f0d32e8af21d6c9fa1f8e6e140c07d15690a0a99279"}, + {file = "asyncpg-0.27.0-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:9654085f2b22f66952124de13a8071b54453ff972c25c59b5ce1173a4283ffd9"}, + {file = "asyncpg-0.27.0-cp310-cp310-win32.whl", hash = "sha256:879c29a75969eb2722f94443752f4720d560d1e748474de54ae8dd230bc4956b"}, + {file = "asyncpg-0.27.0-cp310-cp310-win_amd64.whl", hash = "sha256:ab0f21c4818d46a60ca789ebc92327d6d874d3b7ccff3963f7af0a21dc6cff52"}, + {file = "asyncpg-0.27.0-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:18f77e8e71e826ba2d0c3ba6764930776719ae2b225ca07e014590545928b576"}, + {file = "asyncpg-0.27.0-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:c2232d4625c558f2aa001942cac1d7952aa9f0dbfc212f63bc754277769e1ef2"}, + {file = "asyncpg-0.27.0-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:9a3a4ff43702d39e3c97a8786314123d314e0f0e4dabc8367db5b665c93914de"}, + {file = "asyncpg-0.27.0-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:ccddb9419ab4e1c48742457d0c0362dbdaeb9b28e6875115abfe319b29ee225d"}, + {file = "asyncpg-0.27.0-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:768e0e7c2898d40b16d4ef7a0b44e8150db3dd8995b4652aa1fe2902e92c7df8"}, + {file = "asyncpg-0.27.0-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:609054a1f47292a905582a1cfcca51a6f3f30ab9d822448693e66fdddde27920"}, + {file = "asyncpg-0.27.0-cp311-cp311-win32.whl", hash = "sha256:8113e17cfe236dc2277ec844ba9b3d5312f61bd2fdae6d3ed1c1cdd75f6cf2d8"}, + {file = "asyncpg-0.27.0-cp311-cp311-win_amd64.whl", hash = "sha256:bb71211414dd1eeb8d31ec529fe77cff04bf53efc783a5f6f0a32d84923f45cf"}, + {file = "asyncpg-0.27.0-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:4750f5cf49ed48a6e49c6e5aed390eee367694636c2dcfaf4a273ca832c5c43c"}, + {file = "asyncpg-0.27.0-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:eca01eb112a39d31cc4abb93a5aef2a81514c23f70956729f42fb83b11b3483f"}, + {file = "asyncpg-0.27.0-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:5710cb0937f696ce303f5eed6d272e3f057339bb4139378ccecafa9ee923a71c"}, + {file = "asyncpg-0.27.0-cp37-cp37m-win_amd64.whl", hash = "sha256:71cca80a056ebe19ec74b7117b09e650990c3ca535ac1c35234a96f65604192f"}, + {file = "asyncpg-0.27.0-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:4bb366ae34af5b5cabc3ac6a5347dfb6013af38c68af8452f27968d49085ecc0"}, + {file = "asyncpg-0.27.0-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:16ba8ec2e85d586b4a12bcd03e8d29e3d99e832764d6a1d0b8c27dbbe4a2569d"}, + {file = "asyncpg-0.27.0-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:d20dea7b83651d93b1eb2f353511fe7fd554752844523f17ad30115d8b9c8cd6"}, + {file = "asyncpg-0.27.0-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:e56ac8a8237ad4adec97c0cd4728596885f908053ab725e22900b5902e7f8e69"}, + {file = "asyncpg-0.27.0-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:bf21ebf023ec67335258e0f3d3ad7b91bb9507985ba2b2206346de488267cad0"}, + {file = "asyncpg-0.27.0-cp38-cp38-win32.whl", hash = "sha256:69aa1b443a182b13a17ff926ed6627af2d98f62f2fe5890583270cc4073f63bf"}, + {file = "asyncpg-0.27.0-cp38-cp38-win_amd64.whl", hash = "sha256:62932f29cf2433988fcd799770ec64b374a3691e7902ecf85da14d5e0854d1ea"}, + {file = "asyncpg-0.27.0-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:fddcacf695581a8d856654bc4c8cfb73d5c9df26d5f55201722d3e6a699e9629"}, + {file = "asyncpg-0.27.0-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:7d8585707ecc6661d07367d444bbaa846b4e095d84451340da8df55a3757e152"}, + {file = "asyncpg-0.27.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:975a320baf7020339a67315284a4d3bf7460e664e484672bd3e71dbd881bc692"}, + {file = "asyncpg-0.27.0-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:2232ebae9796d4600a7819fc383da78ab51b32a092795f4555575fc934c1c89d"}, + {file = "asyncpg-0.27.0-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:88b62164738239f62f4af92567b846a8ef7cf8abf53eddd83650603de4d52163"}, + {file = "asyncpg-0.27.0-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:eb4b2fdf88af4fb1cc569781a8f933d2a73ee82cd720e0cb4edabbaecf2a905b"}, + {file = "asyncpg-0.27.0-cp39-cp39-win32.whl", hash = "sha256:8934577e1ed13f7d2d9cea3cc016cc6f95c19faedea2c2b56a6f94f257cea672"}, + {file = "asyncpg-0.27.0-cp39-cp39-win_amd64.whl", hash = "sha256:1b6499de06fe035cf2fa932ec5617ed3f37d4ebbf663b655922e105a484a6af9"}, + {file = "asyncpg-0.27.0.tar.gz", hash = "sha256:720986d9a4705dd8a40fdf172036f5ae787225036a7eb46e704c45aa8f62c054"}, +] + +[package.extras] +dev = ["Cython (>=0.29.24,<0.30.0)", "Sphinx (>=4.1.2,<4.2.0)", "flake8 (>=5.0.4,<5.1.0)", "pytest (>=6.0)", "sphinx-rtd-theme (>=0.5.2,<0.6.0)", "sphinxcontrib-asyncio (>=0.3.0,<0.4.0)", "uvloop (>=0.15.3)"] +docs = ["Sphinx (>=4.1.2,<4.2.0)", "sphinx-rtd-theme (>=0.5.2,<0.6.0)", "sphinxcontrib-asyncio (>=0.3.0,<0.4.0)"] +test = ["flake8 (>=5.0.4,<5.1.0)", "uvloop (>=0.15.3)"] + +[[package]] +name = "asyncpg-trek" +version = "0.3.1" +description = "A simple migrations system for asyncpg" +optional = false +python-versions = ">=3.7,<4" +files = [ + {file = "asyncpg_trek-0.3.1-py3-none-any.whl", hash = "sha256:3dbe0db791c99e5648c3d823142abb8f6b825a2ba0e9d7435e42f6309764e742"}, + {file = "asyncpg_trek-0.3.1.tar.gz", hash = "sha256:22a1f0f49209d135661c258e181c1f0ff1f94e90f02cab8ec15e6bca3420942d"}, +] + +[package.dependencies] +asyncpg = ">=0.26.0" + [[package]] name = "asyncpraw" version = "7.7.0" description = "Async PRAW, an abbreviation for \"Asynchronous Python Reddit API Wrapper\", is a python package that allows for simple access to Reddit's API." -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -295,16 +346,15 @@ update-checker = ">=0.18" [package.extras] ci = ["coveralls"] -dev = ["asynctest (>=0.13.0,<0.14.0)", "mock (>=4.0.0,<5.0.0)", "packaging", "pre-commit", "pytest (>=7.0.0,<8.0.0)", "pytest-asyncio (>=0.18.0,<0.19.0)", "pytest-vcr (>=1.0.0,<2.0.0)", "sphinx", "sphinx-rtd-dark-mode", "sphinx-rtd-theme", "sphinxcontrib-trio", "testfixtures (>=6.0.0,<7.0.0)", "vcrpy (>=4.0.0,<5.0.0)"] +dev = ["asynctest (==0.13.*)", "mock (==4.*)", "packaging", "pre-commit", "pytest (==7.*)", "pytest-asyncio (==0.18.*)", "pytest-vcr (==1.*)", "sphinx", "sphinx-rtd-dark-mode", "sphinx-rtd-theme", "sphinxcontrib-trio", "testfixtures (==6.*)", "vcrpy (==4.*)"] lint = ["pre-commit", "sphinx", "sphinx-rtd-dark-mode", "sphinx-rtd-theme", "sphinxcontrib-trio"] readthedocs = ["sphinx", "sphinx-rtd-dark-mode", "sphinx-rtd-theme", "sphinxcontrib-trio"] -test = ["asynctest (>=0.13.0,<0.14.0)", "mock (>=4.0.0,<5.0.0)", "pytest (>=7.0.0,<8.0.0)", "pytest-asyncio (>=0.18.0,<0.19.0)", "pytest-vcr (>=1.0.0,<2.0.0)", "testfixtures (>=6.0.0,<7.0.0)", "vcrpy (>=4.0.0,<5.0.0)"] +test = ["asynctest (==0.13.*)", "mock (==4.*)", "pytest (==7.*)", "pytest-asyncio (==0.18.*)", "pytest-vcr (==1.*)", "testfixtures (==6.*)", "vcrpy (==4.*)"] [[package]] name = "asyncprawcore" version = "2.3.0" description = "Low-level asynchronous communication layer for Async PRAW 7+." -category = "main" optional = false python-versions = ">=3.6" files = [ @@ -326,7 +376,6 @@ test = ["asynctest (>=0.13.0)", "mock (>=0.8)", "pytest", "pytest-vcr", "testfix name = "attrs" version = "22.2.0" description = "Classes Without Boilerplate" -category = "main" optional = false python-versions = ">=3.6" files = [ @@ -345,7 +394,6 @@ tests-no-zope = ["cloudpickle", "cloudpickle", "hypothesis", "hypothesis", "mypy name = "babel" version = "2.12.1" description = "Internationalization utilities" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -360,7 +408,6 @@ pytz = {version = ">=2015.7", markers = "python_version < \"3.9\""} name = "backoff" version = "2.2.1" description = "Function decoration for backoff and retry" -category = "main" optional = false python-versions = ">=3.7,<4.0" files = [ @@ -372,7 +419,6 @@ files = [ name = "beautifulsoup4" version = "4.12.2" description = "Screen-scraping library" -category = "dev" optional = false python-versions = ">=3.6.0" files = [ @@ -391,7 +437,6 @@ lxml = ["lxml"] name = "better-ipc" version = "2.0.3" description = "A high-performance inter-process communication library designed to work with the latest version of discord.py" -category = "main" optional = false python-versions = ">=3.8.0" files = [ @@ -406,7 +451,6 @@ websockets = ">=10.4" name = "braceexpand" version = "0.1.7" description = "Bash-style brace expansion for Python" -category = "dev" optional = false python-versions = "*" files = [ @@ -418,7 +462,6 @@ files = [ name = "brotli" version = "1.0.9" description = "Python bindings for the Brotli compression library" -category = "main" optional = false python-versions = "*" files = [ @@ -510,7 +553,6 @@ files = [ name = "certifi" version = "2022.12.7" description = "Python package for providing Mozilla's CA Bundle." -category = "main" optional = false python-versions = ">=3.6" files = [ @@ -522,7 +564,6 @@ files = [ name = "cffi" version = "1.15.1" description = "Foreign Function Interface for Python calling C code." -category = "main" optional = false python-versions = "*" files = [ @@ -599,7 +640,6 @@ pycparser = "*" name = "cfgv" version = "3.3.1" description = "Validate configuration and produce human readable error messages." -category = "dev" optional = false python-versions = ">=3.6.1" files = [ @@ -611,7 +651,6 @@ files = [ name = "charset-normalizer" version = "3.1.0" description = "The Real First Universal Charset Detector. Open, modern and actively maintained alternative to Chardet." -category = "main" optional = false python-versions = ">=3.7.0" files = [ @@ -696,7 +735,6 @@ files = [ name = "ciso8601" version = "2.3.0" description = "Fast ISO8601 date time parser for Python written in C" -category = "main" optional = false python-versions = "*" files = [ @@ -751,7 +789,6 @@ files = [ name = "click" version = "8.1.3" description = "Composable command line interface toolkit" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -766,7 +803,6 @@ colorama = {version = "*", markers = "platform_system == \"Windows\""} name = "colorama" version = "0.4.6" description = "Cross-platform colored terminal text." -category = "main" optional = false python-versions = "!=3.0.*,!=3.1.*,!=3.2.*,!=3.3.*,!=3.4.*,!=3.5.*,!=3.6.*,>=2.7" files = [ @@ -778,7 +814,6 @@ files = [ name = "colorlog" version = "6.7.0" description = "Add colours to the output of Python's logging module." -category = "dev" optional = false python-versions = ">=3.6" files = [ @@ -796,7 +831,6 @@ development = ["black", "flake8", "mypy", "pytest", "types-colorama"] name = "contourpy" version = "1.0.7" description = "Python library for calculating contours of 2D quadrilateral grids" -category = "dev" optional = false python-versions = ">=3.8" files = [ @@ -871,7 +905,6 @@ test-no-images = ["pytest"] name = "coverage" version = "7.0.5" description = "Code coverage measurement for Python" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -938,7 +971,6 @@ toml = ["tomli"] name = "cycler" version = "0.11.0" description = "Composable style cycles" -category = "dev" optional = false python-versions = ">=3.6" files = [ @@ -950,7 +982,6 @@ files = [ name = "discord-ext-menus" version = "1.0.0a32+g8686b5d" description = "An extension module to make reaction based menus with discord.py" -category = "main" optional = false python-versions = ">=3.5.3" files = [] @@ -969,7 +1000,6 @@ resolved_reference = "8686b5d1bbc1d3c862292eb436ab630d6e9c9b53" name = "discord-py" version = "2.2.3" description = "A Python wrapper for the Discord API" -category = "main" optional = false python-versions = ">=3.8.0" files = [ @@ -991,7 +1021,6 @@ voice = ["PyNaCl (>=1.3.0,<1.6)"] name = "distlib" version = "0.3.6" description = "Distribution utilities" -category = "dev" optional = false python-versions = "*" files = [ @@ -1003,7 +1032,6 @@ files = [ name = "docutils" version = "0.19" description = "Docutils -- Python Documentation Utilities" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1015,7 +1043,6 @@ files = [ name = "exceptiongroup" version = "1.1.0" description = "Backport of PEP 654 (exception groups)" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1030,7 +1057,6 @@ test = ["pytest (>=6)"] name = "faust-cchardet" version = "2.1.18" description = "cChardet is high speed universal character encoding detector." -category = "main" optional = false python-versions = "*" files = [ @@ -1093,7 +1119,6 @@ files = [ name = "filelock" version = "3.9.0" description = "A platform independent file lock." -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1109,7 +1134,6 @@ testing = ["covdefaults (>=2.2.2)", "coverage (>=7.0.1)", "pytest (>=7.2)", "pyt name = "fonttools" version = "4.39.3" description = "Tools to manipulate font files" -category = "dev" optional = false python-versions = ">=3.8" files = [ @@ -1135,7 +1159,6 @@ woff = ["brotli (>=1.0.1)", "brotlicffi (>=0.8.0)", "zopfli (>=0.1.4)"] name = "frozenlist" version = "1.3.3" description = "A list-like structure which implements collections.abc.MutableSequence" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -1219,7 +1242,6 @@ files = [ name = "furo" version = "2023.5.20" description = "A clean customisable Sphinx documentation theme." -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1237,7 +1259,6 @@ sphinx-basic-ng = "*" name = "gql" version = "3.4.1" description = "GraphQL client for Python" -category = "main" optional = false python-versions = "*" files = [ @@ -1265,7 +1286,6 @@ websockets = ["websockets (>=10,<11)", "websockets (>=9,<10)"] name = "graphql-core" version = "3.2.3" description = "GraphQL implementation for Python, a port of GraphQL.js, the JavaScript reference implementation for GraphQL." -category = "main" optional = false python-versions = ">=3.6,<4" files = [ @@ -1277,7 +1297,6 @@ files = [ name = "h11" version = "0.14.0" description = "A pure-Python, bring-your-own-I/O implementation of HTTP/1.1" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -1289,7 +1308,6 @@ files = [ name = "hiredis" version = "2.2.2" description = "Python wrapper for hiredis" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -1388,7 +1406,6 @@ files = [ name = "httpcore" version = "0.16.3" description = "A minimal low-level HTTP client." -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -1400,17 +1417,16 @@ files = [ anyio = ">=3.0,<5.0" certifi = "*" h11 = ">=0.13,<0.15" -sniffio = ">=1.0.0,<2.0.0" +sniffio = "==1.*" [package.extras] http2 = ["h2 (>=3,<5)"] -socks = ["socksio (>=1.0.0,<2.0.0)"] +socks = ["socksio (==1.*)"] [[package]] name = "httpx" version = "0.23.3" description = "The next generation HTTP client." -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -1426,15 +1442,14 @@ sniffio = "*" [package.extras] brotli = ["brotli", "brotlicffi"] -cli = ["click (>=8.0.0,<9.0.0)", "pygments (>=2.0.0,<3.0.0)", "rich (>=10,<13)"] +cli = ["click (==8.*)", "pygments (==2.*)", "rich (>=10,<13)"] http2 = ["h2 (>=3,<5)"] -socks = ["socksio (>=1.0.0,<2.0.0)"] +socks = ["socksio (==1.*)"] [[package]] name = "identify" version = "2.5.20" description = "File identification library for Python" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1449,7 +1464,6 @@ license = ["ukkonen"] name = "idna" version = "3.4" description = "Internationalized Domain Names in Applications (IDNA)" -category = "main" optional = false python-versions = ">=3.5" files = [ @@ -1461,7 +1475,6 @@ files = [ name = "imagesize" version = "1.4.1" description = "Getting image size from png/jpeg/jpeg2000/gif file" -category = "dev" optional = false python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*" files = [ @@ -1473,7 +1486,6 @@ files = [ name = "import-expression" version = "1.1.4" description = "Parses a superset of Python allowing for inline module import expressions" -category = "dev" optional = false python-versions = "*" files = [ @@ -1491,7 +1503,6 @@ test = ["pytest", "pytest-cov"] name = "importlib-metadata" version = "6.1.0" description = "Read metadata from Python packages" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1511,7 +1522,6 @@ testing = ["flake8 (<5)", "flufl.flake8", "importlib-resources (>=1.3)", "packag name = "importlib-resources" version = "5.12.0" description = "Read resources from Python packages" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1530,7 +1540,6 @@ testing = ["flake8 (<5)", "pytest (>=6)", "pytest-black (>=0.3.7)", "pytest-chec name = "iniconfig" version = "2.0.0" description = "brain-dead simple config-ini parsing" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1542,7 +1551,6 @@ files = [ name = "jinja2" version = "3.1.2" description = "A very fast and expressive template engine." -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -1560,7 +1568,6 @@ i18n = ["Babel (>=2.7)"] name = "jishaku" version = "2.5.1" description = "A discord.py extension including useful tools for bot development and debugging." -category = "dev" optional = false python-versions = ">=3.8.0" files = [ @@ -1588,7 +1595,6 @@ voice = ["yt-dlp (>=2022.3.8)"] name = "kiwisolver" version = "1.4.4" description = "A fast implementation of the Cassowary constraint solver" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1666,7 +1672,6 @@ files = [ name = "line-profiler" version = "4.0.3" description = "Line-by-line profiler" -category = "dev" optional = false python-versions = ">=3.6" files = [ @@ -1729,7 +1734,6 @@ tests-strict = ["IPython (==0.13)", "IPython (==0.13)", "coverage[toml] (==5.3)" name = "livereload" version = "2.6.3" description = "Python LiveReload is an awesome tool for web developers" -category = "dev" optional = false python-versions = "*" files = [ @@ -1745,7 +1749,6 @@ tornado = {version = "*", markers = "python_version > \"2.7\""} name = "markdown-it-py" version = "2.2.0" description = "Python port of markdown-it. Markdown parsing, done right!" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1770,7 +1773,6 @@ testing = ["coverage", "pytest", "pytest-cov", "pytest-regressions"] name = "markupsafe" version = "2.1.2" description = "Safely add untrusted strings to HTML/XML markup." -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -1830,7 +1832,6 @@ files = [ name = "matplotlib" version = "3.7.1" description = "Python plotting package" -category = "dev" optional = false python-versions = ">=3.8" files = [ @@ -1893,7 +1894,6 @@ python-dateutil = ">=2.7" name = "mdit-py-plugins" version = "0.3.5" description = "Collection of plugins for markdown-it-py" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1913,7 +1913,6 @@ testing = ["coverage", "pytest", "pytest-cov", "pytest-regressions"] name = "mdurl" version = "0.1.2" description = "Markdown URL utilities" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1925,7 +1924,6 @@ files = [ name = "multidict" version = "6.0.4" description = "multidict implementation" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -2009,7 +2007,6 @@ files = [ name = "myst-parser" version = "1.0.0" description = "An extended [CommonMark](https://spec.commonmark.org/) compliant parser," -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2036,7 +2033,6 @@ testing-docutils = ["pygments", "pytest (>=7,<8)", "pytest-param-files (>=0.3.4, name = "nodeenv" version = "1.7.0" description = "Node.js virtual environment builder" -category = "main" optional = false python-versions = ">=2.7,!=3.0.*,!=3.1.*,!=3.2.*,!=3.3.*,!=3.4.*,!=3.5.*,!=3.6.*" files = [ @@ -2051,7 +2047,6 @@ setuptools = "*" name = "nox" version = "2023.4.22" description = "Flexible test automation." -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2072,7 +2067,6 @@ tox-to-nox = ["jinja2", "tox (<4)"] name = "nox-poetry" version = "1.0.2" description = "nox-poetry" -category = "dev" optional = false python-versions = ">=3.7,<4.0" files = [ @@ -2089,7 +2083,6 @@ tomlkit = ">=0.7" name = "numpy" version = "1.24.2" description = "Fundamental package for array computing in Python" -category = "dev" optional = false python-versions = ">=3.8" files = [ @@ -2127,7 +2120,6 @@ files = [ name = "orjson" version = "3.8.14" description = "Fast, correct Python JSON library supporting dataclasses, datetimes, and numpy" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -2183,7 +2175,6 @@ files = [ name = "packaging" version = "22.0" description = "Core utilities for Python packages" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2195,7 +2186,6 @@ files = [ name = "pillow" version = "9.5.0" description = "Python Imaging Library (Fork)" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2275,7 +2265,6 @@ tests = ["check-manifest", "coverage", "defusedxml", "markdown2", "olefile", "pa name = "platformdirs" version = "2.6.2" description = "A small Python package for determining appropriate platform-specific dirs, e.g. a \"user data dir\"." -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2291,7 +2280,6 @@ test = ["appdirs (==1.4.4)", "covdefaults (>=2.2.2)", "pytest (>=7.2)", "pytest- name = "pluggy" version = "1.0.0" description = "plugin and hook calling mechanisms for python" -category = "dev" optional = false python-versions = ">=3.6" files = [ @@ -2307,7 +2295,6 @@ testing = ["pytest", "pytest-benchmark"] name = "pre-commit" version = "3.3.2" description = "A framework for managing and maintaining multi-language pre-commit hooks." -category = "dev" optional = false python-versions = ">=3.8" files = [ @@ -2326,7 +2313,6 @@ virtualenv = ">=20.10.0" name = "prisma" version = "0.8.2" description = "Prisma Client Python is an auto-generated and fully type-safe database client" -category = "main" optional = false python-versions = ">=3.7.0" files = [ @@ -2352,7 +2338,6 @@ node = ["nodejs-bin"] name = "pycares" version = "4.3.0" description = "Python interface for c-ares" -category = "main" optional = false python-versions = "*" files = [ @@ -2420,7 +2405,6 @@ idna = ["idna (>=2.1)"] name = "pycparser" version = "2.21" description = "C parser in Python" -category = "main" optional = false python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*" files = [ @@ -2432,7 +2416,6 @@ files = [ name = "pydantic" version = "1.10.4" description = "Data validation and settings management using python type hints" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -2485,7 +2468,6 @@ email = ["email-validator (>=1.0.3)"] name = "pygments" version = "2.15.0" description = "Pygments is a syntax highlighting package written in Python." -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2500,7 +2482,6 @@ plugins = ["importlib-metadata"] name = "pyinstrument" version = "4.4.0" description = "Call stack profiler for Python. Shows you why your code is slow!" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2563,7 +2544,6 @@ jupyter = ["ipython"] name = "pynacl" version = "1.5.0" description = "Python binding to the Networking and Cryptography (NaCl) library" -category = "main" optional = false python-versions = ">=3.6" files = [ @@ -2590,7 +2570,6 @@ tests = ["hypothesis (>=3.27.0)", "pytest (>=3.2.1,!=3.3.0)"] name = "pyparsing" version = "3.0.9" description = "pyparsing module - Classes and methods to define and execute parsing grammars" -category = "dev" optional = false python-versions = ">=3.6.8" files = [ @@ -2605,7 +2584,6 @@ diagrams = ["jinja2", "railroad-diagrams"] name = "pyright" version = "1.1.310" description = "Command line wrapper for pyright" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2624,7 +2602,6 @@ dev = ["twine (>=3.4.1)"] name = "pytest" version = "7.3.1" description = "pytest: simple powerful testing with Python" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2647,7 +2624,6 @@ testing = ["argcomplete", "attrs (>=19.2.0)", "hypothesis (>=3.56)", "mock", "no name = "pytest-asyncio" version = "0.21.0" description = "Pytest support for asyncio" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2666,7 +2642,6 @@ testing = ["coverage (>=6.2)", "flaky (>=3.5.0)", "hypothesis (>=5.7.1)", "mypy name = "pytest-cov" version = "4.1.0" description = "Pytest plugin for measuring coverage." -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2685,7 +2660,6 @@ testing = ["fields", "hunter", "process-tests", "pytest-xdist", "six", "virtuale name = "python-dateutil" version = "2.8.2" description = "Extensions to the standard Python datetime module" -category = "dev" optional = false python-versions = "!=3.0.*,!=3.1.*,!=3.2.*,>=2.7" files = [ @@ -2700,7 +2674,6 @@ six = ">=1.5" name = "python-dotenv" version = "1.0.0" description = "Read key-value pairs from a .env file and set them as environment variables" -category = "main" optional = false python-versions = ">=3.8" files = [ @@ -2715,7 +2688,6 @@ cli = ["click (>=5.0)"] name = "pytz" version = "2023.3" description = "World timezone definitions, modern and historical" -category = "dev" optional = false python-versions = "*" files = [ @@ -2727,7 +2699,6 @@ files = [ name = "pyyaml" version = "6.0" description = "YAML parser and emitter for Python" -category = "dev" optional = false python-versions = ">=3.6" files = [ @@ -2777,7 +2748,6 @@ files = [ name = "redis" version = "4.5.5" description = "Python client for Redis database and key-value store" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -2797,7 +2767,6 @@ ocsp = ["cryptography (>=36.0.1)", "pyopenssl (==20.0.1)", "requests (>=2.26.0)" name = "requests" version = "2.31.0" description = "Python HTTP for Humans." -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -2819,7 +2788,6 @@ use-chardet-on-py3 = ["chardet (>=3.0.2,<6)"] name = "rfc3986" version = "1.5.0" description = "Validating URI References per RFC 3986" -category = "main" optional = false python-versions = "*" files = [ @@ -2837,7 +2805,6 @@ idna2008 = ["idna"] name = "ruff" version = "0.0.270" description = "An extremely fast Python linter, written in Rust." -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2864,7 +2831,6 @@ files = [ name = "setuptools" version = "66.1.1" description = "Easily download, build, install, upgrade, and uninstall Python packages" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -2881,7 +2847,6 @@ testing-integration = ["build[virtualenv]", "filelock (>=3.4.0)", "jaraco.envs ( name = "six" version = "1.16.0" description = "Python 2 and 3 compatibility utilities" -category = "dev" optional = false python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*" files = [ @@ -2893,7 +2858,6 @@ files = [ name = "sniffio" version = "1.3.0" description = "Sniff out which async library your code is running under" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -2905,7 +2869,6 @@ files = [ name = "snowballstemmer" version = "2.2.0" description = "This package provides 29 stemmers for 28 languages generated from Snowball algorithms." -category = "dev" optional = false python-versions = "*" files = [ @@ -2917,7 +2880,6 @@ files = [ name = "soupsieve" version = "2.4.1" description = "A modern CSS selector implementation for Beautiful Soup." -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2929,7 +2891,6 @@ files = [ name = "sphinx" version = "6.2.1" description = "Python documentation generator" -category = "dev" optional = false python-versions = ">=3.8" files = [ @@ -2965,7 +2926,6 @@ test = ["cython", "filelock", "html5lib", "pytest (>=4.6)"] name = "sphinx-autobuild" version = "2021.3.14" description = "Rebuild Sphinx documentation on changes, with live-reload in the browser." -category = "dev" optional = false python-versions = ">=3.6" files = [ @@ -2985,7 +2945,6 @@ test = ["pytest", "pytest-cov"] name = "sphinx-basic-ng" version = "1.0.0b1" description = "A modern skeleton for Sphinx themes." -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -3003,7 +2962,6 @@ docs = ["furo", "ipython", "myst-parser", "sphinx-copybutton", "sphinx-inline-ta name = "sphinxcontrib-applehelp" version = "1.0.4" description = "sphinxcontrib-applehelp is a Sphinx extension which outputs Apple help books" -category = "dev" optional = false python-versions = ">=3.8" files = [ @@ -3019,7 +2977,6 @@ test = ["pytest"] name = "sphinxcontrib-devhelp" version = "1.0.2" description = "sphinxcontrib-devhelp is a sphinx extension which outputs Devhelp document." -category = "dev" optional = false python-versions = ">=3.5" files = [ @@ -3035,7 +2992,6 @@ test = ["pytest"] name = "sphinxcontrib-htmlhelp" version = "2.0.1" description = "sphinxcontrib-htmlhelp is a sphinx extension which renders HTML help files" -category = "dev" optional = false python-versions = ">=3.8" files = [ @@ -3051,7 +3007,6 @@ test = ["html5lib", "pytest"] name = "sphinxcontrib-jsmath" version = "1.0.1" description = "A sphinx extension which renders display math in HTML via JavaScript" -category = "dev" optional = false python-versions = ">=3.5" files = [ @@ -3066,7 +3021,6 @@ test = ["flake8", "mypy", "pytest"] name = "sphinxcontrib-qthelp" version = "1.0.3" description = "sphinxcontrib-qthelp is a sphinx extension which outputs QtHelp document." -category = "dev" optional = false python-versions = ">=3.5" files = [ @@ -3082,7 +3036,6 @@ test = ["pytest"] name = "sphinxcontrib-serializinghtml" version = "1.1.5" description = "sphinxcontrib-serializinghtml is a sphinx extension which outputs \"serialized\" HTML files (json and pickle)." -category = "dev" optional = false python-versions = ">=3.5" files = [ @@ -3098,7 +3051,6 @@ test = ["pytest"] name = "sphinxext-opengraph" version = "0.8.2" description = "Sphinx Extension to enable OGP support" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -3114,7 +3066,6 @@ sphinx = ">=4.0" name = "tomli" version = "2.0.1" description = "A lil' TOML parser" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -3126,7 +3077,6 @@ files = [ name = "tomlkit" version = "0.11.6" description = "Style preserving TOML library" -category = "main" optional = false python-versions = ">=3.6" files = [ @@ -3138,7 +3088,6 @@ files = [ name = "tornado" version = "6.3.2" description = "Tornado is a Python web framework and asynchronous networking library, originally developed at FriendFeed." -category = "dev" optional = false python-versions = ">= 3.8" files = [ @@ -3159,7 +3108,6 @@ files = [ name = "typing-extensions" version = "4.4.0" description = "Backported and Experimental Type Hints for Python 3.7+" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -3171,7 +3119,6 @@ files = [ name = "update-checker" version = "0.18.0" description = "A python module that will check for package updates." -category = "main" optional = false python-versions = "*" files = [ @@ -3191,7 +3138,6 @@ test = ["pytest (>=2.7.3)"] name = "urllib3" version = "1.26.14" description = "HTTP library with thread-safe connection pooling, file post, and more." -category = "main" optional = false python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, !=3.4.*, !=3.5.*" files = [ @@ -3208,7 +3154,6 @@ socks = ["PySocks (>=1.5.6,!=1.5.7,<2.0)"] name = "uvloop" version = "0.17.0" description = "Fast implementation of asyncio event loop on top of libuv" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -3253,7 +3198,6 @@ test = ["Cython (>=0.29.32,<0.30.0)", "aiohttp", "flake8 (>=3.9.2,<3.10.0)", "my name = "virtualenv" version = "20.17.1" description = "Virtual Python Environment builder" -category = "dev" optional = false python-versions = ">=3.6" files = [ @@ -3274,7 +3218,6 @@ testing = ["coverage (>=6.2)", "coverage-enable-subprocess (>=1)", "flaky (>=3.7 name = "watchfiles" version = "0.19.0" description = "Simple, modern and high performance file watching and code reload in python." -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -3309,7 +3252,6 @@ anyio = ">=3.0.0" name = "websockets" version = "10.4" description = "An implementation of the WebSocket Protocol (RFC 6455 & 7692)" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -3388,7 +3330,6 @@ files = [ name = "wheel" version = "0.40.0" description = "A built-package format for Python" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -3403,7 +3344,6 @@ test = ["pytest (>=6.0.0)"] name = "yarl" version = "1.8.2" description = "Yet another URL library" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -3491,7 +3431,6 @@ multidict = ">=4.0" name = "zipp" version = "3.15.0" description = "Backport of pathlib-compatible object wrapper for zip files" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -3506,4 +3445,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "daa326263ecc68a43c2f02ed2de3b6b55596cbb6b79555620a5cf72ca7d4a614" +content-hash = "2b122f6c3df28dd447bd14c772d311dd0033779f369b80628cd0dbcf031d66d3" diff --git a/pyproject.toml b/pyproject.toml index c80f43d5..dfd1f8ea 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -21,6 +21,8 @@ ciso8601 = "^2.3.0" faust-cchardet = "^2.1.18" discord-py = {extras = ["voice"], version = "^2.2.3"} discord-ext-menus = {git = "https://github.com/Rapptz/discord-ext-menus", rev = "8686b5d1bbc1d3c862292eb436ab630d6e9c9b53"} +asyncpg = "^0.27.0" +asyncpg-trek = "^0.3.1" [tool.poetry.group.test.dependencies] pytest = "^7.3.1" From 5e75eefebfccffd25d32d23070bfc684ba0490fa Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 31 May 2023 19:01:21 +0000 Subject: [PATCH 081/184] [pip](deps-dev): Bump pyright from 1.1.310 to 1.1.311 (#340) Bumps [pyright](https://github.com/RobertCraigie/pyright-python) from 1.1.310 to 1.1.311. - [Release notes](https://github.com/RobertCraigie/pyright-python/releases) - [Commits](https://github.com/RobertCraigie/pyright-python/compare/v1.1.310...v1.1.311) --- updated-dependencies: - dependency-name: pyright dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index 00df0311..e1494e9b 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2603,14 +2603,14 @@ diagrams = ["jinja2", "railroad-diagrams"] [[package]] name = "pyright" -version = "1.1.310" +version = "1.1.311" description = "Command line wrapper for pyright" category = "dev" optional = false python-versions = ">=3.7" files = [ - {file = "pyright-1.1.310-py3-none-any.whl", hash = "sha256:55995ac76bf56cb7a44193b7b1ffafc573abab1f1dbc9f62d327f2a1768b3bda"}, - {file = "pyright-1.1.310.tar.gz", hash = "sha256:9e95335a678db2717eaa0c867d61f9399e916289f4a9f47d993e0df74e7d7391"}, + {file = "pyright-1.1.311-py3-none-any.whl", hash = "sha256:04df30c6b31d05068effe5563411291c876f5e4221d0af225a267b61dce1ca85"}, + {file = "pyright-1.1.311.tar.gz", hash = "sha256:554b555d3f770e8da2e76d6bb94e2ac63b3edc7dcd5fb8de202f9dd53e36689a"}, ] [package.dependencies] @@ -3506,4 +3506,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "daa326263ecc68a43c2f02ed2de3b6b55596cbb6b79555620a5cf72ca7d4a614" +content-hash = "cff7c3d7129a5970a699fd2ab594a84ee9356bc37f8ee5f5e4b51cddf3b2123d" diff --git a/pyproject.toml b/pyproject.toml index c80f43d5..9ea5e3e2 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -32,7 +32,7 @@ pytest-cov = "^4.1.0" [tool.poetry.group.dev.dependencies] pre-commit = "^3.3.2" pyinstrument = "^4.4.0" -pyright = "^1.1.310" +pyright = "^1.1.311" watchfiles = "^0.19.0" jishaku = "^2.5.1" ruff = "^0.0.270" From 3b31f33ce6a4f85d28e1ec76d39b07106e239d5e Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Thu, 1 Jun 2023 19:06:06 +0000 Subject: [PATCH 082/184] [pip](deps): Bump orjson from 3.8.14 to 3.9.0 (#341) Bumps [orjson](https://github.com/ijl/orjson) from 3.8.14 to 3.9.0. - [Release notes](https://github.com/ijl/orjson/releases) - [Changelog](https://github.com/ijl/orjson/blob/master/CHANGELOG.md) - [Commits](https://github.com/ijl/orjson/compare/3.8.14...3.9.0) --- updated-dependencies: - dependency-name: orjson dependency-type: direct:production update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 96 +++++++++++++++++++++++++------------------------- pyproject.toml | 2 +- 2 files changed, 49 insertions(+), 49 deletions(-) diff --git a/poetry.lock b/poetry.lock index e1494e9b..658aab79 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2125,58 +2125,58 @@ files = [ [[package]] name = "orjson" -version = "3.8.14" +version = "3.9.0" description = "Fast, correct Python JSON library supporting dataclasses, datetimes, and numpy" category = "main" optional = false python-versions = ">=3.7" files = [ - {file = "orjson-3.8.14-cp310-cp310-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:7a7b0fead2d0115ef927fa46ad005d7a3988a77187500bf895af67b365c10d1f"}, - {file = "orjson-3.8.14-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ca90db8f551b8960da95b0d4cad6c0489df52ea03585b6979595be7b31a3f946"}, - {file = "orjson-3.8.14-cp310-cp310-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:f4ac01a3db4e6a98a8ad1bb1a3e8bfc777928939e87c04e93e0d5006df574a4b"}, - {file = "orjson-3.8.14-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:bf6825e160e4eb0ef65ce37d8c221edcab96ff2ffba65e5da2437a60a12b3ad1"}, - {file = "orjson-3.8.14-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:f80e62afe49e6bfc706e041faa351d7520b5f86572b8e31455802251ea989613"}, - {file = "orjson-3.8.14-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:6112194c11e611596eed72f46efb0e6b4812682eff3c7b48473d1146c3fa0efb"}, - {file = "orjson-3.8.14-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:739f9f633e1544f2a477fa3bef380f488c8dca6e2521c8dc36424b12554ee31e"}, - {file = "orjson-3.8.14-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:7d3d8faded5a514b80b56d0429eb38b429d7a810f8749d25dc10a0cc15b8a3c8"}, - {file = "orjson-3.8.14-cp310-none-win_amd64.whl", hash = "sha256:0bf00c42333412a9338297bf888d7428c99e281e20322070bde8c2314775508b"}, - {file = "orjson-3.8.14-cp311-cp311-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:d66966fd94719beb84e8ed84833bc59c3c005d3d2d0c42f11d7552d3267c6de7"}, - {file = "orjson-3.8.14-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:087c0dc93379e8ba2d59e9f586fab8de8c137d164fccf8afd5523a2137570917"}, - {file = "orjson-3.8.14-cp311-cp311-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:04c70dc8ca79b0072a16d82f94b9d9dd6598a43dd753ab20039e9f7d2b14f017"}, - {file = "orjson-3.8.14-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:aedba48264fe87e5060c0e9c2b28909f1e60626e46dc2f77e0c8c16939e2e1f7"}, - {file = "orjson-3.8.14-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:01640ab79111dd97515cba9fab7c66cb3b0967b0892cc74756a801ff681a01b6"}, - {file = "orjson-3.8.14-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:8b206cca6836a4c6683bcaa523ab467627b5f03902e5e1082dc59cd010e6925f"}, - {file = "orjson-3.8.14-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:ee0299b2dda9afce351a5e8c148ea7a886de213f955aa0288fb874fb44829c36"}, - {file = "orjson-3.8.14-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:31a2a29be559e92dcc5c278787b4166da6f0d45675b59a11c4867f5d1455ebf4"}, - {file = "orjson-3.8.14-cp311-none-win_amd64.whl", hash = "sha256:20b7ffc7736000ea205f9143df322b03961f287b4057606291c62c842ff3c5b5"}, - {file = "orjson-3.8.14-cp37-cp37m-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:de1ee13d6b6727ee1db38722695250984bae81b8fc9d05f1176c74d14b1322d9"}, - {file = "orjson-3.8.14-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:3ee09bfbf1d54c127d3061f6721a1a11d2ce502b50597c3d0d2e1bd2d235b764"}, - {file = "orjson-3.8.14-cp37-cp37m-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:97ebb7fab5f1ae212a6501f17cb7750a6838ffc2f1cebbaa5dec1a90038ca3c6"}, - {file = "orjson-3.8.14-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:38ca39bae7fbc050332a374062d4cdec28095540fa8bb245eada467897a3a0bb"}, - {file = "orjson-3.8.14-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:92374bc35b6da344a927d5a850f7db80a91c7b837de2f0ea90fc870314b1ff44"}, - {file = "orjson-3.8.14-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:9393a63cb0424515ec5e434078b3198de6ec9e057f1d33bad268683935f0a5d5"}, - {file = "orjson-3.8.14-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:5fb66f0ac23e861b817c858515ac1f74d1cd9e72e3f82a5b2c9bae9f92286adc"}, - {file = "orjson-3.8.14-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:19415aaf30525a5baff0d72a089fcdd68f19a3674998263c885c3908228c1086"}, - {file = "orjson-3.8.14-cp37-none-win_amd64.whl", hash = "sha256:87ba7882e146e24a7d8b4a7971c20212c2af75ead8096fc3d55330babb1015fb"}, - {file = "orjson-3.8.14-cp38-cp38-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:9f5cf61b6db68f213c805c55bf0aab9b4cb75a4e9c7f5bfbd4deb3a0aef0ec53"}, - {file = "orjson-3.8.14-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:33bc310da4ad2ffe8f7f1c9e89692146d9ec5aec2d1c9ef6b67f8dc5e2d63241"}, - {file = "orjson-3.8.14-cp38-cp38-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:67a7e883b6f782b106683979ccc43d89b98c28a1f4a33fe3a22e253577499bb1"}, - {file = "orjson-3.8.14-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:9df820e6c8c84c52ec39ea2cc9c79f7999c839c7d1481a056908dce3b90ce9f9"}, - {file = "orjson-3.8.14-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:ebca14ae80814219ea3327e3dfa7ff618621ff335e45781fac26f5cd0b48f2b4"}, - {file = "orjson-3.8.14-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:27967be4c16bd09f4aeff8896d9be9cbd00fd72f5815d5980e4776f821e2f77c"}, - {file = "orjson-3.8.14-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:062829b5e20cd8648bf4c11c3a5ee7cf196fa138e573407b5312c849b0cf354d"}, - {file = "orjson-3.8.14-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:e53bc5beb612df8ddddb065f079d3fd30b5b4e73053518524423549d61177f3f"}, - {file = "orjson-3.8.14-cp38-none-win_amd64.whl", hash = "sha256:d03f29b0369bb1ab55c8a67103eb3a9675daaf92f04388568034fe16be48fa5d"}, - {file = "orjson-3.8.14-cp39-cp39-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:716a3994e039203f0a59056efa28185d4cac51b922cc5bf27ab9182cfa20e12e"}, - {file = "orjson-3.8.14-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:7cb35dd3ba062c1d984d57e6477768ed7b62ed9260f31362b2d69106f9c60ebd"}, - {file = "orjson-3.8.14-cp39-cp39-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:0bc6b7abf27f1dc192dadad249df9b513912506dd420ce50fd18864a33789b71"}, - {file = "orjson-3.8.14-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:7e2f75b7d9285e35c3d4dff9811185535ff2ea637f06b2b242cb84385f8ffe63"}, - {file = "orjson-3.8.14-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:017de5ba22e58dfa6f41914f5edb8cd052d23f171000684c26b2d2ab219db31e"}, - {file = "orjson-3.8.14-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:09a3bf3154f40299b8bc95e9fb8da47436a59a2106fc22cae15f76d649e062da"}, - {file = "orjson-3.8.14-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:64b4fca0531030040e611c6037aaf05359e296877ab0a8e744c26ef9c32738b9"}, - {file = "orjson-3.8.14-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:8a896a12b38fe201a72593810abc1f4f1597e65b8c869d5fc83bbcf75d93398f"}, - {file = "orjson-3.8.14-cp39-none-win_amd64.whl", hash = "sha256:9725226478d1dafe46d26f758eadecc6cf98dcbb985445e14a9c74aaed6ccfea"}, - {file = "orjson-3.8.14.tar.gz", hash = "sha256:5ea93fd3ef7be7386f2516d728c877156de1559cda09453fc7dd7b696d0439b3"}, + {file = "orjson-3.9.0-cp310-cp310-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:128b1cd0f00a37ba64a12cceeba4e8070655d4400edd55a737513ee663c1ed5a"}, + {file = "orjson-3.9.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:7a3693fde44b2eeb80074ecbe8c504b25baf71e66c080af2a574193a5ba81960"}, + {file = "orjson-3.9.0-cp310-cp310-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:3f1193417b5a93deb41bcb8db27b61179b9b3e299b337b578c31f19159664da3"}, + {file = "orjson-3.9.0-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:88626d898c408450c57664899831cf072787898af4847fa4466607ad2a83f454"}, + {file = "orjson-3.9.0-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:1e3bde77c1e0061eb34bae6fea44818b2198e043ee10a16ad7b160921fee26ea"}, + {file = "orjson-3.9.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:45df5bf6531ffda518331cc93cdcd4c84f4a4a0507d72af8fb698c7131a440a0"}, + {file = "orjson-3.9.0-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:2536a7f30fd4d77532769ea9285cd20c69bd2b40acf980de94bbc79b1c6fad5a"}, + {file = "orjson-3.9.0-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:21f6a6fdfbc13cd715c61e9fa9daeff732df6401ab7d6a2ebad0042313a40bd1"}, + {file = "orjson-3.9.0-cp310-none-win_amd64.whl", hash = "sha256:46c9733330b75c116438f555c0b971a2388b5f502e2dd4ec3bf6bacb96f82741"}, + {file = "orjson-3.9.0-cp311-cp311-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:47d7e4a3effc0e9314bd5b06e7431f2490a5e64dcdcbbc4d60e713786fec327d"}, + {file = "orjson-3.9.0-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:c41d1ef6ec308e9e3701764b3de889ed8c1c126eceaea881dd1027bffbed89fe"}, + {file = "orjson-3.9.0-cp311-cp311-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:86da00836029b2a071229c8aecab998a2f316c1bc7de10ae020d7311de3a6d0d"}, + {file = "orjson-3.9.0-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:d4fcf598bd5a99a94caa7ec92ce657939f12491e4753ea7e4d6c03faf5f7912e"}, + {file = "orjson-3.9.0-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:09522937479bd39d5bb32d11a5ecdf6926fda43ac2cbde21cc1a9508b4e4ea29"}, + {file = "orjson-3.9.0-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:d2fbf34667a8be48ec89d5ef479a00d4e7b3acda62d722c97377702da0c30ffd"}, + {file = "orjson-3.9.0-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:edd77183c154cbedaa6dac32fee9cb770b04e2a7f367a5864f444578554cc946"}, + {file = "orjson-3.9.0-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:2af7dff1c7ddb0c83eb5773acf6566b153f8cd32e4ba782ae9ccd6d0f324efd3"}, + {file = "orjson-3.9.0-cp311-none-win_amd64.whl", hash = "sha256:44fa74b497e608a8cdca1ee37fe3533a30f17163c7e2872ab1b854900cf0dfcf"}, + {file = "orjson-3.9.0-cp37-cp37m-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:f6476e2487c0b7387187de15e5b8f6635c29b75934f2e689ca8cad6550439f3d"}, + {file = "orjson-3.9.0-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:c7b241c3229084035b38cac9b5c96b43644da829da41d9d5be0fefb96fb116e1"}, + {file = "orjson-3.9.0-cp37-cp37m-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:d414fd0678e949779104f5b307f0f9fac861728e19d3cdde66759af77f892da0"}, + {file = "orjson-3.9.0-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:8a1fcddcabe121e393f3c4a31ed6d3535214d42a4ece0f9dde2e250006d6a58d"}, + {file = "orjson-3.9.0-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:bd89d63707ac616462832bfc5d16fa0c12483f86add2432ce55c8710c9531c03"}, + {file = "orjson-3.9.0-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:6c50654e4870805e4b1a587c2c3c5ef2f36f3e67fc463a738339ff40d65f7db1"}, + {file = "orjson-3.9.0-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:721d47dffedb7795ffea8a06f2de7d192de7b58e085cf357a99abf0eb931f2c3"}, + {file = "orjson-3.9.0-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:9de2129d40674007cb24164939e075b5b39fee768bf20801e08c0e3283bfb18e"}, + {file = "orjson-3.9.0-cp37-none-win_amd64.whl", hash = "sha256:5afd22847b07b63f2b8fcfddd5b7a6f47c5aaa25e19b97a3d6d39508b8fd465a"}, + {file = "orjson-3.9.0-cp38-cp38-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:d4c2d31178e3027affd98eead033f1c406890df83a0ca2016604cc21f722a1d1"}, + {file = "orjson-3.9.0-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ebe372e9f4e4f0335b7b4ebfab991b3734371e3d5b7f989ca3baa5da25185f4a"}, + {file = "orjson-3.9.0-cp38-cp38-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:c4949fc1304b702197c0840882e84b86d8d5ca33c3d945cc60727bc1786c2b20"}, + {file = "orjson-3.9.0-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:748c1e8df0b0880c63d323e167ad17ab4db2e1178a40902c2fcb68cbe402d7c8"}, + {file = "orjson-3.9.0-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:f6ab80b60195f166a9d666b2eaf6d2c74202b6da2a1fb4b4d66b9cc0ce5c9957"}, + {file = "orjson-3.9.0-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:e44ebe2129d43c5a48f3affa3fa59c6484ed16faf5b00486add1061a95384ab0"}, + {file = "orjson-3.9.0-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:04e61db09ff155846b69d07cf5aa21001f2010ea669ec3169c1fbad9c9e40cd5"}, + {file = "orjson-3.9.0-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:c68af71b1110820c914f9df75842895b5528ff524d3286fde57097b2b5ed8f22"}, + {file = "orjson-3.9.0-cp38-none-win_amd64.whl", hash = "sha256:3a208d0bca609de3152eb8320d5093ad9c52979332f626c13500d1645c66bf8d"}, + {file = "orjson-3.9.0-cp39-cp39-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:a901c432828c191332d75f358142736c433d4a192f7794123e1d30d68193de86"}, + {file = "orjson-3.9.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:271b6f1018757fc6bca40ae72e6cdb6cf84584dde2d1e5eaac30e387a13d9e72"}, + {file = "orjson-3.9.0-cp39-cp39-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:949698bdddb1daff986d73e6bbe6cd68833cd80c4adc6b69fafbd46634d4672c"}, + {file = "orjson-3.9.0-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:108c58d2c7648c991f82f9b2217c50981ad7cf6aaee3efbfaa9d807e49cd69b8"}, + {file = "orjson-3.9.0-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:08cb43569198c1f5c89ecafcbfc62414f6115d894ff908d8cf8e5e24801364e6"}, + {file = "orjson-3.9.0-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:09ee828572fadcd58bf356d2c1bad99a95c7c9c1f182b407abbc7dec1810f542"}, + {file = "orjson-3.9.0-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:0e7fe5d603ee9177ff2e45858b4fc47fea2da0688f23d9773654889d56dfbc82"}, + {file = "orjson-3.9.0-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:9ee5f1ba82146a50d61fb58d310a37c0f406eda898172f9c98673b5d6f9461c3"}, + {file = "orjson-3.9.0-cp39-none-win_amd64.whl", hash = "sha256:3235c31d0fe674f6e3433e9ddfed212aa840c83a9b6ef5ae128950e2c808c303"}, + {file = "orjson-3.9.0.tar.gz", hash = "sha256:f6dd27c71cd6e146795f876449a8eae74f67ae1e4e244dfc1203489103eb2d94"}, ] [[package]] @@ -3506,4 +3506,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "cff7c3d7129a5970a699fd2ab594a84ee9356bc37f8ee5f5e4b51cddf3b2123d" +content-hash = "b5e117bca8d584f9bc17264e98bb11189554e845c258214e1324c0655bf6de34" diff --git a/pyproject.toml b/pyproject.toml index 9ea5e3e2..eea96b9f 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -10,7 +10,7 @@ python = ">=3.8,<4.0" python-dotenv = "^1.0.0" aiodns = "^3.0.0" Brotli = "^1.0.9" -orjson = "^3.8.14" +orjson = "^3.9.0" asyncpraw = "^7.7.0" uvloop = "^0.17.0" gql = { extras = ["aiohttp"], version = "^3.4.1" } From 89daa0a8f681f73812333ce699fd6aaf0536745a Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 6 Jun 2023 19:01:05 +0000 Subject: [PATCH 083/184] [pip](deps-dev): Bump pyinstrument from 4.4.0 to 4.5.0 (#342) Bumps [pyinstrument](https://github.com/joerick/pyinstrument) from 4.4.0 to 4.5.0. - [Release notes](https://github.com/joerick/pyinstrument/releases) - [Commits](https://github.com/joerick/pyinstrument/compare/v4.4.0...v4.5.0) --- updated-dependencies: - dependency-name: pyinstrument dependency-type: direct:development update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 104 ++++++++++++++++++++++++------------------------- pyproject.toml | 2 +- 2 files changed, 53 insertions(+), 53 deletions(-) diff --git a/poetry.lock b/poetry.lock index 658aab79..407be1a7 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2498,62 +2498,62 @@ plugins = ["importlib-metadata"] [[package]] name = "pyinstrument" -version = "4.4.0" +version = "4.5.0" description = "Call stack profiler for Python. Shows you why your code is slow!" category = "dev" optional = false python-versions = ">=3.7" files = [ - {file = "pyinstrument-4.4.0-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:8874f8f58cfcb1ff134dc8e4a2b31ab9175adb271a4423596ed7ac8183592cf8"}, - {file = "pyinstrument-4.4.0-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:e5f4d6e1c395f259f67a923a9c54dc3eaccd5f02540598da4f865c4bb3545762"}, - {file = "pyinstrument-4.4.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d70fed48ddd0078e287fb580daaeede4d8703a9edc8bf4f703308a77920bac37"}, - {file = "pyinstrument-4.4.0-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:9fda1bd596e81ecd2b6a976eb9b930a757a5dd04071583d0141d059e34eed83f"}, - {file = "pyinstrument-4.4.0-cp310-cp310-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:2f57b61d39d3b1a4d773da16baa8456aa66102d6016ce1f39817051550cbe47e"}, - {file = "pyinstrument-4.4.0-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:5a9aead0ca5579473f66fed4c449c693feee464802b5ba9b98772e64e02c575c"}, - {file = "pyinstrument-4.4.0-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:375a340c3fbebd922a35b0834de1c82d1b4fea681df49f99729439a6cb5e6ad4"}, - {file = "pyinstrument-4.4.0-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:b9cbaf3bcda5ad9af4c9a7bf4f1b8f15bb32c4cadf554d0a2c723892c898021b"}, - {file = "pyinstrument-4.4.0-cp310-cp310-win32.whl", hash = "sha256:97cbeb5f5a048dc6eb047495f73db90c9e2ec97606e65298c7ea2c61fa52de38"}, - {file = "pyinstrument-4.4.0-cp310-cp310-win_amd64.whl", hash = "sha256:73edbce7fda1b3d8cab0b6c39c43b012167d783c072f40928600c3357d1a5dc5"}, - {file = "pyinstrument-4.4.0-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:7db8cb55182883be48520eb915bd1769f176a4813ce0cc38243aa2d1182e7ce7"}, - {file = "pyinstrument-4.4.0-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:7c614e2c241fb558a25973019ff43ce027ba4958bcb87383f0b0789af9c4d03b"}, - {file = "pyinstrument-4.4.0-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:3c012422c851f0457c3cb82d8b1259d96fa0dcddc0f1e8bf4d97f0b2efe54485"}, - {file = "pyinstrument-4.4.0-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:e4f5ad100710dda68f9f345961780bf4f0cbb9fd3e46295d099bb9ad65b179ea"}, - {file = "pyinstrument-4.4.0-cp311-cp311-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:9a4a053cd67102c6fcc313366ea6be97cfce7eae2b9e57e62c9be8adbbdebc17"}, - {file = "pyinstrument-4.4.0-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:1d2a1e53615c8ef210286e4d2d93be0d3e8296995b090df29a0b7ddeae5d874b"}, - {file = "pyinstrument-4.4.0-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:b2a6609ef74ad8ba292a11fbd975660bc86466c7eaab1ff11360d24e0300800b"}, - {file = "pyinstrument-4.4.0-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:3643084ee8ad22d9ea2adb13d65d4b6e18810113e4176b19d026a011957f8c7c"}, - {file = "pyinstrument-4.4.0-cp311-cp311-win32.whl", hash = "sha256:fcd717910a8ab6deca353aded890403bbaea14a6dd99a87c3367f24721d2d6aa"}, - {file = "pyinstrument-4.4.0-cp311-cp311-win_amd64.whl", hash = "sha256:be9ac54a4dd07d969d5941e4dcba67d5aef5f6826f43b9ddda65553816f6abca"}, - {file = "pyinstrument-4.4.0-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:39584c0fec147e3bbfa7b28454332f9801af5f93331f4143f24a4b0f9e3cb470"}, - {file = "pyinstrument-4.4.0-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:5491a5cb3ae5e88436d48b4b3de8328286e843e7307116dc2cca397c9c2ffe21"}, - {file = "pyinstrument-4.4.0-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:d66fcc94f0ebaab6bcbbdfa2482f833dd634352a20295616ea45286e990f7446"}, - {file = "pyinstrument-4.4.0-cp37-cp37m-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:b72bde0b1a03d1b2dc9b9d79546f551df6f67673cca816614e98ea0aebd3bc50"}, - {file = "pyinstrument-4.4.0-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:0bbd169b92147ec5d67ed160c300dda504059cfd81e953ed5b059e8ef92bb482"}, - {file = "pyinstrument-4.4.0-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:e5233022ba511ef7ecfef2e07d162c0817048c995f0940f9aa2f6a1936afcb9c"}, - {file = "pyinstrument-4.4.0-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:5e750fc3afb9acc288ad84b183a5ccd863e9185c435b445fcc62e0c133af9b7f"}, - {file = "pyinstrument-4.4.0-cp37-cp37m-win32.whl", hash = "sha256:2d131b98f116fb895d759dfb8c1078e0e9fa8987a9f44f566d29221545f75bd4"}, - {file = "pyinstrument-4.4.0-cp37-cp37m-win_amd64.whl", hash = "sha256:de83152bafc9eed4e5469e340b6002be825151f0654c32bbb9a3a7e31708d227"}, - {file = "pyinstrument-4.4.0-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:a7c774c4b8df21664b082d3e72fa8cbc0631fe9bb222bb9d285ccfe9cd9b4909"}, - {file = "pyinstrument-4.4.0-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:7526f0b1dab721ddc19920fa1f4eeaa5bcb658a4d18ac9c50868e84f911f794b"}, - {file = "pyinstrument-4.4.0-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:59f5f479db277b3dbeb0c6843a7e9a38ee8b7c23d75b9ef764d96cb522d96212"}, - {file = "pyinstrument-4.4.0-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:ffeeaa0d036a8bef31da6fc13c4ea097160f913d86319897314113bb9271af4c"}, - {file = "pyinstrument-4.4.0-cp38-cp38-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:bfc4e2fd670a570ea847f6897283d10d4b9606170e491f01b75488ed1aa37a81"}, - {file = "pyinstrument-4.4.0-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:ffd9a9fa73fd83a40252430c6ebf8dfff7c668cc68eab4a92562b8b27c302598"}, - {file = "pyinstrument-4.4.0-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:09167ece8802bc03a63e97536dcefd9c1a340dae686f40914cf995099bc0d0af"}, - {file = "pyinstrument-4.4.0-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:9e7d1cc3affef4a7e4695bb87c6cfcd577e2dac508624a91481f24217ef78c57"}, - {file = "pyinstrument-4.4.0-cp38-cp38-win32.whl", hash = "sha256:b50cf50513a5318738c3c7147f02596cda4891089acf2f627bb65954fc5bcbfd"}, - {file = "pyinstrument-4.4.0-cp38-cp38-win_amd64.whl", hash = "sha256:dd9625cf136eb6684d9ca555a5088f21a7ac6c6cb2ece3ae45d09772906ceba8"}, - {file = "pyinstrument-4.4.0-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:a8afee175335005d2964848b77579bfc18f011ea74b59b79ab6d5b35433bf3e3"}, - {file = "pyinstrument-4.4.0-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:ebc63b70845e3a44b673f7dcdc78ac2c475684db41b0402eea370f194da2a287"}, - {file = "pyinstrument-4.4.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:bb89033e41e74dc2ac4fd882269e91ddf677588efa665d2be8b718e96ea4cec6"}, - {file = "pyinstrument-4.4.0-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:9b2bcd803d273c8addf01eaf75a42ae0a2a9196a58fb0ebb8d29be75abb88701"}, - {file = "pyinstrument-4.4.0-cp39-cp39-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:50727b686a0961a11eba2fe6205d0899f3479c983bcf34abb114d6da70bc1b93"}, - {file = "pyinstrument-4.4.0-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:4f07941bb5dd5cd730fc84eef6497ef9f0807c686e68d0c6b1f464589646a3b7"}, - {file = "pyinstrument-4.4.0-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:30f5ce299c3219559870117c5b0825f33243808be375be9c3525572ba050c2db"}, - {file = "pyinstrument-4.4.0-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:9a13c75b24bf8eed5a4356ffa8a419cc534284a529f2b314f3e10275a820420f"}, - {file = "pyinstrument-4.4.0-cp39-cp39-win32.whl", hash = "sha256:e5583b0d23f87631af06bb9f3c184190c889c194b02553eed132de966324bdf9"}, - {file = "pyinstrument-4.4.0-cp39-cp39-win_amd64.whl", hash = "sha256:a19784a898133b7e0ffe4489155bacd2d07ec48ea059f9bf50033dc2b814c273"}, - {file = "pyinstrument-4.4.0.tar.gz", hash = "sha256:be34a2e8118c14a616a64538e02430d9099d5d67d8a370f2888e4ac71e52bbb7"}, + {file = "pyinstrument-4.5.0-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:b2f0a36c6edc1c1531f270aec9846b48304de19aea7fb819733d438a6fb4bf2e"}, + {file = "pyinstrument-4.5.0-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:0d8122041f997274d64d0c78d183a4be2337a97bfb9fbec84c1ed8c9ba68265f"}, + {file = "pyinstrument-4.5.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:94f061f3459cb9c509e57273ed6551e37d2d0c8cce0c327b1c8d5cbbc8fb9ddc"}, + {file = "pyinstrument-4.5.0-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:f8ae4434c6b1552e36f32b19e7d3f9fc5c5dc246178adce049f027c4ebb28a98"}, + {file = "pyinstrument-4.5.0-cp310-cp310-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:b6b3071525ca0a7cea708d5ada359dad3561ed272dc58ec9027d46e1b3e11266"}, + {file = "pyinstrument-4.5.0-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:dcf4fd5c6e11d1ba42ec91ecaf97970c59c50bd07b4208f6cdbc1b16d635c130"}, + {file = "pyinstrument-4.5.0-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:8543f2f1ed205e6578459b434ceeeba03ef841108d648b74b27e4e99c91fe439"}, + {file = "pyinstrument-4.5.0-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:53c9ab55fbf73f30a71dae43a2cc6a8733b22e29007091eae65a9b468648597b"}, + {file = "pyinstrument-4.5.0-cp310-cp310-win32.whl", hash = "sha256:ac631d289f271e284052dad3b008a0abcb2a2da72c5de72eb8d56841d6942f15"}, + {file = "pyinstrument-4.5.0-cp310-cp310-win_amd64.whl", hash = "sha256:ec68f7d63c218e998aba55c40fc9cbd4132675ef1ae9b652dce58134e722c229"}, + {file = "pyinstrument-4.5.0-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:e06159e0ecd013e352e4905b4342e71e71b630b77078503979679355a4a77c33"}, + {file = "pyinstrument-4.5.0-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:0922ece1ef965215f912e7b4218cf24b385763ccbb2cbdbb41b2b35826410310"}, + {file = "pyinstrument-4.5.0-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:83f9dd0d581e3b22ee47d1f076037b6ce0cd891fad1f09121ba8638436f1b760"}, + {file = "pyinstrument-4.5.0-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:af29ed2cd39d838473a81c9e40eccc7b8e1ab09acac743f54b80f62728fa4de3"}, + {file = "pyinstrument-4.5.0-cp311-cp311-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:e15ede05892a2273ac062538f7d62136bcfedda0983d3554cf67c2d52a7c9dd9"}, + {file = "pyinstrument-4.5.0-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:385dfbfceee954e90febeed89f89570f27b0956f05cec5d206efa082efcf5acd"}, + {file = "pyinstrument-4.5.0-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:eab6064f3abb9802449bf446a36502399c04714b6b81354fddc8bcae13f82376"}, + {file = "pyinstrument-4.5.0-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:a53fb221e7a7f8658c2cc1afc242158cf721d4f68ba67189524ab0aae61cca12"}, + {file = "pyinstrument-4.5.0-cp311-cp311-win32.whl", hash = "sha256:f736cba0b250cc288571a4b1edf331194eefd36ca06c55ba987a2fcc30ead826"}, + {file = "pyinstrument-4.5.0-cp311-cp311-win_amd64.whl", hash = "sha256:976bc13f2dee5a0a0b065b7695329634496b25574467d0d76285994360186371"}, + {file = "pyinstrument-4.5.0-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:58f538be679f55b9a2ce13e39d6c07c41683c23e37cac40d9a0789d6bc137d35"}, + {file = "pyinstrument-4.5.0-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:5bd24aeebcff18f5ef08961ece3c04bcffaba2ad55ffd243fd04c908b4a17674"}, + {file = "pyinstrument-4.5.0-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:b33a63c5e291b2a2e073803ee6686f5be8536c84688969eeec67608ef76ebca1"}, + {file = "pyinstrument-4.5.0-cp37-cp37m-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:9a9f4164c1534c04f07add30fd2e61f94ea0c68ae8bf082bd83655cb6c15a258"}, + {file = "pyinstrument-4.5.0-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:ca1094ad94d155e709ab8622728ced9a7d19091d346dd18720d8e8ad83ccaf58"}, + {file = "pyinstrument-4.5.0-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:261356a7c47fa0d7da58349112e9e06761674a6dd99f08fc71ba672c01bf7f7c"}, + {file = "pyinstrument-4.5.0-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:c948fd93c215042770c3d0d3d72746720dac26fed6e539020f5c7ad18be953ea"}, + {file = "pyinstrument-4.5.0-cp37-cp37m-win32.whl", hash = "sha256:e1ff10704ec28646ec37f972981763a45a718215b6bd9ff4bc30bafd0887acbb"}, + {file = "pyinstrument-4.5.0-cp37-cp37m-win_amd64.whl", hash = "sha256:c880ea33fa5c2c5bbdfa6d896b7addf31bea8967e4d4c85ec921f7d052749e10"}, + {file = "pyinstrument-4.5.0-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:ab0187c10fee5bf539bf9ba0ab4c081dac50a767a88c7f9e708c4fd0342e06aa"}, + {file = "pyinstrument-4.5.0-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:2e98bf17f7d919dba2494fa6af3bc1704ba704a0adad37e80908a317371ee29d"}, + {file = "pyinstrument-4.5.0-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:876c915ac51ed4b69e8a6d6867f7bc8a02929b32dafb73e2c4ce4c8f06ac260c"}, + {file = "pyinstrument-4.5.0-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:05690e3dfff1ffca38da15f6fdcc8231e7931e92abeb32f36f64785cfc1dca83"}, + {file = "pyinstrument-4.5.0-cp38-cp38-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:20589781fb8245fc9a1654ae46eca8c900d32a14923c947ba32398f8afd8fd1c"}, + {file = "pyinstrument-4.5.0-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:e31b9adf6914ad1f2fb0debd04d2968cd12770dfa7903c0cc7bfc88a7faca0d6"}, + {file = "pyinstrument-4.5.0-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:33039688c0fadf132e70273657e9a4e30c22b648d2f9732c4711ced8a441c650"}, + {file = "pyinstrument-4.5.0-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:fc9e6a617847b4e3d7b59a1e6f252d326703e8719891fc52efee83f56f065c80"}, + {file = "pyinstrument-4.5.0-cp38-cp38-win32.whl", hash = "sha256:57febfcfc61d54c117edb432a939fe974eecd49e4da9711efaa927e61a548fdd"}, + {file = "pyinstrument-4.5.0-cp38-cp38-win_amd64.whl", hash = "sha256:488859b9ea05c36c99c48efcd02f7f781b1fa54b8d09a1f5eda96fdfb9e0356c"}, + {file = "pyinstrument-4.5.0-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:078bbbea6e626da73c38ec6692720a7f7b79a2e7fb6536861e26687f58f5f707"}, + {file = "pyinstrument-4.5.0-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:04e9b88131c1b4bd9917aab2dd4fd47468598cbf719448710f1a6d51bdc295d8"}, + {file = "pyinstrument-4.5.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:63f1c1cf89536fc2084179c69fa65414fc018d1a3e48039f8cb6ff82b278ea28"}, + {file = "pyinstrument-4.5.0-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:4ca55eee67a7a93bd2c24625da312dddf5c4ae6fa5ba59ba0f908e1bf24a84bd"}, + {file = "pyinstrument-4.5.0-cp39-cp39-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:1309b6211ac1ddce56cda9e870c42d9d08ba51930c9d07505179435869c4db16"}, + {file = "pyinstrument-4.5.0-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:bc78253cd2a203812d70a7637b045a6d00b68c4035ad73edf0e03f6828c465f5"}, + {file = "pyinstrument-4.5.0-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:0f122fd1f93a5db81a2acc05b56525b7c197a31e271fe2ae151d242ff599fcb8"}, + {file = "pyinstrument-4.5.0-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:2a7d941df6d433662311cf6ad267b7782d30f78651ce34f3132539d5a7d65e0c"}, + {file = "pyinstrument-4.5.0-cp39-cp39-win32.whl", hash = "sha256:14e2c5f176babd747b4d2fb17c00de36fcbc91fa5e9a4152fb09cf9e19364f18"}, + {file = "pyinstrument-4.5.0-cp39-cp39-win_amd64.whl", hash = "sha256:c28e2f82aedf35686cf95c7d5366a65cf54ef92490307de1ab38efe7b727e997"}, + {file = "pyinstrument-4.5.0.tar.gz", hash = "sha256:ce01c7304b76932761c2be3d998f08b1863fd409a3709851e48af6cc0dc10eb2"}, ] [package.extras] @@ -3506,4 +3506,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "b5e117bca8d584f9bc17264e98bb11189554e845c258214e1324c0655bf6de34" +content-hash = "56e6b9b557b76f6b5c4a03a0063e5ee5a0d8226078a6f5fb3a547c4b38fca406" diff --git a/pyproject.toml b/pyproject.toml index eea96b9f..f6c53ce6 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -31,7 +31,7 @@ pytest-cov = "^4.1.0" [tool.poetry.group.dev.dependencies] pre-commit = "^3.3.2" -pyinstrument = "^4.4.0" +pyinstrument = "^4.5.0" pyright = "^1.1.311" watchfiles = "^0.19.0" jishaku = "^2.5.1" From 570ed0b5c750f035fbb18f0128bdec87719acf02 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 7 Jun 2023 19:04:27 +0000 Subject: [PATCH 084/184] [pip](deps-dev): Bump ruff from 0.0.270 to 0.0.271 (#343) Bumps [ruff](https://github.com/charliermarsh/ruff) from 0.0.270 to 0.0.271. - [Release notes](https://github.com/charliermarsh/ruff/releases) - [Changelog](https://github.com/charliermarsh/ruff/blob/main/BREAKING_CHANGES.md) - [Commits](https://github.com/charliermarsh/ruff/compare/v0.0.270...v0.0.271) --- updated-dependencies: - dependency-name: ruff dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 38 +++++++++++++++++++------------------- pyproject.toml | 2 +- 2 files changed, 20 insertions(+), 20 deletions(-) diff --git a/poetry.lock b/poetry.lock index 407be1a7..5b00eb2e 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2835,29 +2835,29 @@ idna2008 = ["idna"] [[package]] name = "ruff" -version = "0.0.270" +version = "0.0.271" description = "An extremely fast Python linter, written in Rust." category = "dev" optional = false python-versions = ">=3.7" files = [ - {file = "ruff-0.0.270-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:f74c4d550f7b8e808455ac77bbce38daafc458434815ba0bc21ae4bdb276509b"}, - {file = "ruff-0.0.270-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:643de865fd35cb76c4f0739aea5afe7b8e4d40d623df7e9e6ea99054e5cead0a"}, - {file = "ruff-0.0.270-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:eca02e709b3308eb7255b5f74e779be23b5980fca3862eae28bb23069cd61ae4"}, - {file = "ruff-0.0.270-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:3ed3b198768d2b3a2300fb18f730cd39948a5cc36ba29ae9d4639a11040880be"}, - {file = "ruff-0.0.270-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:739495d2dbde87cf4e3110c8d27bc20febf93112539a968a4e02c26f0deccd1d"}, - {file = "ruff-0.0.270-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:08188f8351f4c0b6216e8463df0a76eb57894ca59a3da65e4ed205db980fd3ae"}, - {file = "ruff-0.0.270-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:0827b074635d37984fc98d99316bfab5c8b1231bb83e60dacc83bd92883eedb4"}, - {file = "ruff-0.0.270-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:0d61ae4841313f6eeb8292dc349bef27b4ce426e62c36e80ceedc3824e408734"}, - {file = "ruff-0.0.270-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:0eb412f20e77529a01fb94d578b19dcb8331b56f93632aa0cce4a2ea27b7aeba"}, - {file = "ruff-0.0.270-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:b775e2c5fc869359daf8c8b8aa0fd67240201ab2e8d536d14a0edf279af18786"}, - {file = "ruff-0.0.270-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:21f00e47ab2308617c44435c8dfd9e2e03897461c9e647ec942deb2a235b4cfd"}, - {file = "ruff-0.0.270-py3-none-musllinux_1_2_i686.whl", hash = "sha256:0bbfbf6fd2436165566ca85f6e57be03ed2f0a994faf40180cfbb3604c9232ef"}, - {file = "ruff-0.0.270-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:8af391ef81f7be960be10886a3c1aac0b298bde7cb9a86ec2b05faeb2081ce6b"}, - {file = "ruff-0.0.270-py3-none-win32.whl", hash = "sha256:b4c037fe2f75bcd9aed0c89c7c507cb7fa59abae2bd4c8b6fc331a28178655a4"}, - {file = "ruff-0.0.270-py3-none-win_amd64.whl", hash = "sha256:0012f9b7dc137ab7f1f0355e3c4ca49b562baf6c9fa1180948deeb6648c52957"}, - {file = "ruff-0.0.270-py3-none-win_arm64.whl", hash = "sha256:9613456b0b375766244c25045e353bc8890c856431cd97893c97b10cc93bd28d"}, - {file = "ruff-0.0.270.tar.gz", hash = "sha256:95db07b7850b30ebf32b27fe98bc39e0ab99db3985edbbf0754d399eb2f0e690"}, + {file = "ruff-0.0.271-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:1a627978df924635f7d1a169a98abb2ea488c2d409da56a3f9e44a82d30606ac"}, + {file = "ruff-0.0.271-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:f47d8a192f6869e95896dc5bb7e825a4f9c554136b9c3bddd38389e43d4db08b"}, + {file = "ruff-0.0.271-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:9e5de841e09ea75a26956a2cda930d1260c9d8d94cbe57c13b3e881d96526860"}, + {file = "ruff-0.0.271-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:191cdddfc82165afd63ab29ad671419a90a5e699b026ac2d9c61232543965de6"}, + {file = "ruff-0.0.271-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:7e34ca86329a542ab5d31f4fc2702f556d62748f4217e2f6951aef93176190f0"}, + {file = "ruff-0.0.271-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:7543b8a32e000ed30727ca6e570a90ab26f8899ee23dffb28806dfc2618782fb"}, + {file = "ruff-0.0.271-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:fca503741f4b23a7179fd7a9bc50fc2cca637e9a4da027776f38690c50ae559f"}, + {file = "ruff-0.0.271-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:f445c56cdc8c12fc28a0b16588ba33abebb6340cb5b1b5a7d5668d4c0b31ad33"}, + {file = "ruff-0.0.271-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5a73ffda5548ea8e28e0afcfa698a8675bb17f7048299327f4c1a1287b6e36a2"}, + {file = "ruff-0.0.271-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:67525aa821ff0f8371eaa28c73dc467b8eea18931a8bd749775ad538fe1f35e6"}, + {file = "ruff-0.0.271-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:f3fd9e7c7afb7740d2734af3348e6c88226b42acba2e10a3d1e449caa67e4652"}, + {file = "ruff-0.0.271-py3-none-musllinux_1_2_i686.whl", hash = "sha256:efdfe7fea656eb2ed54f123135c04f71744ad6e4c0c6be156d46e7a2f4730d48"}, + {file = "ruff-0.0.271-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:cd43c1aff3eefb2193a125a12124438f65a8d1a6da0e86f8545141d48f6a39fa"}, + {file = "ruff-0.0.271-py3-none-win32.whl", hash = "sha256:403e8f9de18b2279d65015a45e0e0d98d60ad878d52f46904f502a4d09465815"}, + {file = "ruff-0.0.271-py3-none-win_amd64.whl", hash = "sha256:140e912a18a662062b04b489861e5aebdbe1a1668bf416e5a951f2347aa65907"}, + {file = "ruff-0.0.271-py3-none-win_arm64.whl", hash = "sha256:45b3c3551a798d9786779c6dd7ad2224af6e06162e17f4a0e7678d3e9115ae56"}, + {file = "ruff-0.0.271.tar.gz", hash = "sha256:be4590137a31c47e7f6ef4488d60102c68102f842453355d8073193a30199aa7"}, ] [[package]] @@ -3506,4 +3506,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "56e6b9b557b76f6b5c4a03a0063e5ee5a0d8226078a6f5fb3a547c4b38fca406" +content-hash = "da28e7027e27bf41fdbbef942a31ecf490d98fb1f71ef6aee21dd0b7b82b165a" diff --git a/pyproject.toml b/pyproject.toml index f6c53ce6..4ff252fd 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -35,7 +35,7 @@ pyinstrument = "^4.5.0" pyright = "^1.1.311" watchfiles = "^0.19.0" jishaku = "^2.5.1" -ruff = "^0.0.270" +ruff = "^0.0.271" [tool.poetry.group.docs.dependencies] From 21b2b6114ef8a8551777ad359a573e5a0e447739 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 7 Jun 2023 21:33:11 +0000 Subject: [PATCH 085/184] [pip](deps-dev): Bump pyright from 1.1.311 to 1.1.313 (#344) Bumps [pyright](https://github.com/RobertCraigie/pyright-python) from 1.1.311 to 1.1.313. - [Release notes](https://github.com/RobertCraigie/pyright-python/releases) - [Commits](https://github.com/RobertCraigie/pyright-python/compare/v1.1.311...v1.1.313) --- updated-dependencies: - dependency-name: pyright dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index 5b00eb2e..d9a43ea2 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2603,14 +2603,14 @@ diagrams = ["jinja2", "railroad-diagrams"] [[package]] name = "pyright" -version = "1.1.311" +version = "1.1.313" description = "Command line wrapper for pyright" category = "dev" optional = false python-versions = ">=3.7" files = [ - {file = "pyright-1.1.311-py3-none-any.whl", hash = "sha256:04df30c6b31d05068effe5563411291c876f5e4221d0af225a267b61dce1ca85"}, - {file = "pyright-1.1.311.tar.gz", hash = "sha256:554b555d3f770e8da2e76d6bb94e2ac63b3edc7dcd5fb8de202f9dd53e36689a"}, + {file = "pyright-1.1.313-py3-none-any.whl", hash = "sha256:1aeed72d5563e97461cb9d17847bfa918f7ec0cf79912bb3d2432fbe014daa23"}, + {file = "pyright-1.1.313.tar.gz", hash = "sha256:95fa963337e2cfd4900601197d0f866d8c51732dea6c0bb12f962f92a79c77e3"}, ] [package.dependencies] @@ -3506,4 +3506,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "da28e7027e27bf41fdbbef942a31ecf490d98fb1f71ef6aee21dd0b7b82b165a" +content-hash = "4c9e8c3456cba72d99da8ec2d03d6dc77dd8e566ec9fe408cd131c96f486f448" diff --git a/pyproject.toml b/pyproject.toml index 4ff252fd..58295baa 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -32,7 +32,7 @@ pytest-cov = "^4.1.0" [tool.poetry.group.dev.dependencies] pre-commit = "^3.3.2" pyinstrument = "^4.5.0" -pyright = "^1.1.311" +pyright = "^1.1.313" watchfiles = "^0.19.0" jishaku = "^2.5.1" ruff = "^0.0.271" From 038a222103b0a047327b3d778df2044112a8b9aa Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Thu, 8 Jun 2023 19:02:05 +0000 Subject: [PATCH 086/184] [pip](deps-dev): Bump ruff from 0.0.271 to 0.0.272 (#345) Bumps [ruff](https://github.com/charliermarsh/ruff) from 0.0.271 to 0.0.272. - [Release notes](https://github.com/charliermarsh/ruff/releases) - [Changelog](https://github.com/astral-sh/ruff/blob/main/BREAKING_CHANGES.md) - [Commits](https://github.com/charliermarsh/ruff/compare/v0.0.271...v0.0.272) --- updated-dependencies: - dependency-name: ruff dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 38 +++++++++++++++++++------------------- pyproject.toml | 2 +- 2 files changed, 20 insertions(+), 20 deletions(-) diff --git a/poetry.lock b/poetry.lock index d9a43ea2..bf2893b1 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2835,29 +2835,29 @@ idna2008 = ["idna"] [[package]] name = "ruff" -version = "0.0.271" +version = "0.0.272" description = "An extremely fast Python linter, written in Rust." category = "dev" optional = false python-versions = ">=3.7" files = [ - {file = "ruff-0.0.271-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:1a627978df924635f7d1a169a98abb2ea488c2d409da56a3f9e44a82d30606ac"}, - {file = "ruff-0.0.271-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:f47d8a192f6869e95896dc5bb7e825a4f9c554136b9c3bddd38389e43d4db08b"}, - {file = "ruff-0.0.271-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:9e5de841e09ea75a26956a2cda930d1260c9d8d94cbe57c13b3e881d96526860"}, - {file = "ruff-0.0.271-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:191cdddfc82165afd63ab29ad671419a90a5e699b026ac2d9c61232543965de6"}, - {file = "ruff-0.0.271-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:7e34ca86329a542ab5d31f4fc2702f556d62748f4217e2f6951aef93176190f0"}, - {file = "ruff-0.0.271-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:7543b8a32e000ed30727ca6e570a90ab26f8899ee23dffb28806dfc2618782fb"}, - {file = "ruff-0.0.271-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:fca503741f4b23a7179fd7a9bc50fc2cca637e9a4da027776f38690c50ae559f"}, - {file = "ruff-0.0.271-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:f445c56cdc8c12fc28a0b16588ba33abebb6340cb5b1b5a7d5668d4c0b31ad33"}, - {file = "ruff-0.0.271-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5a73ffda5548ea8e28e0afcfa698a8675bb17f7048299327f4c1a1287b6e36a2"}, - {file = "ruff-0.0.271-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:67525aa821ff0f8371eaa28c73dc467b8eea18931a8bd749775ad538fe1f35e6"}, - {file = "ruff-0.0.271-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:f3fd9e7c7afb7740d2734af3348e6c88226b42acba2e10a3d1e449caa67e4652"}, - {file = "ruff-0.0.271-py3-none-musllinux_1_2_i686.whl", hash = "sha256:efdfe7fea656eb2ed54f123135c04f71744ad6e4c0c6be156d46e7a2f4730d48"}, - {file = "ruff-0.0.271-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:cd43c1aff3eefb2193a125a12124438f65a8d1a6da0e86f8545141d48f6a39fa"}, - {file = "ruff-0.0.271-py3-none-win32.whl", hash = "sha256:403e8f9de18b2279d65015a45e0e0d98d60ad878d52f46904f502a4d09465815"}, - {file = "ruff-0.0.271-py3-none-win_amd64.whl", hash = "sha256:140e912a18a662062b04b489861e5aebdbe1a1668bf416e5a951f2347aa65907"}, - {file = "ruff-0.0.271-py3-none-win_arm64.whl", hash = "sha256:45b3c3551a798d9786779c6dd7ad2224af6e06162e17f4a0e7678d3e9115ae56"}, - {file = "ruff-0.0.271.tar.gz", hash = "sha256:be4590137a31c47e7f6ef4488d60102c68102f842453355d8073193a30199aa7"}, + {file = "ruff-0.0.272-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:ae9b57546e118660175d45d264b87e9b4c19405c75b587b6e4d21e6a17bf4fdf"}, + {file = "ruff-0.0.272-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:1609b864a8d7ee75a8c07578bdea0a7db75a144404e75ef3162e0042bfdc100d"}, + {file = "ruff-0.0.272-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ee76b4f05fcfff37bd6ac209d1370520d509ea70b5a637bdf0a04d0c99e13dff"}, + {file = "ruff-0.0.272-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:48eccf225615e106341a641f826b15224b8a4240b84269ead62f0afd6d7e2d95"}, + {file = "ruff-0.0.272-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:677284430ac539bb23421a2b431b4ebc588097ef3ef918d0e0a8d8ed31fea216"}, + {file = "ruff-0.0.272-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:9c4bfb75456a8e1efe14c52fcefb89cfb8f2a0d31ed8d804b82c6cf2dc29c42c"}, + {file = "ruff-0.0.272-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:86bc788245361a8148ff98667da938a01e1606b28a45e50ac977b09d3ad2c538"}, + {file = "ruff-0.0.272-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:27b2ea68d2aa69fff1b20b67636b1e3e22a6a39e476c880da1282c3e4bf6ee5a"}, + {file = "ruff-0.0.272-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:bd2bbe337a3f84958f796c77820d55ac2db1e6753f39d1d1baed44e07f13f96d"}, + {file = "ruff-0.0.272-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:d5a208f8ef0e51d4746930589f54f9f92f84bb69a7d15b1de34ce80a7681bc00"}, + {file = "ruff-0.0.272-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:905ff8f3d6206ad56fcd70674453527b9011c8b0dc73ead27618426feff6908e"}, + {file = "ruff-0.0.272-py3-none-musllinux_1_2_i686.whl", hash = "sha256:19643d448f76b1eb8a764719072e9c885968971bfba872e14e7257e08bc2f2b7"}, + {file = "ruff-0.0.272-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:691d72a00a99707a4e0b2846690961157aef7b17b6b884f6b4420a9f25cd39b5"}, + {file = "ruff-0.0.272-py3-none-win32.whl", hash = "sha256:dc406e5d756d932da95f3af082814d2467943631a587339ee65e5a4f4fbe83eb"}, + {file = "ruff-0.0.272-py3-none-win_amd64.whl", hash = "sha256:a37ec80e238ead2969b746d7d1b6b0d31aa799498e9ba4281ab505b93e1f4b28"}, + {file = "ruff-0.0.272-py3-none-win_arm64.whl", hash = "sha256:06b8ee4eb8711ab119db51028dd9f5384b44728c23586424fd6e241a5b9c4a3b"}, + {file = "ruff-0.0.272.tar.gz", hash = "sha256:273a01dc8c3c4fd4c2af7ea7a67c8d39bb09bce466e640dd170034da75d14cab"}, ] [[package]] @@ -3506,4 +3506,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "4c9e8c3456cba72d99da8ec2d03d6dc77dd8e566ec9fe408cd131c96f486f448" +content-hash = "4bbed27639da457de9b9d94df10df12de946a5515e33e9da593fac9ac7f6fe8a" diff --git a/pyproject.toml b/pyproject.toml index 58295baa..123329da 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -35,7 +35,7 @@ pyinstrument = "^4.5.0" pyright = "^1.1.313" watchfiles = "^0.19.0" jishaku = "^2.5.1" -ruff = "^0.0.271" +ruff = "^0.0.272" [tool.poetry.group.docs.dependencies] From 7fc374b1838f1808e8a92fa186e07455a1b9bebd Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Fri, 9 Jun 2023 18:58:37 +0000 Subject: [PATCH 087/184] [Actions](deps): Bump docker/build-push-action from 4.0.0 to 4.1.0 (#346) Bumps [docker/build-push-action](https://github.com/docker/build-push-action) from 4.0.0 to 4.1.0. - [Release notes](https://github.com/docker/build-push-action/releases) - [Commits](https://github.com/docker/build-push-action/compare/v4.0.0...v4.1.0) --- updated-dependencies: - dependency-name: docker/build-push-action dependency-type: direct:production update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- .github/workflows/docker-build.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/docker-build.yml b/.github/workflows/docker-build.yml index 626909ad..6afd705d 100644 --- a/.github/workflows/docker-build.yml +++ b/.github/workflows/docker-build.yml @@ -56,7 +56,7 @@ jobs: restore-keys: | ${{ runner.os }}-buildx-debian-ghcr- - name: Build and push - uses: docker/build-push-action@v4.0.0 + uses: docker/build-push-action@v4.1.0 with: context: . file: ./Docker/Dockerfile @@ -116,7 +116,7 @@ jobs: ${{ runner.os }}-buildx-debian-hub- - name: Build and push - uses: docker/build-push-action@v4.0.0 + uses: docker/build-push-action@v4.1.0 with: context: . file: ./Docker/Dockerfile From 93d4f83a567029a3812aa035c01f7e42dc84528f Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Fri, 9 Jun 2023 19:00:31 +0000 Subject: [PATCH 088/184] [pip](deps): Bump orjson from 3.9.0 to 3.9.1 (#347) Bumps [orjson](https://github.com/ijl/orjson) from 3.9.0 to 3.9.1. - [Release notes](https://github.com/ijl/orjson/releases) - [Changelog](https://github.com/ijl/orjson/blob/master/CHANGELOG.md) - [Commits](https://github.com/ijl/orjson/compare/3.9.0...3.9.1) --- updated-dependencies: - dependency-name: orjson dependency-type: direct:production update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 235 ++++++++++++------------------------------------- pyproject.toml | 2 +- 2 files changed, 56 insertions(+), 181 deletions(-) diff --git a/poetry.lock b/poetry.lock index bf2893b1..6547bd68 100644 --- a/poetry.lock +++ b/poetry.lock @@ -1,10 +1,9 @@ -# This file is automatically @generated by Poetry and should not be changed by hand. +# This file is automatically @generated by Poetry 1.5.1 and should not be changed by hand. [[package]] name = "aiodns" version = "3.0.0" description = "Simple DNS resolver for asyncio" -category = "main" optional = false python-versions = "*" files = [ @@ -19,7 +18,6 @@ pycares = ">=4.0.0" name = "aiofiles" version = "0.8.0" description = "File support for asyncio." -category = "main" optional = false python-versions = ">=3.6,<4.0" files = [ @@ -31,7 +29,6 @@ files = [ name = "aiohttp" version = "3.8.4" description = "Async http client/server framework (asyncio)" -category = "main" optional = false python-versions = ">=3.6" files = [ @@ -140,7 +137,6 @@ speedups = ["Brotli", "aiodns", "cchardet"] name = "aiosignal" version = "1.3.1" description = "aiosignal: a list of registered asynchronous callbacks" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -155,7 +151,6 @@ frozenlist = ">=1.1.0" name = "aiosqlite" version = "0.17.0" description = "asyncio bridge to the standard sqlite3 module" -category = "main" optional = false python-versions = ">=3.6" files = [ @@ -170,7 +165,6 @@ typing_extensions = ">=3.7.2" name = "alabaster" version = "0.7.13" description = "A configurable sidebar-enabled Sphinx theme" -category = "dev" optional = false python-versions = ">=3.6" files = [ @@ -182,7 +176,6 @@ files = [ name = "anyio" version = "3.6.2" description = "High level compatibility layer for multiple asynchronous event loop implementations" -category = "main" optional = false python-versions = ">=3.6.2" files = [ @@ -203,7 +196,6 @@ trio = ["trio (>=0.16,<0.22)"] name = "argcomplete" version = "2.0.0" description = "Bash tab completion for argparse" -category = "dev" optional = false python-versions = ">=3.6" files = [ @@ -218,7 +210,6 @@ test = ["coverage", "flake8", "pexpect", "wheel"] name = "astunparse" version = "1.6.3" description = "An AST unparser for Python" -category = "dev" optional = false python-versions = "*" files = [ @@ -234,7 +225,6 @@ wheel = ">=0.23.0,<1.0" name = "async-generator" version = "1.10" description = "Async generators and context managers for Python 3.5+" -category = "main" optional = false python-versions = ">=3.5" files = [ @@ -246,7 +236,6 @@ files = [ name = "async-timeout" version = "4.0.2" description = "Timeout context manager for asyncio programs" -category = "main" optional = false python-versions = ">=3.6" files = [ @@ -258,7 +247,6 @@ files = [ name = "asyncio-extras" version = "1.3.2" description = "Asynchronous generators, context managers and more for asyncio" -category = "main" optional = false python-versions = "*" files = [ @@ -277,7 +265,6 @@ test = ["pytest", "pytest-asyncio", "pytest-cov"] name = "asyncpraw" version = "7.7.0" description = "Async PRAW, an abbreviation for \"Asynchronous Python Reddit API Wrapper\", is a python package that allows for simple access to Reddit's API." -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -295,16 +282,15 @@ update-checker = ">=0.18" [package.extras] ci = ["coveralls"] -dev = ["asynctest (>=0.13.0,<0.14.0)", "mock (>=4.0.0,<5.0.0)", "packaging", "pre-commit", "pytest (>=7.0.0,<8.0.0)", "pytest-asyncio (>=0.18.0,<0.19.0)", "pytest-vcr (>=1.0.0,<2.0.0)", "sphinx", "sphinx-rtd-dark-mode", "sphinx-rtd-theme", "sphinxcontrib-trio", "testfixtures (>=6.0.0,<7.0.0)", "vcrpy (>=4.0.0,<5.0.0)"] +dev = ["asynctest (==0.13.*)", "mock (==4.*)", "packaging", "pre-commit", "pytest (==7.*)", "pytest-asyncio (==0.18.*)", "pytest-vcr (==1.*)", "sphinx", "sphinx-rtd-dark-mode", "sphinx-rtd-theme", "sphinxcontrib-trio", "testfixtures (==6.*)", "vcrpy (==4.*)"] lint = ["pre-commit", "sphinx", "sphinx-rtd-dark-mode", "sphinx-rtd-theme", "sphinxcontrib-trio"] readthedocs = ["sphinx", "sphinx-rtd-dark-mode", "sphinx-rtd-theme", "sphinxcontrib-trio"] -test = ["asynctest (>=0.13.0,<0.14.0)", "mock (>=4.0.0,<5.0.0)", "pytest (>=7.0.0,<8.0.0)", "pytest-asyncio (>=0.18.0,<0.19.0)", "pytest-vcr (>=1.0.0,<2.0.0)", "testfixtures (>=6.0.0,<7.0.0)", "vcrpy (>=4.0.0,<5.0.0)"] +test = ["asynctest (==0.13.*)", "mock (==4.*)", "pytest (==7.*)", "pytest-asyncio (==0.18.*)", "pytest-vcr (==1.*)", "testfixtures (==6.*)", "vcrpy (==4.*)"] [[package]] name = "asyncprawcore" version = "2.3.0" description = "Low-level asynchronous communication layer for Async PRAW 7+." -category = "main" optional = false python-versions = ">=3.6" files = [ @@ -326,7 +312,6 @@ test = ["asynctest (>=0.13.0)", "mock (>=0.8)", "pytest", "pytest-vcr", "testfix name = "attrs" version = "22.2.0" description = "Classes Without Boilerplate" -category = "main" optional = false python-versions = ">=3.6" files = [ @@ -345,7 +330,6 @@ tests-no-zope = ["cloudpickle", "cloudpickle", "hypothesis", "hypothesis", "mypy name = "babel" version = "2.12.1" description = "Internationalization utilities" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -360,7 +344,6 @@ pytz = {version = ">=2015.7", markers = "python_version < \"3.9\""} name = "backoff" version = "2.2.1" description = "Function decoration for backoff and retry" -category = "main" optional = false python-versions = ">=3.7,<4.0" files = [ @@ -372,7 +355,6 @@ files = [ name = "beautifulsoup4" version = "4.12.2" description = "Screen-scraping library" -category = "dev" optional = false python-versions = ">=3.6.0" files = [ @@ -391,7 +373,6 @@ lxml = ["lxml"] name = "better-ipc" version = "2.0.3" description = "A high-performance inter-process communication library designed to work with the latest version of discord.py" -category = "main" optional = false python-versions = ">=3.8.0" files = [ @@ -406,7 +387,6 @@ websockets = ">=10.4" name = "braceexpand" version = "0.1.7" description = "Bash-style brace expansion for Python" -category = "dev" optional = false python-versions = "*" files = [ @@ -418,7 +398,6 @@ files = [ name = "brotli" version = "1.0.9" description = "Python bindings for the Brotli compression library" -category = "main" optional = false python-versions = "*" files = [ @@ -510,7 +489,6 @@ files = [ name = "certifi" version = "2022.12.7" description = "Python package for providing Mozilla's CA Bundle." -category = "main" optional = false python-versions = ">=3.6" files = [ @@ -522,7 +500,6 @@ files = [ name = "cffi" version = "1.15.1" description = "Foreign Function Interface for Python calling C code." -category = "main" optional = false python-versions = "*" files = [ @@ -599,7 +576,6 @@ pycparser = "*" name = "cfgv" version = "3.3.1" description = "Validate configuration and produce human readable error messages." -category = "dev" optional = false python-versions = ">=3.6.1" files = [ @@ -611,7 +587,6 @@ files = [ name = "charset-normalizer" version = "3.1.0" description = "The Real First Universal Charset Detector. Open, modern and actively maintained alternative to Chardet." -category = "main" optional = false python-versions = ">=3.7.0" files = [ @@ -696,7 +671,6 @@ files = [ name = "ciso8601" version = "2.3.0" description = "Fast ISO8601 date time parser for Python written in C" -category = "main" optional = false python-versions = "*" files = [ @@ -751,7 +725,6 @@ files = [ name = "click" version = "8.1.3" description = "Composable command line interface toolkit" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -766,7 +739,6 @@ colorama = {version = "*", markers = "platform_system == \"Windows\""} name = "colorama" version = "0.4.6" description = "Cross-platform colored terminal text." -category = "main" optional = false python-versions = "!=3.0.*,!=3.1.*,!=3.2.*,!=3.3.*,!=3.4.*,!=3.5.*,!=3.6.*,>=2.7" files = [ @@ -778,7 +750,6 @@ files = [ name = "colorlog" version = "6.7.0" description = "Add colours to the output of Python's logging module." -category = "dev" optional = false python-versions = ">=3.6" files = [ @@ -796,7 +767,6 @@ development = ["black", "flake8", "mypy", "pytest", "types-colorama"] name = "contourpy" version = "1.0.7" description = "Python library for calculating contours of 2D quadrilateral grids" -category = "dev" optional = false python-versions = ">=3.8" files = [ @@ -871,7 +841,6 @@ test-no-images = ["pytest"] name = "coverage" version = "7.0.5" description = "Code coverage measurement for Python" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -938,7 +907,6 @@ toml = ["tomli"] name = "cycler" version = "0.11.0" description = "Composable style cycles" -category = "dev" optional = false python-versions = ">=3.6" files = [ @@ -950,7 +918,6 @@ files = [ name = "discord-ext-menus" version = "1.0.0a32+g8686b5d" description = "An extension module to make reaction based menus with discord.py" -category = "main" optional = false python-versions = ">=3.5.3" files = [] @@ -969,7 +936,6 @@ resolved_reference = "8686b5d1bbc1d3c862292eb436ab630d6e9c9b53" name = "discord-py" version = "2.2.3" description = "A Python wrapper for the Discord API" -category = "main" optional = false python-versions = ">=3.8.0" files = [ @@ -991,7 +957,6 @@ voice = ["PyNaCl (>=1.3.0,<1.6)"] name = "distlib" version = "0.3.6" description = "Distribution utilities" -category = "dev" optional = false python-versions = "*" files = [ @@ -1003,7 +968,6 @@ files = [ name = "docutils" version = "0.19" description = "Docutils -- Python Documentation Utilities" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1015,7 +979,6 @@ files = [ name = "exceptiongroup" version = "1.1.0" description = "Backport of PEP 654 (exception groups)" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1030,7 +993,6 @@ test = ["pytest (>=6)"] name = "faust-cchardet" version = "2.1.18" description = "cChardet is high speed universal character encoding detector." -category = "main" optional = false python-versions = "*" files = [ @@ -1093,7 +1055,6 @@ files = [ name = "filelock" version = "3.9.0" description = "A platform independent file lock." -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1109,7 +1070,6 @@ testing = ["covdefaults (>=2.2.2)", "coverage (>=7.0.1)", "pytest (>=7.2)", "pyt name = "fonttools" version = "4.39.3" description = "Tools to manipulate font files" -category = "dev" optional = false python-versions = ">=3.8" files = [ @@ -1135,7 +1095,6 @@ woff = ["brotli (>=1.0.1)", "brotlicffi (>=0.8.0)", "zopfli (>=0.1.4)"] name = "frozenlist" version = "1.3.3" description = "A list-like structure which implements collections.abc.MutableSequence" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -1219,7 +1178,6 @@ files = [ name = "furo" version = "2023.5.20" description = "A clean customisable Sphinx documentation theme." -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1237,7 +1195,6 @@ sphinx-basic-ng = "*" name = "gql" version = "3.4.1" description = "GraphQL client for Python" -category = "main" optional = false python-versions = "*" files = [ @@ -1265,7 +1222,6 @@ websockets = ["websockets (>=10,<11)", "websockets (>=9,<10)"] name = "graphql-core" version = "3.2.3" description = "GraphQL implementation for Python, a port of GraphQL.js, the JavaScript reference implementation for GraphQL." -category = "main" optional = false python-versions = ">=3.6,<4" files = [ @@ -1277,7 +1233,6 @@ files = [ name = "h11" version = "0.14.0" description = "A pure-Python, bring-your-own-I/O implementation of HTTP/1.1" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -1289,7 +1244,6 @@ files = [ name = "hiredis" version = "2.2.2" description = "Python wrapper for hiredis" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -1388,7 +1342,6 @@ files = [ name = "httpcore" version = "0.16.3" description = "A minimal low-level HTTP client." -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -1400,17 +1353,16 @@ files = [ anyio = ">=3.0,<5.0" certifi = "*" h11 = ">=0.13,<0.15" -sniffio = ">=1.0.0,<2.0.0" +sniffio = "==1.*" [package.extras] http2 = ["h2 (>=3,<5)"] -socks = ["socksio (>=1.0.0,<2.0.0)"] +socks = ["socksio (==1.*)"] [[package]] name = "httpx" version = "0.23.3" description = "The next generation HTTP client." -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -1426,15 +1378,14 @@ sniffio = "*" [package.extras] brotli = ["brotli", "brotlicffi"] -cli = ["click (>=8.0.0,<9.0.0)", "pygments (>=2.0.0,<3.0.0)", "rich (>=10,<13)"] +cli = ["click (==8.*)", "pygments (==2.*)", "rich (>=10,<13)"] http2 = ["h2 (>=3,<5)"] -socks = ["socksio (>=1.0.0,<2.0.0)"] +socks = ["socksio (==1.*)"] [[package]] name = "identify" version = "2.5.20" description = "File identification library for Python" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1449,7 +1400,6 @@ license = ["ukkonen"] name = "idna" version = "3.4" description = "Internationalized Domain Names in Applications (IDNA)" -category = "main" optional = false python-versions = ">=3.5" files = [ @@ -1461,7 +1411,6 @@ files = [ name = "imagesize" version = "1.4.1" description = "Getting image size from png/jpeg/jpeg2000/gif file" -category = "dev" optional = false python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*" files = [ @@ -1473,7 +1422,6 @@ files = [ name = "import-expression" version = "1.1.4" description = "Parses a superset of Python allowing for inline module import expressions" -category = "dev" optional = false python-versions = "*" files = [ @@ -1491,7 +1439,6 @@ test = ["pytest", "pytest-cov"] name = "importlib-metadata" version = "6.1.0" description = "Read metadata from Python packages" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1511,7 +1458,6 @@ testing = ["flake8 (<5)", "flufl.flake8", "importlib-resources (>=1.3)", "packag name = "importlib-resources" version = "5.12.0" description = "Read resources from Python packages" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1530,7 +1476,6 @@ testing = ["flake8 (<5)", "pytest (>=6)", "pytest-black (>=0.3.7)", "pytest-chec name = "iniconfig" version = "2.0.0" description = "brain-dead simple config-ini parsing" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1542,7 +1487,6 @@ files = [ name = "jinja2" version = "3.1.2" description = "A very fast and expressive template engine." -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -1560,7 +1504,6 @@ i18n = ["Babel (>=2.7)"] name = "jishaku" version = "2.5.1" description = "A discord.py extension including useful tools for bot development and debugging." -category = "dev" optional = false python-versions = ">=3.8.0" files = [ @@ -1588,7 +1531,6 @@ voice = ["yt-dlp (>=2022.3.8)"] name = "kiwisolver" version = "1.4.4" description = "A fast implementation of the Cassowary constraint solver" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1666,7 +1608,6 @@ files = [ name = "line-profiler" version = "4.0.3" description = "Line-by-line profiler" -category = "dev" optional = false python-versions = ">=3.6" files = [ @@ -1729,7 +1670,6 @@ tests-strict = ["IPython (==0.13)", "IPython (==0.13)", "coverage[toml] (==5.3)" name = "livereload" version = "2.6.3" description = "Python LiveReload is an awesome tool for web developers" -category = "dev" optional = false python-versions = "*" files = [ @@ -1745,7 +1685,6 @@ tornado = {version = "*", markers = "python_version > \"2.7\""} name = "markdown-it-py" version = "2.2.0" description = "Python port of markdown-it. Markdown parsing, done right!" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1770,7 +1709,6 @@ testing = ["coverage", "pytest", "pytest-cov", "pytest-regressions"] name = "markupsafe" version = "2.1.2" description = "Safely add untrusted strings to HTML/XML markup." -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -1830,7 +1768,6 @@ files = [ name = "matplotlib" version = "3.7.1" description = "Python plotting package" -category = "dev" optional = false python-versions = ">=3.8" files = [ @@ -1893,7 +1830,6 @@ python-dateutil = ">=2.7" name = "mdit-py-plugins" version = "0.3.5" description = "Collection of plugins for markdown-it-py" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1913,7 +1849,6 @@ testing = ["coverage", "pytest", "pytest-cov", "pytest-regressions"] name = "mdurl" version = "0.1.2" description = "Markdown URL utilities" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -1925,7 +1860,6 @@ files = [ name = "multidict" version = "6.0.4" description = "multidict implementation" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -2009,7 +1943,6 @@ files = [ name = "myst-parser" version = "1.0.0" description = "An extended [CommonMark](https://spec.commonmark.org/) compliant parser," -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2036,7 +1969,6 @@ testing-docutils = ["pygments", "pytest (>=7,<8)", "pytest-param-files (>=0.3.4, name = "nodeenv" version = "1.7.0" description = "Node.js virtual environment builder" -category = "main" optional = false python-versions = ">=2.7,!=3.0.*,!=3.1.*,!=3.2.*,!=3.3.*,!=3.4.*,!=3.5.*,!=3.6.*" files = [ @@ -2051,7 +1983,6 @@ setuptools = "*" name = "nox" version = "2023.4.22" description = "Flexible test automation." -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2072,7 +2003,6 @@ tox-to-nox = ["jinja2", "tox (<4)"] name = "nox-poetry" version = "1.0.2" description = "nox-poetry" -category = "dev" optional = false python-versions = ">=3.7,<4.0" files = [ @@ -2089,7 +2019,6 @@ tomlkit = ">=0.7" name = "numpy" version = "1.24.2" description = "Fundamental package for array computing in Python" -category = "dev" optional = false python-versions = ">=3.8" files = [ @@ -2125,65 +2054,63 @@ files = [ [[package]] name = "orjson" -version = "3.9.0" +version = "3.9.1" description = "Fast, correct Python JSON library supporting dataclasses, datetimes, and numpy" -category = "main" optional = false python-versions = ">=3.7" files = [ - {file = "orjson-3.9.0-cp310-cp310-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:128b1cd0f00a37ba64a12cceeba4e8070655d4400edd55a737513ee663c1ed5a"}, - {file = "orjson-3.9.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:7a3693fde44b2eeb80074ecbe8c504b25baf71e66c080af2a574193a5ba81960"}, - {file = "orjson-3.9.0-cp310-cp310-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:3f1193417b5a93deb41bcb8db27b61179b9b3e299b337b578c31f19159664da3"}, - {file = "orjson-3.9.0-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:88626d898c408450c57664899831cf072787898af4847fa4466607ad2a83f454"}, - {file = "orjson-3.9.0-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:1e3bde77c1e0061eb34bae6fea44818b2198e043ee10a16ad7b160921fee26ea"}, - {file = "orjson-3.9.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:45df5bf6531ffda518331cc93cdcd4c84f4a4a0507d72af8fb698c7131a440a0"}, - {file = "orjson-3.9.0-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:2536a7f30fd4d77532769ea9285cd20c69bd2b40acf980de94bbc79b1c6fad5a"}, - {file = "orjson-3.9.0-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:21f6a6fdfbc13cd715c61e9fa9daeff732df6401ab7d6a2ebad0042313a40bd1"}, - {file = "orjson-3.9.0-cp310-none-win_amd64.whl", hash = "sha256:46c9733330b75c116438f555c0b971a2388b5f502e2dd4ec3bf6bacb96f82741"}, - {file = "orjson-3.9.0-cp311-cp311-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:47d7e4a3effc0e9314bd5b06e7431f2490a5e64dcdcbbc4d60e713786fec327d"}, - {file = "orjson-3.9.0-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:c41d1ef6ec308e9e3701764b3de889ed8c1c126eceaea881dd1027bffbed89fe"}, - {file = "orjson-3.9.0-cp311-cp311-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:86da00836029b2a071229c8aecab998a2f316c1bc7de10ae020d7311de3a6d0d"}, - {file = "orjson-3.9.0-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:d4fcf598bd5a99a94caa7ec92ce657939f12491e4753ea7e4d6c03faf5f7912e"}, - {file = "orjson-3.9.0-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:09522937479bd39d5bb32d11a5ecdf6926fda43ac2cbde21cc1a9508b4e4ea29"}, - {file = "orjson-3.9.0-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:d2fbf34667a8be48ec89d5ef479a00d4e7b3acda62d722c97377702da0c30ffd"}, - {file = "orjson-3.9.0-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:edd77183c154cbedaa6dac32fee9cb770b04e2a7f367a5864f444578554cc946"}, - {file = "orjson-3.9.0-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:2af7dff1c7ddb0c83eb5773acf6566b153f8cd32e4ba782ae9ccd6d0f324efd3"}, - {file = "orjson-3.9.0-cp311-none-win_amd64.whl", hash = "sha256:44fa74b497e608a8cdca1ee37fe3533a30f17163c7e2872ab1b854900cf0dfcf"}, - {file = "orjson-3.9.0-cp37-cp37m-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:f6476e2487c0b7387187de15e5b8f6635c29b75934f2e689ca8cad6550439f3d"}, - {file = "orjson-3.9.0-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:c7b241c3229084035b38cac9b5c96b43644da829da41d9d5be0fefb96fb116e1"}, - {file = "orjson-3.9.0-cp37-cp37m-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:d414fd0678e949779104f5b307f0f9fac861728e19d3cdde66759af77f892da0"}, - {file = "orjson-3.9.0-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:8a1fcddcabe121e393f3c4a31ed6d3535214d42a4ece0f9dde2e250006d6a58d"}, - {file = "orjson-3.9.0-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:bd89d63707ac616462832bfc5d16fa0c12483f86add2432ce55c8710c9531c03"}, - {file = "orjson-3.9.0-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:6c50654e4870805e4b1a587c2c3c5ef2f36f3e67fc463a738339ff40d65f7db1"}, - {file = "orjson-3.9.0-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:721d47dffedb7795ffea8a06f2de7d192de7b58e085cf357a99abf0eb931f2c3"}, - {file = "orjson-3.9.0-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:9de2129d40674007cb24164939e075b5b39fee768bf20801e08c0e3283bfb18e"}, - {file = "orjson-3.9.0-cp37-none-win_amd64.whl", hash = "sha256:5afd22847b07b63f2b8fcfddd5b7a6f47c5aaa25e19b97a3d6d39508b8fd465a"}, - {file = "orjson-3.9.0-cp38-cp38-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:d4c2d31178e3027affd98eead033f1c406890df83a0ca2016604cc21f722a1d1"}, - {file = "orjson-3.9.0-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ebe372e9f4e4f0335b7b4ebfab991b3734371e3d5b7f989ca3baa5da25185f4a"}, - {file = "orjson-3.9.0-cp38-cp38-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:c4949fc1304b702197c0840882e84b86d8d5ca33c3d945cc60727bc1786c2b20"}, - {file = "orjson-3.9.0-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:748c1e8df0b0880c63d323e167ad17ab4db2e1178a40902c2fcb68cbe402d7c8"}, - {file = "orjson-3.9.0-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:f6ab80b60195f166a9d666b2eaf6d2c74202b6da2a1fb4b4d66b9cc0ce5c9957"}, - {file = "orjson-3.9.0-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:e44ebe2129d43c5a48f3affa3fa59c6484ed16faf5b00486add1061a95384ab0"}, - {file = "orjson-3.9.0-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:04e61db09ff155846b69d07cf5aa21001f2010ea669ec3169c1fbad9c9e40cd5"}, - {file = "orjson-3.9.0-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:c68af71b1110820c914f9df75842895b5528ff524d3286fde57097b2b5ed8f22"}, - {file = "orjson-3.9.0-cp38-none-win_amd64.whl", hash = "sha256:3a208d0bca609de3152eb8320d5093ad9c52979332f626c13500d1645c66bf8d"}, - {file = "orjson-3.9.0-cp39-cp39-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:a901c432828c191332d75f358142736c433d4a192f7794123e1d30d68193de86"}, - {file = "orjson-3.9.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:271b6f1018757fc6bca40ae72e6cdb6cf84584dde2d1e5eaac30e387a13d9e72"}, - {file = "orjson-3.9.0-cp39-cp39-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:949698bdddb1daff986d73e6bbe6cd68833cd80c4adc6b69fafbd46634d4672c"}, - {file = "orjson-3.9.0-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:108c58d2c7648c991f82f9b2217c50981ad7cf6aaee3efbfaa9d807e49cd69b8"}, - {file = "orjson-3.9.0-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:08cb43569198c1f5c89ecafcbfc62414f6115d894ff908d8cf8e5e24801364e6"}, - {file = "orjson-3.9.0-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:09ee828572fadcd58bf356d2c1bad99a95c7c9c1f182b407abbc7dec1810f542"}, - {file = "orjson-3.9.0-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:0e7fe5d603ee9177ff2e45858b4fc47fea2da0688f23d9773654889d56dfbc82"}, - {file = "orjson-3.9.0-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:9ee5f1ba82146a50d61fb58d310a37c0f406eda898172f9c98673b5d6f9461c3"}, - {file = "orjson-3.9.0-cp39-none-win_amd64.whl", hash = "sha256:3235c31d0fe674f6e3433e9ddfed212aa840c83a9b6ef5ae128950e2c808c303"}, - {file = "orjson-3.9.0.tar.gz", hash = "sha256:f6dd27c71cd6e146795f876449a8eae74f67ae1e4e244dfc1203489103eb2d94"}, + {file = "orjson-3.9.1-cp310-cp310-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:c4434b7b786fdc394b95d029fb99949d7c2b05bbd4bf5cb5e3906be96ffeee3b"}, + {file = "orjson-3.9.1-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:09faf14f74ed47e773fa56833be118e04aa534956f661eb491522970b7478e3b"}, + {file = "orjson-3.9.1-cp310-cp310-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:503eb86a8d53a187fe66aa80c69295a3ca35475804da89a9547e4fce5f803822"}, + {file = "orjson-3.9.1-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:20f2804b5a1dbd3609c086041bd243519224d47716efd7429db6c03ed28b7cc3"}, + {file = "orjson-3.9.1-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:0fd828e0656615a711c4cc4da70f3cac142e66a6703ba876c20156a14e28e3fa"}, + {file = "orjson-3.9.1-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:ec53d648176f873203b9c700a0abacab33ca1ab595066e9d616f98cdc56f4434"}, + {file = "orjson-3.9.1-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:e186ae76b0d97c505500664193ddf508c13c1e675d9b25f1f4414a7606100da6"}, + {file = "orjson-3.9.1-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:d4edee78503016f4df30aeede0d999b3cb11fb56f47e9db0e487bce0aaca9285"}, + {file = "orjson-3.9.1-cp310-none-win_amd64.whl", hash = "sha256:a4cc5d21e68af982d9a2528ac61e604f092c60eed27aef3324969c68f182ec7e"}, + {file = "orjson-3.9.1-cp311-cp311-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:761b6efd33c49de20dd73ce64cc59da62c0dab10aa6015f582680e0663cc792c"}, + {file = "orjson-3.9.1-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:31229f9d0b8dc2ef7ee7e4393f2e4433a28e16582d4b25afbfccc9d68dc768f8"}, + {file = "orjson-3.9.1-cp311-cp311-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:0b7ab18d55ecb1de543d452f0a5f8094b52282b916aa4097ac11a4c79f317b86"}, + {file = "orjson-3.9.1-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:db774344c39041f4801c7dfe03483df9203cbd6c84e601a65908e5552228dd25"}, + {file = "orjson-3.9.1-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:ae47ef8c0fe89c4677db7e9e1fb2093ca6e66c3acbee5442d84d74e727edad5e"}, + {file = "orjson-3.9.1-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:103952c21575b9805803c98add2eaecd005580a1e746292ed2ec0d76dd3b9746"}, + {file = "orjson-3.9.1-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:2cb0121e6f2c9da3eddf049b99b95fef0adf8480ea7cb544ce858706cdf916eb"}, + {file = "orjson-3.9.1-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:24d4ddaa2876e657c0fd32902b5c451fd2afc35159d66a58da7837357044b8c2"}, + {file = "orjson-3.9.1-cp311-none-win_amd64.whl", hash = "sha256:0b53b5f72cf536dd8aa4fc4c95e7e09a7adb119f8ff8ee6cc60f735d7740ad6a"}, + {file = "orjson-3.9.1-cp37-cp37m-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:d4b68d01a506242316a07f1d2f29fb0a8b36cee30a7c35076f1ef59dce0890c1"}, + {file = "orjson-3.9.1-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d9dd4abe6c6fd352f00f4246d85228f6a9847d0cc14f4d54ee553718c225388f"}, + {file = "orjson-3.9.1-cp37-cp37m-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:9e20bca5e13041e31ceba7a09bf142e6d63c8a7467f5a9c974f8c13377c75af2"}, + {file = "orjson-3.9.1-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:d8ae0467d01eb1e4bcffef4486d964bfd1c2e608103e75f7074ed34be5df48cc"}, + {file = "orjson-3.9.1-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:06f6ab4697fab090517f295915318763a97a12ee8186054adf21c1e6f6abbd3d"}, + {file = "orjson-3.9.1-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:8515867713301fa065c58ec4c9053ba1a22c35113ab4acad555317b8fd802e50"}, + {file = "orjson-3.9.1-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:393d0697d1dfa18d27d193e980c04fdfb672c87f7765b87952f550521e21b627"}, + {file = "orjson-3.9.1-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:d96747662d3666f79119e5d28c124e7d356c7dc195cd4b09faea4031c9079dc9"}, + {file = "orjson-3.9.1-cp37-none-win_amd64.whl", hash = "sha256:6d173d3921dd58a068c88ec22baea7dbc87a137411501618b1292a9d6252318e"}, + {file = "orjson-3.9.1-cp38-cp38-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:d1c2b0b4246c992ce2529fc610a446b945f1429445ece1c1f826a234c829a918"}, + {file = "orjson-3.9.1-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:19f70ba1f441e1c4bb1a581f0baa092e8b3e3ce5b2aac2e1e090f0ac097966da"}, + {file = "orjson-3.9.1-cp38-cp38-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:375d65f002e686212aac42680aed044872c45ee4bc656cf63d4a215137a6124a"}, + {file = "orjson-3.9.1-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:4751cee4a7b1daeacb90a7f5adf2170ccab893c3ab7c5cea58b45a13f89b30b3"}, + {file = "orjson-3.9.1-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:78d9a2a4b2302d5ebc3695498ebc305c3568e5ad4f3501eb30a6405a32d8af22"}, + {file = "orjson-3.9.1-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:46b4facc32643b2689dfc292c0c463985dac4b6ab504799cf51fc3c6959ed668"}, + {file = "orjson-3.9.1-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:ec7c8a0f1bf35da0d5fd14f8956f3b82a9a6918a3c6963d718dfd414d6d3b604"}, + {file = "orjson-3.9.1-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:d3a40b0fbe06ccd4d6a99e523d20b47985655bcada8d1eba485b1b32a43e4904"}, + {file = "orjson-3.9.1-cp38-none-win_amd64.whl", hash = "sha256:402f9d3edfec4560a98880224ec10eba4c5f7b4791e4bc0d4f4d8df5faf2a006"}, + {file = "orjson-3.9.1-cp39-cp39-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:49c0d78dcd34626e2e934f1192d7c052b94e0ecadc5f386fd2bda6d2e03dadf5"}, + {file = "orjson-3.9.1-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:125f63e56d38393daa0a1a6dc6fedefca16c538614b66ea5997c3bd3af35ef26"}, + {file = "orjson-3.9.1-cp39-cp39-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:08927970365d2e1f3ce4894f9ff928a7b865d53f26768f1bbdd85dd4fee3e966"}, + {file = "orjson-3.9.1-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:f9a744e212d4780ecd67f4b6b128b2e727bee1df03e7059cddb2dfe1083e7dc4"}, + {file = "orjson-3.9.1-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:5d1dbf36db7240c61eec98c8d21545d671bce70be0730deb2c0d772e06b71af3"}, + {file = "orjson-3.9.1-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:80a1e384626f76b66df615f7bb622a79a25c166d08c5d2151ffd41f24c4cc104"}, + {file = "orjson-3.9.1-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:15d28872fb055bf17ffca913826e618af61b2f689d2b170f72ecae1a86f80d52"}, + {file = "orjson-3.9.1-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:1e4d905338f9ef32c67566929dfbfbb23cc80287af8a2c38930fb0eda3d40b76"}, + {file = "orjson-3.9.1-cp39-none-win_amd64.whl", hash = "sha256:48a27da6c7306965846565cc385611d03382bbd84120008653aa2f6741e2105d"}, + {file = "orjson-3.9.1.tar.gz", hash = "sha256:db373a25ec4a4fccf8186f9a72a1b3442837e40807a736a815ab42481e83b7d0"}, ] [[package]] name = "packaging" version = "22.0" description = "Core utilities for Python packages" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2195,7 +2122,6 @@ files = [ name = "pillow" version = "9.5.0" description = "Python Imaging Library (Fork)" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2275,7 +2201,6 @@ tests = ["check-manifest", "coverage", "defusedxml", "markdown2", "olefile", "pa name = "platformdirs" version = "2.6.2" description = "A small Python package for determining appropriate platform-specific dirs, e.g. a \"user data dir\"." -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2291,7 +2216,6 @@ test = ["appdirs (==1.4.4)", "covdefaults (>=2.2.2)", "pytest (>=7.2)", "pytest- name = "pluggy" version = "1.0.0" description = "plugin and hook calling mechanisms for python" -category = "dev" optional = false python-versions = ">=3.6" files = [ @@ -2307,7 +2231,6 @@ testing = ["pytest", "pytest-benchmark"] name = "pre-commit" version = "3.3.2" description = "A framework for managing and maintaining multi-language pre-commit hooks." -category = "dev" optional = false python-versions = ">=3.8" files = [ @@ -2326,7 +2249,6 @@ virtualenv = ">=20.10.0" name = "prisma" version = "0.8.2" description = "Prisma Client Python is an auto-generated and fully type-safe database client" -category = "main" optional = false python-versions = ">=3.7.0" files = [ @@ -2352,7 +2274,6 @@ node = ["nodejs-bin"] name = "pycares" version = "4.3.0" description = "Python interface for c-ares" -category = "main" optional = false python-versions = "*" files = [ @@ -2420,7 +2341,6 @@ idna = ["idna (>=2.1)"] name = "pycparser" version = "2.21" description = "C parser in Python" -category = "main" optional = false python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*" files = [ @@ -2432,7 +2352,6 @@ files = [ name = "pydantic" version = "1.10.4" description = "Data validation and settings management using python type hints" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -2485,7 +2404,6 @@ email = ["email-validator (>=1.0.3)"] name = "pygments" version = "2.15.0" description = "Pygments is a syntax highlighting package written in Python." -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2500,7 +2418,6 @@ plugins = ["importlib-metadata"] name = "pyinstrument" version = "4.5.0" description = "Call stack profiler for Python. Shows you why your code is slow!" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2563,7 +2480,6 @@ jupyter = ["ipython"] name = "pynacl" version = "1.5.0" description = "Python binding to the Networking and Cryptography (NaCl) library" -category = "main" optional = false python-versions = ">=3.6" files = [ @@ -2590,7 +2506,6 @@ tests = ["hypothesis (>=3.27.0)", "pytest (>=3.2.1,!=3.3.0)"] name = "pyparsing" version = "3.0.9" description = "pyparsing module - Classes and methods to define and execute parsing grammars" -category = "dev" optional = false python-versions = ">=3.6.8" files = [ @@ -2605,7 +2520,6 @@ diagrams = ["jinja2", "railroad-diagrams"] name = "pyright" version = "1.1.313" description = "Command line wrapper for pyright" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2624,7 +2538,6 @@ dev = ["twine (>=3.4.1)"] name = "pytest" version = "7.3.1" description = "pytest: simple powerful testing with Python" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2647,7 +2560,6 @@ testing = ["argcomplete", "attrs (>=19.2.0)", "hypothesis (>=3.56)", "mock", "no name = "pytest-asyncio" version = "0.21.0" description = "Pytest support for asyncio" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2666,7 +2578,6 @@ testing = ["coverage (>=6.2)", "flaky (>=3.5.0)", "hypothesis (>=5.7.1)", "mypy name = "pytest-cov" version = "4.1.0" description = "Pytest plugin for measuring coverage." -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2685,7 +2596,6 @@ testing = ["fields", "hunter", "process-tests", "pytest-xdist", "six", "virtuale name = "python-dateutil" version = "2.8.2" description = "Extensions to the standard Python datetime module" -category = "dev" optional = false python-versions = "!=3.0.*,!=3.1.*,!=3.2.*,>=2.7" files = [ @@ -2700,7 +2610,6 @@ six = ">=1.5" name = "python-dotenv" version = "1.0.0" description = "Read key-value pairs from a .env file and set them as environment variables" -category = "main" optional = false python-versions = ">=3.8" files = [ @@ -2715,7 +2624,6 @@ cli = ["click (>=5.0)"] name = "pytz" version = "2023.3" description = "World timezone definitions, modern and historical" -category = "dev" optional = false python-versions = "*" files = [ @@ -2727,7 +2635,6 @@ files = [ name = "pyyaml" version = "6.0" description = "YAML parser and emitter for Python" -category = "dev" optional = false python-versions = ">=3.6" files = [ @@ -2777,7 +2684,6 @@ files = [ name = "redis" version = "4.5.5" description = "Python client for Redis database and key-value store" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -2797,7 +2703,6 @@ ocsp = ["cryptography (>=36.0.1)", "pyopenssl (==20.0.1)", "requests (>=2.26.0)" name = "requests" version = "2.31.0" description = "Python HTTP for Humans." -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -2819,7 +2724,6 @@ use-chardet-on-py3 = ["chardet (>=3.0.2,<6)"] name = "rfc3986" version = "1.5.0" description = "Validating URI References per RFC 3986" -category = "main" optional = false python-versions = "*" files = [ @@ -2837,7 +2741,6 @@ idna2008 = ["idna"] name = "ruff" version = "0.0.272" description = "An extremely fast Python linter, written in Rust." -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2864,7 +2767,6 @@ files = [ name = "setuptools" version = "66.1.1" description = "Easily download, build, install, upgrade, and uninstall Python packages" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -2881,7 +2783,6 @@ testing-integration = ["build[virtualenv]", "filelock (>=3.4.0)", "jaraco.envs ( name = "six" version = "1.16.0" description = "Python 2 and 3 compatibility utilities" -category = "dev" optional = false python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*" files = [ @@ -2893,7 +2794,6 @@ files = [ name = "sniffio" version = "1.3.0" description = "Sniff out which async library your code is running under" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -2905,7 +2805,6 @@ files = [ name = "snowballstemmer" version = "2.2.0" description = "This package provides 29 stemmers for 28 languages generated from Snowball algorithms." -category = "dev" optional = false python-versions = "*" files = [ @@ -2917,7 +2816,6 @@ files = [ name = "soupsieve" version = "2.4.1" description = "A modern CSS selector implementation for Beautiful Soup." -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -2929,7 +2827,6 @@ files = [ name = "sphinx" version = "6.2.1" description = "Python documentation generator" -category = "dev" optional = false python-versions = ">=3.8" files = [ @@ -2965,7 +2862,6 @@ test = ["cython", "filelock", "html5lib", "pytest (>=4.6)"] name = "sphinx-autobuild" version = "2021.3.14" description = "Rebuild Sphinx documentation on changes, with live-reload in the browser." -category = "dev" optional = false python-versions = ">=3.6" files = [ @@ -2985,7 +2881,6 @@ test = ["pytest", "pytest-cov"] name = "sphinx-basic-ng" version = "1.0.0b1" description = "A modern skeleton for Sphinx themes." -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -3003,7 +2898,6 @@ docs = ["furo", "ipython", "myst-parser", "sphinx-copybutton", "sphinx-inline-ta name = "sphinxcontrib-applehelp" version = "1.0.4" description = "sphinxcontrib-applehelp is a Sphinx extension which outputs Apple help books" -category = "dev" optional = false python-versions = ">=3.8" files = [ @@ -3019,7 +2913,6 @@ test = ["pytest"] name = "sphinxcontrib-devhelp" version = "1.0.2" description = "sphinxcontrib-devhelp is a sphinx extension which outputs Devhelp document." -category = "dev" optional = false python-versions = ">=3.5" files = [ @@ -3035,7 +2928,6 @@ test = ["pytest"] name = "sphinxcontrib-htmlhelp" version = "2.0.1" description = "sphinxcontrib-htmlhelp is a sphinx extension which renders HTML help files" -category = "dev" optional = false python-versions = ">=3.8" files = [ @@ -3051,7 +2943,6 @@ test = ["html5lib", "pytest"] name = "sphinxcontrib-jsmath" version = "1.0.1" description = "A sphinx extension which renders display math in HTML via JavaScript" -category = "dev" optional = false python-versions = ">=3.5" files = [ @@ -3066,7 +2957,6 @@ test = ["flake8", "mypy", "pytest"] name = "sphinxcontrib-qthelp" version = "1.0.3" description = "sphinxcontrib-qthelp is a sphinx extension which outputs QtHelp document." -category = "dev" optional = false python-versions = ">=3.5" files = [ @@ -3082,7 +2972,6 @@ test = ["pytest"] name = "sphinxcontrib-serializinghtml" version = "1.1.5" description = "sphinxcontrib-serializinghtml is a sphinx extension which outputs \"serialized\" HTML files (json and pickle)." -category = "dev" optional = false python-versions = ">=3.5" files = [ @@ -3098,7 +2987,6 @@ test = ["pytest"] name = "sphinxext-opengraph" version = "0.8.2" description = "Sphinx Extension to enable OGP support" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -3114,7 +3002,6 @@ sphinx = ">=4.0" name = "tomli" version = "2.0.1" description = "A lil' TOML parser" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -3126,7 +3013,6 @@ files = [ name = "tomlkit" version = "0.11.6" description = "Style preserving TOML library" -category = "main" optional = false python-versions = ">=3.6" files = [ @@ -3138,7 +3024,6 @@ files = [ name = "tornado" version = "6.3.2" description = "Tornado is a Python web framework and asynchronous networking library, originally developed at FriendFeed." -category = "dev" optional = false python-versions = ">= 3.8" files = [ @@ -3159,7 +3044,6 @@ files = [ name = "typing-extensions" version = "4.4.0" description = "Backported and Experimental Type Hints for Python 3.7+" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -3171,7 +3055,6 @@ files = [ name = "update-checker" version = "0.18.0" description = "A python module that will check for package updates." -category = "main" optional = false python-versions = "*" files = [ @@ -3191,7 +3074,6 @@ test = ["pytest (>=2.7.3)"] name = "urllib3" version = "1.26.14" description = "HTTP library with thread-safe connection pooling, file post, and more." -category = "main" optional = false python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, !=3.4.*, !=3.5.*" files = [ @@ -3208,7 +3090,6 @@ socks = ["PySocks (>=1.5.6,!=1.5.7,<2.0)"] name = "uvloop" version = "0.17.0" description = "Fast implementation of asyncio event loop on top of libuv" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -3253,7 +3134,6 @@ test = ["Cython (>=0.29.32,<0.30.0)", "aiohttp", "flake8 (>=3.9.2,<3.10.0)", "my name = "virtualenv" version = "20.17.1" description = "Virtual Python Environment builder" -category = "dev" optional = false python-versions = ">=3.6" files = [ @@ -3274,7 +3154,6 @@ testing = ["coverage (>=6.2)", "coverage-enable-subprocess (>=1)", "flaky (>=3.7 name = "watchfiles" version = "0.19.0" description = "Simple, modern and high performance file watching and code reload in python." -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -3309,7 +3188,6 @@ anyio = ">=3.0.0" name = "websockets" version = "10.4" description = "An implementation of the WebSocket Protocol (RFC 6455 & 7692)" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -3388,7 +3266,6 @@ files = [ name = "wheel" version = "0.40.0" description = "A built-package format for Python" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -3403,7 +3280,6 @@ test = ["pytest (>=6.0.0)"] name = "yarl" version = "1.8.2" description = "Yet another URL library" -category = "main" optional = false python-versions = ">=3.7" files = [ @@ -3491,7 +3367,6 @@ multidict = ">=4.0" name = "zipp" version = "3.15.0" description = "Backport of pathlib-compatible object wrapper for zip files" -category = "dev" optional = false python-versions = ">=3.7" files = [ @@ -3506,4 +3381,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "4bbed27639da457de9b9d94df10df12de946a5515e33e9da593fac9ac7f6fe8a" +content-hash = "3ef6f3374d63edc9591d730ed4e435d518061578572cdfcb0d5fddc43863285b" diff --git a/pyproject.toml b/pyproject.toml index 123329da..33f58679 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -10,7 +10,7 @@ python = ">=3.8,<4.0" python-dotenv = "^1.0.0" aiodns = "^3.0.0" Brotli = "^1.0.9" -orjson = "^3.9.0" +orjson = "^3.9.1" asyncpraw = "^7.7.0" uvloop = "^0.17.0" gql = { extras = ["aiohttp"], version = "^3.4.1" } From 1bc9da18bfb0aad245a7ad80e50ea1ccf8676111 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Mon, 12 Jun 2023 10:38:26 +0000 Subject: [PATCH 089/184] [pip](deps-dev): Bump pytest from 7.3.1 to 7.3.2 (#348) Bumps [pytest](https://github.com/pytest-dev/pytest) from 7.3.1 to 7.3.2. - [Release notes](https://github.com/pytest-dev/pytest/releases) - [Changelog](https://github.com/pytest-dev/pytest/blob/main/CHANGELOG.rst) - [Commits](https://github.com/pytest-dev/pytest/compare/7.3.1...7.3.2) --- updated-dependencies: - dependency-name: pytest dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 10 +++++----- pyproject.toml | 2 +- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/poetry.lock b/poetry.lock index 6547bd68..fb747948 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2536,13 +2536,13 @@ dev = ["twine (>=3.4.1)"] [[package]] name = "pytest" -version = "7.3.1" +version = "7.3.2" description = "pytest: simple powerful testing with Python" optional = false python-versions = ">=3.7" files = [ - {file = "pytest-7.3.1-py3-none-any.whl", hash = "sha256:3799fa815351fea3a5e96ac7e503a96fa51cc9942c3753cda7651b93c1cfa362"}, - {file = "pytest-7.3.1.tar.gz", hash = "sha256:434afafd78b1d78ed0addf160ad2b77a30d35d4bdf8af234fe621919d9ed15e3"}, + {file = "pytest-7.3.2-py3-none-any.whl", hash = "sha256:cdcbd012c9312258922f8cd3f1b62a6580fdced17db6014896053d47cddf9295"}, + {file = "pytest-7.3.2.tar.gz", hash = "sha256:ee990a3cc55ba808b80795a79944756f315c67c12b56abd3ac993a7b8c17030b"}, ] [package.dependencies] @@ -2554,7 +2554,7 @@ pluggy = ">=0.12,<2.0" tomli = {version = ">=1.0.0", markers = "python_version < \"3.11\""} [package.extras] -testing = ["argcomplete", "attrs (>=19.2.0)", "hypothesis (>=3.56)", "mock", "nose", "pygments (>=2.7.2)", "requests", "xmlschema"] +testing = ["argcomplete", "attrs (>=19.2.0)", "hypothesis (>=3.56)", "mock", "nose", "pygments (>=2.7.2)", "requests", "setuptools", "xmlschema"] [[package]] name = "pytest-asyncio" @@ -3381,4 +3381,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "3ef6f3374d63edc9591d730ed4e435d518061578572cdfcb0d5fddc43863285b" +content-hash = "7ae49da45d19b5bd67b460d37b1a22e3adbc89b6797b8968906e8e0bb2efb144" diff --git a/pyproject.toml b/pyproject.toml index 33f58679..285f3d1e 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -23,7 +23,7 @@ discord-py = {extras = ["voice"], version = "^2.2.3"} discord-ext-menus = {git = "https://github.com/Rapptz/discord-ext-menus", rev = "8686b5d1bbc1d3c862292eb436ab630d6e9c9b53"} [tool.poetry.group.test.dependencies] -pytest = "^7.3.1" +pytest = "^7.3.2" pytest-asyncio = "^0.21.0" nox = "^2023.4.22" nox-poetry = "^1.0.2" From 6a265b824cea013516f24a7d8dca65d5f01a4d47 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Mon, 12 Jun 2023 11:17:31 +0000 Subject: [PATCH 090/184] [pip](deps): Bump prisma from 0.8.2 to 0.9.0 (#349) Bumps [prisma](https://github.com/RobertCraigie/prisma-client-py) from 0.8.2 to 0.9.0. - [Release notes](https://github.com/RobertCraigie/prisma-client-py/releases) - [Commits](https://github.com/RobertCraigie/prisma-client-py/compare/v0.8.2...v0.9.0) --- updated-dependencies: - dependency-name: prisma dependency-type: direct:production update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 10 +++++----- pyproject.toml | 2 +- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/poetry.lock b/poetry.lock index fb747948..f3fce723 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2247,13 +2247,13 @@ virtualenv = ">=20.10.0" [[package]] name = "prisma" -version = "0.8.2" +version = "0.9.0" description = "Prisma Client Python is an auto-generated and fully type-safe database client" optional = false python-versions = ">=3.7.0" files = [ - {file = "prisma-0.8.2-py3-none-any.whl", hash = "sha256:4d0ebf63ecd21bc4fda633867403429d24f89e6af5889944b2f9ca4203f50835"}, - {file = "prisma-0.8.2.tar.gz", hash = "sha256:b3a639941f4bf33dbd414fee3e02cf30218968d05b108f8a4d5b7c331dcbc19c"}, + {file = "prisma-0.9.0-py3-none-any.whl", hash = "sha256:bff4b239faeb5d427e8337eadc6fe2d2e2ee4f82e30048fd7de46f8aaf9ef07d"}, + {file = "prisma-0.9.0.tar.gz", hash = "sha256:1f9321efc099401995067d921cab848f5a82cd64ecdb5924fa91fb2f1379897f"}, ] [package.dependencies] @@ -2264,7 +2264,7 @@ nodeenv = "*" pydantic = ">=1.8.0" python-dotenv = ">=0.12.0" tomlkit = "*" -typing-extensions = ">=3.7" +typing-extensions = ">=4.0.1" [package.extras] all = ["nodejs-bin"] @@ -3381,4 +3381,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "7ae49da45d19b5bd67b460d37b1a22e3adbc89b6797b8968906e8e0bb2efb144" +content-hash = "3e5f86738b4ba88d47957a49352268c636b5adc6d0b840856469b8cab10b9601" diff --git a/pyproject.toml b/pyproject.toml index 285f3d1e..cfcc3e2b 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -15,7 +15,7 @@ asyncpraw = "^7.7.0" uvloop = "^0.17.0" gql = { extras = ["aiohttp"], version = "^3.4.1" } better-ipc = "^2.0.3" -prisma = "^0.8.2" +prisma = "^0.9.0" redis = {extras = ["hiredis"], version = "^4.5.5"} ciso8601 = "^2.3.0" faust-cchardet = "^2.1.18" From c2ebd0a53e003244a4362076b00a17be2c04066a Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Mon, 12 Jun 2023 20:50:36 +0900 Subject: [PATCH 091/184] Add an logger system --- Bot/Libs/utils/__init__.py | 32 +++++++++++++------------ Bot/Libs/utils/kumiko_logger.py | 42 +++++++++++++++++++++++++++++++++ Bot/kumikobot.py | 14 ++++------- docker-compose-dev.yml | 2 +- 4 files changed, 64 insertions(+), 26 deletions(-) create mode 100644 Bot/Libs/utils/kumiko_logger.py diff --git a/Bot/Libs/utils/__init__.py b/Bot/Libs/utils/__init__.py index f775c272..c048a420 100644 --- a/Bot/Libs/utils/__init__.py +++ b/Bot/Libs/utils/__init__.py @@ -1,15 +1,17 @@ -from .backoff import backoff -from .embeds import Embed, ErrorEmbed -from .greedy_formatter import formatGreedy -from .utils import encodeDatetime, parseDatetime, parseSubreddit, parseTimeStr - -__all__ = [ - "backoff", - "parseDatetime", - "encodeDatetime", - "Embed", - "ErrorEmbed", - "parseSubreddit", - "parseTimeStr", - "formatGreedy", -] +from .backoff import backoff +from .embeds import Embed, ErrorEmbed +from .greedy_formatter import formatGreedy +from .utils import encodeDatetime, parseDatetime, parseSubreddit, parseTimeStr +from .kumiko_logger import KumikoLogger + +__all__ = [ + "backoff", + "parseDatetime", + "encodeDatetime", + "Embed", + "ErrorEmbed", + "parseSubreddit", + "parseTimeStr", + "formatGreedy", + "KumikoLogger" +] diff --git a/Bot/Libs/utils/kumiko_logger.py b/Bot/Libs/utils/kumiko_logger.py new file mode 100644 index 00000000..819945aa --- /dev/null +++ b/Bot/Libs/utils/kumiko_logger.py @@ -0,0 +1,42 @@ +import logging +import re +from types import TracebackType +from typing import Optional, Type, TypeVar + +import discord + +BE = TypeVar("BE", bound=BaseException) + + +class RemoveIPCNoise(logging.Filter): + def __init__(self) -> None: + self.self = self + + def filter(self, record: logging.LogRecord) -> bool: + matchRegex = r"(connection\s[open|closed])" + if bool(re.search(matchRegex, record.msg)): + return False + return True + + +class KumikoLogger: + def __init__(self) -> None: + self.self = self + self.log = logging.getLogger("discord") + + def __enter__(self) -> None: + logging.getLogger("discord.ext.ipc.server").addFilter(RemoveIPCNoise()) + logging.getLogger("gql").setLevel(logging.WARNING) + fmt = logging.Formatter( + fmt="%(asctime)s %(levelname)s %(message)s", + datefmt="[%Y-%m-%d %H:%M:%S]", + ) + discord.utils.setup_logging(formatter=fmt) + + def __exit__( + self, + exc_type: Optional[Type[BE]], + exc: Optional[BE], + traceback: Optional[TracebackType], + ) -> None: + self.log.info("Shutting down Kumiko...") \ No newline at end of file diff --git a/Bot/kumikobot.py b/Bot/kumikobot.py index ef30731a..a50cfc15 100644 --- a/Bot/kumikobot.py +++ b/Bot/kumikobot.py @@ -1,4 +1,3 @@ -import logging import os import discord @@ -7,6 +6,7 @@ from dotenv import load_dotenv from kumikocore import KumikoCore from Libs.utils.postgresql import PrismaSessionManager +from Libs.utils import KumikoLogger load_dotenv() @@ -15,13 +15,6 @@ intents = discord.Intents.default() intents.message_content = True -FORMATTER = logging.Formatter( - fmt="%(asctime)s %(levelname)s %(message)s", datefmt="[%Y-%m-%d %H:%M:%S]" -) -discord.utils.setup_logging(formatter=FORMATTER) - -logger = logging.getLogger("discord") -logging.getLogger("gql").setLevel(logging.WARNING) async def main() -> None: @@ -41,6 +34,7 @@ def launch() -> None: if __name__ == "__main__": try: - launch() + with KumikoLogger(): + launch() except KeyboardInterrupt: - logger.info("Shutting down...") + pass diff --git a/docker-compose-dev.yml b/docker-compose-dev.yml index 3c7ef949..63f7fd39 100644 --- a/docker-compose-dev.yml +++ b/docker-compose-dev.yml @@ -13,7 +13,7 @@ services: redis: container_name: Kumiko-Redis-Stack-Dev - image: redis/redis-stack:7.0.6-RC6 + image: redis/redis-stack:7.2.0-M01 ports: - 6379:6379 volumes: From 460040f624a7cf08fc23be23e4e418a26756d2e4 Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Mon, 12 Jun 2023 22:21:32 +0900 Subject: [PATCH 092/184] Add migrations + move torwards asyncpg instead of Prisma --- Bot/Libs/cache/cp_manager.py | 56 +++---- Bot/Libs/cache/global_cp.py | 28 ++-- Bot/Libs/utils/postgresql/__init__.py | 6 +- .../utils/postgresql/ensure_open_conns.py | 22 +++ Bot/Libs/utils/redis/__init__.py | 6 +- Bot/Libs/utils/redis/connections.py | 141 ++++++++++-------- Bot/kumikobot.py | 13 +- Bot/kumikocore.py | 43 ++++-- Bot/{Cogs => unloaded_cogs}/economy.py | 0 Bot/{Cogs => unloaded_cogs}/socket-events.py | 0 Migrations/20230612_initial_up_rev1.sql | 36 +++++ migrations-runner.py | 46 ++++++ 12 files changed, 271 insertions(+), 126 deletions(-) create mode 100644 Bot/Libs/utils/postgresql/ensure_open_conns.py rename Bot/{Cogs => unloaded_cogs}/economy.py (100%) rename Bot/{Cogs => unloaded_cogs}/socket-events.py (100%) create mode 100644 Migrations/20230612_initial_up_rev1.sql create mode 100644 migrations-runner.py diff --git a/Bot/Libs/cache/cp_manager.py b/Bot/Libs/cache/cp_manager.py index 663380ad..d9f0706c 100644 --- a/Bot/Libs/cache/cp_manager.py +++ b/Bot/Libs/cache/cp_manager.py @@ -1,26 +1,30 @@ -from typing import Optional - -from redis.asyncio.connection import ConnectionPool - - -class KumikoCPManager: - """Redis connection pool manager""" - - def __init__( - self, host: str = "127.0.0.1", port: int = 6379, password: Optional[str] = None - ) -> None: - self.host = host - self.port = port - self.password = password - self.connPool = None - - def createConnPool(self) -> ConnectionPool: - self.connPool = ConnectionPool( - host=self.host, port=self.port, password=self.password, db=0 - ) - return self.connPool - - def getConnPool(self) -> ConnectionPool: - if not self.connPool: - return self.createConnPool() - return self.connPool +from typing import Optional + +from redis.asyncio.connection import ConnectionPool + + +class KumikoCPManager: + """Redis connection pool manager""" + + def __init__( + self, host: str = "127.0.0.1", port: int = 6379, password: Optional[str] = None, uri: Optional[str] = None + ) -> None: + self.host = host + self.port = port + self.password = password + self.connPool = None + self.uri = uri + + def createConnPool(self) -> ConnectionPool: + if self.uri is not None: + self.connPool = ConnectionPool( + host=self.host, port=self.port, password=self.password, db=0 + ) + return self.connPool + self.connPool = ConnectionPool.from_url(self.uri) + return self.connPool + + def getConnPool(self) -> ConnectionPool: + if not self.connPool: + return self.createConnPool() + return self.connPool diff --git a/Bot/Libs/cache/global_cp.py b/Bot/Libs/cache/global_cp.py index ee8adb60..117dba94 100644 --- a/Bot/Libs/cache/global_cp.py +++ b/Bot/Libs/cache/global_cp.py @@ -1,15 +1,13 @@ -import os -from pathlib import Path - -from dotenv import load_dotenv -from Libs.cache import KumikoCPManager - -path = Path(__file__).parents[2].joinpath(".env") - -load_dotenv(dotenv_path=path) - -REDIS_HOST = os.environ["REDIS_HOST"] -REDIS_PORT = os.environ["REDIS_PORT"] -REDIS_PASSWORD = os.environ["REDIS_PASSWORD"] - -kumikoCP: KumikoCPManager = KumikoCPManager(host=REDIS_HOST, port=int(REDIS_PORT)) +import os +from pathlib import Path + +from dotenv import load_dotenv +from Libs.cache import KumikoCPManager + +path = Path(__file__).parents[2].joinpath(".env") + +load_dotenv(dotenv_path=path) + +REDIS_URI = os.environ["REDIS_URI"] + +kumikoCP: KumikoCPManager = KumikoCPManager(uri=REDIS_URI) diff --git a/Bot/Libs/utils/postgresql/__init__.py b/Bot/Libs/utils/postgresql/__init__.py index 06a7c635..9ef1b553 100644 --- a/Bot/Libs/utils/postgresql/__init__.py +++ b/Bot/Libs/utils/postgresql/__init__.py @@ -1,3 +1,3 @@ -from .ctx import PrismaSessionManager - -__all__ = ["PrismaSessionManager"] +# from .ctx import PrismaSessionManager +from .ensure_open_conns import ensureOpenPostgresConn +__all__ = ["ensureOpenPostgresConn"] diff --git a/Bot/Libs/utils/postgresql/ensure_open_conns.py b/Bot/Libs/utils/postgresql/ensure_open_conns.py new file mode 100644 index 00000000..4000fd94 --- /dev/null +++ b/Bot/Libs/utils/postgresql/ensure_open_conns.py @@ -0,0 +1,22 @@ +import logging + +import asyncpg + + +async def ensureOpenPostgresConn(conn_pool: asyncpg.Pool) -> bool: + """Ensures that the current connection pulled from the pool can be run. + + Args: + conn_pool (asyncpg.Pool): The connection pool to get connections from. + + Returns: + bool: True if the connection can be ran. + """ + logger = logging.getLogger("discord") + async with conn_pool.acquire() as conn: + connStatus = conn.is_closed() + if connStatus is False: + logger.info("PostgreSQL server is up") + return True + logger.error("Failed to connect to PostgreSQL") + return False \ No newline at end of file diff --git a/Bot/Libs/utils/redis/__init__.py b/Bot/Libs/utils/redis/__init__.py index 454a8cb0..cd02a9bb 100644 --- a/Bot/Libs/utils/redis/__init__.py +++ b/Bot/Libs/utils/redis/__init__.py @@ -1,3 +1,3 @@ -from .connections import pingRedis, redisCheck - -__all__ = ["pingRedis", "redisCheck"] +from .connections import pingRedis, redisCheck, ensureOpenRedisConn + +__all__ = ["pingRedis", "redisCheck", "ensureOpenRedisConn"] diff --git a/Bot/Libs/utils/redis/connections.py b/Bot/Libs/utils/redis/connections.py index d81669ab..78e5f7e4 100644 --- a/Bot/Libs/utils/redis/connections.py +++ b/Bot/Libs/utils/redis/connections.py @@ -1,61 +1,80 @@ -import asyncio -import logging -from typing import Union - -import redis.asyncio as redis -from Libs.cache import kumikoCP -from redis.asyncio.connection import ConnectionPool -from redis.exceptions import ConnectionError, TimeoutError - -from ..backoff import backoff - -logger = logging.getLogger("discord") - - -async def pingRedis(connection_pool: ConnectionPool) -> bool: - """Pings the redis server to ensure that it is alive - - Args: - connection_pool (ConnectionPool): ConnectionPool object to use - - Returns: - bool: Whether the Redis server is alive or not - """ - r: redis.Redis = redis.Redis(connection_pool=connection_pool, socket_timeout=10.0) - return await r.ping() - - -async def redisCheck( - backoff_sec: int = 15, - backoff_index: int = 0, -) -> Union[bool, None]: - """Integration method to check if the Redis server is alive - - Also sets up the conn pool cache. This is handled recursively actually. - There is a base case of 5 so the recursion only goes 5 calls deep on the stack. This is to prevent infinite calls on the stack from piling up. - - Args: - backoff_sec (int, optional): Backoff time in seconds. Defaults to 15. - backoff_index (int, optional): Backoff index. This is used privately Defaults to 0. - - Returns: - Union[Literal[True], None]: Returns True if the Redis server is alive. Returns None if the coroutine is in a recursive loop. - """ - try: - connPool = kumikoCP.getConnPool() - res = await pingRedis(connection_pool=connPool) - if backoff_index == 5: - logger.error("Unable to connect to Redis server") - return False - if res is True: - logger.info("Successfully connected to Redis server") - return True - except (ConnectionError, TimeoutError): - backoffTime = backoff(backoff_sec=backoff_sec, backoff_sec_index=backoff_index) - logger.error( - f"Failed to connect to Redis server - Restarting connection in {int(backoffTime)} seconds" - ) - await asyncio.sleep(backoffTime) - await redisCheck( - backoff_index=backoff_index + 1, - ) +import asyncio +import logging +from typing import Union + +import redis.asyncio as redis +from Libs.cache import kumikoCP +from redis.asyncio.connection import ConnectionPool +from redis.exceptions import ConnectionError, TimeoutError + +from ..backoff import backoff + +logger = logging.getLogger("discord") + + +async def pingRedis(connection_pool: ConnectionPool) -> bool: + """Pings the redis server to ensure that it is alive + + Args: + connection_pool (ConnectionPool): ConnectionPool object to use + + Returns: + bool: Whether the Redis server is alive or not + """ + r: redis.Redis = redis.Redis(connection_pool=connection_pool, socket_timeout=10.0) + return await r.ping() + +async def ensureOpenRedisConn() -> bool: + """Pings the Redis server to check if it's open or not + + Args: + connection_pool (Union[ConnectionPool, None]): The supplied connection pool. If none, it will be created automatically + + Returns: + bool: Whether the server is up or not + """ + connPool = kumikoCP.getConnPool() + r: redis.Redis = redis.Redis(connection_pool=connPool) + resultPing = await r.ping() + if resultPing: + logger.info("Sucessfully connected to the Redis server") + return True + logger.error("Failed to connect to the Redis server - Restart Kumiko to reconnect") + return False + + + +async def redisCheck( + backoff_sec: int = 15, + backoff_index: int = 0, +) -> Union[bool, None]: + """Integration method to check if the Redis server is alive + + Also sets up the conn pool cache. This is handled recursively actually. + There is a base case of 5 so the recursion only goes 5 calls deep on the stack. This is to prevent infinite calls on the stack from piling up. + + Args: + backoff_sec (int, optional): Backoff time in seconds. Defaults to 15. + backoff_index (int, optional): Backoff index. This is used privately Defaults to 0. + + Returns: + Union[Literal[True], None]: Returns True if the Redis server is alive. Returns None if the coroutine is in a recursive loop. + """ + try: + connPool = kumikoCP.getConnPool() + res = await pingRedis(connection_pool=connPool) + if backoff_index == 5: + logger.error("Unable to connect to Redis server") + return False + if res is True: + logger.info("Successfully connected to Redis server") + return True + except (ConnectionError, TimeoutError): + backoffTime = backoff(backoff_sec=backoff_sec, backoff_sec_index=backoff_index) + logger.error( + f"Failed to connect to Redis server - Restarting connection in {int(backoffTime)} seconds" + ) + await asyncio.sleep(backoffTime) + await redisCheck( + backoff_index=backoff_index + 1, + ) diff --git a/Bot/kumikobot.py b/Bot/kumikobot.py index a50cfc15..f286a5d4 100644 --- a/Bot/kumikobot.py +++ b/Bot/kumikobot.py @@ -5,36 +5,37 @@ from anyio import run from dotenv import load_dotenv from kumikocore import KumikoCore -from Libs.utils.postgresql import PrismaSessionManager from Libs.utils import KumikoLogger - +import asyncpg load_dotenv() KUMIKO_TOKEN = os.environ["DEV_BOT_TOKEN"] DEV_MODE = os.getenv("DEV_MODE") in ("True", "TRUE") +POSTGRES_URI = os.environ["POSTGRES_URI"] + intents = discord.Intents.default() intents.message_content = True async def main() -> None: - async with ClientSession() as session: + async with ClientSession() as session, asyncpg.create_pool(dsn=POSTGRES_URI, command_timeout=60, max_size=20, min_size=20) as pool: async with KumikoCore( intents=intents, session=session, + pool=pool, dev_mode=DEV_MODE, ) as bot: await bot.start(KUMIKO_TOKEN) def launch() -> None: - with PrismaSessionManager(): + with KumikoLogger(): run(main, backend_options={"use_uvloop": True}) if __name__ == "__main__": try: - with KumikoLogger(): - launch() + launch() except KeyboardInterrupt: pass diff --git a/Bot/kumikocore.py b/Bot/kumikocore.py index 23698667..ef5c1a31 100644 --- a/Bot/kumikocore.py +++ b/Bot/kumikocore.py @@ -6,7 +6,9 @@ from anyio import Path from discord.ext import commands from Libs.utils.help import KumikoHelpPaginated -from Libs.utils.redis import redisCheck +from Libs.utils.redis import ensureOpenRedisConn +from Libs.utils.postgresql import ensureOpenPostgresConn +import asyncpg # Some weird import logic to ensure that watchfiles is there _fsw = True @@ -23,6 +25,7 @@ def __init__( self, intents: discord.Intents, session: ClientSession, + pool: asyncpg.Pool, dev_mode: bool = False, *args, **kwargs, @@ -37,6 +40,7 @@ def __init__( ) self.dev_mode = dev_mode self._session = session + self._pool = pool self.logger: logging.Logger = logging.getLogger("kumikobot") @property @@ -48,6 +52,16 @@ def session(self) -> ClientSession: """ return self._session + @property + def pool(self) -> asyncpg.Pool: + """A global object managed throughout the lifetime of Kumiko + + Holds the asyncpg + + Returns: + asyncpg.Pool: asyncpg connection pool + """ + return self._pool async def fsWatcher(self) -> None: cogsPath = SyncPath(__file__).parent.joinpath("Cogs") async for changes in awatch(cogsPath): @@ -60,18 +74,23 @@ async def fsWatcher(self) -> None: async def setup_hook(self) -> None: cogsPath = Path(__file__).parent.joinpath("Cogs") async for cog in cogsPath.rglob("**/*.py"): - if cog.parent.name == "Cogs": - self.logger.debug( - f"Loaded extension: {cog.parent.name}.{cog.name[:-3]}" - ) - await self.load_extension(f"{cog.parent.name}.{cog.name[:-3]}") - else: - self.logger.debug( - f"Loaded extension: Cogs.{cog.parent.name}.{cog.name[:-3]}" - ) - await self.load_extension(f"Cogs.{cog.parent.name}.{cog.name[:-3]}") + self.logger.debug( + f"Loaded extension: {cog.parent.name}.{cog.name[:-3]}" + ) + await self.load_extension(f"{cog.parent.name}.{cog.name[:-3]}") + # if cog.parent.name == "Cogs": + # self.logger.debug( + # f"Loaded extension: {cog.parent.name}.{cog.name[:-3]}" + # ) + # await self.load_extension(f"{cog.parent.name}.{cog.name[:-3]}") + # else: + # self.logger.debug( + # f"Loaded extension: Cogs.{cog.parent.name}.{cog.name[:-3]}" + # ) + # await self.load_extension(f"Cogs.{cog.parent.name}.{cog.name[:-3]}") - self.loop.create_task(redisCheck()) + self.loop.create_task(ensureOpenPostgresConn(self._pool)) + self.loop.create_task(ensureOpenRedisConn()) if self.dev_mode is True and _fsw is True: self.logger.info("Dev mode is enabled. Loading Jishaku and FSWatcher") diff --git a/Bot/Cogs/economy.py b/Bot/unloaded_cogs/economy.py similarity index 100% rename from Bot/Cogs/economy.py rename to Bot/unloaded_cogs/economy.py diff --git a/Bot/Cogs/socket-events.py b/Bot/unloaded_cogs/socket-events.py similarity index 100% rename from Bot/Cogs/socket-events.py rename to Bot/unloaded_cogs/socket-events.py diff --git a/Migrations/20230612_initial_up_rev1.sql b/Migrations/20230612_initial_up_rev1.sql new file mode 100644 index 00000000..31db8aca --- /dev/null +++ b/Migrations/20230612_initial_up_rev1.sql @@ -0,0 +1,36 @@ +-- Initial Migrations +-- Created while I am in Saijo, Ehime + +CREATE TABLE IF NOT EXISTS guild ( + id BIGINT PRIMARY KEY, + prefix VARCHAR(255) NOT NULL, + logs BOOLEAN DEFAULT FALSE, + birthday BOOLEAN DEFAULT FALSE, + local_economy BOOLEAN DEFAULT FALSE +); + +CREATE TABLE IF NOT EXISTS eco_user ( + id BIGINT PRIMARY KEY, + rank INT DEFAULT 0, + petals INT DEFAULT 0, + date_joined timestamp WITHOUT TIME ZONE DEFAULT CURRENT_TIMESTAMP NOT NULL +); + +CREATE TABLE IF NOT EXISTS eco_item ( + id SERIAL PRIMARY KEY, + user_id BIGINT NOT NULL, + name VARCHAR(255) NOT NULL, + description TEXT, + price INT DEFAULT 0, + amount INT DEFAULT 0, + CONSTRAINT fk_user FOREIGN KEY (user_id) REFERENCES eco_user (id) ON DELETE CASCADE +); + +CREATE TABLE IF NOT EXISTS marketplace ( + id SERIAL PRIMARY KEY, + guild_id BIGINT NOT NULL, + name VARCHAR(255) NOT NULL, + description TEXT, + date_created timestamp WITHOUT TIME ZONE DEFAULT CURRENT_TIMESTAMP NOT NULL, + CONSTRAINT fk_guild FOREIGN KEY (guild_id) REFERENCES guild (id) ON DELETE CASCADE +); diff --git a/migrations-runner.py b/migrations-runner.py new file mode 100644 index 00000000..e30d52ad --- /dev/null +++ b/migrations-runner.py @@ -0,0 +1,46 @@ +import asyncio +import logging +import os +from pathlib import Path + +import asyncpg +from asyncpg_trek import Direction, execute, plan +from asyncpg_trek.asyncpg import AsyncpgBackend +from dotenv import load_dotenv + +load_dotenv() + +MIGRATIONS_DIR = Path(__file__).parent / "Migrations" + +POSTGRES_URI = os.environ["POSTGRES_URI"] +TARGET_REVISION = os.environ["TARGET_REVISION"] +logging.basicConfig( + level=logging.INFO, + format="%(asctime)s [Migrations] %(levelname)s %(message)s", + datefmt="[%Y-%m-%d %H:%M:%S]", +) + + +async def migrate( + conn: asyncpg.Connection, + target_revision: str, +) -> None: + backend = AsyncpgBackend(conn) + async with backend.connect(): + planned = await plan( + backend, + MIGRATIONS_DIR, + target_revision=target_revision, + direction=Direction.up, + ) + await execute(backend, planned) + + +async def main(): + async with asyncpg.create_pool(POSTGRES_URI) as pool: + async with pool.acquire() as conn: + await migrate(conn, TARGET_REVISION) + + +if __name__ == "__main__": + asyncio.run(main()) \ No newline at end of file From 053a9591c9779c89224a7ff50579573f472cae29 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Mon, 12 Jun 2023 19:00:50 +0000 Subject: [PATCH 093/184] [pip](deps): Bump discord-py from 2.2.3 to 2.3.0 (#350) Bumps [discord-py](https://github.com/Rapptz/discord.py) from 2.2.3 to 2.3.0. - [Commits](https://github.com/Rapptz/discord.py/compare/v2.2.3...v2.3.0) --- updated-dependencies: - dependency-name: discord-py dependency-type: direct:production update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index f3fce723..0a7852c0 100644 --- a/poetry.lock +++ b/poetry.lock @@ -934,13 +934,13 @@ resolved_reference = "8686b5d1bbc1d3c862292eb436ab630d6e9c9b53" [[package]] name = "discord-py" -version = "2.2.3" +version = "2.3.0" description = "A Python wrapper for the Discord API" optional = false python-versions = ">=3.8.0" files = [ - {file = "discord.py-2.2.3-py3-none-any.whl", hash = "sha256:792bdcfe71cfe013c446cf379b2e83e08b5050604322ad6fb592864e63511abd"}, - {file = "discord.py-2.2.3.tar.gz", hash = "sha256:f9df95795c6f52c5db43b7ab43634993e12ef233288636a759166dd9c134d077"}, + {file = "discord.py-2.3.0-py3-none-any.whl", hash = "sha256:3e9498967822ad4499f8f72deb9173f942d9827d92b6e4e4e7732d24f78f300c"}, + {file = "discord.py-2.3.0.tar.gz", hash = "sha256:c71066a30f037d069218e59092505c3e8945fd175e396a80748056d989756806"}, ] [package.dependencies] @@ -3381,4 +3381,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "3e5f86738b4ba88d47957a49352268c636b5adc6d0b840856469b8cab10b9601" +content-hash = "57d7ec83642f5405eb1cb30d6e696d5eefdd4f0f48025bd14e5cc406bd750ea8" diff --git a/pyproject.toml b/pyproject.toml index cfcc3e2b..7dddccc1 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -19,7 +19,7 @@ prisma = "^0.9.0" redis = {extras = ["hiredis"], version = "^4.5.5"} ciso8601 = "^2.3.0" faust-cchardet = "^2.1.18" -discord-py = {extras = ["voice"], version = "^2.2.3"} +discord-py = {extras = ["voice"], version = "^2.3.0"} discord-ext-menus = {git = "https://github.com/Rapptz/discord-ext-menus", rev = "8686b5d1bbc1d3c862292eb436ab630d6e9c9b53"} [tool.poetry.group.test.dependencies] From 78c960ca65f2386e775d47f05445b9d6af1f72fd Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 13 Jun 2023 18:58:51 +0000 Subject: [PATCH 094/184] [Actions](deps): Bump docker/build-push-action from 4.1.0 to 4.1.1 (#352) Bumps [docker/build-push-action](https://github.com/docker/build-push-action) from 4.1.0 to 4.1.1. - [Release notes](https://github.com/docker/build-push-action/releases) - [Commits](https://github.com/docker/build-push-action/compare/v4.1.0...v4.1.1) --- updated-dependencies: - dependency-name: docker/build-push-action dependency-type: direct:production update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- .github/workflows/docker-build.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/docker-build.yml b/.github/workflows/docker-build.yml index 6afd705d..2f5cd5a4 100644 --- a/.github/workflows/docker-build.yml +++ b/.github/workflows/docker-build.yml @@ -56,7 +56,7 @@ jobs: restore-keys: | ${{ runner.os }}-buildx-debian-ghcr- - name: Build and push - uses: docker/build-push-action@v4.1.0 + uses: docker/build-push-action@v4.1.1 with: context: . file: ./Docker/Dockerfile @@ -116,7 +116,7 @@ jobs: ${{ runner.os }}-buildx-debian-hub- - name: Build and push - uses: docker/build-push-action@v4.1.0 + uses: docker/build-push-action@v4.1.1 with: context: . file: ./Docker/Dockerfile From 6a578ac9f3a14198b47478176da8bea936017d43 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 13 Jun 2023 18:59:01 +0000 Subject: [PATCH 095/184] [pip](deps-dev): Bump myst-parser from 1.0.0 to 2.0.0 Bumps [myst-parser](https://github.com/executablebooks/MyST-Parser) from 1.0.0 to 2.0.0. - [Release notes](https://github.com/executablebooks/MyST-Parser/releases) - [Changelog](https://github.com/executablebooks/MyST-Parser/blob/master/CHANGELOG.md) - [Commits](https://github.com/executablebooks/MyST-Parser/compare/v1.0.0...v2.0.0) --- updated-dependencies: - dependency-name: myst-parser dependency-type: direct:development update-type: version-update:semver-major ... Signed-off-by: dependabot[bot] --- poetry.lock | 44 ++++++++++++++++++++++---------------------- pyproject.toml | 2 +- 2 files changed, 23 insertions(+), 23 deletions(-) diff --git a/poetry.lock b/poetry.lock index 0a7852c0..294a2148 100644 --- a/poetry.lock +++ b/poetry.lock @@ -1683,13 +1683,13 @@ tornado = {version = "*", markers = "python_version > \"2.7\""} [[package]] name = "markdown-it-py" -version = "2.2.0" +version = "3.0.0" description = "Python port of markdown-it. Markdown parsing, done right!" optional = false -python-versions = ">=3.7" +python-versions = ">=3.8" files = [ - {file = "markdown-it-py-2.2.0.tar.gz", hash = "sha256:7c9a5e412688bc771c67432cbfebcdd686c93ce6484913dccf06cb5a0bea35a1"}, - {file = "markdown_it_py-2.2.0-py3-none-any.whl", hash = "sha256:5a35f8d1870171d9acc47b99612dc146129b631baf04970128b568f190d0cc30"}, + {file = "markdown-it-py-3.0.0.tar.gz", hash = "sha256:e3f60a94fa066dc52ec76661e37c851cb232d92f9886b15cb560aaada2df8feb"}, + {file = "markdown_it_py-3.0.0-py3-none-any.whl", hash = "sha256:355216845c60bd96232cd8d8c40e8f9765cc86f46880e43a8fd22dc1a1a8cab1"}, ] [package.dependencies] @@ -1702,7 +1702,7 @@ compare = ["commonmark (>=0.9,<1.0)", "markdown (>=3.4,<4.0)", "mistletoe (>=1.0 linkify = ["linkify-it-py (>=1,<3)"] plugins = ["mdit-py-plugins"] profiling = ["gprof2dot"] -rtd = ["attrs", "myst-parser", "pyyaml", "sphinx", "sphinx-copybutton", "sphinx-design", "sphinx_book_theme"] +rtd = ["jupyter_sphinx", "mdit-py-plugins", "myst-parser", "pyyaml", "sphinx", "sphinx-copybutton", "sphinx-design", "sphinx_book_theme"] testing = ["coverage", "pytest", "pytest-cov", "pytest-regressions"] [[package]] @@ -1828,21 +1828,21 @@ python-dateutil = ">=2.7" [[package]] name = "mdit-py-plugins" -version = "0.3.5" +version = "0.4.0" description = "Collection of plugins for markdown-it-py" optional = false -python-versions = ">=3.7" +python-versions = ">=3.8" files = [ - {file = "mdit-py-plugins-0.3.5.tar.gz", hash = "sha256:eee0adc7195e5827e17e02d2a258a2ba159944a0748f59c5099a4a27f78fcf6a"}, - {file = "mdit_py_plugins-0.3.5-py3-none-any.whl", hash = "sha256:ca9a0714ea59a24b2b044a1831f48d817dd0c817e84339f20e7889f392d77c4e"}, + {file = "mdit_py_plugins-0.4.0-py3-none-any.whl", hash = "sha256:b51b3bb70691f57f974e257e367107857a93b36f322a9e6d44ca5bf28ec2def9"}, + {file = "mdit_py_plugins-0.4.0.tar.gz", hash = "sha256:d8ab27e9aed6c38aa716819fedfde15ca275715955f8a185a8e1cf90fb1d2c1b"}, ] [package.dependencies] -markdown-it-py = ">=1.0.0,<3.0.0" +markdown-it-py = ">=1.0.0,<4.0.0" [package.extras] code-style = ["pre-commit"] -rtd = ["attrs", "myst-parser (>=0.16.1,<0.17.0)", "sphinx-book-theme (>=0.1.0,<0.2.0)"] +rtd = ["myst-parser", "sphinx-book-theme"] testing = ["coverage", "pytest", "pytest-cov", "pytest-regressions"] [[package]] @@ -1941,27 +1941,27 @@ files = [ [[package]] name = "myst-parser" -version = "1.0.0" +version = "2.0.0" description = "An extended [CommonMark](https://spec.commonmark.org/) compliant parser," optional = false -python-versions = ">=3.7" +python-versions = ">=3.8" files = [ - {file = "myst-parser-1.0.0.tar.gz", hash = "sha256:502845659313099542bd38a2ae62f01360e7dd4b1310f025dd014dfc0439cdae"}, - {file = "myst_parser-1.0.0-py3-none-any.whl", hash = "sha256:69fb40a586c6fa68995e6521ac0a525793935db7e724ca9bac1d33be51be9a4c"}, + {file = "myst_parser-2.0.0-py3-none-any.whl", hash = "sha256:7c36344ae39c8e740dad7fdabf5aa6fc4897a813083c6cc9990044eb93656b14"}, + {file = "myst_parser-2.0.0.tar.gz", hash = "sha256:ea929a67a6a0b1683cdbe19b8d2e724cd7643f8aa3e7bb18dd65beac3483bead"}, ] [package.dependencies] -docutils = ">=0.15,<0.20" +docutils = ">=0.16,<0.21" jinja2 = "*" -markdown-it-py = ">=1.0.0,<3.0.0" -mdit-py-plugins = ">=0.3.4,<0.4.0" +markdown-it-py = ">=3.0,<4.0" +mdit-py-plugins = ">=0.4,<1.0" pyyaml = "*" -sphinx = ">=5,<7" +sphinx = ">=6,<8" [package.extras] code-style = ["pre-commit (>=3.0,<4.0)"] -linkify = ["linkify-it-py (>=1.0,<2.0)"] -rtd = ["ipython", "pydata-sphinx-theme (==v0.13.0rc4)", "sphinx-autodoc2 (>=0.4.2,<0.5.0)", "sphinx-book-theme (==1.0.0rc2)", "sphinx-copybutton", "sphinx-design2", "sphinx-pyscript", "sphinx-tippy (>=0.3.1)", "sphinx-togglebutton", "sphinxext-opengraph (>=0.7.5,<0.8.0)", "sphinxext-rediraffe (>=0.2.7,<0.3.0)"] +linkify = ["linkify-it-py (>=2.0,<3.0)"] +rtd = ["ipython", "pydata-sphinx-theme (==v0.13.0rc4)", "sphinx-autodoc2 (>=0.4.2,<0.5.0)", "sphinx-book-theme (==1.0.0rc2)", "sphinx-copybutton", "sphinx-design2", "sphinx-pyscript", "sphinx-tippy (>=0.3.1)", "sphinx-togglebutton", "sphinxext-opengraph (>=0.8.2,<0.9.0)", "sphinxext-rediraffe (>=0.2.7,<0.3.0)"] testing = ["beautifulsoup4", "coverage[toml]", "pytest (>=7,<8)", "pytest-cov", "pytest-param-files (>=0.3.4,<0.4.0)", "pytest-regressions", "sphinx-pytest"] testing-docutils = ["pygments", "pytest (>=7,<8)", "pytest-param-files (>=0.3.4,<0.4.0)"] @@ -3381,4 +3381,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "57d7ec83642f5405eb1cb30d6e696d5eefdd4f0f48025bd14e5cc406bd750ea8" +content-hash = "5ceb6275f25e6d60a3373541d6ab8057730fa5ae9a271dc796db856dd766337a" diff --git a/pyproject.toml b/pyproject.toml index 7dddccc1..fcff9c49 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -40,7 +40,7 @@ ruff = "^0.0.272" [tool.poetry.group.docs.dependencies] sphinx = "^6.2.1" -myst-parser = "^1.0.0" +myst-parser = "^2.0.0" sphinx-autobuild = "^2021.3.14" furo = "^2023.5.20" sphinxext-opengraph = "^0.8.2" From 7d5b59316e81c6d04d91eab7d316eddade998e9e Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Wed, 14 Jun 2023 08:42:12 +0900 Subject: [PATCH 096/184] [skip ci] Remove the rewrite warning in the Readme --- README.md | 2 -- 1 file changed, 2 deletions(-) diff --git a/README.md b/README.md index 40bce3b0..d229ef20 100644 --- a/README.md +++ b/README.md @@ -14,8 +14,6 @@ A multipurpose Discord bot built with freedom and choice in mind

    -| :bangbang: | Kumiko is currently undergoing a migration from Pycord to Discord.py (including a full rewrite). At this stage, Kumiko may not be working as intended. | -| :--------: | :---------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ## Kumiko (久美子) Kumiko is a multipurpose Discord bot built with freedom and choice in mind. Kumiko allows you to decide on whether you wish to use the services provided. Kumiko includes a opt-in economy system, custom quests, and many more features. Kumiko also includes integration with AniList, Reddit, Twitter, and others. From 805b40f58572bf6d7165c7885e07f812cb97feba Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Thu, 15 Jun 2023 00:21:18 +0900 Subject: [PATCH 097/184] Fix up dockerfiles --- Docker/Dockerfile | 5 +- Docker/start.sh | 128 +++++++++++++++++++++++----------------------- 2 files changed, 67 insertions(+), 66 deletions(-) diff --git a/Docker/Dockerfile b/Docker/Dockerfile index 91fc2fcc..2765ca21 100644 --- a/Docker/Dockerfile +++ b/Docker/Dockerfile @@ -45,9 +45,10 @@ RUN apt update \ WORKDIR /Kumiko COPY /Bot/kumikobot.py /Kumiko/Bot/ COPY /Bot/kumikocore.py /Kumiko/Bot/ -COPY /schema.prisma /Kumiko/Bot +COPY /Migrations /Kumiko/Migrations COPY /Bot/Cogs /Kumiko/Bot/Cogs COPY /Bot/Libs /Kumiko/Bot/Libs/ +COPY /migrations-runner.py /Kumiko/migrations-runner.py COPY /Docker/start.sh /Kumiko/start.sh COPY /Docker/wait-for /Kumiko/wait-for @@ -76,4 +77,4 @@ STOPSIGNAL SIGTERM LABEL org.opencontainers.image.title="Kumiko" LABEL org.opencontainers.image.description="A multipurpose Discord bot built with freedom and choice in mind" LABEL org.opencontainers.image.licenses="Apache-2.0" -LABEL org.opencontainers.image.source="https://github.com/No767/Kumiko" +LABEL org.opencontainers.image.source="https://github.com/No767/Kumiko" \ No newline at end of file diff --git a/Docker/start.sh b/Docker/start.sh index 7acdf7de..18b9a7a2 100644 --- a/Docker/start.sh +++ b/Docker/start.sh @@ -1,65 +1,65 @@ -#!/usr/bin/env bash - -if [[ -v KUMIKO_TOKEN ]]; then - echo "KUMIKO_TOKEN=${KUMIKO_TOKEN}" >> /Kumiko/Bot/.env -else - echo "Missing Kumiko's bot token! KUMIKO_TOKEN environment variable is not set." - exit 1; -fi - -# Testing bot token -# Not needed in production -if [[ -v DEV_BOT_TOKEN ]]; then - echo "DEV_BOT_TOKEN=${DEV_BOT_TOKEN}" >> /Kumiko/Bot/.env -fi - -# API Keys -# GitHub -# if [[ -v GITHUB_API_ACCESS_TOKEN ]]; then -# echo "GitHub_API_Access_Token=${GITHUB_API_ACCESS_TOKEN}" >> /Kumiko/Bot/.env -# else -# echo "Missing GitHub API token! GITHUB_API_ACCESS_TOKEN environment variable is not set." -# fi -# # Reddit ID -# if [[ -v REDDIT_ID ]]; then -# echo "Reddit_ID=${REDDIT_ID}" >> /Kumiko/Bot/.env -# else -# echo "Missing Reddit ID! REDDIT_ID environment variable is not set." -# fi -# # Reddit Secret -# if [[ -v REDDIT_SECRET ]]; then -# echo "Reddit_Secret=${REDDIT_SECRET}" >> /Kumiko/Bot/.env -# else -# echo "Missing Reddit secret! REDDIT_SECRET environment variable is not set." -# fi -# # Tenor -# if [[ -v TENOR_API_KEY ]]; then -# echo "Kumiko_Tenor_API_Key=${TENOR_API_KEY}" >> /Kumiko/Bot/.env -# else -# echo "Missing Tenor API key! TENOR_API_KEY environment variable is not set." -# fi -# YouTube - -# if [[ -v IPC_SECRET_KEY ]]; then -# echo "IPC_SECRET_KEY=${IPC_SECRET_KEY}" >> /Kumiko/Bot/.env -# else -# echo "Missing IPC_Secret_Key env var! IPC_Secret_Key environment variable is not set." -# exit 1; -# fi - -if [[ -v DATABASE_URL ]]; then - echo "DATABASE_URL=${DATABASE_URL}" >> /Kumiko/Bot/.env -else - echo "Missing DATABASE_URL env var! DATABASE_URL environment variable is not set." - exit 1; -fi - -KUMIKO_FIRST_START_CHECK="KUMIKO_FIRST_START" - -if [ ! -f $KUMIKO_FIRST_START_CHECK ]; then - touch $KUMIKO_FIRST_START_CHECK - echo 'DO NOT EDIT THIS FILE! THIS IS USED WHEN YOU FIRST RUN KUMIKO USING DOCKER!' >> $KUMIKO_FIRST_START_CHECK - prisma db push --schema /Kumiko/Bot/schema.prisma -fi - +#!/usr/bin/env bash + +# if [[ -v KUMIKO_TOKEN ]]; then +# echo "KUMIKO_TOKEN=${KUMIKO_TOKEN}" >> /Kumiko/Bot/.env +# else +# echo "Missing Kumiko's bot token! KUMIKO_TOKEN environment variable is not set." +# exit 1; +# fi + +# Testing bot token +# Not needed in production +# if [[ -v DEV_BOT_TOKEN ]]; then +# echo "DEV_BOT_TOKEN=${DEV_BOT_TOKEN}" >> /Kumiko/Bot/.env +# fi + +# API Keys +# GitHub +# if [[ -v GITHUB_API_ACCESS_TOKEN ]]; then +# echo "GitHub_API_Access_Token=${GITHUB_API_ACCESS_TOKEN}" >> /Kumiko/Bot/.env +# else +# echo "Missing GitHub API token! GITHUB_API_ACCESS_TOKEN environment variable is not set." +# fi +# # Reddit ID +# if [[ -v REDDIT_ID ]]; then +# echo "Reddit_ID=${REDDIT_ID}" >> /Kumiko/Bot/.env +# else +# echo "Missing Reddit ID! REDDIT_ID environment variable is not set." +# fi +# # Reddit Secret +# if [[ -v REDDIT_SECRET ]]; then +# echo "Reddit_Secret=${REDDIT_SECRET}" >> /Kumiko/Bot/.env +# else +# echo "Missing Reddit secret! REDDIT_SECRET environment variable is not set." +# fi +# # Tenor +# if [[ -v TENOR_API_KEY ]]; then +# echo "Kumiko_Tenor_API_Key=${TENOR_API_KEY}" >> /Kumiko/Bot/.env +# else +# echo "Missing Tenor API key! TENOR_API_KEY environment variable is not set." +# fi +# YouTube + +# if [[ -v IPC_SECRET_KEY ]]; then +# echo "IPC_SECRET_KEY=${IPC_SECRET_KEY}" >> /Kumiko/Bot/.env +# else +# echo "Missing IPC_Secret_Key env var! IPC_Secret_Key environment variable is not set." +# exit 1; +# fi + +# if [[ -v DATABASE_URL ]]; then +# echo "DATABASE_URL=${DATABASE_URL}" >> /Kumiko/Bot/.env +# else +# echo "Missing DATABASE_URL env var! DATABASE_URL environment variable is not set." +# exit 1; +# fi + +KUMIKO_FIRST_START_CHECK="KUMIKO_FIRST_START" + +if [ ! -f $KUMIKO_FIRST_START_CHECK ]; then + touch $KUMIKO_FIRST_START_CHECK + echo 'DO NOT EDIT THIS FILE! THIS IS USED WHEN YOU FIRST RUN KUMIKO USING DOCKER!' >> $KUMIKO_FIRST_START_CHECK + exec python3 /Kumiko/migrations-runner.py +fi + exec python3 /Kumiko/Bot/kumikobot.py \ No newline at end of file From 7fc0ad3ac2126b26b702c64d148c241c9a8d52bd Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 14 Jun 2023 18:59:53 +0000 Subject: [PATCH 098/184] [pip](deps-dev): Bump pre-commit from 3.3.2 to 3.3.3 (#354) Bumps [pre-commit](https://github.com/pre-commit/pre-commit) from 3.3.2 to 3.3.3. - [Release notes](https://github.com/pre-commit/pre-commit/releases) - [Changelog](https://github.com/pre-commit/pre-commit/blob/main/CHANGELOG.md) - [Commits](https://github.com/pre-commit/pre-commit/compare/v3.3.2...v3.3.3) --- updated-dependencies: - dependency-name: pre-commit dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index 294a2148..e4245116 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2229,13 +2229,13 @@ testing = ["pytest", "pytest-benchmark"] [[package]] name = "pre-commit" -version = "3.3.2" +version = "3.3.3" description = "A framework for managing and maintaining multi-language pre-commit hooks." optional = false python-versions = ">=3.8" files = [ - {file = "pre_commit-3.3.2-py2.py3-none-any.whl", hash = "sha256:8056bc52181efadf4aac792b1f4f255dfd2fb5a350ded7335d251a68561e8cb6"}, - {file = "pre_commit-3.3.2.tar.gz", hash = "sha256:66e37bec2d882de1f17f88075047ef8962581f83c234ac08da21a0c58953d1f0"}, + {file = "pre_commit-3.3.3-py2.py3-none-any.whl", hash = "sha256:10badb65d6a38caff29703362271d7dca483d01da88f9d7e05d0b97171c136cb"}, + {file = "pre_commit-3.3.3.tar.gz", hash = "sha256:a2256f489cd913d575c145132ae196fe335da32d91a8294b7afe6622335dd023"}, ] [package.dependencies] @@ -3381,4 +3381,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "5ceb6275f25e6d60a3373541d6ab8057730fa5ae9a271dc796db856dd766337a" +content-hash = "4d0604dbc4fc77f81618653280a30a9c1a16f6102d96a79b6900a3aec3fc5db4" diff --git a/pyproject.toml b/pyproject.toml index fcff9c49..7d33931a 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -30,7 +30,7 @@ nox-poetry = "^1.0.2" pytest-cov = "^4.1.0" [tool.poetry.group.dev.dependencies] -pre-commit = "^3.3.2" +pre-commit = "^3.3.3" pyinstrument = "^4.5.0" pyright = "^1.1.313" watchfiles = "^0.19.0" From 924b94f43e8cbc08b3e73cc1c22673aaef4d98e9 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Thu, 15 Jun 2023 08:39:48 +0000 Subject: [PATCH 099/184] [pip](deps-dev): Bump pyright from 1.1.313 to 1.1.314 (#356) Bumps [pyright](https://github.com/RobertCraigie/pyright-python) from 1.1.313 to 1.1.314. - [Release notes](https://github.com/RobertCraigie/pyright-python/releases) - [Commits](https://github.com/RobertCraigie/pyright-python/compare/v1.1.313...v1.1.314) --- updated-dependencies: - dependency-name: pyright dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index e4245116..0726b801 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2518,13 +2518,13 @@ diagrams = ["jinja2", "railroad-diagrams"] [[package]] name = "pyright" -version = "1.1.313" +version = "1.1.314" description = "Command line wrapper for pyright" optional = false python-versions = ">=3.7" files = [ - {file = "pyright-1.1.313-py3-none-any.whl", hash = "sha256:1aeed72d5563e97461cb9d17847bfa918f7ec0cf79912bb3d2432fbe014daa23"}, - {file = "pyright-1.1.313.tar.gz", hash = "sha256:95fa963337e2cfd4900601197d0f866d8c51732dea6c0bb12f962f92a79c77e3"}, + {file = "pyright-1.1.314-py3-none-any.whl", hash = "sha256:5008a2e04b71e35c5f1b78b16adae9d012601197442ae6c798e9bb3456d1eecb"}, + {file = "pyright-1.1.314.tar.gz", hash = "sha256:bd104c206fe40eaf5f836efa9027f07cc0efcbc452e6d22dfae36759c5fd28b3"}, ] [package.dependencies] @@ -3381,4 +3381,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "4d0604dbc4fc77f81618653280a30a9c1a16f6102d96a79b6900a3aec3fc5db4" +content-hash = "d520060af463924cbbedbbf3f1e21cc567a83c015c378c04351587522d3ded93" diff --git a/pyproject.toml b/pyproject.toml index 7d33931a..331a3b68 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -32,7 +32,7 @@ pytest-cov = "^4.1.0" [tool.poetry.group.dev.dependencies] pre-commit = "^3.3.3" pyinstrument = "^4.5.0" -pyright = "^1.1.313" +pyright = "^1.1.314" watchfiles = "^0.19.0" jishaku = "^2.5.1" ruff = "^0.0.272" From 0472eae08171488a68d5855e69a9a1cfa98b44f7 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Thu, 15 Jun 2023 08:41:00 +0000 Subject: [PATCH 100/184] [pip](deps-dev): Bump sphinx from 6.2.1 to 7.0.1 Bumps [sphinx](https://github.com/sphinx-doc/sphinx) from 6.2.1 to 7.0.1. - [Release notes](https://github.com/sphinx-doc/sphinx/releases) - [Changelog](https://github.com/sphinx-doc/sphinx/blob/master/CHANGES) - [Commits](https://github.com/sphinx-doc/sphinx/compare/v6.2.1...v7.0.1) --- updated-dependencies: - dependency-name: sphinx dependency-type: direct:development update-type: version-update:semver-major ... Signed-off-by: dependabot[bot] --- poetry.lock | 10 +++++----- pyproject.toml | 2 +- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/poetry.lock b/poetry.lock index 0726b801..b512aadc 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2825,20 +2825,20 @@ files = [ [[package]] name = "sphinx" -version = "6.2.1" +version = "7.0.1" description = "Python documentation generator" optional = false python-versions = ">=3.8" files = [ - {file = "Sphinx-6.2.1.tar.gz", hash = "sha256:6d56a34697bb749ffa0152feafc4b19836c755d90a7c59b72bc7dfd371b9cc6b"}, - {file = "sphinx-6.2.1-py3-none-any.whl", hash = "sha256:97787ff1fa3256a3eef9eda523a63dbf299f7b47e053cfcf684a1c2a8380c912"}, + {file = "Sphinx-7.0.1.tar.gz", hash = "sha256:61e025f788c5977d9412587e733733a289e2b9fdc2fef8868ddfbfc4ccfe881d"}, + {file = "sphinx-7.0.1-py3-none-any.whl", hash = "sha256:60c5e04756c1709a98845ed27a2eed7a556af3993afb66e77fec48189f742616"}, ] [package.dependencies] alabaster = ">=0.7,<0.8" babel = ">=2.9" colorama = {version = ">=0.4.5", markers = "sys_platform == \"win32\""} -docutils = ">=0.18.1,<0.20" +docutils = ">=0.18.1,<0.21" imagesize = ">=1.3" importlib-metadata = {version = ">=4.8", markers = "python_version < \"3.10\""} Jinja2 = ">=3.0" @@ -3381,4 +3381,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "d520060af463924cbbedbbf3f1e21cc567a83c015c378c04351587522d3ded93" +content-hash = "871474ee0cb4b69c8c5d44402751a6dbfd61e18bdc4c36af404a410c2661998e" diff --git a/pyproject.toml b/pyproject.toml index 331a3b68..ec54b65f 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -39,7 +39,7 @@ ruff = "^0.0.272" [tool.poetry.group.docs.dependencies] -sphinx = "^6.2.1" +sphinx = "^7.0.1" myst-parser = "^2.0.0" sphinx-autobuild = "^2021.3.14" furo = "^2023.5.20" From f460ed459f768d179096f3f16795847932c2186c Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Sun, 18 Jun 2023 23:42:13 +0900 Subject: [PATCH 101/184] [skip ci] Add testing cog for embeds --- Bot/unloaded_cogs/embeds.py | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) create mode 100644 Bot/unloaded_cogs/embeds.py diff --git a/Bot/unloaded_cogs/embeds.py b/Bot/unloaded_cogs/embeds.py new file mode 100644 index 00000000..15da7acc --- /dev/null +++ b/Bot/unloaded_cogs/embeds.py @@ -0,0 +1,21 @@ +from Libs.utils import Embed +from discord.ext import commands +from kumikocore import KumikoCore +import logging +from discord.utils import utcnow +class EmbedCog(commands.Cog): + """Embed test cog - Please only sync locally""" + def __init__(self, bot: KumikoCore) -> None: + self.bot = bot + self.logger = logging.getLogger("discord") + + @commands.hybrid_command(name="embed-time") + async def embedTime(self, ctx: commands.Context) -> None: + embed = Embed() + embed.timestamp = utcnow() + self.logger.info(f"Timestamp: {embed.timestamp}") + embed.set_footer(text=f"{embed.timestamp}") + await ctx.send(embed=embed) + +async def setup(bot: KumikoCore) -> None: + await bot.add_cog(EmbedCog(bot)) From f54c4654cd6de032738d860bc074fefa8410d656 Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Sun, 18 Jun 2023 23:45:57 +0900 Subject: [PATCH 102/184] Swap Dockerfiles to use Debian 12 instead of 11 --- Docker/Dockerfile | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Docker/Dockerfile b/Docker/Dockerfile index 2765ca21..e09c33da 100644 --- a/Docker/Dockerfile +++ b/Docker/Dockerfile @@ -1,7 +1,7 @@ #################################################################################################### ## Builder image #################################################################################################### -FROM python:3.11-slim-bullseye AS builder +FROM python:3.11-slim-bookworm AS builder ENV DEBIAN_FRONTEND=noninteractive @@ -29,7 +29,7 @@ RUN poetry export -f requirements.txt --output requirements.txt --without-hashes #################################################################################################### ## Final image #################################################################################################### -FROM python:3.11-slim-bullseye +FROM python:3.11-slim-bookworm RUN apt update \ && apt install -y --no-install-recommends \ From 75fdad7b722c6e81c7c4292505d8a4e22c9f046c Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 21 Jun 2023 18:11:25 +0000 Subject: [PATCH 103/184] [pip](deps-dev): Bump pyright from 1.1.314 to 1.1.315 (#357) Bumps [pyright](https://github.com/RobertCraigie/pyright-python) from 1.1.314 to 1.1.315. - [Release notes](https://github.com/RobertCraigie/pyright-python/releases) - [Commits](https://github.com/RobertCraigie/pyright-python/compare/v1.1.314...v1.1.315) --- updated-dependencies: - dependency-name: pyright dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index b512aadc..21918f60 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2518,13 +2518,13 @@ diagrams = ["jinja2", "railroad-diagrams"] [[package]] name = "pyright" -version = "1.1.314" +version = "1.1.315" description = "Command line wrapper for pyright" optional = false python-versions = ">=3.7" files = [ - {file = "pyright-1.1.314-py3-none-any.whl", hash = "sha256:5008a2e04b71e35c5f1b78b16adae9d012601197442ae6c798e9bb3456d1eecb"}, - {file = "pyright-1.1.314.tar.gz", hash = "sha256:bd104c206fe40eaf5f836efa9027f07cc0efcbc452e6d22dfae36759c5fd28b3"}, + {file = "pyright-1.1.315-py3-none-any.whl", hash = "sha256:262744daa7455f6056f6d6609b6278258e2fd7bd100d8937203516ee71d0eb93"}, + {file = "pyright-1.1.315.tar.gz", hash = "sha256:f124400a1a72ccc5fd04836e7e48ed235e8f7929bcc42b270a571fb34df17979"}, ] [package.dependencies] @@ -3381,4 +3381,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "871474ee0cb4b69c8c5d44402751a6dbfd61e18bdc4c36af404a410c2661998e" +content-hash = "aa7f407867933191c1a7598ed2ae80dec2d117fe4a8798eaeb536ac203a3572a" diff --git a/pyproject.toml b/pyproject.toml index ec54b65f..f8f260f0 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -32,7 +32,7 @@ pytest-cov = "^4.1.0" [tool.poetry.group.dev.dependencies] pre-commit = "^3.3.3" pyinstrument = "^4.5.0" -pyright = "^1.1.314" +pyright = "^1.1.315" watchfiles = "^0.19.0" jishaku = "^2.5.1" ruff = "^0.0.272" From 35494323bb89fd7bbbb67e920f467f429d1cc351 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 21 Jun 2023 23:37:10 +0000 Subject: [PATCH 104/184] [pip](deps-dev): Bump ruff from 0.0.272 to 0.0.274 (#358) Bumps [ruff](https://github.com/astral-sh/ruff) from 0.0.272 to 0.0.274. - [Release notes](https://github.com/astral-sh/ruff/releases) - [Changelog](https://github.com/astral-sh/ruff/blob/main/BREAKING_CHANGES.md) - [Commits](https://github.com/astral-sh/ruff/compare/v0.0.272...v0.0.274) --- updated-dependencies: - dependency-name: ruff dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 38 +++++++++++++++++++------------------- pyproject.toml | 2 +- 2 files changed, 20 insertions(+), 20 deletions(-) diff --git a/poetry.lock b/poetry.lock index 21918f60..fa40295f 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2739,28 +2739,28 @@ idna2008 = ["idna"] [[package]] name = "ruff" -version = "0.0.272" +version = "0.0.274" description = "An extremely fast Python linter, written in Rust." optional = false python-versions = ">=3.7" files = [ - {file = "ruff-0.0.272-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:ae9b57546e118660175d45d264b87e9b4c19405c75b587b6e4d21e6a17bf4fdf"}, - {file = "ruff-0.0.272-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:1609b864a8d7ee75a8c07578bdea0a7db75a144404e75ef3162e0042bfdc100d"}, - {file = "ruff-0.0.272-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ee76b4f05fcfff37bd6ac209d1370520d509ea70b5a637bdf0a04d0c99e13dff"}, - {file = "ruff-0.0.272-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:48eccf225615e106341a641f826b15224b8a4240b84269ead62f0afd6d7e2d95"}, - {file = "ruff-0.0.272-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:677284430ac539bb23421a2b431b4ebc588097ef3ef918d0e0a8d8ed31fea216"}, - {file = "ruff-0.0.272-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:9c4bfb75456a8e1efe14c52fcefb89cfb8f2a0d31ed8d804b82c6cf2dc29c42c"}, - {file = "ruff-0.0.272-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:86bc788245361a8148ff98667da938a01e1606b28a45e50ac977b09d3ad2c538"}, - {file = "ruff-0.0.272-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:27b2ea68d2aa69fff1b20b67636b1e3e22a6a39e476c880da1282c3e4bf6ee5a"}, - {file = "ruff-0.0.272-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:bd2bbe337a3f84958f796c77820d55ac2db1e6753f39d1d1baed44e07f13f96d"}, - {file = "ruff-0.0.272-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:d5a208f8ef0e51d4746930589f54f9f92f84bb69a7d15b1de34ce80a7681bc00"}, - {file = "ruff-0.0.272-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:905ff8f3d6206ad56fcd70674453527b9011c8b0dc73ead27618426feff6908e"}, - {file = "ruff-0.0.272-py3-none-musllinux_1_2_i686.whl", hash = "sha256:19643d448f76b1eb8a764719072e9c885968971bfba872e14e7257e08bc2f2b7"}, - {file = "ruff-0.0.272-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:691d72a00a99707a4e0b2846690961157aef7b17b6b884f6b4420a9f25cd39b5"}, - {file = "ruff-0.0.272-py3-none-win32.whl", hash = "sha256:dc406e5d756d932da95f3af082814d2467943631a587339ee65e5a4f4fbe83eb"}, - {file = "ruff-0.0.272-py3-none-win_amd64.whl", hash = "sha256:a37ec80e238ead2969b746d7d1b6b0d31aa799498e9ba4281ab505b93e1f4b28"}, - {file = "ruff-0.0.272-py3-none-win_arm64.whl", hash = "sha256:06b8ee4eb8711ab119db51028dd9f5384b44728c23586424fd6e241a5b9c4a3b"}, - {file = "ruff-0.0.272.tar.gz", hash = "sha256:273a01dc8c3c4fd4c2af7ea7a67c8d39bb09bce466e640dd170034da75d14cab"}, + {file = "ruff-0.0.274-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:6d7069157a5674be8090c7d89fa69dbb2478f333a80b1312d20ade2a870cca3e"}, + {file = "ruff-0.0.274-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:fa9ad8776cb92f2739b8eee316cde841d6012d0eafbf06bae09166203ddf9bb8"}, + {file = "ruff-0.0.274-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:6133fa856b230a0281197aeba3e89ce9595f9d8a7265113520ad259d416c9f4b"}, + {file = "ruff-0.0.274-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:023cdc5e64b3f34244e12bd236ab412c6056061a2415d50fb862cab333b4ab7c"}, + {file = "ruff-0.0.274-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:34e71a06a4e27554ca2f1c2b1749a802e3e76cac41481cfc2cb86936c1e37d3c"}, + {file = "ruff-0.0.274-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:5137f853fffa7352901038a1b5e36a97058380a554763e534aae9f6c0734fdab"}, + {file = "ruff-0.0.274-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:044084f039a679e557240fefcf521e057941b163014cf969ac6d04620861e04a"}, + {file = "ruff-0.0.274-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:dca36d651f88b4b24f17df5db54487057ce0ccd3599cbf38d237cf4d9f0d63c2"}, + {file = "ruff-0.0.274-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:587130943110e9536018ce139158e2962d46623f379a4486aabfd525e9714b0e"}, + {file = "ruff-0.0.274-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:39b80156ef57b33ab7bfc454b7c2678eaae07f43a7dcf2e7c058f72d87b49538"}, + {file = "ruff-0.0.274-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:86d943107f20fec924f56dc4933cefb0efbc1ec8b729e0a1afabac598c5586ca"}, + {file = "ruff-0.0.274-py3-none-musllinux_1_2_i686.whl", hash = "sha256:b13e765b64487143f05e6ad6f624388b9ac5a6ff8657ff801091c9282de3ca52"}, + {file = "ruff-0.0.274-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:461bda8c3a4c1591fd7a09960b86e2ffc9a59a1c42cf14d725077314c12b60b0"}, + {file = "ruff-0.0.274-py3-none-win32.whl", hash = "sha256:09c87fa2c4f53bd63c1d8a35150683794b022f4f2fbd6ef2fe383ce21ab53fec"}, + {file = "ruff-0.0.274-py3-none-win_amd64.whl", hash = "sha256:e80aa0c7e1347a96db846287695971925eb56760c019a7d66312fbca389a6800"}, + {file = "ruff-0.0.274-py3-none-win_arm64.whl", hash = "sha256:8b99ce776fc60fb938791f558b297e53ed634adeef1a7b84a33455924948c9af"}, + {file = "ruff-0.0.274.tar.gz", hash = "sha256:c7e5f9deffbd02d8054f90b565a1106faee64e16cedf50f3aa05c14b59ff8727"}, ] [[package]] @@ -3381,4 +3381,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "aa7f407867933191c1a7598ed2ae80dec2d117fe4a8798eaeb536ac203a3572a" +content-hash = "12eca92d5c39229f4a6027e6af9e22638de25fdf013e62d3053c796f145a90a5" diff --git a/pyproject.toml b/pyproject.toml index f8f260f0..997fb887 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -35,7 +35,7 @@ pyinstrument = "^4.5.0" pyright = "^1.1.315" watchfiles = "^0.19.0" jishaku = "^2.5.1" -ruff = "^0.0.272" +ruff = "^0.0.274" [tool.poetry.group.docs.dependencies] From e45fe71fc30629bfaa8d237a4522fb65d2a1d5cc Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Thu, 22 Jun 2023 19:02:46 +0000 Subject: [PATCH 105/184] [pip](deps-dev): Bump ruff from 0.0.274 to 0.0.275 (#359) Bumps [ruff](https://github.com/astral-sh/ruff) from 0.0.274 to 0.0.275. - [Release notes](https://github.com/astral-sh/ruff/releases) - [Changelog](https://github.com/astral-sh/ruff/blob/main/BREAKING_CHANGES.md) - [Commits](https://github.com/astral-sh/ruff/compare/v0.0.274...v0.0.275) --- updated-dependencies: - dependency-name: ruff dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 38 +++++++++++++++++++------------------- pyproject.toml | 2 +- 2 files changed, 20 insertions(+), 20 deletions(-) diff --git a/poetry.lock b/poetry.lock index fa40295f..90604c84 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2739,28 +2739,28 @@ idna2008 = ["idna"] [[package]] name = "ruff" -version = "0.0.274" +version = "0.0.275" description = "An extremely fast Python linter, written in Rust." optional = false python-versions = ">=3.7" files = [ - {file = "ruff-0.0.274-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:6d7069157a5674be8090c7d89fa69dbb2478f333a80b1312d20ade2a870cca3e"}, - {file = "ruff-0.0.274-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:fa9ad8776cb92f2739b8eee316cde841d6012d0eafbf06bae09166203ddf9bb8"}, - {file = "ruff-0.0.274-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:6133fa856b230a0281197aeba3e89ce9595f9d8a7265113520ad259d416c9f4b"}, - {file = "ruff-0.0.274-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:023cdc5e64b3f34244e12bd236ab412c6056061a2415d50fb862cab333b4ab7c"}, - {file = "ruff-0.0.274-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:34e71a06a4e27554ca2f1c2b1749a802e3e76cac41481cfc2cb86936c1e37d3c"}, - {file = "ruff-0.0.274-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:5137f853fffa7352901038a1b5e36a97058380a554763e534aae9f6c0734fdab"}, - {file = "ruff-0.0.274-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:044084f039a679e557240fefcf521e057941b163014cf969ac6d04620861e04a"}, - {file = "ruff-0.0.274-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:dca36d651f88b4b24f17df5db54487057ce0ccd3599cbf38d237cf4d9f0d63c2"}, - {file = "ruff-0.0.274-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:587130943110e9536018ce139158e2962d46623f379a4486aabfd525e9714b0e"}, - {file = "ruff-0.0.274-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:39b80156ef57b33ab7bfc454b7c2678eaae07f43a7dcf2e7c058f72d87b49538"}, - {file = "ruff-0.0.274-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:86d943107f20fec924f56dc4933cefb0efbc1ec8b729e0a1afabac598c5586ca"}, - {file = "ruff-0.0.274-py3-none-musllinux_1_2_i686.whl", hash = "sha256:b13e765b64487143f05e6ad6f624388b9ac5a6ff8657ff801091c9282de3ca52"}, - {file = "ruff-0.0.274-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:461bda8c3a4c1591fd7a09960b86e2ffc9a59a1c42cf14d725077314c12b60b0"}, - {file = "ruff-0.0.274-py3-none-win32.whl", hash = "sha256:09c87fa2c4f53bd63c1d8a35150683794b022f4f2fbd6ef2fe383ce21ab53fec"}, - {file = "ruff-0.0.274-py3-none-win_amd64.whl", hash = "sha256:e80aa0c7e1347a96db846287695971925eb56760c019a7d66312fbca389a6800"}, - {file = "ruff-0.0.274-py3-none-win_arm64.whl", hash = "sha256:8b99ce776fc60fb938791f558b297e53ed634adeef1a7b84a33455924948c9af"}, - {file = "ruff-0.0.274.tar.gz", hash = "sha256:c7e5f9deffbd02d8054f90b565a1106faee64e16cedf50f3aa05c14b59ff8727"}, + {file = "ruff-0.0.275-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:5e6554a072e7ce81eb6f0bec1cebd3dcb0e358652c0f4900d7d630d61691e914"}, + {file = "ruff-0.0.275-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:1cc599022fe5ffb143a965b8d659eb64161ab8ab4433d208777eab018a1aab67"}, + {file = "ruff-0.0.275-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:5206fc1cd8c1c1deadd2e6360c0dbcd690f1c845da588ca9d32e4a764a402c60"}, + {file = "ruff-0.0.275-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:0c4e6468da26f77b90cae35319d310999f471a8c352998e9b39937a23750149e"}, + {file = "ruff-0.0.275-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:0dbdea02942131dbc15dd45f431d152224f15e1dd1859fcd0c0487b658f60f1a"}, + {file = "ruff-0.0.275-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:22efd9f41af27ef8fb9779462c46c35c89134d33e326c889971e10b2eaf50c63"}, + {file = "ruff-0.0.275-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:2c09662112cfa22d7467a19252a546291fd0eae4f423e52b75a7a2000a1894db"}, + {file = "ruff-0.0.275-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:80043726662144876a381efaab88841c88e8df8baa69559f96b22d4fa216bef1"}, + {file = "ruff-0.0.275-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5859ee543b01b7eb67835dfd505faa8bb7cc1550f0295c92c1401b45b42be399"}, + {file = "ruff-0.0.275-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:c8ace4d40a57b5ea3c16555f25a6b16bc5d8b2779ae1912ce2633543d4e9b1da"}, + {file = "ruff-0.0.275-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:8347fc16aa185aae275906c4ac5b770e00c896b6a0acd5ba521f158801911998"}, + {file = "ruff-0.0.275-py3-none-musllinux_1_2_i686.whl", hash = "sha256:ec43658c64bfda44fd84bbea9da8c7a3b34f65448192d1c4dd63e9f4e7abfdd4"}, + {file = "ruff-0.0.275-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:508b13f7ca37274cceaba4fb3ea5da6ca192356323d92acf39462337c33ad14e"}, + {file = "ruff-0.0.275-py3-none-win32.whl", hash = "sha256:6afb1c4422f24f361e877937e2a44b3f8176774a476f5e33845ebfe887dd5ec2"}, + {file = "ruff-0.0.275-py3-none-win_amd64.whl", hash = "sha256:d9b264d78621bf7b698b6755d4913ab52c19bd28bee1a16001f954d64c1a1220"}, + {file = "ruff-0.0.275-py3-none-win_arm64.whl", hash = "sha256:a19ce3bea71023eee5f0f089dde4a4272d088d5ac0b675867e074983238ccc65"}, + {file = "ruff-0.0.275.tar.gz", hash = "sha256:a63a0b645da699ae5c758fce19188e901b3033ec54d862d93fcd042addf7f38d"}, ] [[package]] @@ -3381,4 +3381,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "12eca92d5c39229f4a6027e6af9e22638de25fdf013e62d3053c796f145a90a5" +content-hash = "470103fc1e679855c0b0fa043f5e36091f62868ee17cdb1664a6b475f7210197" diff --git a/pyproject.toml b/pyproject.toml index 997fb887..35f80cfc 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -35,7 +35,7 @@ pyinstrument = "^4.5.0" pyright = "^1.1.315" watchfiles = "^0.19.0" jishaku = "^2.5.1" -ruff = "^0.0.274" +ruff = "^0.0.275" [tool.poetry.group.docs.dependencies] From 9bd8a5886a2901d9b7bbb84e234483f560d345e8 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Fri, 23 Jun 2023 18:59:09 +0000 Subject: [PATCH 106/184] [pip](deps-dev): Bump pytest from 7.3.2 to 7.4.0 (#360) Bumps [pytest](https://github.com/pytest-dev/pytest) from 7.3.2 to 7.4.0. - [Release notes](https://github.com/pytest-dev/pytest/releases) - [Changelog](https://github.com/pytest-dev/pytest/blob/main/CHANGELOG.rst) - [Commits](https://github.com/pytest-dev/pytest/compare/7.3.2...7.4.0) --- updated-dependencies: - dependency-name: pytest dependency-type: direct:development update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index 90604c84..9daa70c4 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2536,13 +2536,13 @@ dev = ["twine (>=3.4.1)"] [[package]] name = "pytest" -version = "7.3.2" +version = "7.4.0" description = "pytest: simple powerful testing with Python" optional = false python-versions = ">=3.7" files = [ - {file = "pytest-7.3.2-py3-none-any.whl", hash = "sha256:cdcbd012c9312258922f8cd3f1b62a6580fdced17db6014896053d47cddf9295"}, - {file = "pytest-7.3.2.tar.gz", hash = "sha256:ee990a3cc55ba808b80795a79944756f315c67c12b56abd3ac993a7b8c17030b"}, + {file = "pytest-7.4.0-py3-none-any.whl", hash = "sha256:78bf16451a2eb8c7a2ea98e32dc119fd2aa758f1d5d66dbf0a59d69a3969df32"}, + {file = "pytest-7.4.0.tar.gz", hash = "sha256:b4bf8c45bd59934ed84001ad51e11b4ee40d40a1229d2c79f9c592b0a3f6bd8a"}, ] [package.dependencies] @@ -3381,4 +3381,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "470103fc1e679855c0b0fa043f5e36091f62868ee17cdb1664a6b475f7210197" +content-hash = "a0380e9ba09b8b253fc2a9a95bccd3c3ae183e35c6bf0961a55bae8c8e66dd59" diff --git a/pyproject.toml b/pyproject.toml index 35f80cfc..17c5e73c 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -23,7 +23,7 @@ discord-py = {extras = ["voice"], version = "^2.3.0"} discord-ext-menus = {git = "https://github.com/Rapptz/discord-ext-menus", rev = "8686b5d1bbc1d3c862292eb436ab630d6e9c9b53"} [tool.poetry.group.test.dependencies] -pytest = "^7.3.2" +pytest = "^7.4.0" pytest-asyncio = "^0.21.0" nox = "^2023.4.22" nox-poetry = "^1.0.2" From 3ea06bc57ab4e5f6b039cf6466d788838a1c0c03 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Mon, 26 Jun 2023 19:00:27 +0000 Subject: [PATCH 107/184] [pip](deps): Bump discord-py from 2.3.0 to 2.3.1 (#361) Bumps [discord-py](https://github.com/Rapptz/discord.py) from 2.3.0 to 2.3.1. - [Commits](https://github.com/Rapptz/discord.py/compare/v2.3.0...v2.3.1) --- updated-dependencies: - dependency-name: discord-py dependency-type: direct:production update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index 9daa70c4..b41d086b 100644 --- a/poetry.lock +++ b/poetry.lock @@ -934,13 +934,13 @@ resolved_reference = "8686b5d1bbc1d3c862292eb436ab630d6e9c9b53" [[package]] name = "discord-py" -version = "2.3.0" +version = "2.3.1" description = "A Python wrapper for the Discord API" optional = false python-versions = ">=3.8.0" files = [ - {file = "discord.py-2.3.0-py3-none-any.whl", hash = "sha256:3e9498967822ad4499f8f72deb9173f942d9827d92b6e4e4e7732d24f78f300c"}, - {file = "discord.py-2.3.0.tar.gz", hash = "sha256:c71066a30f037d069218e59092505c3e8945fd175e396a80748056d989756806"}, + {file = "discord.py-2.3.1-py3-none-any.whl", hash = "sha256:149652f24da299706270bf8c03c2fcf80cf1caf3a480744c61d5b001688b380d"}, + {file = "discord.py-2.3.1.tar.gz", hash = "sha256:8eb4fe66b5d503da6de3a8425e23012711dc2fbcd7a782107a92beac15ee3459"}, ] [package.dependencies] @@ -3381,4 +3381,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "a0380e9ba09b8b253fc2a9a95bccd3c3ae183e35c6bf0961a55bae8c8e66dd59" +content-hash = "de7851499e4278e42e191b472332c176a257b25d58ae8899c4c2670b471cde41" diff --git a/pyproject.toml b/pyproject.toml index 17c5e73c..280ae3d1 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -19,7 +19,7 @@ prisma = "^0.9.0" redis = {extras = ["hiredis"], version = "^4.5.5"} ciso8601 = "^2.3.0" faust-cchardet = "^2.1.18" -discord-py = {extras = ["voice"], version = "^2.3.0"} +discord-py = {extras = ["voice"], version = "^2.3.1"} discord-ext-menus = {git = "https://github.com/Rapptz/discord-ext-menus", rev = "8686b5d1bbc1d3c862292eb436ab630d6e9c9b53"} [tool.poetry.group.test.dependencies] From e389e9ef3355535794f04f68ca87e87a1cf3a2b7 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 28 Jun 2023 08:14:09 +0000 Subject: [PATCH 108/184] [pip](deps): Bump redis from 4.5.5 to 4.6.0 (#363) Bumps [redis](https://github.com/redis/redis-py) from 4.5.5 to 4.6.0. - [Release notes](https://github.com/redis/redis-py/releases) - [Changelog](https://github.com/redis/redis-py/blob/master/CHANGES) - [Commits](https://github.com/redis/redis-py/compare/v4.5.5...v4.6.0) --- updated-dependencies: - dependency-name: redis dependency-type: direct:production update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index b41d086b..eed8f5bb 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2682,13 +2682,13 @@ files = [ [[package]] name = "redis" -version = "4.5.5" +version = "4.6.0" description = "Python client for Redis database and key-value store" optional = false python-versions = ">=3.7" files = [ - {file = "redis-4.5.5-py3-none-any.whl", hash = "sha256:77929bc7f5dab9adf3acba2d3bb7d7658f1e0c2f1cafe7eb36434e751c471119"}, - {file = "redis-4.5.5.tar.gz", hash = "sha256:dc87a0bdef6c8bfe1ef1e1c40be7034390c2ae02d92dcd0c7ca1729443899880"}, + {file = "redis-4.6.0-py3-none-any.whl", hash = "sha256:e2b03db868160ee4591de3cb90d40ebb50a90dd302138775937f6a42b7ed183c"}, + {file = "redis-4.6.0.tar.gz", hash = "sha256:585dc516b9eb042a619ef0a39c3d7d55fe81bdb4df09a52c9cdde0d07bf1aa7d"}, ] [package.dependencies] @@ -3381,4 +3381,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "de7851499e4278e42e191b472332c176a257b25d58ae8899c4c2670b471cde41" +content-hash = "4420181e83a63dea429dd6b65a477177c45be7e0fd9c9c4a33712907227fb0ec" diff --git a/pyproject.toml b/pyproject.toml index 280ae3d1..14739a88 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -16,7 +16,7 @@ uvloop = "^0.17.0" gql = { extras = ["aiohttp"], version = "^3.4.1" } better-ipc = "^2.0.3" prisma = "^0.9.0" -redis = {extras = ["hiredis"], version = "^4.5.5"} +redis = {extras = ["hiredis"], version = "^4.6.0"} ciso8601 = "^2.3.0" faust-cchardet = "^2.1.18" discord-py = {extras = ["voice"], version = "^2.3.1"} From 33fd13d725f15f7853cc8c47cb5078940fdc081c Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 28 Jun 2023 08:17:04 +0000 Subject: [PATCH 109/184] [pip](deps-dev): Bump pyright from 1.1.315 to 1.1.316 (#362) Bumps [pyright](https://github.com/RobertCraigie/pyright-python) from 1.1.315 to 1.1.316. - [Release notes](https://github.com/RobertCraigie/pyright-python/releases) - [Commits](https://github.com/RobertCraigie/pyright-python/compare/v1.1.315...v1.1.316) --- updated-dependencies: - dependency-name: pyright dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index eed8f5bb..24bede14 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2518,13 +2518,13 @@ diagrams = ["jinja2", "railroad-diagrams"] [[package]] name = "pyright" -version = "1.1.315" +version = "1.1.316" description = "Command line wrapper for pyright" optional = false python-versions = ">=3.7" files = [ - {file = "pyright-1.1.315-py3-none-any.whl", hash = "sha256:262744daa7455f6056f6d6609b6278258e2fd7bd100d8937203516ee71d0eb93"}, - {file = "pyright-1.1.315.tar.gz", hash = "sha256:f124400a1a72ccc5fd04836e7e48ed235e8f7929bcc42b270a571fb34df17979"}, + {file = "pyright-1.1.316-py3-none-any.whl", hash = "sha256:7259d73287c882f933d8cd88c238ef02336e172171ae95117a963a962a1fed4a"}, + {file = "pyright-1.1.316.tar.gz", hash = "sha256:bac1baf8567b90f2082ec95b61fc1cb50a68917119212c5608a72210870c6a9a"}, ] [package.dependencies] @@ -3381,4 +3381,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "4420181e83a63dea429dd6b65a477177c45be7e0fd9c9c4a33712907227fb0ec" +content-hash = "ba19565aba6b3b84495dcbce3d8a4b0032da29d47d5007e0ae8e34485be6f166" diff --git a/pyproject.toml b/pyproject.toml index 14739a88..9ef404ef 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -32,7 +32,7 @@ pytest-cov = "^4.1.0" [tool.poetry.group.dev.dependencies] pre-commit = "^3.3.3" pyinstrument = "^4.5.0" -pyright = "^1.1.315" +pyright = "^1.1.316" watchfiles = "^0.19.0" jishaku = "^2.5.1" ruff = "^0.0.275" From 6c2f200fad541046bcd334aa5c854f5b79cc632a Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Wed, 28 Jun 2023 18:23:06 -0700 Subject: [PATCH 110/184] Relock the poetry.lock file --- poetry.lock | 1175 ++++++++++++++++++++++++++------------------------- 1 file changed, 593 insertions(+), 582 deletions(-) diff --git a/poetry.lock b/poetry.lock index 3db9a9a9..09d55212 100644 --- a/poetry.lock +++ b/poetry.lock @@ -174,37 +174,38 @@ files = [ [[package]] name = "anyio" -version = "3.6.2" +version = "3.7.0" description = "High level compatibility layer for multiple asynchronous event loop implementations" optional = false -python-versions = ">=3.6.2" +python-versions = ">=3.7" files = [ - {file = "anyio-3.6.2-py3-none-any.whl", hash = "sha256:fbbe32bd270d2a2ef3ed1c5d45041250284e31fc0a4df4a5a6071842051a51e3"}, - {file = "anyio-3.6.2.tar.gz", hash = "sha256:25ea0d673ae30af41a0c442f81cf3b38c7e79fdc7b60335a4c14e05eb0947421"}, + {file = "anyio-3.7.0-py3-none-any.whl", hash = "sha256:eddca883c4175f14df8aedce21054bfca3adb70ffe76a9f607aef9d7fa2ea7f0"}, + {file = "anyio-3.7.0.tar.gz", hash = "sha256:275d9973793619a5374e1c89a4f4ad3f4b0a5510a2b5b939444bee8f4c4d37ce"}, ] [package.dependencies] +exceptiongroup = {version = "*", markers = "python_version < \"3.11\""} idna = ">=2.8" sniffio = ">=1.1" [package.extras] -doc = ["packaging", "sphinx-autodoc-typehints (>=1.2.0)", "sphinx-rtd-theme"] -test = ["contextlib2", "coverage[toml] (>=4.5)", "hypothesis (>=4.0)", "mock (>=4)", "pytest (>=7.0)", "pytest-mock (>=3.6.1)", "trustme", "uvloop (<0.15)", "uvloop (>=0.15)"] -trio = ["trio (>=0.16,<0.22)"] +doc = ["Sphinx (>=6.1.0)", "packaging", "sphinx-autodoc-typehints (>=1.2.0)", "sphinx-rtd-theme", "sphinxcontrib-jquery"] +test = ["anyio[trio]", "coverage[toml] (>=4.5)", "hypothesis (>=4.0)", "mock (>=4)", "psutil (>=5.9)", "pytest (>=7.0)", "pytest-mock (>=3.6.1)", "trustme", "uvloop (>=0.17)"] +trio = ["trio (<0.22)"] [[package]] name = "argcomplete" -version = "2.0.0" +version = "3.1.1" description = "Bash tab completion for argparse" optional = false python-versions = ">=3.6" files = [ - {file = "argcomplete-2.0.0-py2.py3-none-any.whl", hash = "sha256:cffa11ea77999bb0dd27bb25ff6dc142a6796142f68d45b1a26b11f58724561e"}, - {file = "argcomplete-2.0.0.tar.gz", hash = "sha256:6372ad78c89d662035101418ae253668445b391755cfe94ea52f1b9d22425b20"}, + {file = "argcomplete-3.1.1-py3-none-any.whl", hash = "sha256:35fa893a88deea85ea7b20d241100e64516d6af6d7b0ae2bed1d263d26f70948"}, + {file = "argcomplete-3.1.1.tar.gz", hash = "sha256:6c4c563f14f01440aaffa3eae13441c5db2357b5eec639abe7c0b15334627dff"}, ] [package.extras] -test = ["coverage", "flake8", "pexpect", "wheel"] +test = ["coverage", "mypy", "pexpect", "ruff", "wheel"] [[package]] name = "astunparse" @@ -374,21 +375,21 @@ test = ["asynctest (>=0.13.0)", "mock (>=0.8)", "pytest", "pytest-vcr", "testfix [[package]] name = "attrs" -version = "22.2.0" +version = "23.1.0" description = "Classes Without Boilerplate" optional = false -python-versions = ">=3.6" +python-versions = ">=3.7" files = [ - {file = "attrs-22.2.0-py3-none-any.whl", hash = "sha256:29e95c7f6778868dbd49170f98f8818f78f3dc5e0e37c0b1f474e3561b240836"}, - {file = "attrs-22.2.0.tar.gz", hash = "sha256:c9227bfc2f01993c03f68db37d1d15c9690188323c067c641f1a35ca58185f99"}, + {file = "attrs-23.1.0-py3-none-any.whl", hash = "sha256:1f28b4522cdc2fb4256ac1a020c78acf9cba2c6b461ccd2c126f3aa8e8335d04"}, + {file = "attrs-23.1.0.tar.gz", hash = "sha256:6279836d581513a26f1bf235f9acd333bc9115683f14f7e8fae46c98fc50e015"}, ] [package.extras] -cov = ["attrs[tests]", "coverage-enable-subprocess", "coverage[toml] (>=5.3)"] -dev = ["attrs[docs,tests]"] -docs = ["furo", "myst-parser", "sphinx", "sphinx-notfound-page", "sphinxcontrib-towncrier", "towncrier", "zope.interface"] -tests = ["attrs[tests-no-zope]", "zope.interface"] -tests-no-zope = ["cloudpickle", "cloudpickle", "hypothesis", "hypothesis", "mypy (>=0.971,<0.990)", "mypy (>=0.971,<0.990)", "pympler", "pympler", "pytest (>=4.3.0)", "pytest (>=4.3.0)", "pytest-mypy-plugins", "pytest-mypy-plugins", "pytest-xdist[psutil]", "pytest-xdist[psutil]"] +cov = ["attrs[tests]", "coverage[toml] (>=5.3)"] +dev = ["attrs[docs,tests]", "pre-commit"] +docs = ["furo", "myst-parser", "sphinx", "sphinx-notfound-page", "sphinxcontrib-towncrier", "towncrier", "zope-interface"] +tests = ["attrs[tests-no-zope]", "zope-interface"] +tests-no-zope = ["cloudpickle", "hypothesis", "mypy (>=1.1.1)", "pympler", "pytest (>=4.3.0)", "pytest-mypy-plugins", "pytest-xdist[psutil]"] [[package]] name = "babel" @@ -551,13 +552,13 @@ files = [ [[package]] name = "certifi" -version = "2022.12.7" +version = "2023.5.7" description = "Python package for providing Mozilla's CA Bundle." optional = false python-versions = ">=3.6" files = [ - {file = "certifi-2022.12.7-py3-none-any.whl", hash = "sha256:4ad3232f5e926d6718ec31cfc1fcadfde020920e278684144551c91769c7bc18"}, - {file = "certifi-2022.12.7.tar.gz", hash = "sha256:35824b4c3a97115964b408844d64aa14db1cc518f6562e8d7261699d1350a9e3"}, + {file = "certifi-2023.5.7-py3-none-any.whl", hash = "sha256:c6c2e98f5c7869efca1f8916fed228dd91539f9f1b444c314c06eef02980c716"}, + {file = "certifi-2023.5.7.tar.gz", hash = "sha256:0f0d56dc5a6ad56fd4ba36484d6cc34451e1c6548c61daad8c320169f91eddc7"}, ] [[package]] @@ -829,136 +830,129 @@ development = ["black", "flake8", "mypy", "pytest", "types-colorama"] [[package]] name = "contourpy" -version = "1.0.7" +version = "1.1.0" description = "Python library for calculating contours of 2D quadrilateral grids" optional = false python-versions = ">=3.8" files = [ - {file = "contourpy-1.0.7-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:95c3acddf921944f241b6773b767f1cbce71d03307270e2d769fd584d5d1092d"}, - {file = "contourpy-1.0.7-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:fc1464c97579da9f3ab16763c32e5c5d5bb5fa1ec7ce509a4ca6108b61b84fab"}, - {file = "contourpy-1.0.7-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:8acf74b5d383414401926c1598ed77825cd530ac7b463ebc2e4f46638f56cce6"}, - {file = "contourpy-1.0.7-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:1c71fdd8f1c0f84ffd58fca37d00ca4ebaa9e502fb49825484da075ac0b0b803"}, - {file = "contourpy-1.0.7-cp310-cp310-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:f99e9486bf1bb979d95d5cffed40689cb595abb2b841f2991fc894b3452290e8"}, - {file = "contourpy-1.0.7-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:87f4d8941a9564cda3f7fa6a6cd9b32ec575830780677932abdec7bcb61717b0"}, - {file = "contourpy-1.0.7-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:9e20e5a1908e18aaa60d9077a6d8753090e3f85ca25da6e25d30dc0a9e84c2c6"}, - {file = "contourpy-1.0.7-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:a877ada905f7d69b2a31796c4b66e31a8068b37aa9b78832d41c82fc3e056ddd"}, - {file = "contourpy-1.0.7-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:6381fa66866b0ea35e15d197fc06ac3840a9b2643a6475c8fff267db8b9f1e69"}, - {file = "contourpy-1.0.7-cp310-cp310-win32.whl", hash = "sha256:3c184ad2433635f216645fdf0493011a4667e8d46b34082f5a3de702b6ec42e3"}, - {file = "contourpy-1.0.7-cp310-cp310-win_amd64.whl", hash = "sha256:3caea6365b13119626ee996711ab63e0c9d7496f65641f4459c60a009a1f3e80"}, - {file = "contourpy-1.0.7-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:ed33433fc3820263a6368e532f19ddb4c5990855e4886088ad84fd7c4e561c71"}, - {file = "contourpy-1.0.7-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:38e2e577f0f092b8e6774459317c05a69935a1755ecfb621c0a98f0e3c09c9a5"}, - {file = "contourpy-1.0.7-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:ae90d5a8590e5310c32a7630b4b8618cef7563cebf649011da80874d0aa8f414"}, - {file = "contourpy-1.0.7-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:130230b7e49825c98edf0b428b7aa1125503d91732735ef897786fe5452b1ec2"}, - {file = "contourpy-1.0.7-cp311-cp311-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:58569c491e7f7e874f11519ef46737cea1d6eda1b514e4eb5ac7dab6aa864d02"}, - {file = "contourpy-1.0.7-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:54d43960d809c4c12508a60b66cb936e7ed57d51fb5e30b513934a4a23874fae"}, - {file = "contourpy-1.0.7-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:152fd8f730c31fd67fe0ffebe1df38ab6a669403da93df218801a893645c6ccc"}, - {file = "contourpy-1.0.7-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:9056c5310eb1daa33fc234ef39ebfb8c8e2533f088bbf0bc7350f70a29bde1ac"}, - {file = "contourpy-1.0.7-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:a9d7587d2fdc820cc9177139b56795c39fb8560f540bba9ceea215f1f66e1566"}, - {file = "contourpy-1.0.7-cp311-cp311-win32.whl", hash = "sha256:4ee3ee247f795a69e53cd91d927146fb16c4e803c7ac86c84104940c7d2cabf0"}, - {file = "contourpy-1.0.7-cp311-cp311-win_amd64.whl", hash = "sha256:5caeacc68642e5f19d707471890f037a13007feba8427eb7f2a60811a1fc1350"}, - {file = "contourpy-1.0.7-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:fd7dc0e6812b799a34f6d12fcb1000539098c249c8da54f3566c6a6461d0dbad"}, - {file = "contourpy-1.0.7-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:0f9d350b639db6c2c233d92c7f213d94d2e444d8e8fc5ca44c9706cf72193772"}, - {file = "contourpy-1.0.7-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:e96a08b62bb8de960d3a6afbc5ed8421bf1a2d9c85cc4ea73f4bc81b4910500f"}, - {file = "contourpy-1.0.7-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:031154ed61f7328ad7f97662e48660a150ef84ee1bc8876b6472af88bf5a9b98"}, - {file = "contourpy-1.0.7-cp38-cp38-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:2e9ebb4425fc1b658e13bace354c48a933b842d53c458f02c86f371cecbedecc"}, - {file = "contourpy-1.0.7-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:efb8f6d08ca7998cf59eaf50c9d60717f29a1a0a09caa46460d33b2924839dbd"}, - {file = "contourpy-1.0.7-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:6c180d89a28787e4b73b07e9b0e2dac7741261dbdca95f2b489c4f8f887dd810"}, - {file = "contourpy-1.0.7-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:b8d587cc39057d0afd4166083d289bdeff221ac6d3ee5046aef2d480dc4b503c"}, - {file = "contourpy-1.0.7-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:769eef00437edf115e24d87f8926955f00f7704bede656ce605097584f9966dc"}, - {file = "contourpy-1.0.7-cp38-cp38-win32.whl", hash = "sha256:62398c80ef57589bdbe1eb8537127321c1abcfdf8c5f14f479dbbe27d0322e66"}, - {file = "contourpy-1.0.7-cp38-cp38-win_amd64.whl", hash = "sha256:57119b0116e3f408acbdccf9eb6ef19d7fe7baf0d1e9aaa5381489bc1aa56556"}, - {file = "contourpy-1.0.7-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:30676ca45084ee61e9c3da589042c24a57592e375d4b138bd84d8709893a1ba4"}, - {file = "contourpy-1.0.7-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:3e927b3868bd1e12acee7cc8f3747d815b4ab3e445a28d2e5373a7f4a6e76ba1"}, - {file = "contourpy-1.0.7-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:366a0cf0fc079af5204801786ad7a1c007714ee3909e364dbac1729f5b0849e5"}, - {file = "contourpy-1.0.7-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:89ba9bb365446a22411f0673abf6ee1fea3b2cf47b37533b970904880ceb72f3"}, - {file = "contourpy-1.0.7-cp39-cp39-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:71b0bf0c30d432278793d2141362ac853859e87de0a7dee24a1cea35231f0d50"}, - {file = "contourpy-1.0.7-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:e7281244c99fd7c6f27c1c6bfafba878517b0b62925a09b586d88ce750a016d2"}, - {file = "contourpy-1.0.7-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:b6d0f9e1d39dbfb3977f9dd79f156c86eb03e57a7face96f199e02b18e58d32a"}, - {file = "contourpy-1.0.7-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:7f6979d20ee5693a1057ab53e043adffa1e7418d734c1532e2d9e915b08d8ec2"}, - {file = "contourpy-1.0.7-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:5dd34c1ae752515318224cba7fc62b53130c45ac6a1040c8b7c1a223c46e8967"}, - {file = "contourpy-1.0.7-cp39-cp39-win32.whl", hash = "sha256:c5210e5d5117e9aec8c47d9156d1d3835570dd909a899171b9535cb4a3f32693"}, - {file = "contourpy-1.0.7-cp39-cp39-win_amd64.whl", hash = "sha256:60835badb5ed5f4e194a6f21c09283dd6e007664a86101431bf870d9e86266c4"}, - {file = "contourpy-1.0.7-pp38-pypy38_pp73-macosx_10_9_x86_64.whl", hash = "sha256:ce41676b3d0dd16dbcfabcc1dc46090aaf4688fd6e819ef343dbda5a57ef0161"}, - {file = "contourpy-1.0.7-pp38-pypy38_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:5a011cf354107b47c58ea932d13b04d93c6d1d69b8b6dce885e642531f847566"}, - {file = "contourpy-1.0.7-pp38-pypy38_pp73-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:31a55dccc8426e71817e3fe09b37d6d48ae40aae4ecbc8c7ad59d6893569c436"}, - {file = "contourpy-1.0.7-pp38-pypy38_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:69f8ff4db108815addd900a74df665e135dbbd6547a8a69333a68e1f6e368ac2"}, - {file = "contourpy-1.0.7-pp38-pypy38_pp73-win_amd64.whl", hash = "sha256:efe99298ba37e37787f6a2ea868265465410822f7bea163edcc1bd3903354ea9"}, - {file = "contourpy-1.0.7-pp39-pypy39_pp73-macosx_10_9_x86_64.whl", hash = "sha256:a1e97b86f73715e8670ef45292d7cc033548266f07d54e2183ecb3c87598888f"}, - {file = "contourpy-1.0.7-pp39-pypy39_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:cc331c13902d0f50845099434cd936d49d7a2ca76cb654b39691974cb1e4812d"}, - {file = "contourpy-1.0.7-pp39-pypy39_pp73-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:24847601071f740837aefb730e01bd169fbcaa610209779a78db7ebb6e6a7051"}, - {file = "contourpy-1.0.7-pp39-pypy39_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:abf298af1e7ad44eeb93501e40eb5a67abbf93b5d90e468d01fc0c4451971afa"}, - {file = "contourpy-1.0.7-pp39-pypy39_pp73-win_amd64.whl", hash = "sha256:64757f6460fc55d7e16ed4f1de193f362104285c667c112b50a804d482777edd"}, - {file = "contourpy-1.0.7.tar.gz", hash = "sha256:d8165a088d31798b59e91117d1f5fc3df8168d8b48c4acc10fc0df0d0bdbcc5e"}, + {file = "contourpy-1.1.0-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:89f06eff3ce2f4b3eb24c1055a26981bffe4e7264acd86f15b97e40530b794bc"}, + {file = "contourpy-1.1.0-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:dffcc2ddec1782dd2f2ce1ef16f070861af4fb78c69862ce0aab801495dda6a3"}, + {file = "contourpy-1.1.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:25ae46595e22f93592d39a7eac3d638cda552c3e1160255258b695f7b58e5655"}, + {file = "contourpy-1.1.0-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:17cfaf5ec9862bc93af1ec1f302457371c34e688fbd381f4035a06cd47324f48"}, + {file = "contourpy-1.1.0-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:18a64814ae7bce73925131381603fff0116e2df25230dfc80d6d690aa6e20b37"}, + {file = "contourpy-1.1.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:90c81f22b4f572f8a2110b0b741bb64e5a6427e0a198b2cdc1fbaf85f352a3aa"}, + {file = "contourpy-1.1.0-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:53cc3a40635abedbec7f1bde60f8c189c49e84ac180c665f2cd7c162cc454baa"}, + {file = "contourpy-1.1.0-cp310-cp310-win_amd64.whl", hash = "sha256:1f795597073b09d631782e7245016a4323cf1cf0b4e06eef7ea6627e06a37ff2"}, + {file = "contourpy-1.1.0-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:0b7b04ed0961647691cfe5d82115dd072af7ce8846d31a5fac6c142dcce8b882"}, + {file = "contourpy-1.1.0-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:27bc79200c742f9746d7dd51a734ee326a292d77e7d94c8af6e08d1e6c15d545"}, + {file = "contourpy-1.1.0-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:052cc634bf903c604ef1a00a5aa093c54f81a2612faedaa43295809ffdde885e"}, + {file = "contourpy-1.1.0-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:9382a1c0bc46230fb881c36229bfa23d8c303b889b788b939365578d762b5c18"}, + {file = "contourpy-1.1.0-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:e5cec36c5090e75a9ac9dbd0ff4a8cf7cecd60f1b6dc23a374c7d980a1cd710e"}, + {file = "contourpy-1.1.0-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:1f0cbd657e9bde94cd0e33aa7df94fb73c1ab7799378d3b3f902eb8eb2e04a3a"}, + {file = "contourpy-1.1.0-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:181cbace49874f4358e2929aaf7ba84006acb76694102e88dd15af861996c16e"}, + {file = "contourpy-1.1.0-cp311-cp311-win_amd64.whl", hash = "sha256:fb3b7d9e6243bfa1efb93ccfe64ec610d85cfe5aec2c25f97fbbd2e58b531256"}, + {file = "contourpy-1.1.0-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:bcb41692aa09aeb19c7c213411854402f29f6613845ad2453d30bf421fe68fed"}, + {file = "contourpy-1.1.0-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:5d123a5bc63cd34c27ff9c7ac1cd978909e9c71da12e05be0231c608048bb2ae"}, + {file = "contourpy-1.1.0-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:62013a2cf68abc80dadfd2307299bfa8f5aa0dcaec5b2954caeb5fa094171103"}, + {file = "contourpy-1.1.0-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:0b6616375d7de55797d7a66ee7d087efe27f03d336c27cf1f32c02b8c1a5ac70"}, + {file = "contourpy-1.1.0-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:317267d915490d1e84577924bd61ba71bf8681a30e0d6c545f577363157e5e94"}, + {file = "contourpy-1.1.0-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:d551f3a442655f3dcc1285723f9acd646ca5858834efeab4598d706206b09c9f"}, + {file = "contourpy-1.1.0-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:e7a117ce7df5a938fe035cad481b0189049e8d92433b4b33aa7fc609344aafa1"}, + {file = "contourpy-1.1.0-cp38-cp38-win_amd64.whl", hash = "sha256:d4f26b25b4f86087e7d75e63212756c38546e70f2a92d2be44f80114826e1cd4"}, + {file = "contourpy-1.1.0-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:bc00bb4225d57bff7ebb634646c0ee2a1298402ec10a5fe7af79df9a51c1bfd9"}, + {file = "contourpy-1.1.0-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:189ceb1525eb0655ab8487a9a9c41f42a73ba52d6789754788d1883fb06b2d8a"}, + {file = "contourpy-1.1.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:9f2931ed4741f98f74b410b16e5213f71dcccee67518970c42f64153ea9313b9"}, + {file = "contourpy-1.1.0-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:30f511c05fab7f12e0b1b7730ebdc2ec8deedcfb505bc27eb570ff47c51a8f15"}, + {file = "contourpy-1.1.0-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:143dde50520a9f90e4a2703f367cf8ec96a73042b72e68fcd184e1279962eb6f"}, + {file = "contourpy-1.1.0-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:e94bef2580e25b5fdb183bf98a2faa2adc5b638736b2c0a4da98691da641316a"}, + {file = "contourpy-1.1.0-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:ed614aea8462735e7d70141374bd7650afd1c3f3cb0c2dbbcbe44e14331bf002"}, + {file = "contourpy-1.1.0-cp39-cp39-win_amd64.whl", hash = "sha256:438ba416d02f82b692e371858143970ed2eb6337d9cdbbede0d8ad9f3d7dd17d"}, + {file = "contourpy-1.1.0-pp38-pypy38_pp73-macosx_10_9_x86_64.whl", hash = "sha256:a698c6a7a432789e587168573a864a7ea374c6be8d4f31f9d87c001d5a843493"}, + {file = "contourpy-1.1.0-pp38-pypy38_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:397b0ac8a12880412da3551a8cb5a187d3298a72802b45a3bd1805e204ad8439"}, + {file = "contourpy-1.1.0-pp38-pypy38_pp73-win_amd64.whl", hash = "sha256:a67259c2b493b00e5a4d0f7bfae51fb4b3371395e47d079a4446e9b0f4d70e76"}, + {file = "contourpy-1.1.0-pp39-pypy39_pp73-macosx_10_9_x86_64.whl", hash = "sha256:2b836d22bd2c7bb2700348e4521b25e077255ebb6ab68e351ab5aa91ca27e027"}, + {file = "contourpy-1.1.0-pp39-pypy39_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:084eaa568400cfaf7179b847ac871582199b1b44d5699198e9602ecbbb5f6104"}, + {file = "contourpy-1.1.0-pp39-pypy39_pp73-win_amd64.whl", hash = "sha256:911ff4fd53e26b019f898f32db0d4956c9d227d51338fb3b03ec72ff0084ee5f"}, + {file = "contourpy-1.1.0.tar.gz", hash = "sha256:e53046c3863828d21d531cc3b53786e6580eb1ba02477e8681009b6aa0870b21"}, ] [package.dependencies] numpy = ">=1.16" [package.extras] -bokeh = ["bokeh", "chromedriver", "selenium"] +bokeh = ["bokeh", "selenium"] docs = ["furo", "sphinx-copybutton"] -mypy = ["contourpy[bokeh]", "docutils-stubs", "mypy (==0.991)", "types-Pillow"] -test = ["Pillow", "matplotlib", "pytest"] -test-no-images = ["pytest"] +mypy = ["contourpy[bokeh,docs]", "docutils-stubs", "mypy (==1.2.0)", "types-Pillow"] +test = ["Pillow", "contourpy[test-no-images]", "matplotlib"] +test-no-images = ["pytest", "pytest-cov", "wurlitzer"] [[package]] name = "coverage" -version = "7.0.5" +version = "7.2.7" description = "Code coverage measurement for Python" optional = false python-versions = ">=3.7" files = [ - {file = "coverage-7.0.5-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:2a7f23bbaeb2a87f90f607730b45564076d870f1fb07b9318d0c21f36871932b"}, - {file = "coverage-7.0.5-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:c18d47f314b950dbf24a41787ced1474e01ca816011925976d90a88b27c22b89"}, - {file = "coverage-7.0.5-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ef14d75d86f104f03dea66c13188487151760ef25dd6b2dbd541885185f05f40"}, - {file = "coverage-7.0.5-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:66e50680e888840c0995f2ad766e726ce71ca682e3c5f4eee82272c7671d38a2"}, - {file = "coverage-7.0.5-cp310-cp310-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:a9fed35ca8c6e946e877893bbac022e8563b94404a605af1d1e6accc7eb73289"}, - {file = "coverage-7.0.5-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:d8d04e755934195bdc1db45ba9e040b8d20d046d04d6d77e71b3b34a8cc002d0"}, - {file = "coverage-7.0.5-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:7e109f1c9a3ece676597831874126555997c48f62bddbcace6ed17be3e372de8"}, - {file = "coverage-7.0.5-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:0a1890fca2962c4f1ad16551d660b46ea77291fba2cc21c024cd527b9d9c8809"}, - {file = "coverage-7.0.5-cp310-cp310-win32.whl", hash = "sha256:be9fcf32c010da0ba40bf4ee01889d6c737658f4ddff160bd7eb9cac8f094b21"}, - {file = "coverage-7.0.5-cp310-cp310-win_amd64.whl", hash = "sha256:cbfcba14a3225b055a28b3199c3d81cd0ab37d2353ffd7f6fd64844cebab31ad"}, - {file = "coverage-7.0.5-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:30b5fec1d34cc932c1bc04017b538ce16bf84e239378b8f75220478645d11fca"}, - {file = "coverage-7.0.5-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:1caed2367b32cc80a2b7f58a9f46658218a19c6cfe5bc234021966dc3daa01f0"}, - {file = "coverage-7.0.5-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d254666d29540a72d17cc0175746cfb03d5123db33e67d1020e42dae611dc196"}, - {file = "coverage-7.0.5-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:19245c249aa711d954623d94f23cc94c0fd65865661f20b7781210cb97c471c0"}, - {file = "coverage-7.0.5-cp311-cp311-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:7b05ed4b35bf6ee790832f68932baf1f00caa32283d66cc4d455c9e9d115aafc"}, - {file = "coverage-7.0.5-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:29de916ba1099ba2aab76aca101580006adfac5646de9b7c010a0f13867cba45"}, - {file = "coverage-7.0.5-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:e057e74e53db78122a3979f908973e171909a58ac20df05c33998d52e6d35757"}, - {file = "coverage-7.0.5-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:411d4ff9d041be08fdfc02adf62e89c735b9468f6d8f6427f8a14b6bb0a85095"}, - {file = "coverage-7.0.5-cp311-cp311-win32.whl", hash = "sha256:52ab14b9e09ce052237dfe12d6892dd39b0401690856bcfe75d5baba4bfe2831"}, - {file = "coverage-7.0.5-cp311-cp311-win_amd64.whl", hash = "sha256:1f66862d3a41674ebd8d1a7b6f5387fe5ce353f8719040a986551a545d7d83ea"}, - {file = "coverage-7.0.5-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:b69522b168a6b64edf0c33ba53eac491c0a8f5cc94fa4337f9c6f4c8f2f5296c"}, - {file = "coverage-7.0.5-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:436e103950d05b7d7f55e39beeb4d5be298ca3e119e0589c0227e6d0b01ee8c7"}, - {file = "coverage-7.0.5-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:b8c56bec53d6e3154eaff6ea941226e7bd7cc0d99f9b3756c2520fc7a94e6d96"}, - {file = "coverage-7.0.5-cp37-cp37m-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:7a38362528a9115a4e276e65eeabf67dcfaf57698e17ae388599568a78dcb029"}, - {file = "coverage-7.0.5-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:f67472c09a0c7486e27f3275f617c964d25e35727af952869dd496b9b5b7f6a3"}, - {file = "coverage-7.0.5-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:220e3fa77d14c8a507b2d951e463b57a1f7810a6443a26f9b7591ef39047b1b2"}, - {file = "coverage-7.0.5-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:ecb0f73954892f98611e183f50acdc9e21a4653f294dfbe079da73c6378a6f47"}, - {file = "coverage-7.0.5-cp37-cp37m-win32.whl", hash = "sha256:d8f3e2e0a1d6777e58e834fd5a04657f66affa615dae61dd67c35d1568c38882"}, - {file = "coverage-7.0.5-cp37-cp37m-win_amd64.whl", hash = "sha256:9e662e6fc4f513b79da5d10a23edd2b87685815b337b1a30cd11307a6679148d"}, - {file = "coverage-7.0.5-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:790e4433962c9f454e213b21b0fd4b42310ade9c077e8edcb5113db0818450cb"}, - {file = "coverage-7.0.5-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:49640bda9bda35b057b0e65b7c43ba706fa2335c9a9896652aebe0fa399e80e6"}, - {file = "coverage-7.0.5-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d66187792bfe56f8c18ba986a0e4ae44856b1c645336bd2c776e3386da91e1dd"}, - {file = "coverage-7.0.5-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:276f4cd0001cd83b00817c8db76730938b1ee40f4993b6a905f40a7278103b3a"}, - {file = "coverage-7.0.5-cp38-cp38-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:95304068686545aa368b35dfda1cdfbbdbe2f6fe43de4a2e9baa8ebd71be46e2"}, - {file = "coverage-7.0.5-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:17e01dd8666c445025c29684d4aabf5a90dc6ef1ab25328aa52bedaa95b65ad7"}, - {file = "coverage-7.0.5-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:ea76dbcad0b7b0deb265d8c36e0801abcddf6cc1395940a24e3595288b405ca0"}, - {file = "coverage-7.0.5-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:50a6adc2be8edd7ee67d1abc3cd20678987c7b9d79cd265de55941e3d0d56499"}, - {file = "coverage-7.0.5-cp38-cp38-win32.whl", hash = "sha256:e4ce984133b888cc3a46867c8b4372c7dee9cee300335e2925e197bcd45b9e16"}, - {file = "coverage-7.0.5-cp38-cp38-win_amd64.whl", hash = "sha256:4a950f83fd3f9bca23b77442f3a2b2ea4ac900944d8af9993743774c4fdc57af"}, - {file = "coverage-7.0.5-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:3c2155943896ac78b9b0fd910fb381186d0c345911f5333ee46ac44c8f0e43ab"}, - {file = "coverage-7.0.5-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:54f7e9705e14b2c9f6abdeb127c390f679f6dbe64ba732788d3015f7f76ef637"}, - {file = "coverage-7.0.5-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:0ee30375b409d9a7ea0f30c50645d436b6f5dfee254edffd27e45a980ad2c7f4"}, - {file = "coverage-7.0.5-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:b78729038abea6a5df0d2708dce21e82073463b2d79d10884d7d591e0f385ded"}, - {file = "coverage-7.0.5-cp39-cp39-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:13250b1f0bd023e0c9f11838bdeb60214dd5b6aaf8e8d2f110c7e232a1bff83b"}, - {file = "coverage-7.0.5-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:2c407b1950b2d2ffa091f4e225ca19a66a9bd81222f27c56bd12658fc5ca1209"}, - {file = "coverage-7.0.5-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:c76a3075e96b9c9ff00df8b5f7f560f5634dffd1658bafb79eb2682867e94f78"}, - {file = "coverage-7.0.5-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:f26648e1b3b03b6022b48a9b910d0ae209e2d51f50441db5dce5b530fad6d9b1"}, - {file = "coverage-7.0.5-cp39-cp39-win32.whl", hash = "sha256:ba3027deb7abf02859aca49c865ece538aee56dcb4871b4cced23ba4d5088904"}, - {file = "coverage-7.0.5-cp39-cp39-win_amd64.whl", hash = "sha256:949844af60ee96a376aac1ded2a27e134b8c8d35cc006a52903fc06c24a3296f"}, - {file = "coverage-7.0.5-pp37.pp38.pp39-none-any.whl", hash = "sha256:b9727ac4f5cf2cbf87880a63870b5b9730a8ae3a4a360241a0fdaa2f71240ff0"}, - {file = "coverage-7.0.5.tar.gz", hash = "sha256:051afcbd6d2ac39298d62d340f94dbb6a1f31de06dfaf6fcef7b759dd3860c45"}, + {file = "coverage-7.2.7-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:d39b5b4f2a66ccae8b7263ac3c8170994b65266797fb96cbbfd3fb5b23921db8"}, + {file = "coverage-7.2.7-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:6d040ef7c9859bb11dfeb056ff5b3872436e3b5e401817d87a31e1750b9ae2fb"}, + {file = "coverage-7.2.7-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ba90a9563ba44a72fda2e85302c3abc71c5589cea608ca16c22b9804262aaeb6"}, + {file = "coverage-7.2.7-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:e7d9405291c6928619403db1d10bd07888888ec1abcbd9748fdaa971d7d661b2"}, + {file = "coverage-7.2.7-cp310-cp310-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:31563e97dae5598556600466ad9beea39fb04e0229e61c12eaa206e0aa202063"}, + {file = "coverage-7.2.7-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:ebba1cd308ef115925421d3e6a586e655ca5a77b5bf41e02eb0e4562a111f2d1"}, + {file = "coverage-7.2.7-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:cb017fd1b2603ef59e374ba2063f593abe0fc45f2ad9abdde5b4d83bd922a353"}, + {file = "coverage-7.2.7-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:d62a5c7dad11015c66fbb9d881bc4caa5b12f16292f857842d9d1871595f4495"}, + {file = "coverage-7.2.7-cp310-cp310-win32.whl", hash = "sha256:ee57190f24fba796e36bb6d3aa8a8783c643d8fa9760c89f7a98ab5455fbf818"}, + {file = "coverage-7.2.7-cp310-cp310-win_amd64.whl", hash = "sha256:f75f7168ab25dd93110c8a8117a22450c19976afbc44234cbf71481094c1b850"}, + {file = "coverage-7.2.7-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:06a9a2be0b5b576c3f18f1a241f0473575c4a26021b52b2a85263a00f034d51f"}, + {file = "coverage-7.2.7-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:5baa06420f837184130752b7c5ea0808762083bf3487b5038d68b012e5937dbe"}, + {file = "coverage-7.2.7-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:fdec9e8cbf13a5bf63290fc6013d216a4c7232efb51548594ca3631a7f13c3a3"}, + {file = "coverage-7.2.7-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:52edc1a60c0d34afa421c9c37078817b2e67a392cab17d97283b64c5833f427f"}, + {file = "coverage-7.2.7-cp311-cp311-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:63426706118b7f5cf6bb6c895dc215d8a418d5952544042c8a2d9fe87fcf09cb"}, + {file = "coverage-7.2.7-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:afb17f84d56068a7c29f5fa37bfd38d5aba69e3304af08ee94da8ed5b0865833"}, + {file = "coverage-7.2.7-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:48c19d2159d433ccc99e729ceae7d5293fbffa0bdb94952d3579983d1c8c9d97"}, + {file = "coverage-7.2.7-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:0e1f928eaf5469c11e886fe0885ad2bf1ec606434e79842a879277895a50942a"}, + {file = "coverage-7.2.7-cp311-cp311-win32.whl", hash = "sha256:33d6d3ea29d5b3a1a632b3c4e4f4ecae24ef170b0b9ee493883f2df10039959a"}, + {file = "coverage-7.2.7-cp311-cp311-win_amd64.whl", hash = "sha256:5b7540161790b2f28143191f5f8ec02fb132660ff175b7747b95dcb77ac26562"}, + {file = "coverage-7.2.7-cp312-cp312-macosx_10_9_x86_64.whl", hash = "sha256:f2f67fe12b22cd130d34d0ef79206061bfb5eda52feb6ce0dba0644e20a03cf4"}, + {file = "coverage-7.2.7-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:a342242fe22407f3c17f4b499276a02b01e80f861f1682ad1d95b04018e0c0d4"}, + {file = "coverage-7.2.7-cp312-cp312-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:171717c7cb6b453aebac9a2ef603699da237f341b38eebfee9be75d27dc38e01"}, + {file = "coverage-7.2.7-cp312-cp312-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:49969a9f7ffa086d973d91cec8d2e31080436ef0fb4a359cae927e742abfaaa6"}, + {file = "coverage-7.2.7-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:b46517c02ccd08092f4fa99f24c3b83d8f92f739b4657b0f146246a0ca6a831d"}, + {file = "coverage-7.2.7-cp312-cp312-musllinux_1_1_i686.whl", hash = "sha256:a3d33a6b3eae87ceaefa91ffdc130b5e8536182cd6dfdbfc1aa56b46ff8c86de"}, + {file = "coverage-7.2.7-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:976b9c42fb2a43ebf304fa7d4a310e5f16cc99992f33eced91ef6f908bd8f33d"}, + {file = "coverage-7.2.7-cp312-cp312-win32.whl", hash = "sha256:8de8bb0e5ad103888d65abef8bca41ab93721647590a3f740100cd65c3b00511"}, + {file = "coverage-7.2.7-cp312-cp312-win_amd64.whl", hash = "sha256:9e31cb64d7de6b6f09702bb27c02d1904b3aebfca610c12772452c4e6c21a0d3"}, + {file = "coverage-7.2.7-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:58c2ccc2f00ecb51253cbe5d8d7122a34590fac9646a960d1430d5b15321d95f"}, + {file = "coverage-7.2.7-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d22656368f0e6189e24722214ed8d66b8022db19d182927b9a248a2a8a2f67eb"}, + {file = "coverage-7.2.7-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:a895fcc7b15c3fc72beb43cdcbdf0ddb7d2ebc959edac9cef390b0d14f39f8a9"}, + {file = "coverage-7.2.7-cp37-cp37m-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:e84606b74eb7de6ff581a7915e2dab7a28a0517fbe1c9239eb227e1354064dcd"}, + {file = "coverage-7.2.7-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:0a5f9e1dbd7fbe30196578ca36f3fba75376fb99888c395c5880b355e2875f8a"}, + {file = "coverage-7.2.7-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:419bfd2caae268623dd469eff96d510a920c90928b60f2073d79f8fe2bbc5959"}, + {file = "coverage-7.2.7-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:2aee274c46590717f38ae5e4650988d1af340fe06167546cc32fe2f58ed05b02"}, + {file = "coverage-7.2.7-cp37-cp37m-win32.whl", hash = "sha256:61b9a528fb348373c433e8966535074b802c7a5d7f23c4f421e6c6e2f1697a6f"}, + {file = "coverage-7.2.7-cp37-cp37m-win_amd64.whl", hash = "sha256:b1c546aca0ca4d028901d825015dc8e4d56aac4b541877690eb76490f1dc8ed0"}, + {file = "coverage-7.2.7-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:54b896376ab563bd38453cecb813c295cf347cf5906e8b41d340b0321a5433e5"}, + {file = "coverage-7.2.7-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:3d376df58cc111dc8e21e3b6e24606b5bb5dee6024f46a5abca99124b2229ef5"}, + {file = "coverage-7.2.7-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:5e330fc79bd7207e46c7d7fd2bb4af2963f5f635703925543a70b99574b0fea9"}, + {file = "coverage-7.2.7-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:1e9d683426464e4a252bf70c3498756055016f99ddaec3774bf368e76bbe02b6"}, + {file = "coverage-7.2.7-cp38-cp38-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:8d13c64ee2d33eccf7437961b6ea7ad8673e2be040b4f7fd4fd4d4d28d9ccb1e"}, + {file = "coverage-7.2.7-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:b7aa5f8a41217360e600da646004f878250a0d6738bcdc11a0a39928d7dc2050"}, + {file = "coverage-7.2.7-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:8fa03bce9bfbeeef9f3b160a8bed39a221d82308b4152b27d82d8daa7041fee5"}, + {file = "coverage-7.2.7-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:245167dd26180ab4c91d5e1496a30be4cd721a5cf2abf52974f965f10f11419f"}, + {file = "coverage-7.2.7-cp38-cp38-win32.whl", hash = "sha256:d2c2db7fd82e9b72937969bceac4d6ca89660db0a0967614ce2481e81a0b771e"}, + {file = "coverage-7.2.7-cp38-cp38-win_amd64.whl", hash = "sha256:2e07b54284e381531c87f785f613b833569c14ecacdcb85d56b25c4622c16c3c"}, + {file = "coverage-7.2.7-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:537891ae8ce59ef63d0123f7ac9e2ae0fc8b72c7ccbe5296fec45fd68967b6c9"}, + {file = "coverage-7.2.7-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:06fb182e69f33f6cd1d39a6c597294cff3143554b64b9825d1dc69d18cc2fff2"}, + {file = "coverage-7.2.7-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:201e7389591af40950a6480bd9edfa8ed04346ff80002cec1a66cac4549c1ad7"}, + {file = "coverage-7.2.7-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:f6951407391b639504e3b3be51b7ba5f3528adbf1a8ac3302b687ecababf929e"}, + {file = "coverage-7.2.7-cp39-cp39-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:6f48351d66575f535669306aa7d6d6f71bc43372473b54a832222803eb956fd1"}, + {file = "coverage-7.2.7-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:b29019c76039dc3c0fd815c41392a044ce555d9bcdd38b0fb60fb4cd8e475ba9"}, + {file = "coverage-7.2.7-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:81c13a1fc7468c40f13420732805a4c38a105d89848b7c10af65a90beff25250"}, + {file = "coverage-7.2.7-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:975d70ab7e3c80a3fe86001d8751f6778905ec723f5b110aed1e450da9d4b7f2"}, + {file = "coverage-7.2.7-cp39-cp39-win32.whl", hash = "sha256:7ee7d9d4822c8acc74a5e26c50604dff824710bc8de424904c0982e25c39c6cb"}, + {file = "coverage-7.2.7-cp39-cp39-win_amd64.whl", hash = "sha256:eb393e5ebc85245347950143969b241d08b52b88a3dc39479822e073a1a8eb27"}, + {file = "coverage-7.2.7-pp37.pp38.pp39-none-any.whl", hash = "sha256:b7b4c971f05e6ae490fef852c218b0e79d4e52f79ef0c8475566584a8fb3e01d"}, + {file = "coverage-7.2.7.tar.gz", hash = "sha256:924d94291ca674905fe9481f12294eb11f2d3d3fd1adb20314ba89e94f44ed59"}, ] [package.dependencies] @@ -1030,24 +1024,24 @@ files = [ [[package]] name = "docutils" -version = "0.19" +version = "0.20.1" description = "Docutils -- Python Documentation Utilities" optional = false python-versions = ">=3.7" files = [ - {file = "docutils-0.19-py3-none-any.whl", hash = "sha256:5e1de4d849fee02c63b040a4a3fd567f4ab104defd8a5511fbbc24a8a017efbc"}, - {file = "docutils-0.19.tar.gz", hash = "sha256:33995a6753c30b7f577febfc2c50411fec6aac7f7ffeb7c4cfe5991072dcf9e6"}, + {file = "docutils-0.20.1-py3-none-any.whl", hash = "sha256:96f387a2c5562db4476f09f13bbab2192e764cac08ebbf3a34a95d9b1e4a59d6"}, + {file = "docutils-0.20.1.tar.gz", hash = "sha256:f08a4e276c3a1583a86dce3e34aba3fe04d02bba2dd51ed16106244e8a923e3b"}, ] [[package]] name = "exceptiongroup" -version = "1.1.0" +version = "1.1.1" description = "Backport of PEP 654 (exception groups)" optional = false python-versions = ">=3.7" files = [ - {file = "exceptiongroup-1.1.0-py3-none-any.whl", hash = "sha256:327cbda3da756e2de031a3107b81ab7b3770a602c4d16ca618298c526f4bec1e"}, - {file = "exceptiongroup-1.1.0.tar.gz", hash = "sha256:bcb67d800a4497e1b404c2dd44fca47d3b7a5e5433dbab67f96c1a685cdfdf23"}, + {file = "exceptiongroup-1.1.1-py3-none-any.whl", hash = "sha256:232c37c63e4f682982c8b6459f33a8981039e5fb8756b2074364e5055c498c9e"}, + {file = "exceptiongroup-1.1.1.tar.gz", hash = "sha256:d484c3090ba2889ae2928419117447a14daf3c1231d5e30d0aae34f354f01785"}, ] [package.extras] @@ -1117,28 +1111,60 @@ files = [ [[package]] name = "filelock" -version = "3.9.0" +version = "3.12.2" description = "A platform independent file lock." optional = false python-versions = ">=3.7" files = [ - {file = "filelock-3.9.0-py3-none-any.whl", hash = "sha256:f58d535af89bb9ad5cd4df046f741f8553a418c01a7856bf0d173bbc9f6bd16d"}, - {file = "filelock-3.9.0.tar.gz", hash = "sha256:7b319f24340b51f55a2bf7a12ac0755a9b03e718311dac567a0f4f7fabd2f5de"}, + {file = "filelock-3.12.2-py3-none-any.whl", hash = "sha256:cbb791cdea2a72f23da6ac5b5269ab0a0d161e9ef0100e653b69049a7706d1ec"}, + {file = "filelock-3.12.2.tar.gz", hash = "sha256:002740518d8aa59a26b0c76e10fb8c6e15eae825d34b6fdf670333fd7b938d81"}, ] [package.extras] -docs = ["furo (>=2022.12.7)", "sphinx (>=5.3)", "sphinx-autodoc-typehints (>=1.19.5)"] -testing = ["covdefaults (>=2.2.2)", "coverage (>=7.0.1)", "pytest (>=7.2)", "pytest-cov (>=4)", "pytest-timeout (>=2.1)"] +docs = ["furo (>=2023.5.20)", "sphinx (>=7.0.1)", "sphinx-autodoc-typehints (>=1.23,!=1.23.4)"] +testing = ["covdefaults (>=2.3)", "coverage (>=7.2.7)", "diff-cover (>=7.5)", "pytest (>=7.3.1)", "pytest-cov (>=4.1)", "pytest-mock (>=3.10)", "pytest-timeout (>=2.1)"] [[package]] name = "fonttools" -version = "4.39.3" +version = "4.40.0" description = "Tools to manipulate font files" optional = false python-versions = ">=3.8" files = [ - {file = "fonttools-4.39.3-py3-none-any.whl", hash = "sha256:64c0c05c337f826183637570ac5ab49ee220eec66cf50248e8df527edfa95aeb"}, - {file = "fonttools-4.39.3.zip", hash = "sha256:9234b9f57b74e31b192c3fc32ef1a40750a8fbc1cd9837a7b7bfc4ca4a5c51d7"}, + {file = "fonttools-4.40.0-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:b802dcbf9bcff74672f292b2466f6589ab8736ce4dcf36f48eb994c2847c4b30"}, + {file = "fonttools-4.40.0-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:7f6e3fa3da923063c286320e728ba2270e49c73386e3a711aa680f4b0747d692"}, + {file = "fonttools-4.40.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:5fdf60f8a5c6bcce7d024a33f7e4bc7921f5b74e8ea13bccd204f2c8b86f3470"}, + {file = "fonttools-4.40.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:91784e21a1a085fac07c6a407564f4a77feb471b5954c9ee55a4f9165151f6c1"}, + {file = "fonttools-4.40.0-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:05171f3c546f64d78569f10adc0de72561882352cac39ec7439af12304d8d8c0"}, + {file = "fonttools-4.40.0-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:7449e5e306f3a930a8944c85d0cbc8429cba13503372a1a40f23124d6fb09b58"}, + {file = "fonttools-4.40.0-cp310-cp310-win32.whl", hash = "sha256:bae8c13abbc2511e9a855d2142c0ab01178dd66b1a665798f357da0d06253e0d"}, + {file = "fonttools-4.40.0-cp310-cp310-win_amd64.whl", hash = "sha256:425b74a608427499b0e45e433c34ddc350820b6f25b7c8761963a08145157a66"}, + {file = "fonttools-4.40.0-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:00ab569b2a3e591e00425023ade87e8fef90380c1dde61be7691cb524ca5f743"}, + {file = "fonttools-4.40.0-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:18ea64ac43e94c9e0c23d7a9475f1026be0e25b10dda8f236fc956188761df97"}, + {file = "fonttools-4.40.0-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:022c4a16b412293e7f1ce21b8bab7a6f9d12c4ffdf171fdc67122baddb973069"}, + {file = "fonttools-4.40.0-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:530c5d35109f3e0cea2535742d6a3bc99c0786cf0cbd7bb2dc9212387f0d908c"}, + {file = "fonttools-4.40.0-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:5e00334c66f4e83535384cb5339526d01d02d77f142c23b2f97bd6a4f585497a"}, + {file = "fonttools-4.40.0-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:eb52c10fda31159c22c7ed85074e05f8b97da8773ea461706c273e31bcbea836"}, + {file = "fonttools-4.40.0-cp311-cp311-win32.whl", hash = "sha256:6a8d71b9a5c884c72741868e845c0e563c5d83dcaf10bb0ceeec3b4b2eb14c67"}, + {file = "fonttools-4.40.0-cp311-cp311-win_amd64.whl", hash = "sha256:15abb3d055c1b2dff9ce376b6c3db10777cb74b37b52b78f61657634fd348a0d"}, + {file = "fonttools-4.40.0-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:14037c31138fbd21847ad5e5441dfdde003e0a8f3feb5812a1a21fd1c255ffbd"}, + {file = "fonttools-4.40.0-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:94c915f6716589f78bc00fbc14c5b8de65cfd11ee335d32504f1ef234524cb24"}, + {file = "fonttools-4.40.0-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:37467cee0f32cada2ec08bc16c9c31f9b53ea54b2f5604bf25a1246b5f50593a"}, + {file = "fonttools-4.40.0-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:56d4d85f5374b45b08d2f928517d1e313ea71b4847240398decd0ab3ebbca885"}, + {file = "fonttools-4.40.0-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:8c4305b171b61040b1ee75d18f9baafe58bd3b798d1670078efe2c92436bfb63"}, + {file = "fonttools-4.40.0-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:a954b90d1473c85a22ecf305761d9fd89da93bbd31dae86e7dea436ad2cb5dc9"}, + {file = "fonttools-4.40.0-cp38-cp38-win32.whl", hash = "sha256:1bc4c5b147be8dbc5df9cc8ac5e93ee914ad030fe2a201cc8f02f499db71011d"}, + {file = "fonttools-4.40.0-cp38-cp38-win_amd64.whl", hash = "sha256:8a917828dbfdb1cbe50cf40eeae6fbf9c41aef9e535649ed8f4982b2ef65c091"}, + {file = "fonttools-4.40.0-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:882983279bf39afe4e945109772c2ffad2be2c90983d6559af8b75c19845a80a"}, + {file = "fonttools-4.40.0-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:c55f1b4109dbc3aeb496677b3e636d55ef46dc078c2a5e3f3db4e90f1c6d2907"}, + {file = "fonttools-4.40.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ec468c022d09f1817c691cf884feb1030ef6f1e93e3ea6831b0d8144c06480d1"}, + {file = "fonttools-4.40.0-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:6d5adf4ba114f028fc3f5317a221fd8b0f4ef7a2e5524a2b1e0fd891b093791a"}, + {file = "fonttools-4.40.0-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:aa83b3f151bc63970f39b2b42a06097c5a22fd7ed9f7ba008e618de4503d3895"}, + {file = "fonttools-4.40.0-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:97d95b8301b62bdece1af943b88bcb3680fd385f88346a4a899ee145913b414a"}, + {file = "fonttools-4.40.0-cp39-cp39-win32.whl", hash = "sha256:1a003608400dd1cca3e089e8c94973c6b51a4fb1ef00ff6d7641617b9242e637"}, + {file = "fonttools-4.40.0-cp39-cp39-win_amd64.whl", hash = "sha256:7961575221e3da0841c75da53833272c520000d76f7f71274dbf43370f8a1065"}, + {file = "fonttools-4.40.0-py3-none-any.whl", hash = "sha256:200729d12461e2038700d31f0d49ad5a7b55855dec7525074979a06b46f88505"}, + {file = "fonttools-4.40.0.tar.gz", hash = "sha256:337b6e83d7ee73c40ea62407f2ce03b07c3459e213b6f332b94a69923b9e1cb9"}, ] [package.extras] @@ -1306,111 +1332,111 @@ files = [ [[package]] name = "hiredis" -version = "2.2.2" +version = "2.2.3" description = "Python wrapper for hiredis" optional = false python-versions = ">=3.7" files = [ - {file = "hiredis-2.2.2-cp310-cp310-macosx_10_12_universal2.whl", hash = "sha256:ba6123ff137275e2f4c31fc74b93813fcbb79160d43f5357163e09638c7743de"}, - {file = "hiredis-2.2.2-cp310-cp310-macosx_10_12_x86_64.whl", hash = "sha256:d995846acc8e3339fb7833cd19bf6f3946ff5157c8488a4df9c51cd119a36870"}, - {file = "hiredis-2.2.2-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:82f869ca44bcafa37cd71cfa1429648fa354d6021dcd72f03a2f66bcb339c546"}, - {file = "hiredis-2.2.2-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:aa90a5ee7a7f30c3d72d3513914b8f51f953a71b8cbd52a241b6db6685e55645"}, - {file = "hiredis-2.2.2-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:01e2e588392b5fdcc3a6aa0eb62a2eb2a142f829082fa4c3354228029d3aa1ce"}, - {file = "hiredis-2.2.2-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:5dac177a6ab8b4eb4d5e74978c29eef7cc9eef14086f814cb3893f7465578044"}, - {file = "hiredis-2.2.2-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:4cb992e3f9753c5a0c637f333c2010d1ad702aebf2d730ee4d484f32b19bae97"}, - {file = "hiredis-2.2.2-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:e61c22fda5fc25d31bbced24a8322d33c5cb8cad9ba698634c16edb5b3e79a91"}, - {file = "hiredis-2.2.2-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:9873898e26e50cd41415e9d1ea128bfdb60eb26abb4f5be28a4500fd7834dc0c"}, - {file = "hiredis-2.2.2-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:2c18b00a382546e19bcda8b83dcca5b6e0dbc238d235723434405f48a18e8f77"}, - {file = "hiredis-2.2.2-cp310-cp310-musllinux_1_1_ppc64le.whl", hash = "sha256:8c3a6998f6f88d7ca4d082fd26525074df13162b274d7c64034784b6fdc56666"}, - {file = "hiredis-2.2.2-cp310-cp310-musllinux_1_1_s390x.whl", hash = "sha256:0fc1f9a9791d028b2b8afa318ccff734c7fc8861d37a04ca9b3d27c9b05f9718"}, - {file = "hiredis-2.2.2-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:5f2cfd323f83985f2bed6ed013107873275025af270485b7d04c338bfb47bd14"}, - {file = "hiredis-2.2.2-cp310-cp310-win32.whl", hash = "sha256:55c7e9a9e05f8c0555bfba5c16d98492f8b6db650e56d0c35cc28aeabfc86020"}, - {file = "hiredis-2.2.2-cp310-cp310-win_amd64.whl", hash = "sha256:eaff526c2fed31c971b0fa338a25237ae5513550ef75d0b85b9420ec778cca45"}, - {file = "hiredis-2.2.2-cp311-cp311-macosx_10_12_universal2.whl", hash = "sha256:688b9b7458b4f3f452fea6ed062c04fa1fd9a69d9223d95c6cb052581aba553b"}, - {file = "hiredis-2.2.2-cp311-cp311-macosx_10_12_x86_64.whl", hash = "sha256:544d52fde3a8dac7854673eac20deca05214758193c01926ffbb0d57c6bf4ffe"}, - {file = "hiredis-2.2.2-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:990916e8b0b4eedddef787e73549b562f8c9e73a7fea82f9b8ff517806774ad0"}, - {file = "hiredis-2.2.2-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:10dc34854e9acfb3e7cc4157606e2efcb497b1c6fca07bd6c3be34ae5e413f13"}, - {file = "hiredis-2.2.2-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:c446a2007985ae49c2ecd946dd819dea72b931beb5f647ba08655a1a1e133fa8"}, - {file = "hiredis-2.2.2-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:02b9f928dc6cd43ed0f0ffc1c75fb209fb180f004b7e2e19994805f998d247aa"}, - {file = "hiredis-2.2.2-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:2a355aff8dfa02ebfe67f0946dd706e490bddda9ea260afac9cdc43942310c53"}, - {file = "hiredis-2.2.2-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:831461abe5b63e73719621a5f31d8fc175528a05dc09d5a8aa8ef565d6deefa4"}, - {file = "hiredis-2.2.2-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:75349f7c8f77eb0fd33ede4575d1e5b0a902a8176a436bf03293d7fec4bd3894"}, - {file = "hiredis-2.2.2-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:1eb39b34d15220095dc49ad1e1082580d35cd3b6d9741def52988b5075e4ff03"}, - {file = "hiredis-2.2.2-cp311-cp311-musllinux_1_1_ppc64le.whl", hash = "sha256:a9b306f4e870747eea8b008dcba2e9f1e4acd12b333a684bc1cc120e633a280e"}, - {file = "hiredis-2.2.2-cp311-cp311-musllinux_1_1_s390x.whl", hash = "sha256:03dfb4ab7a2136ce1be305592553f102e1bd91a96068ab2778e3252aed20d9bc"}, - {file = "hiredis-2.2.2-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:d8bc89c7e33fecb083a199ade0131a34d20365a8c32239e218da57290987ca9a"}, - {file = "hiredis-2.2.2-cp311-cp311-win32.whl", hash = "sha256:ed44b3c711cecde920f238ac35f70ac08744f2079b6369655856e43944464a72"}, - {file = "hiredis-2.2.2-cp311-cp311-win_amd64.whl", hash = "sha256:2e2f0ce3e8ab1314a52f562386220f6714fd24d7968a95528135ad04e88cc741"}, - {file = "hiredis-2.2.2-cp37-cp37m-macosx_10_12_x86_64.whl", hash = "sha256:e7e61ab75b851aac2d6bc634d03738a242a6ef255a44178437b427c5ebac0a87"}, - {file = "hiredis-2.2.2-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:9eb14339e399554bb436cc4628e8aaa3943adf7afcf34aba4cbd1e3e6b9ec7ec"}, - {file = "hiredis-2.2.2-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:e4ec57886f20f4298537cb1ab9dbda98594fb8d7c724c5fbf9a4b55329fd4a63"}, - {file = "hiredis-2.2.2-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:a89f5afb9827eab07b9c8c585cd4dc95e5232c727508ae2c935d09531abe9e33"}, - {file = "hiredis-2.2.2-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:3645590b9234cafd21c8ecfbf252ad9aa1d67629f4bdc98ba3627f48f8f7b5aa"}, - {file = "hiredis-2.2.2-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:99350e89f52186146938bdba0b9c6cd68802c20346707d6ca8366f2d69d89b2f"}, - {file = "hiredis-2.2.2-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:b5d290f3d8f7a05c4adbe6c355055b87c7081bfa1eccd1ae5491216307ee5f53"}, - {file = "hiredis-2.2.2-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:c95be6f20377d5995ef41a98314542e194d2dc9c2579d8f130a1aea78d48fd42"}, - {file = "hiredis-2.2.2-cp37-cp37m-musllinux_1_1_ppc64le.whl", hash = "sha256:e4e2da61a04251121cb551f569c3250e6e27e95f2a80f8351c36822eda1f5d2b"}, - {file = "hiredis-2.2.2-cp37-cp37m-musllinux_1_1_s390x.whl", hash = "sha256:ac7f8d68826f95a3652e44b0c12bfa74d3aa6531d47d5dbe6a2fbfc7979bc20f"}, - {file = "hiredis-2.2.2-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:359e662324318baadb768d3c4ade8c4bdcfbb313570eb01e15d75dc5db781815"}, - {file = "hiredis-2.2.2-cp37-cp37m-win32.whl", hash = "sha256:fd0ca35e2cf44866137cbb5ae7e439fab18a0b0e0e1cf51d45137622d59ec012"}, - {file = "hiredis-2.2.2-cp37-cp37m-win_amd64.whl", hash = "sha256:c9488ffb10acc6b121c498875278b0a6715d193742dc92d21a281712169ac06d"}, - {file = "hiredis-2.2.2-cp38-cp38-macosx_10_12_universal2.whl", hash = "sha256:1570fe4f93bc1ea487fb566f2b863fd0ed146f643a4ea31e4e07036db9e0c7f8"}, - {file = "hiredis-2.2.2-cp38-cp38-macosx_10_12_x86_64.whl", hash = "sha256:8753c561b37cccbda7264c9b4486e206a6318c18377cd647beb3aa41a15a6beb"}, - {file = "hiredis-2.2.2-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:a06d0dd84f10be6b15a92edbca2490b64917280f66d8267c63de99b6550308ad"}, - {file = "hiredis-2.2.2-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:40ff3f1ec3a4046732e9e41df08dcb1a559847196755d295d43e32528aae39e6"}, - {file = "hiredis-2.2.2-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:c24d856e13c02bd9d28a189e47be70cbba6f2c2a4bd85a8cc98819db9e7e3e06"}, - {file = "hiredis-2.2.2-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:4ee9fe7cef505e8d925c70bebcc16bfab12aa7af922f948346baffd4730f7b00"}, - {file = "hiredis-2.2.2-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:03ab1d545794bb0e09f3b1e2c8b3adcfacd84f6f2d402bfdcd441a98c0e9643c"}, - {file = "hiredis-2.2.2-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:14dfccf4696d75395c587a5dafafb4f7aa0a5d55309341d10bc2e7f1eaa20771"}, - {file = "hiredis-2.2.2-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:2ddc573809ca4374da1b24b48604f34f3d5f0911fcccfb1c403ff8d8ca31c232"}, - {file = "hiredis-2.2.2-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:24301ca2bf9b2f843b4c3015c90f161798fa3bbc5b95fd494785751b137dbbe2"}, - {file = "hiredis-2.2.2-cp38-cp38-musllinux_1_1_ppc64le.whl", hash = "sha256:b083a69e158138ffa95740ff6984d328259387b5596908021b3ccb946469ff66"}, - {file = "hiredis-2.2.2-cp38-cp38-musllinux_1_1_s390x.whl", hash = "sha256:8e16dc949cc2e9c5fbcd08de05b5fb61b89ff65738d772863c5c96248628830e"}, - {file = "hiredis-2.2.2-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:674f296c3c89cb53f97aa9ba2508d3f360ad481b9e0c0e3a59b342a15192adaf"}, - {file = "hiredis-2.2.2-cp38-cp38-win32.whl", hash = "sha256:20ecbf87aac4f0f33f9c55ae15cb73b485d256c57518c590b7d0c9c152150632"}, - {file = "hiredis-2.2.2-cp38-cp38-win_amd64.whl", hash = "sha256:b11960237a3025bf248135e5b497dc4923e83d137eb798fbfe78b40d57c4b156"}, - {file = "hiredis-2.2.2-cp39-cp39-macosx_10_12_universal2.whl", hash = "sha256:18103090b8eda9c529830e26594e88b0b1472055785f3ed29b8adc694d03862a"}, - {file = "hiredis-2.2.2-cp39-cp39-macosx_10_12_x86_64.whl", hash = "sha256:d1acb7c957e5343303b3862947df3232dc7395da320b3b9ae076dfaa56ad59dc"}, - {file = "hiredis-2.2.2-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:4997f55e1208af95a8fbd0fa187b04c672fcec8f66e49b9ab7fcc45cc1657dc4"}, - {file = "hiredis-2.2.2-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:449e18506d22af40977abd0f5a8979f57f88d4562fe591478a3438d76a15133d"}, - {file = "hiredis-2.2.2-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:a32a4474f7a4abdea954f3365608edee3f90f1de9fa05b81d214d4cad04c718a"}, - {file = "hiredis-2.2.2-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:e86c800c6941698777fc58419216a66a7f76504f1cea72381d2ee206888e964d"}, - {file = "hiredis-2.2.2-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:c73aa295c5369135247ff63aa1fbb116067485d0506cd787cc0c868e72bbee55"}, - {file = "hiredis-2.2.2-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:2e10a66680023bd5c5a3d605dae0844e3dde60eac5b79e39f51395a2aceaf634"}, - {file = "hiredis-2.2.2-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:03ab760fc96e0c5d36226eb727f30645bf6a53c97f14bfc0a4d0401bfc9b8af7"}, - {file = "hiredis-2.2.2-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:855d258e7f1aee3d7fbd5b1dc87790b1b5016e23d369a97b934a25ae7bc0171f"}, - {file = "hiredis-2.2.2-cp39-cp39-musllinux_1_1_ppc64le.whl", hash = "sha256:ccc33d87866d213f84f857a98f69c13f94fbf99a3304e328869890c9e49c8d65"}, - {file = "hiredis-2.2.2-cp39-cp39-musllinux_1_1_s390x.whl", hash = "sha256:339af17bb9817f8acb127247c79a99cad63db6738c0fb2aec9fa3d4f35d2a250"}, - {file = "hiredis-2.2.2-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:57f73aa04d0b70ff436fb35fa7ea2b796aa7addbd7ebb8d1aa1f3d1b3e4439f1"}, - {file = "hiredis-2.2.2-cp39-cp39-win32.whl", hash = "sha256:e97d4e650b8d933a1229f341db92b610fc52b8d752490235977b63b81fbbc2cb"}, - {file = "hiredis-2.2.2-cp39-cp39-win_amd64.whl", hash = "sha256:8d43a7bba66a800279e33229a206861be09c279e261eaa8db4824e59465f4848"}, - {file = "hiredis-2.2.2-pp37-pypy37_pp73-macosx_10_12_x86_64.whl", hash = "sha256:632d79fd02b03e8d9fbaebbe40bfe34b920c5d0a9c0ef6270752e0db85208175"}, - {file = "hiredis-2.2.2-pp37-pypy37_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:3a5fefac31c84143782ec1ebc323c04e733a6e4bfebcef9907a34e47a465e648"}, - {file = "hiredis-2.2.2-pp37-pypy37_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5155bc1710df8e21aa48c9b2f4d4e13e4987e1efff363a1ef9c84fae2cc6c145"}, - {file = "hiredis-2.2.2-pp37-pypy37_pp73-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:2f220b71235d2deab1b4b22681c8aee444720d973b80f1b86a4e2a85f6bcf1e1"}, - {file = "hiredis-2.2.2-pp37-pypy37_pp73-win_amd64.whl", hash = "sha256:f1f1efbe9cc29a3af39cf7eed27225f951aed3f48a1149c7fb74529fb5ab86d4"}, - {file = "hiredis-2.2.2-pp38-pypy38_pp73-macosx_10_12_x86_64.whl", hash = "sha256:1f1c44242c18b1f02e6d1162f133d65d00e09cc10d9165dccc78662def72abc2"}, - {file = "hiredis-2.2.2-pp38-pypy38_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:9e0f444d9062f7e487ef42bab2fb2e290f1704afcbca48ad3ec23de63eef0fda"}, - {file = "hiredis-2.2.2-pp38-pypy38_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:ac15e7e1efca51b4695e540c80c328accb352c9608da7c2df82d1fa1a3c539ef"}, - {file = "hiredis-2.2.2-pp38-pypy38_pp73-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:20cfbc469400669a5999aa34ccba3872a1e34490ec3d5c84e8c0752c27977b7c"}, - {file = "hiredis-2.2.2-pp38-pypy38_pp73-win_amd64.whl", hash = "sha256:bae004a0b978bf62e38d0eef5ab9156f8101d01167b3ca7054bd0994b773e917"}, - {file = "hiredis-2.2.2-pp39-pypy39_pp73-macosx_10_12_x86_64.whl", hash = "sha256:a1ce725542133dbdda9e8704867ef52651886bd1ef568c6fd997a27404381985"}, - {file = "hiredis-2.2.2-pp39-pypy39_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:6e6ea7532221c97fa6d79f7d19d452cd9d1141d759c54279cc4774ce24728f13"}, - {file = "hiredis-2.2.2-pp39-pypy39_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:a7114961ed78d708142f6c6eb1d2ed65dc3da4b5ae8a4660ad889dd7fc891971"}, - {file = "hiredis-2.2.2-pp39-pypy39_pp73-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:1b084fbc3e69f99865242f8e1ccd4ea2a34bf6a3983d015d61133377526c0ce2"}, - {file = "hiredis-2.2.2-pp39-pypy39_pp73-win_amd64.whl", hash = "sha256:2d1ba0799f3487294f72b2157944d5c3a4fb33c99e2d495d63eab98c7ec7234b"}, - {file = "hiredis-2.2.2.tar.gz", hash = "sha256:9c270bd0567a9c60673284e000132f603bb4ecbcd707567647a68f85ef45c4d4"}, + {file = "hiredis-2.2.3-cp310-cp310-macosx_10_12_universal2.whl", hash = "sha256:9a1a80a8fa767f2fdc3870316a54b84fe9fc09fa6ab6a2686783de6a228a4604"}, + {file = "hiredis-2.2.3-cp310-cp310-macosx_10_12_x86_64.whl", hash = "sha256:3f006c28c885deb99b670a5a66f367a175ab8955b0374029bad7111f5357dcd4"}, + {file = "hiredis-2.2.3-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:ffaf841546905d90ff189de7397aa56413b1ce5e54547f17a98f0ebf3a3b0a3b"}, + {file = "hiredis-2.2.3-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:1cadb0ac7ba3babfd804e425946bec9717b320564a1390f163a54af9365a720a"}, + {file = "hiredis-2.2.3-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:33bc4721632ef9708fa44e5df0066053fccc8e65410a2c48573192517a533b48"}, + {file = "hiredis-2.2.3-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:227c5b4bcb60f89008c275d596e4a7b6625a6b3c827b8a66ae582eace7051f71"}, + {file = "hiredis-2.2.3-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:61995eb826009d99ed8590747bc0da683a5f4fbb4faa8788166bf3810845cd5c"}, + {file = "hiredis-2.2.3-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:6f969edc851efe23010e0f53a64269f2629a9364135e9ec81c842e8b2277d0c1"}, + {file = "hiredis-2.2.3-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:d27e560eefb57914d742a837f1da98d3b29cb22eff013c8023b7cf52ae6e051d"}, + {file = "hiredis-2.2.3-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:3759f4789ae1913b7df278dfc9e8749205b7a106f888cd2903d19461e24a7697"}, + {file = "hiredis-2.2.3-cp310-cp310-musllinux_1_1_ppc64le.whl", hash = "sha256:c6cb613148422c523945cdb8b6bed617856f2602fd8750e33773ede2616e55d5"}, + {file = "hiredis-2.2.3-cp310-cp310-musllinux_1_1_s390x.whl", hash = "sha256:1d274d5c511dfc03f83f997d3238eaa9b6ee3f982640979f509373cced891e98"}, + {file = "hiredis-2.2.3-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:3b7fe075e91b9d9cff40eba4fb6a8eff74964d3979a39be9a9ef58b1b4cb3604"}, + {file = "hiredis-2.2.3-cp310-cp310-win32.whl", hash = "sha256:77924b0d32fd1f493d3df15d9609ddf9d94c31a364022a6bf6b525ce9da75bea"}, + {file = "hiredis-2.2.3-cp310-cp310-win_amd64.whl", hash = "sha256:dcb0569dd5bfe6004658cd0f229efa699a3169dcb4f77bd72e188adda302063d"}, + {file = "hiredis-2.2.3-cp311-cp311-macosx_10_12_universal2.whl", hash = "sha256:d115790f18daa99b5c11a506e48923b630ef712e9e4b40482af942c3d40638b8"}, + {file = "hiredis-2.2.3-cp311-cp311-macosx_10_12_x86_64.whl", hash = "sha256:4c3b8be557e08b234774925622e196f0ee36fe4eab66cd19df934d3efd8f3743"}, + {file = "hiredis-2.2.3-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:3f5446068197b35a11ccc697720c41879c8657e2e761aaa8311783aac84cef20"}, + {file = "hiredis-2.2.3-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:aa17a3b22b3726d54d7af20394f65d4a1735a842a4e0f557dc67a90f6965c4bc"}, + {file = "hiredis-2.2.3-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:7df645b6b7800e8b748c217fbd6a4ca8361bcb9a1ae6206cc02377833ec8a1aa"}, + {file = "hiredis-2.2.3-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:2fb9300959a0048138791f3d68359d61a788574ec9556bddf1fec07f2dbc5320"}, + {file = "hiredis-2.2.3-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:2d7e459fe7313925f395148d36d9b7f4f8dac65be06e45d7af356b187cef65fc"}, + {file = "hiredis-2.2.3-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:8eceffca3941775b646cd585cd19b275d382de43cc3327d22f7c75d7b003d481"}, + {file = "hiredis-2.2.3-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:b17baf702c6e5b4bb66e1281a3efbb1d749c9d06cdb92b665ad81e03118f78fc"}, + {file = "hiredis-2.2.3-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:4e43e2b5acaad09cf48c032f7e4926392bb3a3f01854416cf6d82ebff94d5467"}, + {file = "hiredis-2.2.3-cp311-cp311-musllinux_1_1_ppc64le.whl", hash = "sha256:a7205497d7276a81fe92951a29616ef96562ed2f91a02066f72b6f93cb34b40e"}, + {file = "hiredis-2.2.3-cp311-cp311-musllinux_1_1_s390x.whl", hash = "sha256:126623b03c31cb6ac3e0d138feb6fcc36dd43dd34fc7da7b7a0c38b5d75bc896"}, + {file = "hiredis-2.2.3-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:071c5814b850574036506a8118034f97c3cbf2fe9947ff45a27b07a48da56240"}, + {file = "hiredis-2.2.3-cp311-cp311-win32.whl", hash = "sha256:d1be9e30e675f5bc1cb534633324578f6f0944a1bcffe53242cf632f554f83b6"}, + {file = "hiredis-2.2.3-cp311-cp311-win_amd64.whl", hash = "sha256:b9a7c987e161e3c58f992c63b7e26fea7fe0777f3b975799d23d65bbb8cb5899"}, + {file = "hiredis-2.2.3-cp37-cp37m-macosx_10_12_x86_64.whl", hash = "sha256:f2dcb8389fa3d453927b1299f46bdb38473c293c8269d5c777d33ea0e526b610"}, + {file = "hiredis-2.2.3-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:a2df98f5e071320c7d84e8bd07c0542acdd0a7519307fc31774d60e4b842ec4f"}, + {file = "hiredis-2.2.3-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:61a72e4a523cdfc521762137559c08dfa360a3caef63620be58c699d1717dac1"}, + {file = "hiredis-2.2.3-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:c9b9e5bde7030cae83aa900b5bd660decc65afd2db8c400f3c568c815a47ca2a"}, + {file = "hiredis-2.2.3-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:cd2614f17e261f72efc2f19f5e5ff2ee19e2296570c0dcf33409e22be30710de"}, + {file = "hiredis-2.2.3-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:46525fbd84523cac75af5bf524bc74aaac848beaf31b142d2df8a787d9b4bbc4"}, + {file = "hiredis-2.2.3-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:d1a4ce40ba11da9382c14da31f4f9e88c18f7d294f523decd0fadfb81f51ad18"}, + {file = "hiredis-2.2.3-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:5cda592405bbd29d53942e0389dc3fa77b49c362640210d7e94a10c14a677d4d"}, + {file = "hiredis-2.2.3-cp37-cp37m-musllinux_1_1_ppc64le.whl", hash = "sha256:5e6674a017629284ef373b50496d9fb1a89b85a20a7fa100ecd109484ec748e5"}, + {file = "hiredis-2.2.3-cp37-cp37m-musllinux_1_1_s390x.whl", hash = "sha256:e62ec131816c6120eff40dffe43424e140264a15fa4ab88c301bd6a595913af3"}, + {file = "hiredis-2.2.3-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:17e938d9d3ee92e1adbff361706f1c36cc60eeb3e3eeca7a3a353eae344f4c91"}, + {file = "hiredis-2.2.3-cp37-cp37m-win32.whl", hash = "sha256:95d2305fd2a7b179cacb48b10f618872fc565c175f9f62b854e8d1acac3e8a9e"}, + {file = "hiredis-2.2.3-cp37-cp37m-win_amd64.whl", hash = "sha256:8f9dbe12f011a9b784f58faecc171d22465bb532c310bd588d769ba79a59ef5a"}, + {file = "hiredis-2.2.3-cp38-cp38-macosx_10_12_universal2.whl", hash = "sha256:5a4bcef114fc071d5f52c386c47f35aae0a5b43673197b9288a15b584da8fa3a"}, + {file = "hiredis-2.2.3-cp38-cp38-macosx_10_12_x86_64.whl", hash = "sha256:232d0a70519865741ba56e1dfefd160a580ae78c30a1517bad47b3cf95a3bc7d"}, + {file = "hiredis-2.2.3-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:9076ce8429785c85f824650735791738de7143f61f43ae9ed83e163c0ca0fa44"}, + {file = "hiredis-2.2.3-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ec58fb7c2062f835595c12f0f02dcda76d0eb0831423cc191d1e18c9276648de"}, + {file = "hiredis-2.2.3-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:7f2b34a6444b8f9c1e9f84bd2c639388e5d14f128afd14a869dfb3d9af893aa2"}, + {file = "hiredis-2.2.3-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:818dfd310aa1020a13cd08ee48e116dd8c3bb2e23b8161f8ac4df587dd5093d7"}, + {file = "hiredis-2.2.3-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:96d9ea6c8d4cbdeee2e0d43379ce2881e4af0454b00570677c59f33f2531cd38"}, + {file = "hiredis-2.2.3-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:f1eadbcd3de55ac42310ff82550d3302cb4efcd4e17d76646a17b6e7004bb42b"}, + {file = "hiredis-2.2.3-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:477c34c4489666dc73cb5e89dafe2617c3e13da1298917f73d55aac4696bd793"}, + {file = "hiredis-2.2.3-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:14824e457e4f5cda685c3345d125da13949bcf3bb1c88eb5d248c8d2c3dee08f"}, + {file = "hiredis-2.2.3-cp38-cp38-musllinux_1_1_ppc64le.whl", hash = "sha256:9cd32326dfa6ce87edf754153b0105aca64486bebe93b9600ccff74fa0b224df"}, + {file = "hiredis-2.2.3-cp38-cp38-musllinux_1_1_s390x.whl", hash = "sha256:51341e70b467004dcbec3a6ce8c478d2d6241e0f6b01e4c56764afd5022e1e9d"}, + {file = "hiredis-2.2.3-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:2443659c76b226267e2a04dbbb21bc2a3f91aa53bdc0c22964632753ae43a247"}, + {file = "hiredis-2.2.3-cp38-cp38-win32.whl", hash = "sha256:4e3e3e31423f888d396b1fc1f936936e52af868ac1ec17dd15e3eeba9dd4de24"}, + {file = "hiredis-2.2.3-cp38-cp38-win_amd64.whl", hash = "sha256:20f509e3a1a20d6e5f5794fc37ceb21f70f409101fcfe7a8bde783894d51b369"}, + {file = "hiredis-2.2.3-cp39-cp39-macosx_10_12_universal2.whl", hash = "sha256:d20891e3f33803b26d54c77fd5745878497091e33f4bbbdd454cf6e71aee8890"}, + {file = "hiredis-2.2.3-cp39-cp39-macosx_10_12_x86_64.whl", hash = "sha256:50171f985e17970f87d5a29e16603d1e5b03bdbf5c2691a37e6c912942a6b657"}, + {file = "hiredis-2.2.3-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:9944a2cac25ffe049a7e89f306e11b900640837d1ef38d9be0eaa4a4e2b73a52"}, + {file = "hiredis-2.2.3-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:5a5c8019ff94988d56eb49b15de76fe83f6b42536d76edeb6565dbf7fe14b973"}, + {file = "hiredis-2.2.3-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:a286ded34eb16501002e3713b3130c987366eee2ba0d58c33c72f27778e31676"}, + {file = "hiredis-2.2.3-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:4b3e974ad15eb32b1f537730dea70b93a4c3db7b026de3ad2b59da49c6f7454d"}, + {file = "hiredis-2.2.3-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:08415ea74c1c29b9d6a4ca3dd0e810dc1af343c1d1d442e15ba133b11ab5be6a"}, + {file = "hiredis-2.2.3-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:7e17d04ea58ab8cf3f2dc52e875db16077c6357846006780086fff3189fb199d"}, + {file = "hiredis-2.2.3-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:6ccdcb635dae85b006592f78e32d97f4bc7541cb27829d505f9c7fefcef48298"}, + {file = "hiredis-2.2.3-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:69536b821dd1bc78058a6e7541743f8d82bf2d981b91280b14c4daa6cdc7faba"}, + {file = "hiredis-2.2.3-cp39-cp39-musllinux_1_1_ppc64le.whl", hash = "sha256:3753df5f873d473f055e1f8837bfad0bd3b277c86f3c9bf058c58f14204cd901"}, + {file = "hiredis-2.2.3-cp39-cp39-musllinux_1_1_s390x.whl", hash = "sha256:6f88cafe46612b6fa68e6dea49e25bebf160598bba00101caa51cc8c1f18d597"}, + {file = "hiredis-2.2.3-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:33ee3ea5cad3a8cb339352cd230b411eb437a2e75d7736c4899acab32056ccdb"}, + {file = "hiredis-2.2.3-cp39-cp39-win32.whl", hash = "sha256:b4f3d06dc16671b88a13ae85d8ca92534c0b637d59e49f0558d040a691246422"}, + {file = "hiredis-2.2.3-cp39-cp39-win_amd64.whl", hash = "sha256:4f674e309cd055ee7a48304ceb8cf43265d859faf4d7d01d270ce45e976ae9d3"}, + {file = "hiredis-2.2.3-pp37-pypy37_pp73-macosx_10_12_x86_64.whl", hash = "sha256:8f280ab4e043b089777b43b4227bdc2035f88da5072ab36588e0ccf77d45d058"}, + {file = "hiredis-2.2.3-pp37-pypy37_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:15c2a551f3b8a26f7940d6ee10b837810201754b8d7e6f6b1391655370882c5a"}, + {file = "hiredis-2.2.3-pp37-pypy37_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:60c4e3c258eafaab21b174b17270a0cc093718d61cdbde8c03f85ec4bf835343"}, + {file = "hiredis-2.2.3-pp37-pypy37_pp73-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:cc36a9dded458d4e37492fe3e619c6c83caae794d26ad925adbce61d592f8428"}, + {file = "hiredis-2.2.3-pp37-pypy37_pp73-win_amd64.whl", hash = "sha256:4ed68a3b1ccb4313d2a42546fd7e7439ad4745918a48b6c9bcaa61e1e3e42634"}, + {file = "hiredis-2.2.3-pp38-pypy38_pp73-macosx_10_12_x86_64.whl", hash = "sha256:3bf4b5bae472630c229518e4a814b1b68f10a3d9b00aeaec45f1a330f03a0251"}, + {file = "hiredis-2.2.3-pp38-pypy38_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:33a94d264e6e12a79d9bb8af333b01dc286b9f39c99072ab5fef94ce1f018e17"}, + {file = "hiredis-2.2.3-pp38-pypy38_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:3fa6811a618653164f918b891a0fa07052bd71a799defa5c44d167cac5557b26"}, + {file = "hiredis-2.2.3-pp38-pypy38_pp73-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:af33f370be90b48bbaf0dab32decbdcc522b1fa95d109020a963282086518a8e"}, + {file = "hiredis-2.2.3-pp38-pypy38_pp73-win_amd64.whl", hash = "sha256:b9953d87418ac228f508d93898ab572775e4d3b0eeb886a1a7734553bcdaf291"}, + {file = "hiredis-2.2.3-pp39-pypy39_pp73-macosx_10_12_x86_64.whl", hash = "sha256:5e7bb4dd524f50b71c20ef5a12bd61da9b463f8894b18a06130942fe31509881"}, + {file = "hiredis-2.2.3-pp39-pypy39_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:89a258424158eb8b3ed9f65548d68998da334ef155d09488c5637723eb1cd697"}, + {file = "hiredis-2.2.3-pp39-pypy39_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:9f4a65276f6ecdebe75f2a53f578fbc40e8d2860658420d5e0611c56bbf5054c"}, + {file = "hiredis-2.2.3-pp39-pypy39_pp73-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:334f2738700b20faa04a0d813366fb16ed17287430a6b50584161d5ad31ca6d7"}, + {file = "hiredis-2.2.3-pp39-pypy39_pp73-win_amd64.whl", hash = "sha256:d194decd9608f11c777946f596f31d5aacad13972a0a87829ae1e6f2d26c1885"}, + {file = "hiredis-2.2.3.tar.gz", hash = "sha256:e75163773a309e56a9b58165cf5a50e0f84b755f6ff863b2c01a38918fe92daa"}, ] [[package]] name = "httpcore" -version = "0.16.3" +version = "0.17.2" description = "A minimal low-level HTTP client." optional = false python-versions = ">=3.7" files = [ - {file = "httpcore-0.16.3-py3-none-any.whl", hash = "sha256:da1fb708784a938aa084bde4feb8317056c55037247c787bd7e19eb2c2949dc0"}, - {file = "httpcore-0.16.3.tar.gz", hash = "sha256:c5d6f04e2fc530f39e0c077e6a30caa53f1451096120f1f38b954afd0b17c0cb"}, + {file = "httpcore-0.17.2-py3-none-any.whl", hash = "sha256:5581b9c12379c4288fe70f43c710d16060c10080617001e6b22a3b6dbcbefd36"}, + {file = "httpcore-0.17.2.tar.gz", hash = "sha256:125f8375ab60036db632f34f4b627a9ad085048eef7cb7d2616fea0f739f98af"}, ] [package.dependencies] @@ -1425,36 +1451,36 @@ socks = ["socksio (==1.*)"] [[package]] name = "httpx" -version = "0.23.3" +version = "0.24.1" description = "The next generation HTTP client." optional = false python-versions = ">=3.7" files = [ - {file = "httpx-0.23.3-py3-none-any.whl", hash = "sha256:a211fcce9b1254ea24f0cd6af9869b3d29aba40154e947d2a07bb499b3e310d6"}, - {file = "httpx-0.23.3.tar.gz", hash = "sha256:9818458eb565bb54898ccb9b8b251a28785dd4a55afbc23d0eb410754fe7d0f9"}, + {file = "httpx-0.24.1-py3-none-any.whl", hash = "sha256:06781eb9ac53cde990577af654bd990a4949de37a28bdb4a230d434f3a30b9bd"}, + {file = "httpx-0.24.1.tar.gz", hash = "sha256:5853a43053df830c20f8110c5e69fe44d035d850b2dfe795e196f00fdb774bdd"}, ] [package.dependencies] certifi = "*" -httpcore = ">=0.15.0,<0.17.0" -rfc3986 = {version = ">=1.3,<2", extras = ["idna2008"]} +httpcore = ">=0.15.0,<0.18.0" +idna = "*" sniffio = "*" [package.extras] brotli = ["brotli", "brotlicffi"] -cli = ["click (==8.*)", "pygments (==2.*)", "rich (>=10,<13)"] +cli = ["click (==8.*)", "pygments (==2.*)", "rich (>=10,<14)"] http2 = ["h2 (>=3,<5)"] socks = ["socksio (==1.*)"] [[package]] name = "identify" -version = "2.5.20" +version = "2.5.24" description = "File identification library for Python" optional = false python-versions = ">=3.7" files = [ - {file = "identify-2.5.20-py2.py3-none-any.whl", hash = "sha256:5dfef8a745ca4f2c95f27e9db74cb4c8b6d9916383988e8791f3595868f78a33"}, - {file = "identify-2.5.20.tar.gz", hash = "sha256:c8b288552bc5f05a08aff09af2f58e6976bf8ac87beb38498a0e3d98ba64eb18"}, + {file = "identify-2.5.24-py2.py3-none-any.whl", hash = "sha256:986dbfb38b1140e763e413e6feb44cd731faf72d1909543178aa79b0e258265d"}, + {file = "identify-2.5.24.tar.gz", hash = "sha256:0aac67d5b4812498056d28a9a512a483f5085cc28640b02b258a59dac34301d4"}, ] [package.extras] @@ -1501,13 +1527,13 @@ test = ["pytest", "pytest-cov"] [[package]] name = "importlib-metadata" -version = "6.1.0" +version = "6.7.0" description = "Read metadata from Python packages" optional = false python-versions = ">=3.7" files = [ - {file = "importlib_metadata-6.1.0-py3-none-any.whl", hash = "sha256:ff80f3b5394912eb1b108fcfd444dc78b7f1f3e16b16188054bd01cb9cb86f09"}, - {file = "importlib_metadata-6.1.0.tar.gz", hash = "sha256:43ce9281e097583d758c2c708c4376371261a02c34682491a8e98352365aad20"}, + {file = "importlib_metadata-6.7.0-py3-none-any.whl", hash = "sha256:cb52082e659e97afc5dac71e79de97d8681de3aa07ff18578330904a9d18e5b5"}, + {file = "importlib_metadata-6.7.0.tar.gz", hash = "sha256:1aaf550d4f73e5d6783e7acb77aec43d49da8017410afae93822cc9cca98c4d4"}, ] [package.dependencies] @@ -1516,7 +1542,7 @@ zipp = ">=0.5" [package.extras] docs = ["furo", "jaraco.packaging (>=9)", "jaraco.tidelift (>=1.4)", "rst.linker (>=1.9)", "sphinx (>=3.5)", "sphinx-lint"] perf = ["ipython"] -testing = ["flake8 (<5)", "flufl.flake8", "importlib-resources (>=1.3)", "packaging", "pyfakefs", "pytest (>=6)", "pytest-black (>=0.3.7)", "pytest-checkdocs (>=2.4)", "pytest-cov", "pytest-enabler (>=1.3)", "pytest-flake8", "pytest-mypy (>=0.9.1)", "pytest-perf (>=0.9.2)"] +testing = ["flufl.flake8", "importlib-resources (>=1.3)", "packaging", "pyfakefs", "pytest (>=6)", "pytest-black (>=0.3.7)", "pytest-checkdocs (>=2.4)", "pytest-cov", "pytest-enabler (>=1.3)", "pytest-mypy (>=0.9.1)", "pytest-perf (>=0.9.2)", "pytest-ruff"] [[package]] name = "importlib-resources" @@ -1771,61 +1797,61 @@ testing = ["coverage", "pytest", "pytest-cov", "pytest-regressions"] [[package]] name = "markupsafe" -version = "2.1.2" +version = "2.1.3" description = "Safely add untrusted strings to HTML/XML markup." optional = false python-versions = ">=3.7" files = [ - {file = "MarkupSafe-2.1.2-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:665a36ae6f8f20a4676b53224e33d456a6f5a72657d9c83c2aa00765072f31f7"}, - {file = "MarkupSafe-2.1.2-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:340bea174e9761308703ae988e982005aedf427de816d1afe98147668cc03036"}, - {file = "MarkupSafe-2.1.2-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:22152d00bf4a9c7c83960521fc558f55a1adbc0631fbb00a9471e097b19d72e1"}, - {file = "MarkupSafe-2.1.2-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:28057e985dace2f478e042eaa15606c7efccb700797660629da387eb289b9323"}, - {file = "MarkupSafe-2.1.2-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:ca244fa73f50a800cf8c3ebf7fd93149ec37f5cb9596aa8873ae2c1d23498601"}, - {file = "MarkupSafe-2.1.2-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:d9d971ec1e79906046aa3ca266de79eac42f1dbf3612a05dc9368125952bd1a1"}, - {file = "MarkupSafe-2.1.2-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:7e007132af78ea9df29495dbf7b5824cb71648d7133cf7848a2a5dd00d36f9ff"}, - {file = "MarkupSafe-2.1.2-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:7313ce6a199651c4ed9d7e4cfb4aa56fe923b1adf9af3b420ee14e6d9a73df65"}, - {file = "MarkupSafe-2.1.2-cp310-cp310-win32.whl", hash = "sha256:c4a549890a45f57f1ebf99c067a4ad0cb423a05544accaf2b065246827ed9603"}, - {file = "MarkupSafe-2.1.2-cp310-cp310-win_amd64.whl", hash = "sha256:835fb5e38fd89328e9c81067fd642b3593c33e1e17e2fdbf77f5676abb14a156"}, - {file = "MarkupSafe-2.1.2-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:2ec4f2d48ae59bbb9d1f9d7efb9236ab81429a764dedca114f5fdabbc3788013"}, - {file = "MarkupSafe-2.1.2-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:608e7073dfa9e38a85d38474c082d4281f4ce276ac0010224eaba11e929dd53a"}, - {file = "MarkupSafe-2.1.2-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:65608c35bfb8a76763f37036547f7adfd09270fbdbf96608be2bead319728fcd"}, - {file = "MarkupSafe-2.1.2-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f2bfb563d0211ce16b63c7cb9395d2c682a23187f54c3d79bfec33e6705473c6"}, - {file = "MarkupSafe-2.1.2-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:da25303d91526aac3672ee6d49a2f3db2d9502a4a60b55519feb1a4c7714e07d"}, - {file = "MarkupSafe-2.1.2-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:9cad97ab29dfc3f0249b483412c85c8ef4766d96cdf9dcf5a1e3caa3f3661cf1"}, - {file = "MarkupSafe-2.1.2-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:085fd3201e7b12809f9e6e9bc1e5c96a368c8523fad5afb02afe3c051ae4afcc"}, - {file = "MarkupSafe-2.1.2-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:1bea30e9bf331f3fef67e0a3877b2288593c98a21ccb2cf29b74c581a4eb3af0"}, - {file = "MarkupSafe-2.1.2-cp311-cp311-win32.whl", hash = "sha256:7df70907e00c970c60b9ef2938d894a9381f38e6b9db73c5be35e59d92e06625"}, - {file = "MarkupSafe-2.1.2-cp311-cp311-win_amd64.whl", hash = "sha256:e55e40ff0cc8cc5c07996915ad367fa47da6b3fc091fdadca7f5403239c5fec3"}, - {file = "MarkupSafe-2.1.2-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:a6e40afa7f45939ca356f348c8e23048e02cb109ced1eb8420961b2f40fb373a"}, - {file = "MarkupSafe-2.1.2-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:cf877ab4ed6e302ec1d04952ca358b381a882fbd9d1b07cccbfd61783561f98a"}, - {file = "MarkupSafe-2.1.2-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:63ba06c9941e46fa389d389644e2d8225e0e3e5ebcc4ff1ea8506dce646f8c8a"}, - {file = "MarkupSafe-2.1.2-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:f1cd098434e83e656abf198f103a8207a8187c0fc110306691a2e94a78d0abb2"}, - {file = "MarkupSafe-2.1.2-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:55f44b440d491028addb3b88f72207d71eeebfb7b5dbf0643f7c023ae1fba619"}, - {file = "MarkupSafe-2.1.2-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:a6f2fcca746e8d5910e18782f976489939d54a91f9411c32051b4aab2bd7c513"}, - {file = "MarkupSafe-2.1.2-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:0b462104ba25f1ac006fdab8b6a01ebbfbce9ed37fd37fd4acd70c67c973e460"}, - {file = "MarkupSafe-2.1.2-cp37-cp37m-win32.whl", hash = "sha256:7668b52e102d0ed87cb082380a7e2e1e78737ddecdde129acadb0eccc5423859"}, - {file = "MarkupSafe-2.1.2-cp37-cp37m-win_amd64.whl", hash = "sha256:6d6607f98fcf17e534162f0709aaad3ab7a96032723d8ac8750ffe17ae5a0666"}, - {file = "MarkupSafe-2.1.2-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:a806db027852538d2ad7555b203300173dd1b77ba116de92da9afbc3a3be3eed"}, - {file = "MarkupSafe-2.1.2-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:a4abaec6ca3ad8660690236d11bfe28dfd707778e2442b45addd2f086d6ef094"}, - {file = "MarkupSafe-2.1.2-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:f03a532d7dee1bed20bc4884194a16160a2de9ffc6354b3878ec9682bb623c54"}, - {file = "MarkupSafe-2.1.2-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:4cf06cdc1dda95223e9d2d3c58d3b178aa5dacb35ee7e3bbac10e4e1faacb419"}, - {file = "MarkupSafe-2.1.2-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:22731d79ed2eb25059ae3df1dfc9cb1546691cc41f4e3130fe6bfbc3ecbbecfa"}, - {file = "MarkupSafe-2.1.2-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:f8ffb705ffcf5ddd0e80b65ddf7bed7ee4f5a441ea7d3419e861a12eaf41af58"}, - {file = "MarkupSafe-2.1.2-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:8db032bf0ce9022a8e41a22598eefc802314e81b879ae093f36ce9ddf39ab1ba"}, - {file = "MarkupSafe-2.1.2-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:2298c859cfc5463f1b64bd55cb3e602528db6fa0f3cfd568d3605c50678f8f03"}, - {file = "MarkupSafe-2.1.2-cp38-cp38-win32.whl", hash = "sha256:50c42830a633fa0cf9e7d27664637532791bfc31c731a87b202d2d8ac40c3ea2"}, - {file = "MarkupSafe-2.1.2-cp38-cp38-win_amd64.whl", hash = "sha256:bb06feb762bade6bf3c8b844462274db0c76acc95c52abe8dbed28ae3d44a147"}, - {file = "MarkupSafe-2.1.2-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:99625a92da8229df6d44335e6fcc558a5037dd0a760e11d84be2260e6f37002f"}, - {file = "MarkupSafe-2.1.2-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:8bca7e26c1dd751236cfb0c6c72d4ad61d986e9a41bbf76cb445f69488b2a2bd"}, - {file = "MarkupSafe-2.1.2-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:40627dcf047dadb22cd25ea7ecfe9cbf3bbbad0482ee5920b582f3809c97654f"}, - {file = "MarkupSafe-2.1.2-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:40dfd3fefbef579ee058f139733ac336312663c6706d1163b82b3003fb1925c4"}, - {file = "MarkupSafe-2.1.2-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:090376d812fb6ac5f171e5938e82e7f2d7adc2b629101cec0db8b267815c85e2"}, - {file = "MarkupSafe-2.1.2-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:2e7821bffe00aa6bd07a23913b7f4e01328c3d5cc0b40b36c0bd81d362faeb65"}, - {file = "MarkupSafe-2.1.2-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:c0a33bc9f02c2b17c3ea382f91b4db0e6cde90b63b296422a939886a7a80de1c"}, - {file = "MarkupSafe-2.1.2-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:b8526c6d437855442cdd3d87eede9c425c4445ea011ca38d937db299382e6fa3"}, - {file = "MarkupSafe-2.1.2-cp39-cp39-win32.whl", hash = "sha256:137678c63c977754abe9086a3ec011e8fd985ab90631145dfb9294ad09c102a7"}, - {file = "MarkupSafe-2.1.2-cp39-cp39-win_amd64.whl", hash = "sha256:0576fe974b40a400449768941d5d0858cc624e3249dfd1e0c33674e5c7ca7aed"}, - {file = "MarkupSafe-2.1.2.tar.gz", hash = "sha256:abcabc8c2b26036d62d4c746381a6f7cf60aafcc653198ad678306986b09450d"}, + {file = "MarkupSafe-2.1.3-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:cd0f502fe016460680cd20aaa5a76d241d6f35a1c3350c474bac1273803893fa"}, + {file = "MarkupSafe-2.1.3-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:e09031c87a1e51556fdcb46e5bd4f59dfb743061cf93c4d6831bf894f125eb57"}, + {file = "MarkupSafe-2.1.3-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:68e78619a61ecf91e76aa3e6e8e33fc4894a2bebe93410754bd28fce0a8a4f9f"}, + {file = "MarkupSafe-2.1.3-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:65c1a9bcdadc6c28eecee2c119465aebff8f7a584dd719facdd9e825ec61ab52"}, + {file = "MarkupSafe-2.1.3-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:525808b8019e36eb524b8c68acdd63a37e75714eac50e988180b169d64480a00"}, + {file = "MarkupSafe-2.1.3-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:962f82a3086483f5e5f64dbad880d31038b698494799b097bc59c2edf392fce6"}, + {file = "MarkupSafe-2.1.3-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:aa7bd130efab1c280bed0f45501b7c8795f9fdbeb02e965371bbef3523627779"}, + {file = "MarkupSafe-2.1.3-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:c9c804664ebe8f83a211cace637506669e7890fec1b4195b505c214e50dd4eb7"}, + {file = "MarkupSafe-2.1.3-cp310-cp310-win32.whl", hash = "sha256:10bbfe99883db80bdbaff2dcf681dfc6533a614f700da1287707e8a5d78a8431"}, + {file = "MarkupSafe-2.1.3-cp310-cp310-win_amd64.whl", hash = "sha256:1577735524cdad32f9f694208aa75e422adba74f1baee7551620e43a3141f559"}, + {file = "MarkupSafe-2.1.3-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:ad9e82fb8f09ade1c3e1b996a6337afac2b8b9e365f926f5a61aacc71adc5b3c"}, + {file = "MarkupSafe-2.1.3-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:3c0fae6c3be832a0a0473ac912810b2877c8cb9d76ca48de1ed31e1c68386575"}, + {file = "MarkupSafe-2.1.3-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:b076b6226fb84157e3f7c971a47ff3a679d837cf338547532ab866c57930dbee"}, + {file = "MarkupSafe-2.1.3-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:bfce63a9e7834b12b87c64d6b155fdd9b3b96191b6bd334bf37db7ff1fe457f2"}, + {file = "MarkupSafe-2.1.3-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:338ae27d6b8745585f87218a3f23f1512dbf52c26c28e322dbe54bcede54ccb9"}, + {file = "MarkupSafe-2.1.3-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:e4dd52d80b8c83fdce44e12478ad2e85c64ea965e75d66dbeafb0a3e77308fcc"}, + {file = "MarkupSafe-2.1.3-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:df0be2b576a7abbf737b1575f048c23fb1d769f267ec4358296f31c2479db8f9"}, + {file = "MarkupSafe-2.1.3-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:5bbe06f8eeafd38e5d0a4894ffec89378b6c6a625ff57e3028921f8ff59318ac"}, + {file = "MarkupSafe-2.1.3-cp311-cp311-win32.whl", hash = "sha256:dd15ff04ffd7e05ffcb7fe79f1b98041b8ea30ae9234aed2a9168b5797c3effb"}, + {file = "MarkupSafe-2.1.3-cp311-cp311-win_amd64.whl", hash = "sha256:134da1eca9ec0ae528110ccc9e48041e0828d79f24121a1a146161103c76e686"}, + {file = "MarkupSafe-2.1.3-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:8e254ae696c88d98da6555f5ace2279cf7cd5b3f52be2b5cf97feafe883b58d2"}, + {file = "MarkupSafe-2.1.3-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:cb0932dc158471523c9637e807d9bfb93e06a95cbf010f1a38b98623b929ef2b"}, + {file = "MarkupSafe-2.1.3-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:9402b03f1a1b4dc4c19845e5c749e3ab82d5078d16a2a4c2cd2df62d57bb0707"}, + {file = "MarkupSafe-2.1.3-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:ca379055a47383d02a5400cb0d110cef0a776fc644cda797db0c5696cfd7e18e"}, + {file = "MarkupSafe-2.1.3-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:b7ff0f54cb4ff66dd38bebd335a38e2c22c41a8ee45aa608efc890ac3e3931bc"}, + {file = "MarkupSafe-2.1.3-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:c011a4149cfbcf9f03994ec2edffcb8b1dc2d2aede7ca243746df97a5d41ce48"}, + {file = "MarkupSafe-2.1.3-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:56d9f2ecac662ca1611d183feb03a3fa4406469dafe241673d521dd5ae92a155"}, + {file = "MarkupSafe-2.1.3-cp37-cp37m-win32.whl", hash = "sha256:8758846a7e80910096950b67071243da3e5a20ed2546e6392603c096778d48e0"}, + {file = "MarkupSafe-2.1.3-cp37-cp37m-win_amd64.whl", hash = "sha256:787003c0ddb00500e49a10f2844fac87aa6ce977b90b0feaaf9de23c22508b24"}, + {file = "MarkupSafe-2.1.3-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:2ef12179d3a291be237280175b542c07a36e7f60718296278d8593d21ca937d4"}, + {file = "MarkupSafe-2.1.3-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:2c1b19b3aaacc6e57b7e25710ff571c24d6c3613a45e905b1fde04d691b98ee0"}, + {file = "MarkupSafe-2.1.3-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:8afafd99945ead6e075b973fefa56379c5b5c53fd8937dad92c662da5d8fd5ee"}, + {file = "MarkupSafe-2.1.3-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:8c41976a29d078bb235fea9b2ecd3da465df42a562910f9022f1a03107bd02be"}, + {file = "MarkupSafe-2.1.3-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:d080e0a5eb2529460b30190fcfcc4199bd7f827663f858a226a81bc27beaa97e"}, + {file = "MarkupSafe-2.1.3-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:69c0f17e9f5a7afdf2cc9fb2d1ce6aabdb3bafb7f38017c0b77862bcec2bbad8"}, + {file = "MarkupSafe-2.1.3-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:504b320cd4b7eff6f968eddf81127112db685e81f7e36e75f9f84f0df46041c3"}, + {file = "MarkupSafe-2.1.3-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:42de32b22b6b804f42c5d98be4f7e5e977ecdd9ee9b660fda1a3edf03b11792d"}, + {file = "MarkupSafe-2.1.3-cp38-cp38-win32.whl", hash = "sha256:ceb01949af7121f9fc39f7d27f91be8546f3fb112c608bc4029aef0bab86a2a5"}, + {file = "MarkupSafe-2.1.3-cp38-cp38-win_amd64.whl", hash = "sha256:1b40069d487e7edb2676d3fbdb2b0829ffa2cd63a2ec26c4938b2d34391b4ecc"}, + {file = "MarkupSafe-2.1.3-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:8023faf4e01efadfa183e863fefde0046de576c6f14659e8782065bcece22198"}, + {file = "MarkupSafe-2.1.3-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:6b2b56950d93e41f33b4223ead100ea0fe11f8e6ee5f641eb753ce4b77a7042b"}, + {file = "MarkupSafe-2.1.3-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:9dcdfd0eaf283af041973bff14a2e143b8bd64e069f4c383416ecd79a81aab58"}, + {file = "MarkupSafe-2.1.3-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:05fb21170423db021895e1ea1e1f3ab3adb85d1c2333cbc2310f2a26bc77272e"}, + {file = "MarkupSafe-2.1.3-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:282c2cb35b5b673bbcadb33a585408104df04f14b2d9b01d4c345a3b92861c2c"}, + {file = "MarkupSafe-2.1.3-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:ab4a0df41e7c16a1392727727e7998a467472d0ad65f3ad5e6e765015df08636"}, + {file = "MarkupSafe-2.1.3-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:7ef3cb2ebbf91e330e3bb937efada0edd9003683db6b57bb108c4001f37a02ea"}, + {file = "MarkupSafe-2.1.3-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:0a4e4a1aff6c7ac4cd55792abf96c915634c2b97e3cc1c7129578aa68ebd754e"}, + {file = "MarkupSafe-2.1.3-cp39-cp39-win32.whl", hash = "sha256:fec21693218efe39aa7f8599346e90c705afa52c5b31ae019b2e57e8f6542bb2"}, + {file = "MarkupSafe-2.1.3-cp39-cp39-win_amd64.whl", hash = "sha256:3fd4abcb888d15a94f32b75d8fd18ee162ca0c064f35b11134be77050296d6ba"}, + {file = "MarkupSafe-2.1.3.tar.gz", hash = "sha256:af598ed32d6ae86f1b747b82783958b1a4ab8f617b06fe68795c7f026abbdcad"}, ] [[package]] @@ -2031,13 +2057,13 @@ testing-docutils = ["pygments", "pytest (>=7,<8)", "pytest-param-files (>=0.3.4, [[package]] name = "nodeenv" -version = "1.7.0" +version = "1.8.0" description = "Node.js virtual environment builder" optional = false python-versions = ">=2.7,!=3.0.*,!=3.1.*,!=3.2.*,!=3.3.*,!=3.4.*,!=3.5.*,!=3.6.*" files = [ - {file = "nodeenv-1.7.0-py2.py3-none-any.whl", hash = "sha256:27083a7b96a25f2f5e1d8cb4b6317ee8aeda3bdd121394e5ac54e498028a042e"}, - {file = "nodeenv-1.7.0.tar.gz", hash = "sha256:e0e7f7dfb85fc5394c6fe1e8fa98131a2473e04311a45afb6508f7cf1836fa2b"}, + {file = "nodeenv-1.8.0-py2.py3-none-any.whl", hash = "sha256:df865724bb3c3adc86b3876fa209771517b0cfe596beff01a92700e0e8be4cec"}, + {file = "nodeenv-1.8.0.tar.gz", hash = "sha256:d51e0c37e64fbf47d017feac3145cdbb58836d7eee8c6f6d3b6880c5456227d2"}, ] [package.dependencies] @@ -2081,39 +2107,39 @@ tomlkit = ">=0.7" [[package]] name = "numpy" -version = "1.24.2" +version = "1.24.4" description = "Fundamental package for array computing in Python" optional = false python-versions = ">=3.8" files = [ - {file = "numpy-1.24.2-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:eef70b4fc1e872ebddc38cddacc87c19a3709c0e3e5d20bf3954c147b1dd941d"}, - {file = "numpy-1.24.2-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:e8d2859428712785e8a8b7d2b3ef0a1d1565892367b32f915c4a4df44d0e64f5"}, - {file = "numpy-1.24.2-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:6524630f71631be2dabe0c541e7675db82651eb998496bbe16bc4f77f0772253"}, - {file = "numpy-1.24.2-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:a51725a815a6188c662fb66fb32077709a9ca38053f0274640293a14fdd22978"}, - {file = "numpy-1.24.2-cp310-cp310-win32.whl", hash = "sha256:2620e8592136e073bd12ee4536149380695fbe9ebeae845b81237f986479ffc9"}, - {file = "numpy-1.24.2-cp310-cp310-win_amd64.whl", hash = "sha256:97cf27e51fa078078c649a51d7ade3c92d9e709ba2bfb97493007103c741f1d0"}, - {file = "numpy-1.24.2-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:7de8fdde0003f4294655aa5d5f0a89c26b9f22c0a58790c38fae1ed392d44a5a"}, - {file = "numpy-1.24.2-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:4173bde9fa2a005c2c6e2ea8ac1618e2ed2c1c6ec8a7657237854d42094123a0"}, - {file = "numpy-1.24.2-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:4cecaed30dc14123020f77b03601559fff3e6cd0c048f8b5289f4eeabb0eb281"}, - {file = "numpy-1.24.2-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:9a23f8440561a633204a67fb44617ce2a299beecf3295f0d13c495518908e910"}, - {file = "numpy-1.24.2-cp311-cp311-win32.whl", hash = "sha256:e428c4fbfa085f947b536706a2fc349245d7baa8334f0c5723c56a10595f9b95"}, - {file = "numpy-1.24.2-cp311-cp311-win_amd64.whl", hash = "sha256:557d42778a6869c2162deb40ad82612645e21d79e11c1dc62c6e82a2220ffb04"}, - {file = "numpy-1.24.2-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:d0a2db9d20117bf523dde15858398e7c0858aadca7c0f088ac0d6edd360e9ad2"}, - {file = "numpy-1.24.2-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:c72a6b2f4af1adfe193f7beb91ddf708ff867a3f977ef2ec53c0ffb8283ab9f5"}, - {file = "numpy-1.24.2-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:c29e6bd0ec49a44d7690ecb623a8eac5ab8a923bce0bea6293953992edf3a76a"}, - {file = "numpy-1.24.2-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:2eabd64ddb96a1239791da78fa5f4e1693ae2dadc82a76bc76a14cbb2b966e96"}, - {file = "numpy-1.24.2-cp38-cp38-win32.whl", hash = "sha256:e3ab5d32784e843fc0dd3ab6dcafc67ef806e6b6828dc6af2f689be0eb4d781d"}, - {file = "numpy-1.24.2-cp38-cp38-win_amd64.whl", hash = "sha256:76807b4063f0002c8532cfeac47a3068a69561e9c8715efdad3c642eb27c0756"}, - {file = "numpy-1.24.2-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:4199e7cfc307a778f72d293372736223e39ec9ac096ff0a2e64853b866a8e18a"}, - {file = "numpy-1.24.2-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:adbdce121896fd3a17a77ab0b0b5eedf05a9834a18699db6829a64e1dfccca7f"}, - {file = "numpy-1.24.2-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:889b2cc88b837d86eda1b17008ebeb679d82875022200c6e8e4ce6cf549b7acb"}, - {file = "numpy-1.24.2-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f64bb98ac59b3ea3bf74b02f13836eb2e24e48e0ab0145bbda646295769bd780"}, - {file = "numpy-1.24.2-cp39-cp39-win32.whl", hash = "sha256:63e45511ee4d9d976637d11e6c9864eae50e12dc9598f531c035265991910468"}, - {file = "numpy-1.24.2-cp39-cp39-win_amd64.whl", hash = "sha256:a77d3e1163a7770164404607b7ba3967fb49b24782a6ef85d9b5f54126cc39e5"}, - {file = "numpy-1.24.2-pp38-pypy38_pp73-macosx_10_9_x86_64.whl", hash = "sha256:92011118955724465fb6853def593cf397b4a1367495e0b59a7e69d40c4eb71d"}, - {file = "numpy-1.24.2-pp38-pypy38_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f9006288bcf4895917d02583cf3411f98631275bc67cce355a7f39f8c14338fa"}, - {file = "numpy-1.24.2-pp38-pypy38_pp73-win_amd64.whl", hash = "sha256:150947adbdfeceec4e5926d956a06865c1c690f2fd902efede4ca6fe2e657c3f"}, - {file = "numpy-1.24.2.tar.gz", hash = "sha256:003a9f530e880cb2cd177cba1af7220b9aa42def9c4afc2a2fc3ee6be7eb2b22"}, + {file = "numpy-1.24.4-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:c0bfb52d2169d58c1cdb8cc1f16989101639b34c7d3ce60ed70b19c63eba0b64"}, + {file = "numpy-1.24.4-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:ed094d4f0c177b1b8e7aa9cba7d6ceed51c0e569a5318ac0ca9a090680a6a1b1"}, + {file = "numpy-1.24.4-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:79fc682a374c4a8ed08b331bef9c5f582585d1048fa6d80bc6c35bc384eee9b4"}, + {file = "numpy-1.24.4-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:7ffe43c74893dbf38c2b0a1f5428760a1a9c98285553c89e12d70a96a7f3a4d6"}, + {file = "numpy-1.24.4-cp310-cp310-win32.whl", hash = "sha256:4c21decb6ea94057331e111a5bed9a79d335658c27ce2adb580fb4d54f2ad9bc"}, + {file = "numpy-1.24.4-cp310-cp310-win_amd64.whl", hash = "sha256:b4bea75e47d9586d31e892a7401f76e909712a0fd510f58f5337bea9572c571e"}, + {file = "numpy-1.24.4-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:f136bab9c2cfd8da131132c2cf6cc27331dd6fae65f95f69dcd4ae3c3639c810"}, + {file = "numpy-1.24.4-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:e2926dac25b313635e4d6cf4dc4e51c8c0ebfed60b801c799ffc4c32bf3d1254"}, + {file = "numpy-1.24.4-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:222e40d0e2548690405b0b3c7b21d1169117391c2e82c378467ef9ab4c8f0da7"}, + {file = "numpy-1.24.4-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:7215847ce88a85ce39baf9e89070cb860c98fdddacbaa6c0da3ffb31b3350bd5"}, + {file = "numpy-1.24.4-cp311-cp311-win32.whl", hash = "sha256:4979217d7de511a8d57f4b4b5b2b965f707768440c17cb70fbf254c4b225238d"}, + {file = "numpy-1.24.4-cp311-cp311-win_amd64.whl", hash = "sha256:b7b1fc9864d7d39e28f41d089bfd6353cb5f27ecd9905348c24187a768c79694"}, + {file = "numpy-1.24.4-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:1452241c290f3e2a312c137a9999cdbf63f78864d63c79039bda65ee86943f61"}, + {file = "numpy-1.24.4-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:04640dab83f7c6c85abf9cd729c5b65f1ebd0ccf9de90b270cd61935eef0197f"}, + {file = "numpy-1.24.4-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:a5425b114831d1e77e4b5d812b69d11d962e104095a5b9c3b641a218abcc050e"}, + {file = "numpy-1.24.4-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:dd80e219fd4c71fc3699fc1dadac5dcf4fd882bfc6f7ec53d30fa197b8ee22dc"}, + {file = "numpy-1.24.4-cp38-cp38-win32.whl", hash = "sha256:4602244f345453db537be5314d3983dbf5834a9701b7723ec28923e2889e0bb2"}, + {file = "numpy-1.24.4-cp38-cp38-win_amd64.whl", hash = "sha256:692f2e0f55794943c5bfff12b3f56f99af76f902fc47487bdfe97856de51a706"}, + {file = "numpy-1.24.4-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:2541312fbf09977f3b3ad449c4e5f4bb55d0dbf79226d7724211acc905049400"}, + {file = "numpy-1.24.4-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:9667575fb6d13c95f1b36aca12c5ee3356bf001b714fc354eb5465ce1609e62f"}, + {file = "numpy-1.24.4-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:f3a86ed21e4f87050382c7bc96571755193c4c1392490744ac73d660e8f564a9"}, + {file = "numpy-1.24.4-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:d11efb4dbecbdf22508d55e48d9c8384db795e1b7b51ea735289ff96613ff74d"}, + {file = "numpy-1.24.4-cp39-cp39-win32.whl", hash = "sha256:6620c0acd41dbcb368610bb2f4d83145674040025e5536954782467100aa8835"}, + {file = "numpy-1.24.4-cp39-cp39-win_amd64.whl", hash = "sha256:befe2bf740fd8373cf56149a5c23a0f601e82869598d41f8e188a0e9869926f8"}, + {file = "numpy-1.24.4-pp38-pypy38_pp73-macosx_10_9_x86_64.whl", hash = "sha256:31f13e25b4e304632a4619d0e0777662c2ffea99fcae2029556b17d8ff958aef"}, + {file = "numpy-1.24.4-pp38-pypy38_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:95f7ac6540e95bc440ad77f56e520da5bf877f87dca58bd095288dce8940532a"}, + {file = "numpy-1.24.4-pp38-pypy38_pp73-win_amd64.whl", hash = "sha256:e98f220aa76ca2a977fe435f5b04d7b3470c0a2e6312907b37ba6068f26787f2"}, + {file = "numpy-1.24.4.tar.gz", hash = "sha256:80f5e3a4e498641401868df4208b74581206afbee7cf7b8329daae82676d9463"}, ] [[package]] @@ -2173,13 +2199,13 @@ files = [ [[package]] name = "packaging" -version = "22.0" +version = "23.1" description = "Core utilities for Python packages" optional = false python-versions = ">=3.7" files = [ - {file = "packaging-22.0-py3-none-any.whl", hash = "sha256:957e2148ba0e1a3b282772e791ef1d8083648bc131c8ab0c1feba110ce1146c3"}, - {file = "packaging-22.0.tar.gz", hash = "sha256:2198ec20bd4c017b8f9717e00f0c8714076fc2fd93816750ab48e2c41de2cfd3"}, + {file = "packaging-23.1-py3-none-any.whl", hash = "sha256:994793af429502c4ea2ebf6bf664629d07c1a9fe974af92966e4b8d2df7edc61"}, + {file = "packaging-23.1.tar.gz", hash = "sha256:a392980d2b6cffa644431898be54b0045151319d1e7ec34f0cfed48767dd334f"}, ] [[package]] @@ -2263,28 +2289,28 @@ tests = ["check-manifest", "coverage", "defusedxml", "markdown2", "olefile", "pa [[package]] name = "platformdirs" -version = "2.6.2" +version = "3.8.0" description = "A small Python package for determining appropriate platform-specific dirs, e.g. a \"user data dir\"." optional = false python-versions = ">=3.7" files = [ - {file = "platformdirs-2.6.2-py3-none-any.whl", hash = "sha256:83c8f6d04389165de7c9b6f0c682439697887bca0aa2f1c87ef1826be3584490"}, - {file = "platformdirs-2.6.2.tar.gz", hash = "sha256:e1fea1fe471b9ff8332e229df3cb7de4f53eeea4998d3b6bfff542115e998bd2"}, + {file = "platformdirs-3.8.0-py3-none-any.whl", hash = "sha256:ca9ed98ce73076ba72e092b23d3c93ea6c4e186b3f1c3dad6edd98ff6ffcca2e"}, + {file = "platformdirs-3.8.0.tar.gz", hash = "sha256:b0cabcb11063d21a0b261d557acb0a9d2126350e63b70cdf7db6347baea456dc"}, ] [package.extras] -docs = ["furo (>=2022.12.7)", "proselint (>=0.13)", "sphinx (>=5.3)", "sphinx-autodoc-typehints (>=1.19.5)"] -test = ["appdirs (==1.4.4)", "covdefaults (>=2.2.2)", "pytest (>=7.2)", "pytest-cov (>=4)", "pytest-mock (>=3.10)"] +docs = ["furo (>=2023.5.20)", "proselint (>=0.13)", "sphinx (>=7.0.1)", "sphinx-autodoc-typehints (>=1.23,!=1.23.4)"] +test = ["appdirs (==1.4.4)", "covdefaults (>=2.3)", "pytest (>=7.3.1)", "pytest-cov (>=4.1)", "pytest-mock (>=3.10)"] [[package]] name = "pluggy" -version = "1.0.0" +version = "1.2.0" description = "plugin and hook calling mechanisms for python" optional = false -python-versions = ">=3.6" +python-versions = ">=3.7" files = [ - {file = "pluggy-1.0.0-py2.py3-none-any.whl", hash = "sha256:74134bbf457f031a36d68416e1509f34bd5ccc019f0bcc952c7b909d06b37bd3"}, - {file = "pluggy-1.0.0.tar.gz", hash = "sha256:4224373bacce55f955a878bf9cfa763c1e360858e330072059e10bad68531159"}, + {file = "pluggy-1.2.0-py3-none-any.whl", hash = "sha256:c2fd55a7d7a3863cba1a013e4e2414658b1d07b6bc57b3919e0c63c9abb99849"}, + {file = "pluggy-1.2.0.tar.gz", hash = "sha256:d12f0c4b579b15f5e054301bb226ee85eeeba08ffec228092f8defbaa3a4c4b3"}, ] [package.extras] @@ -2414,47 +2440,47 @@ files = [ [[package]] name = "pydantic" -version = "1.10.4" +version = "1.10.9" description = "Data validation and settings management using python type hints" optional = false python-versions = ">=3.7" files = [ - {file = "pydantic-1.10.4-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:b5635de53e6686fe7a44b5cf25fcc419a0d5e5c1a1efe73d49d48fe7586db854"}, - {file = "pydantic-1.10.4-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:6dc1cc241440ed7ca9ab59d9929075445da6b7c94ced281b3dd4cfe6c8cff817"}, - {file = "pydantic-1.10.4-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:51bdeb10d2db0f288e71d49c9cefa609bca271720ecd0c58009bd7504a0c464c"}, - {file = "pydantic-1.10.4-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:78cec42b95dbb500a1f7120bdf95c401f6abb616bbe8785ef09887306792e66e"}, - {file = "pydantic-1.10.4-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:8775d4ef5e7299a2f4699501077a0defdaac5b6c4321173bcb0f3c496fbadf85"}, - {file = "pydantic-1.10.4-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:572066051eeac73d23f95ba9a71349c42a3e05999d0ee1572b7860235b850cc6"}, - {file = "pydantic-1.10.4-cp310-cp310-win_amd64.whl", hash = "sha256:7feb6a2d401f4d6863050f58325b8d99c1e56f4512d98b11ac64ad1751dc647d"}, - {file = "pydantic-1.10.4-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:39f4a73e5342b25c2959529f07f026ef58147249f9b7431e1ba8414a36761f53"}, - {file = "pydantic-1.10.4-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:983e720704431a6573d626b00662eb78a07148c9115129f9b4351091ec95ecc3"}, - {file = "pydantic-1.10.4-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:75d52162fe6b2b55964fbb0af2ee58e99791a3138588c482572bb6087953113a"}, - {file = "pydantic-1.10.4-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:fdf8d759ef326962b4678d89e275ffc55b7ce59d917d9f72233762061fd04a2d"}, - {file = "pydantic-1.10.4-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:05a81b006be15655b2a1bae5faa4280cf7c81d0e09fcb49b342ebf826abe5a72"}, - {file = "pydantic-1.10.4-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:d88c4c0e5c5dfd05092a4b271282ef0588e5f4aaf345778056fc5259ba098857"}, - {file = "pydantic-1.10.4-cp311-cp311-win_amd64.whl", hash = "sha256:6a05a9db1ef5be0fe63e988f9617ca2551013f55000289c671f71ec16f4985e3"}, - {file = "pydantic-1.10.4-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:887ca463c3bc47103c123bc06919c86720e80e1214aab79e9b779cda0ff92a00"}, - {file = "pydantic-1.10.4-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:fdf88ab63c3ee282c76d652fc86518aacb737ff35796023fae56a65ced1a5978"}, - {file = "pydantic-1.10.4-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:a48f1953c4a1d9bd0b5167ac50da9a79f6072c63c4cef4cf2a3736994903583e"}, - {file = "pydantic-1.10.4-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:a9f2de23bec87ff306aef658384b02aa7c32389766af3c5dee9ce33e80222dfa"}, - {file = "pydantic-1.10.4-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:cd8702c5142afda03dc2b1ee6bc358b62b3735b2cce53fc77b31ca9f728e4bc8"}, - {file = "pydantic-1.10.4-cp37-cp37m-win_amd64.whl", hash = "sha256:6e7124d6855b2780611d9f5e1e145e86667eaa3bd9459192c8dc1a097f5e9903"}, - {file = "pydantic-1.10.4-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:0b53e1d41e97063d51a02821b80538053ee4608b9a181c1005441f1673c55423"}, - {file = "pydantic-1.10.4-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:55b1625899acd33229c4352ce0ae54038529b412bd51c4915349b49ca575258f"}, - {file = "pydantic-1.10.4-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:301d626a59edbe5dfb48fcae245896379a450d04baeed50ef40d8199f2733b06"}, - {file = "pydantic-1.10.4-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:b6f9d649892a6f54a39ed56b8dfd5e08b5f3be5f893da430bed76975f3735d15"}, - {file = "pydantic-1.10.4-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:d7b5a3821225f5c43496c324b0d6875fde910a1c2933d726a743ce328fbb2a8c"}, - {file = "pydantic-1.10.4-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:f2f7eb6273dd12472d7f218e1fef6f7c7c2f00ac2e1ecde4db8824c457300416"}, - {file = "pydantic-1.10.4-cp38-cp38-win_amd64.whl", hash = "sha256:4b05697738e7d2040696b0a66d9f0a10bec0efa1883ca75ee9e55baf511909d6"}, - {file = "pydantic-1.10.4-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:a9a6747cac06c2beb466064dda999a13176b23535e4c496c9d48e6406f92d42d"}, - {file = "pydantic-1.10.4-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:eb992a1ef739cc7b543576337bebfc62c0e6567434e522e97291b251a41dad7f"}, - {file = "pydantic-1.10.4-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:990406d226dea0e8f25f643b370224771878142155b879784ce89f633541a024"}, - {file = "pydantic-1.10.4-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:2e82a6d37a95e0b1b42b82ab340ada3963aea1317fd7f888bb6b9dfbf4fff57c"}, - {file = "pydantic-1.10.4-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:9193d4f4ee8feca58bc56c8306bcb820f5c7905fd919e0750acdeeeef0615b28"}, - {file = "pydantic-1.10.4-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:2b3ce5f16deb45c472dde1a0ee05619298c864a20cded09c4edd820e1454129f"}, - {file = "pydantic-1.10.4-cp39-cp39-win_amd64.whl", hash = "sha256:9cbdc268a62d9a98c56e2452d6c41c0263d64a2009aac69246486f01b4f594c4"}, - {file = "pydantic-1.10.4-py3-none-any.whl", hash = "sha256:4948f264678c703f3877d1c8877c4e3b2e12e549c57795107f08cf70c6ec7774"}, - {file = "pydantic-1.10.4.tar.gz", hash = "sha256:b9a3859f24eb4e097502a3be1fb4b2abb79b6103dd9e2e0edb70613a4459a648"}, + {file = "pydantic-1.10.9-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:e692dec4a40bfb40ca530e07805b1208c1de071a18d26af4a2a0d79015b352ca"}, + {file = "pydantic-1.10.9-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:3c52eb595db83e189419bf337b59154bdcca642ee4b2a09e5d7797e41ace783f"}, + {file = "pydantic-1.10.9-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:939328fd539b8d0edf244327398a667b6b140afd3bf7e347cf9813c736211896"}, + {file = "pydantic-1.10.9-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:b48d3d634bca23b172f47f2335c617d3fcb4b3ba18481c96b7943a4c634f5c8d"}, + {file = "pydantic-1.10.9-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:f0b7628fb8efe60fe66fd4adadd7ad2304014770cdc1f4934db41fe46cc8825f"}, + {file = "pydantic-1.10.9-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:e1aa5c2410769ca28aa9a7841b80d9d9a1c5f223928ca8bec7e7c9a34d26b1d4"}, + {file = "pydantic-1.10.9-cp310-cp310-win_amd64.whl", hash = "sha256:eec39224b2b2e861259d6f3c8b6290d4e0fbdce147adb797484a42278a1a486f"}, + {file = "pydantic-1.10.9-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:d111a21bbbfd85c17248130deac02bbd9b5e20b303338e0dbe0faa78330e37e0"}, + {file = "pydantic-1.10.9-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:2e9aec8627a1a6823fc62fb96480abe3eb10168fd0d859ee3d3b395105ae19a7"}, + {file = "pydantic-1.10.9-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:07293ab08e7b4d3c9d7de4949a0ea571f11e4557d19ea24dd3ae0c524c0c334d"}, + {file = "pydantic-1.10.9-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:7ee829b86ce984261d99ff2fd6e88f2230068d96c2a582f29583ed602ef3fc2c"}, + {file = "pydantic-1.10.9-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:4b466a23009ff5cdd7076eb56aca537c745ca491293cc38e72bf1e0e00de5b91"}, + {file = "pydantic-1.10.9-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:7847ca62e581e6088d9000f3c497267868ca2fa89432714e21a4fb33a04d52e8"}, + {file = "pydantic-1.10.9-cp311-cp311-win_amd64.whl", hash = "sha256:7845b31959468bc5b78d7b95ec52fe5be32b55d0d09983a877cca6aedc51068f"}, + {file = "pydantic-1.10.9-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:517a681919bf880ce1dac7e5bc0c3af1e58ba118fd774da2ffcd93c5f96eaece"}, + {file = "pydantic-1.10.9-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:67195274fd27780f15c4c372f4ba9a5c02dad6d50647b917b6a92bf00b3d301a"}, + {file = "pydantic-1.10.9-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:2196c06484da2b3fded1ab6dbe182bdabeb09f6318b7fdc412609ee2b564c49a"}, + {file = "pydantic-1.10.9-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:6257bb45ad78abacda13f15bde5886efd6bf549dd71085e64b8dcf9919c38b60"}, + {file = "pydantic-1.10.9-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:3283b574b01e8dbc982080d8287c968489d25329a463b29a90d4157de4f2baaf"}, + {file = "pydantic-1.10.9-cp37-cp37m-win_amd64.whl", hash = "sha256:5f8bbaf4013b9a50e8100333cc4e3fa2f81214033e05ac5aa44fa24a98670a29"}, + {file = "pydantic-1.10.9-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:b9cd67fb763248cbe38f0593cd8611bfe4b8ad82acb3bdf2b0898c23415a1f82"}, + {file = "pydantic-1.10.9-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:f50e1764ce9353be67267e7fd0da08349397c7db17a562ad036aa7c8f4adfdb6"}, + {file = "pydantic-1.10.9-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:73ef93e5e1d3c8e83f1ff2e7fdd026d9e063c7e089394869a6e2985696693766"}, + {file = "pydantic-1.10.9-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:128d9453d92e6e81e881dd7e2484e08d8b164da5507f62d06ceecf84bf2e21d3"}, + {file = "pydantic-1.10.9-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:ad428e92ab68798d9326bb3e5515bc927444a3d71a93b4a2ca02a8a5d795c572"}, + {file = "pydantic-1.10.9-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:fab81a92f42d6d525dd47ced310b0c3e10c416bbfae5d59523e63ea22f82b31e"}, + {file = "pydantic-1.10.9-cp38-cp38-win_amd64.whl", hash = "sha256:963671eda0b6ba6926d8fc759e3e10335e1dc1b71ff2a43ed2efd6996634dafb"}, + {file = "pydantic-1.10.9-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:970b1bdc6243ef663ba5c7e36ac9ab1f2bfecb8ad297c9824b542d41a750b298"}, + {file = "pydantic-1.10.9-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:7e1d5290044f620f80cf1c969c542a5468f3656de47b41aa78100c5baa2b8276"}, + {file = "pydantic-1.10.9-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:83fcff3c7df7adff880622a98022626f4f6dbce6639a88a15a3ce0f96466cb60"}, + {file = "pydantic-1.10.9-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:0da48717dc9495d3a8f215e0d012599db6b8092db02acac5e0d58a65248ec5bc"}, + {file = "pydantic-1.10.9-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:0a2aabdc73c2a5960e87c3ffebca6ccde88665616d1fd6d3db3178ef427b267a"}, + {file = "pydantic-1.10.9-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:9863b9420d99dfa9c064042304868e8ba08e89081428a1c471858aa2af6f57c4"}, + {file = "pydantic-1.10.9-cp39-cp39-win_amd64.whl", hash = "sha256:e7c9900b43ac14110efa977be3da28931ffc74c27e96ee89fbcaaf0b0fe338e1"}, + {file = "pydantic-1.10.9-py3-none-any.whl", hash = "sha256:6cafde02f6699ce4ff643417d1a9223716ec25e228ddc3b436fe7e2d25a1f305"}, + {file = "pydantic-1.10.9.tar.gz", hash = "sha256:95c70da2cd3b6ddf3b9645ecaa8d98f3d80c606624b6d245558d202cd23ea3be"}, ] [package.dependencies] @@ -2466,13 +2492,13 @@ email = ["email-validator (>=1.0.3)"] [[package]] name = "pygments" -version = "2.15.0" +version = "2.15.1" description = "Pygments is a syntax highlighting package written in Python." optional = false python-versions = ">=3.7" files = [ - {file = "Pygments-2.15.0-py3-none-any.whl", hash = "sha256:77a3299119af881904cd5ecd1ac6a66214b6e9bed1f2db16993b54adede64094"}, - {file = "Pygments-2.15.0.tar.gz", hash = "sha256:f7e36cffc4c517fbc252861b9a6e4644ca0e5abadf9a113c72d1358ad09b9500"}, + {file = "Pygments-2.15.1-py3-none-any.whl", hash = "sha256:db2db3deb4b4179f399a09054b023b6a586b76499d36965813c71aa8ed7b5fd1"}, + {file = "Pygments-2.15.1.tar.gz", hash = "sha256:8ace4d3c1dd481894b2005f560ead0f9f19ee64fe983366be1a21e171d12775c"}, ] [package.extras] @@ -2568,13 +2594,13 @@ tests = ["hypothesis (>=3.27.0)", "pytest (>=3.2.1,!=3.3.0)"] [[package]] name = "pyparsing" -version = "3.0.9" +version = "3.1.0" description = "pyparsing module - Classes and methods to define and execute parsing grammars" optional = false python-versions = ">=3.6.8" files = [ - {file = "pyparsing-3.0.9-py3-none-any.whl", hash = "sha256:5026bae9a10eeaefb61dab2f09052b9f4307d44aee4eda64b309723d8d206bbc"}, - {file = "pyparsing-3.0.9.tar.gz", hash = "sha256:2b020ecf7d21b687f219b71ecad3631f644a47f01403fa1d1036b0c6416d70fb"}, + {file = "pyparsing-3.1.0-py3-none-any.whl", hash = "sha256:d554a96d1a7d3ddaf7183104485bc19fd80543ad6ac5bdb6426719d766fb06c1"}, + {file = "pyparsing-3.1.0.tar.gz", hash = "sha256:edb662d6fe322d6e990b1594b5feaeadf806803359e3d4d42f11e295e588f0ea"}, ] [package.extras] @@ -2784,23 +2810,6 @@ urllib3 = ">=1.21.1,<3" socks = ["PySocks (>=1.5.6,!=1.5.7)"] use-chardet-on-py3 = ["chardet (>=3.0.2,<6)"] -[[package]] -name = "rfc3986" -version = "1.5.0" -description = "Validating URI References per RFC 3986" -optional = false -python-versions = "*" -files = [ - {file = "rfc3986-1.5.0-py2.py3-none-any.whl", hash = "sha256:a86d6e1f5b1dc238b218b012df0aa79409667bb209e58da56d0b94704e712a97"}, - {file = "rfc3986-1.5.0.tar.gz", hash = "sha256:270aaf10d87d0d4e095063c65bf3ddbc6ee3d0b226328ce21e036f946e421835"}, -] - -[package.dependencies] -idna = {version = "*", optional = true, markers = "extra == \"idna2008\""} - -[package.extras] -idna2008 = ["idna"] - [[package]] name = "ruff" version = "0.0.275" @@ -2829,18 +2838,18 @@ files = [ [[package]] name = "setuptools" -version = "66.1.1" +version = "68.0.0" description = "Easily download, build, install, upgrade, and uninstall Python packages" optional = false python-versions = ">=3.7" files = [ - {file = "setuptools-66.1.1-py3-none-any.whl", hash = "sha256:6f590d76b713d5de4e49fe4fbca24474469f53c83632d5d0fd056f7ff7e8112b"}, - {file = "setuptools-66.1.1.tar.gz", hash = "sha256:ac4008d396bc9cd983ea483cb7139c0240a07bbc74ffb6232fceffedc6cf03a8"}, + {file = "setuptools-68.0.0-py3-none-any.whl", hash = "sha256:11e52c67415a381d10d6b462ced9cfb97066179f0e871399e006c4ab101fc85f"}, + {file = "setuptools-68.0.0.tar.gz", hash = "sha256:baf1fdb41c6da4cd2eae722e135500da913332ab3f2f5c7d33af9b492acb5235"}, ] [package.extras] docs = ["furo", "jaraco.packaging (>=9)", "jaraco.tidelift (>=1.4)", "pygments-github-lexers (==0.0.5)", "rst.linker (>=1.9)", "sphinx (>=3.5)", "sphinx-favicon", "sphinx-hoverxref (<2)", "sphinx-inline-tabs", "sphinx-lint", "sphinx-notfound-page (==0.8.3)", "sphinx-reredirects", "sphinxcontrib-towncrier"] -testing = ["build[virtualenv]", "filelock (>=3.4.0)", "flake8 (<5)", "flake8-2020", "ini2toml[lite] (>=0.9)", "jaraco.envs (>=2.2)", "jaraco.path (>=3.2.0)", "pip (>=19.1)", "pip-run (>=8.8)", "pytest (>=6)", "pytest-black (>=0.3.7)", "pytest-checkdocs (>=2.4)", "pytest-cov", "pytest-enabler (>=1.3)", "pytest-flake8", "pytest-mypy (>=0.9.1)", "pytest-perf", "pytest-timeout", "pytest-xdist", "tomli-w (>=1.0.0)", "virtualenv (>=13.0.0)", "wheel"] +testing = ["build[virtualenv]", "filelock (>=3.4.0)", "flake8-2020", "ini2toml[lite] (>=0.9)", "jaraco.envs (>=2.2)", "jaraco.path (>=3.2.0)", "pip (>=19.1)", "pip-run (>=8.8)", "pytest (>=6)", "pytest-black (>=0.3.7)", "pytest-checkdocs (>=2.4)", "pytest-cov", "pytest-enabler (>=1.3)", "pytest-mypy (>=0.9.1)", "pytest-perf", "pytest-ruff", "pytest-timeout", "pytest-xdist", "tomli-w (>=1.0.0)", "virtualenv (>=13.0.0)", "wheel"] testing-integration = ["build[virtualenv]", "filelock (>=3.4.0)", "jaraco.envs (>=2.2)", "jaraco.path (>=3.2.0)", "pytest", "pytest-enabler", "pytest-xdist", "tomli", "virtualenv (>=13.0.0)", "wheel"] [[package]] @@ -3075,13 +3084,13 @@ files = [ [[package]] name = "tomlkit" -version = "0.11.6" +version = "0.11.8" description = "Style preserving TOML library" optional = false -python-versions = ">=3.6" +python-versions = ">=3.7" files = [ - {file = "tomlkit-0.11.6-py3-none-any.whl", hash = "sha256:07de26b0d8cfc18f871aec595fda24d95b08fef89d147caa861939f37230bf4b"}, - {file = "tomlkit-0.11.6.tar.gz", hash = "sha256:71b952e5721688937fb02cf9d354dbcf0785066149d2855e44531ebdd2b65d73"}, + {file = "tomlkit-0.11.8-py3-none-any.whl", hash = "sha256:8c726c4c202bdb148667835f68d68780b9a003a9ec34167b6c673b38eff2a171"}, + {file = "tomlkit-0.11.8.tar.gz", hash = "sha256:9330fc7faa1db67b541b28e62018c17d20be733177d290a13b24c62d1614e0c3"}, ] [[package]] @@ -3106,13 +3115,13 @@ files = [ [[package]] name = "typing-extensions" -version = "4.4.0" +version = "4.7.0" description = "Backported and Experimental Type Hints for Python 3.7+" optional = false python-versions = ">=3.7" files = [ - {file = "typing_extensions-4.4.0-py3-none-any.whl", hash = "sha256:16fa4864408f655d35ec496218b85f79b3437c829e93320c7c9215ccfd92489e"}, - {file = "typing_extensions-4.4.0.tar.gz", hash = "sha256:1511434bb92bf8dd198c12b1cc812e800d4181cfcb867674e0f8279cc93087aa"}, + {file = "typing_extensions-4.7.0-py3-none-any.whl", hash = "sha256:5d8c9dac95c27d20df12fb1d97b9793ab8b2af8a3a525e68c80e21060c161771"}, + {file = "typing_extensions-4.7.0.tar.gz", hash = "sha256:935ccf31549830cda708b42289d44b6f74084d616a00be651601a4f968e77c82"}, ] [[package]] @@ -3136,19 +3145,20 @@ test = ["pytest (>=2.7.3)"] [[package]] name = "urllib3" -version = "1.26.14" +version = "2.0.3" description = "HTTP library with thread-safe connection pooling, file post, and more." optional = false -python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, !=3.4.*, !=3.5.*" +python-versions = ">=3.7" files = [ - {file = "urllib3-1.26.14-py2.py3-none-any.whl", hash = "sha256:75edcdc2f7d85b137124a6c3c9fc3933cdeaa12ecb9a6a959f22797a0feca7e1"}, - {file = "urllib3-1.26.14.tar.gz", hash = "sha256:076907bf8fd355cde77728471316625a4d2f7e713c125f51953bb5b3eecf4f72"}, + {file = "urllib3-2.0.3-py3-none-any.whl", hash = "sha256:48e7fafa40319d358848e1bc6809b208340fafe2096f1725d05d67443d0483d1"}, + {file = "urllib3-2.0.3.tar.gz", hash = "sha256:bee28b5e56addb8226c96f7f13ac28cb4c301dd5ea8a6ca179c0b9835e032825"}, ] [package.extras] -brotli = ["brotli (>=1.0.9)", "brotlicffi (>=0.8.0)", "brotlipy (>=0.6.0)"] -secure = ["certifi", "cryptography (>=1.3.4)", "idna (>=2.0.0)", "ipaddress", "pyOpenSSL (>=0.14)", "urllib3-secure-extra"] -socks = ["PySocks (>=1.5.6,!=1.5.7,<2.0)"] +brotli = ["brotli (>=1.0.9)", "brotlicffi (>=0.8.0)"] +secure = ["certifi", "cryptography (>=1.9)", "idna (>=2.0.0)", "pyopenssl (>=17.1.0)", "urllib3-secure-extra"] +socks = ["pysocks (>=1.5.6,!=1.5.7,<2.0)"] +zstd = ["zstandard (>=0.18.0)"] [[package]] name = "uvloop" @@ -3196,23 +3206,23 @@ test = ["Cython (>=0.29.32,<0.30.0)", "aiohttp", "flake8 (>=3.9.2,<3.10.0)", "my [[package]] name = "virtualenv" -version = "20.17.1" +version = "20.23.1" description = "Virtual Python Environment builder" optional = false -python-versions = ">=3.6" +python-versions = ">=3.7" files = [ - {file = "virtualenv-20.17.1-py3-none-any.whl", hash = "sha256:ce3b1684d6e1a20a3e5ed36795a97dfc6af29bc3970ca8dab93e11ac6094b3c4"}, - {file = "virtualenv-20.17.1.tar.gz", hash = "sha256:f8b927684efc6f1cc206c9db297a570ab9ad0e51c16fa9e45487d36d1905c058"}, + {file = "virtualenv-20.23.1-py3-none-any.whl", hash = "sha256:34da10f14fea9be20e0fd7f04aba9732f84e593dac291b757ce42e3368a39419"}, + {file = "virtualenv-20.23.1.tar.gz", hash = "sha256:8ff19a38c1021c742148edc4f81cb43d7f8c6816d2ede2ab72af5b84c749ade1"}, ] [package.dependencies] distlib = ">=0.3.6,<1" -filelock = ">=3.4.1,<4" -platformdirs = ">=2.4,<3" +filelock = ">=3.12,<4" +platformdirs = ">=3.5.1,<4" [package.extras] -docs = ["proselint (>=0.13)", "sphinx (>=5.3)", "sphinx-argparse (>=0.3.2)", "sphinx-rtd-theme (>=1)", "towncrier (>=22.8)"] -testing = ["coverage (>=6.2)", "coverage-enable-subprocess (>=1)", "flaky (>=3.7)", "packaging (>=21.3)", "pytest (>=7.0.1)", "pytest-env (>=0.6.2)", "pytest-freezegun (>=0.4.2)", "pytest-mock (>=3.6.1)", "pytest-randomly (>=3.10.3)", "pytest-timeout (>=2.1)"] +docs = ["furo (>=2023.5.20)", "proselint (>=0.13)", "sphinx (>=7.0.1)", "sphinx-argparse (>=0.4)", "sphinxcontrib-towncrier (>=0.2.1a0)", "towncrier (>=23.6)"] +test = ["covdefaults (>=2.3)", "coverage (>=7.2.7)", "coverage-enable-subprocess (>=1)", "flaky (>=3.7)", "packaging (>=23.1)", "pytest (>=7.3.1)", "pytest-env (>=0.8.1)", "pytest-freezer (>=0.4.6)", "pytest-mock (>=3.10)", "pytest-randomly (>=3.12)", "pytest-timeout (>=2.1)", "setuptools (>=67.8)", "time-machine (>=2.9)"] [[package]] name = "watchfiles" @@ -3250,80 +3260,81 @@ anyio = ">=3.0.0" [[package]] name = "websockets" -version = "10.4" +version = "11.0.3" description = "An implementation of the WebSocket Protocol (RFC 6455 & 7692)" optional = false python-versions = ">=3.7" files = [ - {file = "websockets-10.4-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:d58804e996d7d2307173d56c297cf7bc132c52df27a3efaac5e8d43e36c21c48"}, - {file = "websockets-10.4-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:bc0b82d728fe21a0d03e65f81980abbbcb13b5387f733a1a870672c5be26edab"}, - {file = "websockets-10.4-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:ba089c499e1f4155d2a3c2a05d2878a3428cf321c848f2b5a45ce55f0d7d310c"}, - {file = "websockets-10.4-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:33d69ca7612f0ddff3316b0c7b33ca180d464ecac2d115805c044bf0a3b0d032"}, - {file = "websockets-10.4-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:62e627f6b6d4aed919a2052efc408da7a545c606268d5ab5bfab4432734b82b4"}, - {file = "websockets-10.4-cp310-cp310-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:38ea7b82bfcae927eeffc55d2ffa31665dc7fec7b8dc654506b8e5a518eb4d50"}, - {file = "websockets-10.4-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:e0cb5cc6ece6ffa75baccfd5c02cffe776f3f5c8bf486811f9d3ea3453676ce8"}, - {file = "websockets-10.4-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:ae5e95cfb53ab1da62185e23b3130e11d64431179debac6dc3c6acf08760e9b1"}, - {file = "websockets-10.4-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:7c584f366f46ba667cfa66020344886cf47088e79c9b9d39c84ce9ea98aaa331"}, - {file = "websockets-10.4-cp310-cp310-win32.whl", hash = "sha256:b029fb2032ae4724d8ae8d4f6b363f2cc39e4c7b12454df8df7f0f563ed3e61a"}, - {file = "websockets-10.4-cp310-cp310-win_amd64.whl", hash = "sha256:8dc96f64ae43dde92530775e9cb169979f414dcf5cff670455d81a6823b42089"}, - {file = "websockets-10.4-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:47a2964021f2110116cc1125b3e6d87ab5ad16dea161949e7244ec583b905bb4"}, - {file = "websockets-10.4-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:e789376b52c295c4946403bd0efecf27ab98f05319df4583d3c48e43c7342c2f"}, - {file = "websockets-10.4-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:7d3f0b61c45c3fa9a349cf484962c559a8a1d80dae6977276df8fd1fa5e3cb8c"}, - {file = "websockets-10.4-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:f55b5905705725af31ccef50e55391621532cd64fbf0bc6f4bac935f0fccec46"}, - {file = "websockets-10.4-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:00c870522cdb69cd625b93f002961ffb0c095394f06ba8c48f17eef7c1541f96"}, - {file = "websockets-10.4-cp311-cp311-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:8f38706e0b15d3c20ef6259fd4bc1700cd133b06c3c1bb108ffe3f8947be15fa"}, - {file = "websockets-10.4-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:f2c38d588887a609191d30e902df2a32711f708abfd85d318ca9b367258cfd0c"}, - {file = "websockets-10.4-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:fe10ddc59b304cb19a1bdf5bd0a7719cbbc9fbdd57ac80ed436b709fcf889106"}, - {file = "websockets-10.4-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:90fcf8929836d4a0e964d799a58823547df5a5e9afa83081761630553be731f9"}, - {file = "websockets-10.4-cp311-cp311-win32.whl", hash = "sha256:b9968694c5f467bf67ef97ae7ad4d56d14be2751000c1207d31bf3bb8860bae8"}, - {file = "websockets-10.4-cp311-cp311-win_amd64.whl", hash = "sha256:a7a240d7a74bf8d5cb3bfe6be7f21697a28ec4b1a437607bae08ac7acf5b4882"}, - {file = "websockets-10.4-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:74de2b894b47f1d21cbd0b37a5e2b2392ad95d17ae983e64727e18eb281fe7cb"}, - {file = "websockets-10.4-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:e3a686ecb4aa0d64ae60c9c9f1a7d5d46cab9bfb5d91a2d303d00e2cd4c4c5cc"}, - {file = "websockets-10.4-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:b0d15c968ea7a65211e084f523151dbf8ae44634de03c801b8bd070b74e85033"}, - {file = "websockets-10.4-cp37-cp37m-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:00213676a2e46b6ebf6045bc11d0f529d9120baa6f58d122b4021ad92adabd41"}, - {file = "websockets-10.4-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:e23173580d740bf8822fd0379e4bf30aa1d5a92a4f252d34e893070c081050df"}, - {file = "websockets-10.4-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:dd500e0a5e11969cdd3320935ca2ff1e936f2358f9c2e61f100a1660933320ea"}, - {file = "websockets-10.4-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:4239b6027e3d66a89446908ff3027d2737afc1a375f8fd3eea630a4842ec9a0c"}, - {file = "websockets-10.4-cp37-cp37m-win32.whl", hash = "sha256:8a5cc00546e0a701da4639aa0bbcb0ae2bb678c87f46da01ac2d789e1f2d2038"}, - {file = "websockets-10.4-cp37-cp37m-win_amd64.whl", hash = "sha256:a9f9a735deaf9a0cadc2d8c50d1a5bcdbae8b6e539c6e08237bc4082d7c13f28"}, - {file = "websockets-10.4-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:5c1289596042fad2cdceb05e1ebf7aadf9995c928e0da2b7a4e99494953b1b94"}, - {file = "websockets-10.4-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:0cff816f51fb33c26d6e2b16b5c7d48eaa31dae5488ace6aae468b361f422b63"}, - {file = "websockets-10.4-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:dd9becd5fe29773d140d68d607d66a38f60e31b86df75332703757ee645b6faf"}, - {file = "websockets-10.4-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:45ec8e75b7dbc9539cbfafa570742fe4f676eb8b0d3694b67dabe2f2ceed8aa6"}, - {file = "websockets-10.4-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:4f72e5cd0f18f262f5da20efa9e241699e0cf3a766317a17392550c9ad7b37d8"}, - {file = "websockets-10.4-cp38-cp38-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:185929b4808b36a79c65b7865783b87b6841e852ef5407a2fb0c03381092fa3b"}, - {file = "websockets-10.4-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:7d27a7e34c313b3a7f91adcd05134315002aaf8540d7b4f90336beafaea6217c"}, - {file = "websockets-10.4-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:884be66c76a444c59f801ac13f40c76f176f1bfa815ef5b8ed44321e74f1600b"}, - {file = "websockets-10.4-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:931c039af54fc195fe6ad536fde4b0de04da9d5916e78e55405436348cfb0e56"}, - {file = "websockets-10.4-cp38-cp38-win32.whl", hash = "sha256:db3c336f9eda2532ec0fd8ea49fef7a8df8f6c804cdf4f39e5c5c0d4a4ad9a7a"}, - {file = "websockets-10.4-cp38-cp38-win_amd64.whl", hash = "sha256:48c08473563323f9c9debac781ecf66f94ad5a3680a38fe84dee5388cf5acaf6"}, - {file = "websockets-10.4-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:40e826de3085721dabc7cf9bfd41682dadc02286d8cf149b3ad05bff89311e4f"}, - {file = "websockets-10.4-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:56029457f219ade1f2fc12a6504ea61e14ee227a815531f9738e41203a429112"}, - {file = "websockets-10.4-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:f5fc088b7a32f244c519a048c170f14cf2251b849ef0e20cbbb0fdf0fdaf556f"}, - {file = "websockets-10.4-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:2fc8709c00704194213d45e455adc106ff9e87658297f72d544220e32029cd3d"}, - {file = "websockets-10.4-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:0154f7691e4fe6c2b2bc275b5701e8b158dae92a1ab229e2b940efe11905dff4"}, - {file = "websockets-10.4-cp39-cp39-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:4c6d2264f485f0b53adf22697ac11e261ce84805c232ed5dbe6b1bcb84b00ff0"}, - {file = "websockets-10.4-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:9bc42e8402dc5e9905fb8b9649f57efcb2056693b7e88faa8fb029256ba9c68c"}, - {file = "websockets-10.4-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:edc344de4dac1d89300a053ac973299e82d3db56330f3494905643bb68801269"}, - {file = "websockets-10.4-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:84bc2a7d075f32f6ed98652db3a680a17a4edb21ca7f80fe42e38753a58ee02b"}, - {file = "websockets-10.4-cp39-cp39-win32.whl", hash = "sha256:c94ae4faf2d09f7c81847c63843f84fe47bf6253c9d60b20f25edfd30fb12588"}, - {file = "websockets-10.4-cp39-cp39-win_amd64.whl", hash = "sha256:bbccd847aa0c3a69b5f691a84d2341a4f8a629c6922558f2a70611305f902d74"}, - {file = "websockets-10.4-pp37-pypy37_pp73-macosx_10_9_x86_64.whl", hash = "sha256:82ff5e1cae4e855147fd57a2863376ed7454134c2bf49ec604dfe71e446e2193"}, - {file = "websockets-10.4-pp37-pypy37_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d210abe51b5da0ffdbf7b43eed0cfdff8a55a1ab17abbec4301c9ff077dd0342"}, - {file = "websockets-10.4-pp37-pypy37_pp73-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:942de28af58f352a6f588bc72490ae0f4ccd6dfc2bd3de5945b882a078e4e179"}, - {file = "websockets-10.4-pp37-pypy37_pp73-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:c9b27d6c1c6cd53dc93614967e9ce00ae7f864a2d9f99fe5ed86706e1ecbf485"}, - {file = "websockets-10.4-pp37-pypy37_pp73-win_amd64.whl", hash = "sha256:3d3cac3e32b2c8414f4f87c1b2ab686fa6284a980ba283617404377cd448f631"}, - {file = "websockets-10.4-pp38-pypy38_pp73-macosx_10_9_x86_64.whl", hash = "sha256:da39dd03d130162deb63da51f6e66ed73032ae62e74aaccc4236e30edccddbb0"}, - {file = "websockets-10.4-pp38-pypy38_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:389f8dbb5c489e305fb113ca1b6bdcdaa130923f77485db5b189de343a179393"}, - {file = "websockets-10.4-pp38-pypy38_pp73-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:09a1814bb15eff7069e51fed0826df0bc0702652b5cb8f87697d469d79c23576"}, - {file = "websockets-10.4-pp38-pypy38_pp73-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:ff64a1d38d156d429404aaa84b27305e957fd10c30e5880d1765c9480bea490f"}, - {file = "websockets-10.4-pp38-pypy38_pp73-win_amd64.whl", hash = "sha256:b343f521b047493dc4022dd338fc6db9d9282658862756b4f6fd0e996c1380e1"}, - {file = "websockets-10.4-pp39-pypy39_pp73-macosx_10_9_x86_64.whl", hash = "sha256:932af322458da7e4e35df32f050389e13d3d96b09d274b22a7aa1808f292fee4"}, - {file = "websockets-10.4-pp39-pypy39_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d6a4162139374a49eb18ef5b2f4da1dd95c994588f5033d64e0bbfda4b6b6fcf"}, - {file = "websockets-10.4-pp39-pypy39_pp73-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:c57e4c1349fbe0e446c9fa7b19ed2f8a4417233b6984277cce392819123142d3"}, - {file = "websockets-10.4-pp39-pypy39_pp73-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:b627c266f295de9dea86bd1112ed3d5fafb69a348af30a2422e16590a8ecba13"}, - {file = "websockets-10.4-pp39-pypy39_pp73-win_amd64.whl", hash = "sha256:05a7233089f8bd355e8cbe127c2e8ca0b4ea55467861906b80d2ebc7db4d6b72"}, - {file = "websockets-10.4.tar.gz", hash = "sha256:eef610b23933c54d5d921c92578ae5f89813438fded840c2e9809d378dc765d3"}, + {file = "websockets-11.0.3-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:3ccc8a0c387629aec40f2fc9fdcb4b9d5431954f934da3eaf16cdc94f67dbfac"}, + {file = "websockets-11.0.3-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:d67ac60a307f760c6e65dad586f556dde58e683fab03323221a4e530ead6f74d"}, + {file = "websockets-11.0.3-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:84d27a4832cc1a0ee07cdcf2b0629a8a72db73f4cf6de6f0904f6661227f256f"}, + {file = "websockets-11.0.3-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ffd7dcaf744f25f82190856bc26ed81721508fc5cbf2a330751e135ff1283564"}, + {file = "websockets-11.0.3-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:7622a89d696fc87af8e8d280d9b421db5133ef5b29d3f7a1ce9f1a7bf7fcfa11"}, + {file = "websockets-11.0.3-cp310-cp310-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:bceab846bac555aff6427d060f2fcfff71042dba6f5fca7dc4f75cac815e57ca"}, + {file = "websockets-11.0.3-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:54c6e5b3d3a8936a4ab6870d46bdd6ec500ad62bde9e44462c32d18f1e9a8e54"}, + {file = "websockets-11.0.3-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:41f696ba95cd92dc047e46b41b26dd24518384749ed0d99bea0a941ca87404c4"}, + {file = "websockets-11.0.3-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:86d2a77fd490ae3ff6fae1c6ceaecad063d3cc2320b44377efdde79880e11526"}, + {file = "websockets-11.0.3-cp310-cp310-win32.whl", hash = "sha256:2d903ad4419f5b472de90cd2d40384573b25da71e33519a67797de17ef849b69"}, + {file = "websockets-11.0.3-cp310-cp310-win_amd64.whl", hash = "sha256:1d2256283fa4b7f4c7d7d3e84dc2ece74d341bce57d5b9bf385df109c2a1a82f"}, + {file = "websockets-11.0.3-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:e848f46a58b9fcf3d06061d17be388caf70ea5b8cc3466251963c8345e13f7eb"}, + {file = "websockets-11.0.3-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:aa5003845cdd21ac0dc6c9bf661c5beddd01116f6eb9eb3c8e272353d45b3288"}, + {file = "websockets-11.0.3-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:b58cbf0697721120866820b89f93659abc31c1e876bf20d0b3d03cef14faf84d"}, + {file = "websockets-11.0.3-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:660e2d9068d2bedc0912af508f30bbeb505bbbf9774d98def45f68278cea20d3"}, + {file = "websockets-11.0.3-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:c1f0524f203e3bd35149f12157438f406eff2e4fb30f71221c8a5eceb3617b6b"}, + {file = "websockets-11.0.3-cp311-cp311-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:def07915168ac8f7853812cc593c71185a16216e9e4fa886358a17ed0fd9fcf6"}, + {file = "websockets-11.0.3-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:b30c6590146e53149f04e85a6e4fcae068df4289e31e4aee1fdf56a0dead8f97"}, + {file = "websockets-11.0.3-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:619d9f06372b3a42bc29d0cd0354c9bb9fb39c2cbc1a9c5025b4538738dbffaf"}, + {file = "websockets-11.0.3-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:01f5567d9cf6f502d655151645d4e8b72b453413d3819d2b6f1185abc23e82dd"}, + {file = "websockets-11.0.3-cp311-cp311-win32.whl", hash = "sha256:e1459677e5d12be8bbc7584c35b992eea142911a6236a3278b9b5ce3326f282c"}, + {file = "websockets-11.0.3-cp311-cp311-win_amd64.whl", hash = "sha256:e7837cb169eca3b3ae94cc5787c4fed99eef74c0ab9506756eea335e0d6f3ed8"}, + {file = "websockets-11.0.3-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:9f59a3c656fef341a99e3d63189852be7084c0e54b75734cde571182c087b152"}, + {file = "websockets-11.0.3-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:2529338a6ff0eb0b50c7be33dc3d0e456381157a31eefc561771ee431134a97f"}, + {file = "websockets-11.0.3-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:34fd59a4ac42dff6d4681d8843217137f6bc85ed29722f2f7222bd619d15e95b"}, + {file = "websockets-11.0.3-cp37-cp37m-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:332d126167ddddec94597c2365537baf9ff62dfcc9db4266f263d455f2f031cb"}, + {file = "websockets-11.0.3-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:6505c1b31274723ccaf5f515c1824a4ad2f0d191cec942666b3d0f3aa4cb4007"}, + {file = "websockets-11.0.3-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:f467ba0050b7de85016b43f5a22b46383ef004c4f672148a8abf32bc999a87f0"}, + {file = "websockets-11.0.3-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:9d9acd80072abcc98bd2c86c3c9cd4ac2347b5a5a0cae7ed5c0ee5675f86d9af"}, + {file = "websockets-11.0.3-cp37-cp37m-win32.whl", hash = "sha256:e590228200fcfc7e9109509e4d9125eace2042fd52b595dd22bbc34bb282307f"}, + {file = "websockets-11.0.3-cp37-cp37m-win_amd64.whl", hash = "sha256:b16fff62b45eccb9c7abb18e60e7e446998093cdcb50fed33134b9b6878836de"}, + {file = "websockets-11.0.3-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:fb06eea71a00a7af0ae6aefbb932fb8a7df3cb390cc217d51a9ad7343de1b8d0"}, + {file = "websockets-11.0.3-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:8a34e13a62a59c871064dfd8ffb150867e54291e46d4a7cf11d02c94a5275bae"}, + {file = "websockets-11.0.3-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:4841ed00f1026dfbced6fca7d963c4e7043aa832648671b5138008dc5a8f6d99"}, + {file = "websockets-11.0.3-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:1a073fc9ab1c8aff37c99f11f1641e16da517770e31a37265d2755282a5d28aa"}, + {file = "websockets-11.0.3-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:68b977f21ce443d6d378dbd5ca38621755f2063d6fdb3335bda981d552cfff86"}, + {file = "websockets-11.0.3-cp38-cp38-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:e1a99a7a71631f0efe727c10edfba09ea6bee4166a6f9c19aafb6c0b5917d09c"}, + {file = "websockets-11.0.3-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:bee9fcb41db2a23bed96c6b6ead6489702c12334ea20a297aa095ce6d31370d0"}, + {file = "websockets-11.0.3-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:4b253869ea05a5a073ebfdcb5cb3b0266a57c3764cf6fe114e4cd90f4bfa5f5e"}, + {file = "websockets-11.0.3-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:1553cb82942b2a74dd9b15a018dce645d4e68674de2ca31ff13ebc2d9f283788"}, + {file = "websockets-11.0.3-cp38-cp38-win32.whl", hash = "sha256:f61bdb1df43dc9c131791fbc2355535f9024b9a04398d3bd0684fc16ab07df74"}, + {file = "websockets-11.0.3-cp38-cp38-win_amd64.whl", hash = "sha256:03aae4edc0b1c68498f41a6772d80ac7c1e33c06c6ffa2ac1c27a07653e79d6f"}, + {file = "websockets-11.0.3-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:777354ee16f02f643a4c7f2b3eff8027a33c9861edc691a2003531f5da4f6bc8"}, + {file = "websockets-11.0.3-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:8c82f11964f010053e13daafdc7154ce7385ecc538989a354ccc7067fd7028fd"}, + {file = "websockets-11.0.3-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:3580dd9c1ad0701169e4d6fc41e878ffe05e6bdcaf3c412f9d559389d0c9e016"}, + {file = "websockets-11.0.3-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:6f1a3f10f836fab6ca6efa97bb952300b20ae56b409414ca85bff2ad241d2a61"}, + {file = "websockets-11.0.3-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:df41b9bc27c2c25b486bae7cf42fccdc52ff181c8c387bfd026624a491c2671b"}, + {file = "websockets-11.0.3-cp39-cp39-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:279e5de4671e79a9ac877427f4ac4ce93751b8823f276b681d04b2156713b9dd"}, + {file = "websockets-11.0.3-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:1fdf26fa8a6a592f8f9235285b8affa72748dc12e964a5518c6c5e8f916716f7"}, + {file = "websockets-11.0.3-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:69269f3a0b472e91125b503d3c0b3566bda26da0a3261c49f0027eb6075086d1"}, + {file = "websockets-11.0.3-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:97b52894d948d2f6ea480171a27122d77af14ced35f62e5c892ca2fae9344311"}, + {file = "websockets-11.0.3-cp39-cp39-win32.whl", hash = "sha256:c7f3cb904cce8e1be667c7e6fef4516b98d1a6a0635a58a57528d577ac18a128"}, + {file = "websockets-11.0.3-cp39-cp39-win_amd64.whl", hash = "sha256:c792ea4eabc0159535608fc5658a74d1a81020eb35195dd63214dcf07556f67e"}, + {file = "websockets-11.0.3-pp37-pypy37_pp73-macosx_10_9_x86_64.whl", hash = "sha256:f2e58f2c36cc52d41f2659e4c0cbf7353e28c8c9e63e30d8c6d3494dc9fdedcf"}, + {file = "websockets-11.0.3-pp37-pypy37_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:de36fe9c02995c7e6ae6efe2e205816f5f00c22fd1fbf343d4d18c3d5ceac2f5"}, + {file = "websockets-11.0.3-pp37-pypy37_pp73-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:0ac56b661e60edd453585f4bd68eb6a29ae25b5184fd5ba51e97652580458998"}, + {file = "websockets-11.0.3-pp37-pypy37_pp73-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:e052b8467dd07d4943936009f46ae5ce7b908ddcac3fda581656b1b19c083d9b"}, + {file = "websockets-11.0.3-pp37-pypy37_pp73-win_amd64.whl", hash = "sha256:42cc5452a54a8e46a032521d7365da775823e21bfba2895fb7b77633cce031bb"}, + {file = "websockets-11.0.3-pp38-pypy38_pp73-macosx_10_9_x86_64.whl", hash = "sha256:e6316827e3e79b7b8e7d8e3b08f4e331af91a48e794d5d8b099928b6f0b85f20"}, + {file = "websockets-11.0.3-pp38-pypy38_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:8531fdcad636d82c517b26a448dcfe62f720e1922b33c81ce695d0edb91eb931"}, + {file = "websockets-11.0.3-pp38-pypy38_pp73-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:c114e8da9b475739dde229fd3bc6b05a6537a88a578358bc8eb29b4030fac9c9"}, + {file = "websockets-11.0.3-pp38-pypy38_pp73-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:e063b1865974611313a3849d43f2c3f5368093691349cf3c7c8f8f75ad7cb280"}, + {file = "websockets-11.0.3-pp38-pypy38_pp73-win_amd64.whl", hash = "sha256:92b2065d642bf8c0a82d59e59053dd2fdde64d4ed44efe4870fa816c1232647b"}, + {file = "websockets-11.0.3-pp39-pypy39_pp73-macosx_10_9_x86_64.whl", hash = "sha256:0ee68fe502f9031f19d495dae2c268830df2760c0524cbac5d759921ba8c8e82"}, + {file = "websockets-11.0.3-pp39-pypy39_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:dcacf2c7a6c3a84e720d1bb2b543c675bf6c40e460300b628bab1b1efc7c034c"}, + {file = "websockets-11.0.3-pp39-pypy39_pp73-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:b67c6f5e5a401fc56394f191f00f9b3811fe843ee93f4a70df3c389d1adf857d"}, + {file = "websockets-11.0.3-pp39-pypy39_pp73-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:1d5023a4b6a5b183dc838808087033ec5df77580485fc533e7dab2567851b0a4"}, + {file = "websockets-11.0.3-pp39-pypy39_pp73-win_amd64.whl", hash = "sha256:ed058398f55163a79bb9f06a90ef9ccc063b204bb346c4de78efc5d15abfe602"}, + {file = "websockets-11.0.3-py3-none-any.whl", hash = "sha256:6681ba9e7f8f3b19440921e99efbb40fc89f26cd71bf539e45d8c8a25c976dc6"}, + {file = "websockets-11.0.3.tar.gz", hash = "sha256:88fc51d9a26b10fc331be344f1781224a375b78488fc343620184e95a4b27016"}, ] [[package]] @@ -3342,85 +3353,85 @@ test = ["pytest (>=6.0.0)"] [[package]] name = "yarl" -version = "1.8.2" +version = "1.9.2" description = "Yet another URL library" optional = false python-versions = ">=3.7" files = [ - {file = "yarl-1.8.2-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:bb81f753c815f6b8e2ddd2eef3c855cf7da193b82396ac013c661aaa6cc6b0a5"}, - {file = "yarl-1.8.2-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:47d49ac96156f0928f002e2424299b2c91d9db73e08c4cd6742923a086f1c863"}, - {file = "yarl-1.8.2-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:3fc056e35fa6fba63248d93ff6e672c096f95f7836938241ebc8260e062832fe"}, - {file = "yarl-1.8.2-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:58a3c13d1c3005dbbac5c9f0d3210b60220a65a999b1833aa46bd6677c69b08e"}, - {file = "yarl-1.8.2-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:10b08293cda921157f1e7c2790999d903b3fd28cd5c208cf8826b3b508026996"}, - {file = "yarl-1.8.2-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:de986979bbd87272fe557e0a8fcb66fd40ae2ddfe28a8b1ce4eae22681728fef"}, - {file = "yarl-1.8.2-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:6c4fcfa71e2c6a3cb568cf81aadc12768b9995323186a10827beccf5fa23d4f8"}, - {file = "yarl-1.8.2-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:ae4d7ff1049f36accde9e1ef7301912a751e5bae0a9d142459646114c70ecba6"}, - {file = "yarl-1.8.2-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:bf071f797aec5b96abfc735ab97da9fd8f8768b43ce2abd85356a3127909d146"}, - {file = "yarl-1.8.2-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:74dece2bfc60f0f70907c34b857ee98f2c6dd0f75185db133770cd67300d505f"}, - {file = "yarl-1.8.2-cp310-cp310-musllinux_1_1_ppc64le.whl", hash = "sha256:df60a94d332158b444301c7f569659c926168e4d4aad2cfbf4bce0e8fb8be826"}, - {file = "yarl-1.8.2-cp310-cp310-musllinux_1_1_s390x.whl", hash = "sha256:63243b21c6e28ec2375f932a10ce7eda65139b5b854c0f6b82ed945ba526bff3"}, - {file = "yarl-1.8.2-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:cfa2bbca929aa742b5084fd4663dd4b87c191c844326fcb21c3afd2d11497f80"}, - {file = "yarl-1.8.2-cp310-cp310-win32.whl", hash = "sha256:b05df9ea7496df11b710081bd90ecc3a3db6adb4fee36f6a411e7bc91a18aa42"}, - {file = "yarl-1.8.2-cp310-cp310-win_amd64.whl", hash = "sha256:24ad1d10c9db1953291f56b5fe76203977f1ed05f82d09ec97acb623a7976574"}, - {file = "yarl-1.8.2-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:2a1fca9588f360036242f379bfea2b8b44cae2721859b1c56d033adfd5893634"}, - {file = "yarl-1.8.2-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:f37db05c6051eff17bc832914fe46869f8849de5b92dc4a3466cd63095d23dfd"}, - {file = "yarl-1.8.2-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:77e913b846a6b9c5f767b14dc1e759e5aff05502fe73079f6f4176359d832581"}, - {file = "yarl-1.8.2-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:0978f29222e649c351b173da2b9b4665ad1feb8d1daa9d971eb90df08702668a"}, - {file = "yarl-1.8.2-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:388a45dc77198b2460eac0aca1efd6a7c09e976ee768b0d5109173e521a19daf"}, - {file = "yarl-1.8.2-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:2305517e332a862ef75be8fad3606ea10108662bc6fe08509d5ca99503ac2aee"}, - {file = "yarl-1.8.2-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:42430ff511571940d51e75cf42f1e4dbdded477e71c1b7a17f4da76c1da8ea76"}, - {file = "yarl-1.8.2-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:3150078118f62371375e1e69b13b48288e44f6691c1069340081c3fd12c94d5b"}, - {file = "yarl-1.8.2-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:c15163b6125db87c8f53c98baa5e785782078fbd2dbeaa04c6141935eb6dab7a"}, - {file = "yarl-1.8.2-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:4d04acba75c72e6eb90745447d69f84e6c9056390f7a9724605ca9c56b4afcc6"}, - {file = "yarl-1.8.2-cp311-cp311-musllinux_1_1_ppc64le.whl", hash = "sha256:e7fd20d6576c10306dea2d6a5765f46f0ac5d6f53436217913e952d19237efc4"}, - {file = "yarl-1.8.2-cp311-cp311-musllinux_1_1_s390x.whl", hash = "sha256:75c16b2a900b3536dfc7014905a128a2bea8fb01f9ee26d2d7d8db0a08e7cb2c"}, - {file = "yarl-1.8.2-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:6d88056a04860a98341a0cf53e950e3ac9f4e51d1b6f61a53b0609df342cc8b2"}, - {file = "yarl-1.8.2-cp311-cp311-win32.whl", hash = "sha256:fb742dcdd5eec9f26b61224c23baea46c9055cf16f62475e11b9b15dfd5c117b"}, - {file = "yarl-1.8.2-cp311-cp311-win_amd64.whl", hash = "sha256:8c46d3d89902c393a1d1e243ac847e0442d0196bbd81aecc94fcebbc2fd5857c"}, - {file = "yarl-1.8.2-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:ceff9722e0df2e0a9e8a79c610842004fa54e5b309fe6d218e47cd52f791d7ef"}, - {file = "yarl-1.8.2-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:3f6b4aca43b602ba0f1459de647af954769919c4714706be36af670a5f44c9c1"}, - {file = "yarl-1.8.2-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:1684a9bd9077e922300ecd48003ddae7a7474e0412bea38d4631443a91d61077"}, - {file = "yarl-1.8.2-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:ebb78745273e51b9832ef90c0898501006670d6e059f2cdb0e999494eb1450c2"}, - {file = "yarl-1.8.2-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:3adeef150d528ded2a8e734ebf9ae2e658f4c49bf413f5f157a470e17a4a2e89"}, - {file = "yarl-1.8.2-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:57a7c87927a468e5a1dc60c17caf9597161d66457a34273ab1760219953f7f4c"}, - {file = "yarl-1.8.2-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:efff27bd8cbe1f9bd127e7894942ccc20c857aa8b5a0327874f30201e5ce83d0"}, - {file = "yarl-1.8.2-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:a783cd344113cb88c5ff7ca32f1f16532a6f2142185147822187913eb989f739"}, - {file = "yarl-1.8.2-cp37-cp37m-musllinux_1_1_ppc64le.whl", hash = "sha256:705227dccbe96ab02c7cb2c43e1228e2826e7ead880bb19ec94ef279e9555b5b"}, - {file = "yarl-1.8.2-cp37-cp37m-musllinux_1_1_s390x.whl", hash = "sha256:34c09b43bd538bf6c4b891ecce94b6fa4f1f10663a8d4ca589a079a5018f6ed7"}, - {file = "yarl-1.8.2-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:a48f4f7fea9a51098b02209d90297ac324241bf37ff6be6d2b0149ab2bd51b37"}, - {file = "yarl-1.8.2-cp37-cp37m-win32.whl", hash = "sha256:0414fd91ce0b763d4eadb4456795b307a71524dbacd015c657bb2a39db2eab89"}, - {file = "yarl-1.8.2-cp37-cp37m-win_amd64.whl", hash = "sha256:d881d152ae0007809c2c02e22aa534e702f12071e6b285e90945aa3c376463c5"}, - {file = "yarl-1.8.2-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:5df5e3d04101c1e5c3b1d69710b0574171cc02fddc4b23d1b2813e75f35a30b1"}, - {file = "yarl-1.8.2-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:7a66c506ec67eb3159eea5096acd05f5e788ceec7b96087d30c7d2865a243918"}, - {file = "yarl-1.8.2-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:2b4fa2606adf392051d990c3b3877d768771adc3faf2e117b9de7eb977741229"}, - {file = "yarl-1.8.2-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:1e21fb44e1eff06dd6ef971d4bdc611807d6bd3691223d9c01a18cec3677939e"}, - {file = "yarl-1.8.2-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:93202666046d9edadfe9f2e7bf5e0782ea0d497b6d63da322e541665d65a044e"}, - {file = "yarl-1.8.2-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:fc77086ce244453e074e445104f0ecb27530d6fd3a46698e33f6c38951d5a0f1"}, - {file = "yarl-1.8.2-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:64dd68a92cab699a233641f5929a40f02a4ede8c009068ca8aa1fe87b8c20ae3"}, - {file = "yarl-1.8.2-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:1b372aad2b5f81db66ee7ec085cbad72c4da660d994e8e590c997e9b01e44901"}, - {file = "yarl-1.8.2-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:e6f3515aafe0209dd17fb9bdd3b4e892963370b3de781f53e1746a521fb39fc0"}, - {file = "yarl-1.8.2-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:dfef7350ee369197106805e193d420b75467b6cceac646ea5ed3049fcc950a05"}, - {file = "yarl-1.8.2-cp38-cp38-musllinux_1_1_ppc64le.whl", hash = "sha256:728be34f70a190566d20aa13dc1f01dc44b6aa74580e10a3fb159691bc76909d"}, - {file = "yarl-1.8.2-cp38-cp38-musllinux_1_1_s390x.whl", hash = "sha256:ff205b58dc2929191f68162633d5e10e8044398d7a45265f90a0f1d51f85f72c"}, - {file = "yarl-1.8.2-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:baf211dcad448a87a0d9047dc8282d7de59473ade7d7fdf22150b1d23859f946"}, - {file = "yarl-1.8.2-cp38-cp38-win32.whl", hash = "sha256:272b4f1599f1b621bf2aabe4e5b54f39a933971f4e7c9aa311d6d7dc06965165"}, - {file = "yarl-1.8.2-cp38-cp38-win_amd64.whl", hash = "sha256:326dd1d3caf910cd26a26ccbfb84c03b608ba32499b5d6eeb09252c920bcbe4f"}, - {file = "yarl-1.8.2-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:f8ca8ad414c85bbc50f49c0a106f951613dfa5f948ab69c10ce9b128d368baf8"}, - {file = "yarl-1.8.2-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:418857f837347e8aaef682679f41e36c24250097f9e2f315d39bae3a99a34cbf"}, - {file = "yarl-1.8.2-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:ae0eec05ab49e91a78700761777f284c2df119376e391db42c38ab46fd662b77"}, - {file = "yarl-1.8.2-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:009a028127e0a1755c38b03244c0bea9d5565630db9c4cf9572496e947137a87"}, - {file = "yarl-1.8.2-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:3edac5d74bb3209c418805bda77f973117836e1de7c000e9755e572c1f7850d0"}, - {file = "yarl-1.8.2-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:da65c3f263729e47351261351b8679c6429151ef9649bba08ef2528ff2c423b2"}, - {file = "yarl-1.8.2-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:0ef8fb25e52663a1c85d608f6dd72e19bd390e2ecaf29c17fb08f730226e3a08"}, - {file = "yarl-1.8.2-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:bcd7bb1e5c45274af9a1dd7494d3c52b2be5e6bd8d7e49c612705fd45420b12d"}, - {file = "yarl-1.8.2-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:44ceac0450e648de86da8e42674f9b7077d763ea80c8ceb9d1c3e41f0f0a9951"}, - {file = "yarl-1.8.2-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:97209cc91189b48e7cfe777237c04af8e7cc51eb369004e061809bcdf4e55220"}, - {file = "yarl-1.8.2-cp39-cp39-musllinux_1_1_ppc64le.whl", hash = "sha256:48dd18adcf98ea9cd721a25313aef49d70d413a999d7d89df44f469edfb38a06"}, - {file = "yarl-1.8.2-cp39-cp39-musllinux_1_1_s390x.whl", hash = "sha256:e59399dda559688461762800d7fb34d9e8a6a7444fd76ec33220a926c8be1516"}, - {file = "yarl-1.8.2-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:d617c241c8c3ad5c4e78a08429fa49e4b04bedfc507b34b4d8dceb83b4af3588"}, - {file = "yarl-1.8.2-cp39-cp39-win32.whl", hash = "sha256:cb6d48d80a41f68de41212f3dfd1a9d9898d7841c8f7ce6696cf2fd9cb57ef83"}, - {file = "yarl-1.8.2-cp39-cp39-win_amd64.whl", hash = "sha256:6604711362f2dbf7160df21c416f81fac0de6dbcf0b5445a2ef25478ecc4c778"}, - {file = "yarl-1.8.2.tar.gz", hash = "sha256:49d43402c6e3013ad0978602bf6bf5328535c48d192304b91b97a3c6790b1562"}, + {file = "yarl-1.9.2-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:8c2ad583743d16ddbdf6bb14b5cd76bf43b0d0006e918809d5d4ddf7bde8dd82"}, + {file = "yarl-1.9.2-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:82aa6264b36c50acfb2424ad5ca537a2060ab6de158a5bd2a72a032cc75b9eb8"}, + {file = "yarl-1.9.2-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:c0c77533b5ed4bcc38e943178ccae29b9bcf48ffd1063f5821192f23a1bd27b9"}, + {file = "yarl-1.9.2-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ee4afac41415d52d53a9833ebae7e32b344be72835bbb589018c9e938045a560"}, + {file = "yarl-1.9.2-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:9bf345c3a4f5ba7f766430f97f9cc1320786f19584acc7086491f45524a551ac"}, + {file = "yarl-1.9.2-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:2a96c19c52ff442a808c105901d0bdfd2e28575b3d5f82e2f5fd67e20dc5f4ea"}, + {file = "yarl-1.9.2-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:891c0e3ec5ec881541f6c5113d8df0315ce5440e244a716b95f2525b7b9f3608"}, + {file = "yarl-1.9.2-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:c3a53ba34a636a256d767c086ceb111358876e1fb6b50dfc4d3f4951d40133d5"}, + {file = "yarl-1.9.2-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:566185e8ebc0898b11f8026447eacd02e46226716229cea8db37496c8cdd26e0"}, + {file = "yarl-1.9.2-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:2b0738fb871812722a0ac2154be1f049c6223b9f6f22eec352996b69775b36d4"}, + {file = "yarl-1.9.2-cp310-cp310-musllinux_1_1_ppc64le.whl", hash = "sha256:32f1d071b3f362c80f1a7d322bfd7b2d11e33d2adf395cc1dd4df36c9c243095"}, + {file = "yarl-1.9.2-cp310-cp310-musllinux_1_1_s390x.whl", hash = "sha256:e9fdc7ac0d42bc3ea78818557fab03af6181e076a2944f43c38684b4b6bed8e3"}, + {file = "yarl-1.9.2-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:56ff08ab5df8429901ebdc5d15941b59f6253393cb5da07b4170beefcf1b2528"}, + {file = "yarl-1.9.2-cp310-cp310-win32.whl", hash = "sha256:8ea48e0a2f931064469bdabca50c2f578b565fc446f302a79ba6cc0ee7f384d3"}, + {file = "yarl-1.9.2-cp310-cp310-win_amd64.whl", hash = "sha256:50f33040f3836e912ed16d212f6cc1efb3231a8a60526a407aeb66c1c1956dde"}, + {file = "yarl-1.9.2-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:646d663eb2232d7909e6601f1a9107e66f9791f290a1b3dc7057818fe44fc2b6"}, + {file = "yarl-1.9.2-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:aff634b15beff8902d1f918012fc2a42e0dbae6f469fce134c8a0dc51ca423bb"}, + {file = "yarl-1.9.2-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:a83503934c6273806aed765035716216cc9ab4e0364f7f066227e1aaea90b8d0"}, + {file = "yarl-1.9.2-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:b25322201585c69abc7b0e89e72790469f7dad90d26754717f3310bfe30331c2"}, + {file = "yarl-1.9.2-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:22a94666751778629f1ec4280b08eb11815783c63f52092a5953faf73be24191"}, + {file = "yarl-1.9.2-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:8ec53a0ea2a80c5cd1ab397925f94bff59222aa3cf9c6da938ce05c9ec20428d"}, + {file = "yarl-1.9.2-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:159d81f22d7a43e6eabc36d7194cb53f2f15f498dbbfa8edc8a3239350f59fe7"}, + {file = "yarl-1.9.2-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:832b7e711027c114d79dffb92576acd1bd2decc467dec60e1cac96912602d0e6"}, + {file = "yarl-1.9.2-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:95d2ecefbcf4e744ea952d073c6922e72ee650ffc79028eb1e320e732898d7e8"}, + {file = "yarl-1.9.2-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:d4e2c6d555e77b37288eaf45b8f60f0737c9efa3452c6c44626a5455aeb250b9"}, + {file = "yarl-1.9.2-cp311-cp311-musllinux_1_1_ppc64le.whl", hash = "sha256:783185c75c12a017cc345015ea359cc801c3b29a2966c2655cd12b233bf5a2be"}, + {file = "yarl-1.9.2-cp311-cp311-musllinux_1_1_s390x.whl", hash = "sha256:b8cc1863402472f16c600e3e93d542b7e7542a540f95c30afd472e8e549fc3f7"}, + {file = "yarl-1.9.2-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:822b30a0f22e588b32d3120f6d41e4ed021806418b4c9f0bc3048b8c8cb3f92a"}, + {file = "yarl-1.9.2-cp311-cp311-win32.whl", hash = "sha256:a60347f234c2212a9f0361955007fcf4033a75bf600a33c88a0a8e91af77c0e8"}, + {file = "yarl-1.9.2-cp311-cp311-win_amd64.whl", hash = "sha256:be6b3fdec5c62f2a67cb3f8c6dbf56bbf3f61c0f046f84645cd1ca73532ea051"}, + {file = "yarl-1.9.2-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:38a3928ae37558bc1b559f67410df446d1fbfa87318b124bf5032c31e3447b74"}, + {file = "yarl-1.9.2-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ac9bb4c5ce3975aeac288cfcb5061ce60e0d14d92209e780c93954076c7c4367"}, + {file = "yarl-1.9.2-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:3da8a678ca8b96c8606bbb8bfacd99a12ad5dd288bc6f7979baddd62f71c63ef"}, + {file = "yarl-1.9.2-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:13414591ff516e04fcdee8dc051c13fd3db13b673c7a4cb1350e6b2ad9639ad3"}, + {file = "yarl-1.9.2-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:bf74d08542c3a9ea97bb8f343d4fcbd4d8f91bba5ec9d5d7f792dbe727f88938"}, + {file = "yarl-1.9.2-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:6e7221580dc1db478464cfeef9b03b95c5852cc22894e418562997df0d074ccc"}, + {file = "yarl-1.9.2-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:494053246b119b041960ddcd20fd76224149cfea8ed8777b687358727911dd33"}, + {file = "yarl-1.9.2-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:52a25809fcbecfc63ac9ba0c0fb586f90837f5425edfd1ec9f3372b119585e45"}, + {file = "yarl-1.9.2-cp37-cp37m-musllinux_1_1_ppc64le.whl", hash = "sha256:e65610c5792870d45d7b68c677681376fcf9cc1c289f23e8e8b39c1485384185"}, + {file = "yarl-1.9.2-cp37-cp37m-musllinux_1_1_s390x.whl", hash = "sha256:1b1bba902cba32cdec51fca038fd53f8beee88b77efc373968d1ed021024cc04"}, + {file = "yarl-1.9.2-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:662e6016409828ee910f5d9602a2729a8a57d74b163c89a837de3fea050c7582"}, + {file = "yarl-1.9.2-cp37-cp37m-win32.whl", hash = "sha256:f364d3480bffd3aa566e886587eaca7c8c04d74f6e8933f3f2c996b7f09bee1b"}, + {file = "yarl-1.9.2-cp37-cp37m-win_amd64.whl", hash = "sha256:6a5883464143ab3ae9ba68daae8e7c5c95b969462bbe42e2464d60e7e2698368"}, + {file = "yarl-1.9.2-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:5610f80cf43b6202e2c33ba3ec2ee0a2884f8f423c8f4f62906731d876ef4fac"}, + {file = "yarl-1.9.2-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:b9a4e67ad7b646cd6f0938c7ebfd60e481b7410f574c560e455e938d2da8e0f4"}, + {file = "yarl-1.9.2-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:83fcc480d7549ccebe9415d96d9263e2d4226798c37ebd18c930fce43dfb9574"}, + {file = "yarl-1.9.2-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:5fcd436ea16fee7d4207c045b1e340020e58a2597301cfbcfdbe5abd2356c2fb"}, + {file = "yarl-1.9.2-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:84e0b1599334b1e1478db01b756e55937d4614f8654311eb26012091be109d59"}, + {file = "yarl-1.9.2-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:3458a24e4ea3fd8930e934c129b676c27452e4ebda80fbe47b56d8c6c7a63a9e"}, + {file = "yarl-1.9.2-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:838162460b3a08987546e881a2bfa573960bb559dfa739e7800ceeec92e64417"}, + {file = "yarl-1.9.2-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:f4e2d08f07a3d7d3e12549052eb5ad3eab1c349c53ac51c209a0e5991bbada78"}, + {file = "yarl-1.9.2-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:de119f56f3c5f0e2fb4dee508531a32b069a5f2c6e827b272d1e0ff5ac040333"}, + {file = "yarl-1.9.2-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:149ddea5abf329752ea5051b61bd6c1d979e13fbf122d3a1f9f0c8be6cb6f63c"}, + {file = "yarl-1.9.2-cp38-cp38-musllinux_1_1_ppc64le.whl", hash = "sha256:674ca19cbee4a82c9f54e0d1eee28116e63bc6fd1e96c43031d11cbab8b2afd5"}, + {file = "yarl-1.9.2-cp38-cp38-musllinux_1_1_s390x.whl", hash = "sha256:9b3152f2f5677b997ae6c804b73da05a39daa6a9e85a512e0e6823d81cdad7cc"}, + {file = "yarl-1.9.2-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:5415d5a4b080dc9612b1b63cba008db84e908b95848369aa1da3686ae27b6d2b"}, + {file = "yarl-1.9.2-cp38-cp38-win32.whl", hash = "sha256:f7a3d8146575e08c29ed1cd287068e6d02f1c7bdff8970db96683b9591b86ee7"}, + {file = "yarl-1.9.2-cp38-cp38-win_amd64.whl", hash = "sha256:63c48f6cef34e6319a74c727376e95626f84ea091f92c0250a98e53e62c77c72"}, + {file = "yarl-1.9.2-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:75df5ef94c3fdc393c6b19d80e6ef1ecc9ae2f4263c09cacb178d871c02a5ba9"}, + {file = "yarl-1.9.2-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:c027a6e96ef77d401d8d5a5c8d6bc478e8042f1e448272e8d9752cb0aff8b5c8"}, + {file = "yarl-1.9.2-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:f3b078dbe227f79be488ffcfc7a9edb3409d018e0952cf13f15fd6512847f3f7"}, + {file = "yarl-1.9.2-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:59723a029760079b7d991a401386390c4be5bfec1e7dd83e25a6a0881859e716"}, + {file = "yarl-1.9.2-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:b03917871bf859a81ccb180c9a2e6c1e04d2f6a51d953e6a5cdd70c93d4e5a2a"}, + {file = "yarl-1.9.2-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:c1012fa63eb6c032f3ce5d2171c267992ae0c00b9e164efe4d73db818465fac3"}, + {file = "yarl-1.9.2-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:a74dcbfe780e62f4b5a062714576f16c2f3493a0394e555ab141bf0d746bb955"}, + {file = "yarl-1.9.2-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:8c56986609b057b4839968ba901944af91b8e92f1725d1a2d77cbac6972b9ed1"}, + {file = "yarl-1.9.2-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:2c315df3293cd521033533d242d15eab26583360b58f7ee5d9565f15fee1bef4"}, + {file = "yarl-1.9.2-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:b7232f8dfbd225d57340e441d8caf8652a6acd06b389ea2d3222b8bc89cbfca6"}, + {file = "yarl-1.9.2-cp39-cp39-musllinux_1_1_ppc64le.whl", hash = "sha256:53338749febd28935d55b41bf0bcc79d634881195a39f6b2f767870b72514caf"}, + {file = "yarl-1.9.2-cp39-cp39-musllinux_1_1_s390x.whl", hash = "sha256:066c163aec9d3d073dc9ffe5dd3ad05069bcb03fcaab8d221290ba99f9f69ee3"}, + {file = "yarl-1.9.2-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:8288d7cd28f8119b07dd49b7230d6b4562f9b61ee9a4ab02221060d21136be80"}, + {file = "yarl-1.9.2-cp39-cp39-win32.whl", hash = "sha256:b124e2a6d223b65ba8768d5706d103280914d61f5cae3afbc50fc3dfcc016623"}, + {file = "yarl-1.9.2-cp39-cp39-win_amd64.whl", hash = "sha256:61016e7d582bc46a5378ffdd02cd0314fb8ba52f40f9cf4d9a5e7dbef88dee18"}, + {file = "yarl-1.9.2.tar.gz", hash = "sha256:04ab9d4b9f587c06d801c2abfe9317b77cdf996c65a90d5e84ecc45010823571"}, ] [package.dependencies] @@ -3445,4 +3456,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "ba19565aba6b3b84495dcbce3d8a4b0032da29d47d5007e0ae8e34485be6f166" +content-hash = "66b92ac81e5083c8b13956b6860b0ea390e008110036d9091a6948ae5f349351" From 28af36ace3f88effa830664941ad68b23fa5c755 Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Wed, 28 Jun 2023 18:33:15 -0700 Subject: [PATCH 111/184] Cleanup gitignore --- .gitignore | 247 ++++++++++++++++++++++++++++++++---------------- .python-version | 1 - 2 files changed, 163 insertions(+), 85 deletions(-) delete mode 100644 .python-version diff --git a/.gitignore b/.gitignore index b7375cd9..dcad195d 100644 --- a/.gitignore +++ b/.gitignore @@ -1,84 +1,163 @@ -*.env -Bot/.env -.vscode -*.vscode -*.idea -.idea -__pycache__ -reddit-api-oauth.py -reddit -*reddit.db -*responses.json -Kana -.pytest_cache -disquest -.dccache -*.dccache -.metadata -*.metadata -json_parser.py -deviantarttest.py -chat/responses.json -chat -*.un~ # Vim's temp files -*.py~ # Also Vim's temp files -.py~ -.un~ -.jisho.py.un~ -jisho.py~ -.gitignore~ -..gitignore.un~ -kanji_jmdict.py -tester.py -twitterv2_cred.yaml -qrcode -changelog.md.un~ -*changelog.md~ -jikan-tester.py -spiget-tester.py -instagram-tester.py -modrinth-tester.py -top-gg-tester.py -pinterest-tester.py -spotify-tester.py -Cog-Testers/ -.cache -DeviantArt_API_Keys.txt -deviantart_links -Cogs-Misc/ -deviantart-tokens/ -test.db -text.txt -tokens.db -daTokens/ -button-test.py -reddit-links.txt -test-script.py -pages.py -Bot/database-testing.py -spotify-links.txt -Bot/Cogs/test.py -marketplace_filters.yml -Bot/Cog/economy/config/* -Bot/Cog/economy/config -config -gws-items.py -docker-compose.yml -docker-compose -docker-compose2.yml -redis-cache.py -eco_user_tester.py -quests-test.py -test.sh -user-inv-test.py -ah-test.py -gws-test.py -.env-docker -test-scripts -image-testspy -.vagrant -migrations -.env-old -database.db -json-tests -Kumiko-Docs/build \ No newline at end of file +# Byte-compiled / optimized / DLL files +__pycache__/ +*.py[cod] +*$py.class + +# C extensions +*.so + +# Distribution / packaging +.Python +build/ +develop-eggs/ +dist/ +downloads/ +eggs/ +.eggs/ +lib/ +lib64/ +parts/ +sdist/ +var/ +wheels/ +share/python-wheels/ +*.egg-info/ +.installed.cfg +*.egg +MANIFEST + +# PyInstaller +# Usually these files are written by a python script from a template +# before PyInstaller builds the exe, so as to inject date/other infos into it. +*.manifest +*.spec + +# Installer logs +pip-log.txt +pip-delete-this-directory.txt + +# Unit test / coverage reports +htmlcov/ +.tox/ +.nox/ +.coverage +.coverage.* +.cache +nosetests.xml +coverage.xml +*.cover +*.py,cover +.hypothesis/ +.pytest_cache/ +cover/ + +# Translations +*.mo +*.pot + +# Django stuff: +*.log +local_settings.py +db.sqlite3 +db.sqlite3-journal + +# Flask stuff: +instance/ +.webassets-cache + +# Scrapy stuff: +.scrapy + +# Sphinx documentation +docs/_build/ + +# PyBuilder +.pybuilder/ +target/ + +# Jupyter Notebook +.ipynb_checkpoints + +# IPython +profile_default/ +ipython_config.py + +# pyenv +# For a library or package, you might want to ignore these files since the code is +# intended to run in multiple environments; otherwise, check them in: +.python-version + +# pipenv +# According to pypa/pipenv#598, it is recommended to include Pipfile.lock in version control. +# However, in case of collaboration, if having platform-specific dependencies or dependencies +# having no cross-platform support, pipenv may install dependencies that don't work, or not +# install all needed dependencies. +#Pipfile.lock + +# poetry +# Similar to Pipfile.lock, it is generally recommended to include poetry.lock in version control. +# This is especially recommended for binary packages to ensure reproducibility, and is more +# commonly ignored for libraries. +# https://python-poetry.org/docs/basic-usage/#commit-your-poetrylock-file-to-version-control +#poetry.lock + +# pdm +# Similar to Pipfile.lock, it is generally recommended to include pdm.lock in version control. +#pdm.lock +# pdm stores project-wide configurations in .pdm.toml, but it is recommended to not include it +# in version control. +# https://pdm.fming.dev/#use-with-ide +.pdm.toml + +# PEP 582; used by e.g. github.com/David-OConnor/pyflow and github.com/pdm-project/pdm +__pypackages__/ + +# Celery stuff +celerybeat-schedule +celerybeat.pid + +# SageMath parsed files +*.sage.py + +# Environments +.env +.venv +env/ +venv/ +ENV/ +env.bak/ +venv.bak/ + +# Spyder project settings +.spyderproject +.spyproject + +# Rope project settings +.ropeproject + +# mkdocs documentation +/site + +# mypy +.mypy_cache/ +.dmypy.json +dmypy.json + +# Pyre type checker +.pyre/ + +# pytype static type analyzer +.pytype/ + +# Cython debug symbols +cython_debug/ + +# PyCharm +# JetBrains specific template is maintained in a separate JetBrains.gitignore that can +# be found at https://github.com/github/gitignore/blob/main/Global/JetBrains.gitignore +# and can be added to the global gitignore or merged into this file. For a more nuclear +# option (not recommended) you can uncomment the following to ignore the entire idea folder. +#.idea/ + +# VSC +.vscode \ No newline at end of file diff --git a/.python-version b/.python-version deleted file mode 100644 index d2c96c0a..00000000 --- a/.python-version +++ /dev/null @@ -1 +0,0 @@ -3.11.3 From 3fc7479dcf47d5d58a589a7aa938c9eec56efc7f Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Fri, 30 Jun 2023 18:53:56 -0700 Subject: [PATCH 112/184] [skip ci] Upload prod docker compose + update gitignore --- .gitignore | 13 +++++++++++-- Bot/unloaded_cogs/embeds.py | 27 ++++++++++++++++++++++++--- docker-compose.yml | 25 +++++++++++++++++++++++++ 3 files changed, 60 insertions(+), 5 deletions(-) create mode 100644 docker-compose.yml diff --git a/.gitignore b/.gitignore index dcad195d..cac5caf9 100644 --- a/.gitignore +++ b/.gitignore @@ -157,7 +157,16 @@ cython_debug/ # be found at https://github.com/github/gitignore/blob/main/Global/JetBrains.gitignore # and can be added to the global gitignore or merged into this file. For a more nuclear # option (not recommended) you can uncomment the following to ignore the entire idea folder. -#.idea/ +.idea/ + +# Vagrant project cache files +.vagrant # VSC -.vscode \ No newline at end of file +.vscode/ + +# Cache files +.dccache + +# Testing scripts +test-scripts/ \ No newline at end of file diff --git a/Bot/unloaded_cogs/embeds.py b/Bot/unloaded_cogs/embeds.py index 15da7acc..ccd048cd 100644 --- a/Bot/unloaded_cogs/embeds.py +++ b/Bot/unloaded_cogs/embeds.py @@ -1,21 +1,42 @@ -from Libs.utils import Embed -from discord.ext import commands -from kumikocore import KumikoCore import logging + +import discord +from discord.ext import commands from discord.utils import utcnow +from kumikocore import KumikoCore +from Libs.utils import Embed + + class EmbedCog(commands.Cog): """Embed test cog - Please only sync locally""" + def __init__(self, bot: KumikoCore) -> None: self.bot = bot self.logger = logging.getLogger("discord") @commands.hybrid_command(name="embed-time") async def embedTime(self, ctx: commands.Context) -> None: + # await self.bot.change_presence(status=discord.Status.online, activity=discord.Activity(type=discord.ActivityType.watching, name="you")) + await self.bot.change_presence( + status=discord.Status.idle, + activity=discord.Activity(type=discord.ActivityType.watching, name="you"), + ) + # await ctx.send("set status to idle") embed = Embed() embed.timestamp = utcnow() self.logger.info(f"Timestamp: {embed.timestamp}") embed.set_footer(text=f"{embed.timestamp}") await ctx.send(embed=embed) + @commands.hybrid_command(name="embed-user") + async def embedUser(self, ctx: commands.Context) -> None: + + await self.bot.change_presence( + status=discord.Status.idle, + activity=discord.Activity(type=discord.ActivityType.watching, name="you"), + ) + await ctx.send("set status to idle") + + async def setup(bot: KumikoCore) -> None: await bot.add_cog(EmbedCog(bot)) diff --git a/docker-compose.yml b/docker-compose.yml new file mode 100644 index 00000000..21b7ccfd --- /dev/null +++ b/docker-compose.yml @@ -0,0 +1,25 @@ +# This docker compose file is actually not used by Kumiko, since Kumiko relies on the db and other stuff via a seperate server +# This is just for example +# MAKE SURE TO CHANGE THE VALUES FOR KUMIKO + +version: "3.9" +name: "kumiko" +services: + postgres: + container_name: Kumiko-Postgres + image: postgres:15 + env_file: + - .env + volumes: + - postgres_volume:/var/lib/postgresql/data + ports: + - 5432:5432 + + redis: + container_name: Kumiko-Redis + image: redis/redis-stack-server:latest + ports: + - 6379:6379 + +volumes: + postgres_volume: \ No newline at end of file From 555fca4cac655699d956c305998a51c37558aef4 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Sun, 2 Jul 2023 00:53:56 -0700 Subject: [PATCH 113/184] Add custom prefix support --- Bot/Cogs/prefix.py | 45 ++++++++++++ Bot/Libs/utils/__init__.py | 6 +- Bot/Libs/utils/prefix.py | 29 ++++++++ Bot/kumikocore.py | 52 ++++++++----- Migrations/20230612_initial_up_rev1.sql | 8 +- migrations-runner.py | 8 +- poetry.lock | 98 ++++++++++++++++++++++++- pyproject.toml | 1 + 8 files changed, 217 insertions(+), 30 deletions(-) create mode 100644 Bot/Cogs/prefix.py create mode 100644 Bot/Libs/utils/prefix.py diff --git a/Bot/Cogs/prefix.py b/Bot/Cogs/prefix.py new file mode 100644 index 00000000..ab21dafa --- /dev/null +++ b/Bot/Cogs/prefix.py @@ -0,0 +1,45 @@ +from discord import app_commands +from discord.ext import commands +from kumikocore import KumikoCore + + +# TODO - Straight up slap an GIN index on the prefixes column +# TODO - Add a bunch more commands (add, delete, update, etc) +class Prefixes(commands.Cog): + """Kumiko's custom prefix manager! Set a custom prefix for your server!""" + + def __init__(self, bot: KumikoCore) -> None: + self.bot = bot + self.pool = self.bot.pool + + @commands.hybrid_group(name="prefixes") + async def prefixes(self, ctx: commands.Context) -> None: + """Base parent command for Prefixes - See the subcommands for more info""" + if ctx.invoked_subcommand is None: + await ctx.send_help(ctx.command) + + # TODO - Make sure that the prefixes is a list, not just one str + @prefixes.command(name="update") + @app_commands.describe(prefix="The new prefix to use") + async def updatePrefixes(self, ctx: commands.Context, prefix: str) -> None: + """Updates the prefix for your server + + Args: + ctx (commands.Context): Base context + """ + query = """ + UPDATE guild + SET column = $1 + WHERE id = $2; + """ + if ctx.guild is None: + await ctx.send("You can't set a prefix in DMs!") + return + async with self.pool.acquire() as conn: + await conn.execute(query, prefix, ctx.guild.id) + self.bot.prefixes[ctx.guild.id] = prefix + await ctx.send(f"Prefix updated to `{prefix}`") + + +async def setup(bot: KumikoCore) -> None: + await bot.add_cog(Prefixes(bot)) diff --git a/Bot/Libs/utils/__init__.py b/Bot/Libs/utils/__init__.py index c048a420..622f02e3 100644 --- a/Bot/Libs/utils/__init__.py +++ b/Bot/Libs/utils/__init__.py @@ -1,8 +1,9 @@ from .backoff import backoff from .embeds import Embed, ErrorEmbed from .greedy_formatter import formatGreedy -from .utils import encodeDatetime, parseDatetime, parseSubreddit, parseTimeStr from .kumiko_logger import KumikoLogger +from .prefix import get_prefix +from .utils import encodeDatetime, parseDatetime, parseSubreddit, parseTimeStr __all__ = [ "backoff", @@ -13,5 +14,6 @@ "parseSubreddit", "parseTimeStr", "formatGreedy", - "KumikoLogger" + "KumikoLogger", + "get_prefix", ] diff --git a/Bot/Libs/utils/prefix.py b/Bot/Libs/utils/prefix.py new file mode 100644 index 00000000..536d13d5 --- /dev/null +++ b/Bot/Libs/utils/prefix.py @@ -0,0 +1,29 @@ +import discord +from discord.ext import commands +from kumikocore import KumikoCore + + +async def get_prefix(bot: KumikoCore, msg: discord.Message): + if msg.guild is None: + return commands.when_mentioned_or(bot.default_prefix)(bot, msg) + try: + return commands.when_mentioned_or(bot.prefixes[msg.guild.id])(bot, msg) + except KeyError: + # if not in the LRU cache + async with bot.pool.acquire() as conn: + query = """ + SELECT prefix FROM guilds WHERE id = $1; + """ + updateQuery = """ + UPDATE guild + SET column = $1 + WHERE id = $2; + """ + fetchPrefix = await conn.fetchval(query, msg.guild.id) + if fetchPrefix: + bot.prefixes[msg.guild.id] = fetchPrefix + return commands.when_mentioned_or(bot.prefixes[msg.guild.id])(bot, msg) + else: + await conn.execute(updateQuery, bot.default_prefix, msg.guild.id) + bot.prefixes[msg.guild.id] = bot.default_prefix + return commands.when_mentioned_or(bot.prefixes[msg.guild.id])(bot, msg) diff --git a/Bot/kumikocore.py b/Bot/kumikocore.py index ef5c1a31..a9048fc9 100644 --- a/Bot/kumikocore.py +++ b/Bot/kumikocore.py @@ -1,14 +1,16 @@ import logging from pathlib import Path as SyncPath +import asyncpg import discord from aiohttp import ClientSession from anyio import Path from discord.ext import commands +from Libs.utils import get_prefix from Libs.utils.help import KumikoHelpPaginated -from Libs.utils.redis import ensureOpenRedisConn from Libs.utils.postgresql import ensureOpenPostgresConn -import asyncpg +from Libs.utils.redis import ensureOpenRedisConn +from lru import LRU # Some weird import logic to ensure that watchfiles is there _fsw = True @@ -26,21 +28,25 @@ def __init__( intents: discord.Intents, session: ClientSession, pool: asyncpg.Pool, + lru_size: int = 50, dev_mode: bool = False, *args, **kwargs, ): super().__init__( intents=intents, - command_prefix=commands.when_mentioned_or(">"), + command_prefix=get_prefix, help_command=KumikoHelpPaginated(), activity=discord.Activity(type=discord.ActivityType.watching, name="/help"), *args, **kwargs, ) self.dev_mode = dev_mode + self.lru_size = lru_size self._session = session self._pool = pool + self._prefixes: LRU = LRU(self.lru_size) + self.default_prefix = ">" self.logger: logging.Logger = logging.getLogger("kumikobot") @property @@ -55,13 +61,35 @@ def session(self) -> ClientSession: @property def pool(self) -> asyncpg.Pool: """A global object managed throughout the lifetime of Kumiko - - Holds the asyncpg + + Holds the asyncpg Returns: asyncpg.Pool: asyncpg connection pool """ return self._pool + + # It is preffered in this case to keep an LRU cache instead of a regular Dict cache + # For example, if an running instance keeps 100 entries ({guild_id: prefix}) + # then this would take up too much memory. + # + # By instead using an LRU cache, if we reach the max, then we evict the prefix from the guild that hasn't used it in a while + # The limit for the LRU cache is set to 100 + # + # The primary goal of Kumiko is to keep the footprint of the RAM usage as low as possible + # We don't need to have the bot consuming 250-300MB of RAM like when Prisma was used. + @property + def prefixes(self) -> LRU: + """A LRU cache of the guild prefixes + + The LRU cache's implementation is built in C, + so we natively can keep the performance the same as if it was a regular dict + + Returns: + LRU: LRU cache of the guild prefixes + """ + return self._prefixes + async def fsWatcher(self) -> None: cogsPath = SyncPath(__file__).parent.joinpath("Cogs") async for changes in awatch(cogsPath): @@ -74,20 +102,8 @@ async def fsWatcher(self) -> None: async def setup_hook(self) -> None: cogsPath = Path(__file__).parent.joinpath("Cogs") async for cog in cogsPath.rglob("**/*.py"): - self.logger.debug( - f"Loaded extension: {cog.parent.name}.{cog.name[:-3]}" - ) + self.logger.debug(f"Loaded extension: {cog.parent.name}.{cog.name[:-3]}") await self.load_extension(f"{cog.parent.name}.{cog.name[:-3]}") - # if cog.parent.name == "Cogs": - # self.logger.debug( - # f"Loaded extension: {cog.parent.name}.{cog.name[:-3]}" - # ) - # await self.load_extension(f"{cog.parent.name}.{cog.name[:-3]}") - # else: - # self.logger.debug( - # f"Loaded extension: Cogs.{cog.parent.name}.{cog.name[:-3]}" - # ) - # await self.load_extension(f"Cogs.{cog.parent.name}.{cog.name[:-3]}") self.loop.create_task(ensureOpenPostgresConn(self._pool)) self.loop.create_task(ensureOpenRedisConn()) diff --git a/Migrations/20230612_initial_up_rev1.sql b/Migrations/20230612_initial_up_rev1.sql index 31db8aca..e38e8383 100644 --- a/Migrations/20230612_initial_up_rev1.sql +++ b/Migrations/20230612_initial_up_rev1.sql @@ -18,8 +18,8 @@ CREATE TABLE IF NOT EXISTS eco_user ( CREATE TABLE IF NOT EXISTS eco_item ( id SERIAL PRIMARY KEY, - user_id BIGINT NOT NULL, - name VARCHAR(255) NOT NULL, + user_id BIGINT, + name VARCHAR(255), description TEXT, price INT DEFAULT 0, amount INT DEFAULT 0, @@ -28,8 +28,8 @@ CREATE TABLE IF NOT EXISTS eco_item ( CREATE TABLE IF NOT EXISTS marketplace ( id SERIAL PRIMARY KEY, - guild_id BIGINT NOT NULL, - name VARCHAR(255) NOT NULL, + guild_id BIGINT, + name VARCHAR(255), description TEXT, date_created timestamp WITHOUT TIME ZONE DEFAULT CURRENT_TIMESTAMP NOT NULL, CONSTRAINT fk_guild FOREIGN KEY (guild_id) REFERENCES guild (id) ON DELETE CASCADE diff --git a/migrations-runner.py b/migrations-runner.py index e30d52ad..f6c2b62b 100644 --- a/migrations-runner.py +++ b/migrations-runner.py @@ -37,10 +37,10 @@ async def migrate( async def main(): - async with asyncpg.create_pool(POSTGRES_URI) as pool: - async with pool.acquire() as conn: - await migrate(conn, TARGET_REVISION) + conn = await asyncpg.connect(dsn=POSTGRES_URI) + await migrate(conn, TARGET_REVISION) + await conn.close() if __name__ == "__main__": - asyncio.run(main()) \ No newline at end of file + asyncio.run(main()) diff --git a/poetry.lock b/poetry.lock index 09d55212..c78d3638 100644 --- a/poetry.lock +++ b/poetry.lock @@ -1,4 +1,4 @@ -# This file is automatically @generated by Poetry 1.5.1 and should not be changed by hand. +# This file is automatically @generated by Poetry 1.5.0 and should not be changed by hand. [[package]] name = "aiodns" @@ -1771,6 +1771,100 @@ files = [ six = "*" tornado = {version = "*", markers = "python_version > \"2.7\""} +[[package]] +name = "lru-dict" +version = "1.2.0" +description = "An Dict like LRU container." +optional = false +python-versions = "*" +files = [ + {file = "lru-dict-1.2.0.tar.gz", hash = "sha256:13c56782f19d68ddf4d8db0170041192859616514c706b126d0df2ec72a11bd7"}, + {file = "lru_dict-1.2.0-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:de906e5486b5c053d15b7731583c25e3c9147c288ac8152a6d1f9bccdec72641"}, + {file = "lru_dict-1.2.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:604d07c7604b20b3130405d137cae61579578b0e8377daae4125098feebcb970"}, + {file = "lru_dict-1.2.0-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:203b3e78d03d88f491fa134f85a42919020686b6e6f2d09759b2f5517260c651"}, + {file = "lru_dict-1.2.0-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:020b93870f8c7195774cbd94f033b96c14f51c57537969965c3af300331724fe"}, + {file = "lru_dict-1.2.0-cp310-cp310-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:1184d91cfebd5d1e659d47f17a60185bbf621635ca56dcdc46c6a1745d25df5c"}, + {file = "lru_dict-1.2.0-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:fc42882b554a86e564e0b662da47b8a4b32fa966920bd165e27bb8079a323bc1"}, + {file = "lru_dict-1.2.0-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:18ee88ada65bd2ffd483023be0fa1c0a6a051ef666d1cd89e921dcce134149f2"}, + {file = "lru_dict-1.2.0-cp310-cp310-musllinux_1_1_ppc64le.whl", hash = "sha256:756230c22257597b7557eaef7f90484c489e9ba78e5bb6ab5a5bcfb6b03cb075"}, + {file = "lru_dict-1.2.0-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:c4da599af36618881748b5db457d937955bb2b4800db891647d46767d636c408"}, + {file = "lru_dict-1.2.0-cp310-cp310-win32.whl", hash = "sha256:35a142a7d1a4fd5d5799cc4f8ab2fff50a598d8cee1d1c611f50722b3e27874f"}, + {file = "lru_dict-1.2.0-cp310-cp310-win_amd64.whl", hash = "sha256:6da5b8099766c4da3bf1ed6e7d7f5eff1681aff6b5987d1258a13bd2ed54f0c9"}, + {file = "lru_dict-1.2.0-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:b20b7c9beb481e92e07368ebfaa363ed7ef61e65ffe6e0edbdbaceb33e134124"}, + {file = "lru_dict-1.2.0-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:22147367b296be31cc858bf167c448af02435cac44806b228c9be8117f1bfce4"}, + {file = "lru_dict-1.2.0-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:34a3091abeb95e707f381a8b5b7dc8e4ee016316c659c49b726857b0d6d1bd7a"}, + {file = "lru_dict-1.2.0-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:877801a20f05c467126b55338a4e9fa30e2a141eb7b0b740794571b7d619ee11"}, + {file = "lru_dict-1.2.0-cp311-cp311-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:7d3336e901acec897bcd318c42c2b93d5f1d038e67688f497045fc6bad2c0be7"}, + {file = "lru_dict-1.2.0-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:8dafc481d2defb381f19b22cc51837e8a42631e98e34b9e0892245cc96593deb"}, + {file = "lru_dict-1.2.0-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:87bbad3f5c3de8897b8c1263a9af73bbb6469fb90e7b57225dad89b8ef62cd8d"}, + {file = "lru_dict-1.2.0-cp311-cp311-musllinux_1_1_ppc64le.whl", hash = "sha256:25f9e0bc2fe8f41c2711ccefd2871f8a5f50a39e6293b68c3dec576112937aad"}, + {file = "lru_dict-1.2.0-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:ae301c282a499dc1968dd633cfef8771dd84228ae9d40002a3ea990e4ff0c469"}, + {file = "lru_dict-1.2.0-cp311-cp311-win32.whl", hash = "sha256:c9617583173a29048e11397f165501edc5ae223504a404b2532a212a71ecc9ed"}, + {file = "lru_dict-1.2.0-cp311-cp311-win_amd64.whl", hash = "sha256:6b7a031e47421d4b7aa626b8c91c180a9f037f89e5d0a71c4bb7afcf4036c774"}, + {file = "lru_dict-1.2.0-cp36-cp36m-macosx_10_9_x86_64.whl", hash = "sha256:ea2ac3f7a7a2f32f194c84d82a034e66780057fd908b421becd2f173504d040e"}, + {file = "lru_dict-1.2.0-cp36-cp36m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:cd46c94966f631a81ffe33eee928db58e9fbee15baba5923d284aeadc0e0fa76"}, + {file = "lru_dict-1.2.0-cp36-cp36m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:086ce993414f0b28530ded7e004c77dc57c5748fa6da488602aa6e7f79e6210e"}, + {file = "lru_dict-1.2.0-cp36-cp36m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:df25a426446197488a6702954dcc1de511deee20c9db730499a2aa83fddf0df1"}, + {file = "lru_dict-1.2.0-cp36-cp36m-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:c53b12b89bd7a6c79f0536ff0d0a84fdf4ab5f6252d94b24b9b753bd9ada2ddf"}, + {file = "lru_dict-1.2.0-cp36-cp36m-musllinux_1_1_aarch64.whl", hash = "sha256:f9484016e6765bd295708cccc9def49f708ce07ac003808f69efa386633affb9"}, + {file = "lru_dict-1.2.0-cp36-cp36m-musllinux_1_1_i686.whl", hash = "sha256:d0f7ec902a0097ac39f1922c89be9eaccf00eb87751e28915320b4f72912d057"}, + {file = "lru_dict-1.2.0-cp36-cp36m-musllinux_1_1_ppc64le.whl", hash = "sha256:981ef3edc82da38d39eb60eae225b88a538d47b90cce2e5808846fd2cf64384b"}, + {file = "lru_dict-1.2.0-cp36-cp36m-musllinux_1_1_x86_64.whl", hash = "sha256:e25b2e90a032dc248213af7f3f3e975e1934b204f3b16aeeaeaff27a3b65e128"}, + {file = "lru_dict-1.2.0-cp36-cp36m-win32.whl", hash = "sha256:59f3df78e94e07959f17764e7fa7ca6b54e9296953d2626a112eab08e1beb2db"}, + {file = "lru_dict-1.2.0-cp36-cp36m-win_amd64.whl", hash = "sha256:de24b47159e07833aeab517d9cb1c3c5c2d6445cc378b1c2f1d8d15fb4841d63"}, + {file = "lru_dict-1.2.0-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:d0dd4cd58220351233002f910e35cc01d30337696b55c6578f71318b137770f9"}, + {file = "lru_dict-1.2.0-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:a87bdc291718bbdf9ea4be12ae7af26cbf0706fa62c2ac332748e3116c5510a7"}, + {file = "lru_dict-1.2.0-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:05fb8744f91f58479cbe07ed80ada6696ec7df21ea1740891d4107a8dd99a970"}, + {file = "lru_dict-1.2.0-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:00f6e8a3fc91481b40395316a14c94daa0f0a5de62e7e01a7d589f8d29224052"}, + {file = "lru_dict-1.2.0-cp37-cp37m-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5b172fce0a0ffc0fa6d282c14256d5a68b5db1e64719c2915e69084c4b6bf555"}, + {file = "lru_dict-1.2.0-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:e707d93bae8f0a14e6df1ae8b0f076532b35f00e691995f33132d806a88e5c18"}, + {file = "lru_dict-1.2.0-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:b9ec7a4a0d6b8297102aa56758434fb1fca276a82ed7362e37817407185c3abb"}, + {file = "lru_dict-1.2.0-cp37-cp37m-musllinux_1_1_ppc64le.whl", hash = "sha256:f404dcc8172da1f28da9b1f0087009578e608a4899b96d244925c4f463201f2a"}, + {file = "lru_dict-1.2.0-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:1171ad3bff32aa8086778be4a3bdff595cc2692e78685bcce9cb06b96b22dcc2"}, + {file = "lru_dict-1.2.0-cp37-cp37m-win32.whl", hash = "sha256:0c316dfa3897fabaa1fe08aae89352a3b109e5f88b25529bc01e98ac029bf878"}, + {file = "lru_dict-1.2.0-cp37-cp37m-win_amd64.whl", hash = "sha256:5919dd04446bc1ee8d6ecda2187deeebfff5903538ae71083e069bc678599446"}, + {file = "lru_dict-1.2.0-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:fbf36c5a220a85187cacc1fcb7dd87070e04b5fc28df7a43f6842f7c8224a388"}, + {file = "lru_dict-1.2.0-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:712e71b64da181e1c0a2eaa76cd860265980cd15cb0e0498602b8aa35d5db9f8"}, + {file = "lru_dict-1.2.0-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:f54908bf91280a9b8fa6a8c8f3c2f65850ce6acae2852bbe292391628ebca42f"}, + {file = "lru_dict-1.2.0-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:3838e33710935da2ade1dd404a8b936d571e29268a70ff4ca5ba758abb3850df"}, + {file = "lru_dict-1.2.0-cp38-cp38-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f5d5a5f976b39af73324f2b793862859902ccb9542621856d51a5993064f25e4"}, + {file = "lru_dict-1.2.0-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:8bda3a9afd241ee0181661decaae25e5336ce513ac268ab57da737eacaa7871f"}, + {file = "lru_dict-1.2.0-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:bd2cd1b998ea4c8c1dad829fc4fa88aeed4dee555b5e03c132fc618e6123f168"}, + {file = "lru_dict-1.2.0-cp38-cp38-musllinux_1_1_ppc64le.whl", hash = "sha256:b55753ee23028ba8644fd22e50de7b8f85fa60b562a0fafaad788701d6131ff8"}, + {file = "lru_dict-1.2.0-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:7e51fa6a203fa91d415f3b2900e5748ec8e06ad75777c98cc3aeb3983ca416d7"}, + {file = "lru_dict-1.2.0-cp38-cp38-win32.whl", hash = "sha256:cd6806313606559e6c7adfa0dbeb30fc5ab625f00958c3d93f84831e7a32b71e"}, + {file = "lru_dict-1.2.0-cp38-cp38-win_amd64.whl", hash = "sha256:5d90a70c53b0566084447c3ef9374cc5a9be886e867b36f89495f211baabd322"}, + {file = "lru_dict-1.2.0-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:a3ea7571b6bf2090a85ff037e6593bbafe1a8598d5c3b4560eb56187bcccb4dc"}, + {file = "lru_dict-1.2.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:287c2115a59c1c9ed0d5d8ae7671e594b1206c36ea9df2fca6b17b86c468ff99"}, + {file = "lru_dict-1.2.0-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:b5ccfd2291c93746a286c87c3f895165b697399969d24c54804ec3ec559d4e43"}, + {file = "lru_dict-1.2.0-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:b710f0f4d7ec4f9fa89dfde7002f80bcd77de8024017e70706b0911ea086e2ef"}, + {file = "lru_dict-1.2.0-cp39-cp39-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5345bf50e127bd2767e9fd42393635bbc0146eac01f6baf6ef12c332d1a6a329"}, + {file = "lru_dict-1.2.0-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:291d13f85224551913a78fe695cde04cbca9dcb1d84c540167c443eb913603c9"}, + {file = "lru_dict-1.2.0-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:d5bb41bc74b321789803d45b124fc2145c1b3353b4ad43296d9d1d242574969b"}, + {file = "lru_dict-1.2.0-cp39-cp39-musllinux_1_1_ppc64le.whl", hash = "sha256:0facf49b053bf4926d92d8d5a46fe07eecd2af0441add0182c7432d53d6da667"}, + {file = "lru_dict-1.2.0-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:987b73a06bcf5a95d7dc296241c6b1f9bc6cda42586948c9dabf386dc2bef1cd"}, + {file = "lru_dict-1.2.0-cp39-cp39-win32.whl", hash = "sha256:231d7608f029dda42f9610e5723614a35b1fff035a8060cf7d2be19f1711ace8"}, + {file = "lru_dict-1.2.0-cp39-cp39-win_amd64.whl", hash = "sha256:71da89e134747e20ed5b8ad5b4ee93fc5b31022c2b71e8176e73c5a44699061b"}, + {file = "lru_dict-1.2.0-pp37-pypy37_pp73-macosx_10_9_x86_64.whl", hash = "sha256:21b3090928c7b6cec509e755cc3ab742154b33660a9b433923bd12c37c448e3e"}, + {file = "lru_dict-1.2.0-pp37-pypy37_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:aaecd7085212d0aa4cd855f38b9d61803d6509731138bf798a9594745953245b"}, + {file = "lru_dict-1.2.0-pp37-pypy37_pp73-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:ead83ac59a29d6439ddff46e205ce32f8b7f71a6bd8062347f77e232825e3d0a"}, + {file = "lru_dict-1.2.0-pp37-pypy37_pp73-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:312b6b2a30188586fe71358f0f33e4bac882d33f5e5019b26f084363f42f986f"}, + {file = "lru_dict-1.2.0-pp37-pypy37_pp73-win_amd64.whl", hash = "sha256:b30122e098c80e36d0117810d46459a46313421ce3298709170b687dc1240b02"}, + {file = "lru_dict-1.2.0-pp38-pypy38_pp73-macosx_10_9_x86_64.whl", hash = "sha256:f010cfad3ab10676e44dc72a813c968cd586f37b466d27cde73d1f7f1ba158c2"}, + {file = "lru_dict-1.2.0-pp38-pypy38_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:20f5f411f7751ad9a2c02e80287cedf69ae032edd321fe696e310d32dd30a1f8"}, + {file = "lru_dict-1.2.0-pp38-pypy38_pp73-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:afdadd73304c9befaed02eb42f5f09fdc16288de0a08b32b8080f0f0f6350aa6"}, + {file = "lru_dict-1.2.0-pp38-pypy38_pp73-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:d7ab0c10c4fa99dc9e26b04e6b62ac32d2bcaea3aad9b81ec8ce9a7aa32b7b1b"}, + {file = "lru_dict-1.2.0-pp38-pypy38_pp73-win_amd64.whl", hash = "sha256:edad398d5d402c43d2adada390dd83c74e46e020945ff4df801166047013617e"}, + {file = "lru_dict-1.2.0-pp39-pypy39_pp73-macosx_10_9_x86_64.whl", hash = "sha256:91d577a11b84387013815b1ad0bb6e604558d646003b44c92b3ddf886ad0f879"}, + {file = "lru_dict-1.2.0-pp39-pypy39_pp73-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:bb12f19cdf9c4f2d9aa259562e19b188ff34afab28dd9509ff32a3f1c2c29326"}, + {file = "lru_dict-1.2.0-pp39-pypy39_pp73-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:9e4c85aa8844bdca3c8abac3b7f78da1531c74e9f8b3e4890c6e6d86a5a3f6c0"}, + {file = "lru_dict-1.2.0-pp39-pypy39_pp73-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5c6acbd097b15bead4de8e83e8a1030bb4d8257723669097eac643a301a952f0"}, + {file = "lru_dict-1.2.0-pp39-pypy39_pp73-win_amd64.whl", hash = "sha256:b6613daa851745dd22b860651de930275be9d3e9373283a2164992abacb75b62"}, +] + +[package.extras] +test = ["pytest"] + [[package]] name = "markdown-it-py" version = "3.0.0" @@ -3456,4 +3550,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "66b92ac81e5083c8b13956b6860b0ea390e008110036d9091a6948ae5f349351" +content-hash = "54d9a344c37971fe437d4e6f4b23712bc7845ce5308289c25f2fb39734367127" diff --git a/pyproject.toml b/pyproject.toml index ad5b19b7..3dac8086 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -23,6 +23,7 @@ discord-py = {extras = ["voice"], version = "^2.3.1"} discord-ext-menus = {git = "https://github.com/Rapptz/discord-ext-menus", rev = "8686b5d1bbc1d3c862292eb436ab630d6e9c9b53"} asyncpg = "^0.27.0" asyncpg-trek = "^0.3.1" +lru-dict = "^1.2.0" [tool.poetry.group.test.dependencies] pytest = "^7.4.0" From 31c4a0756c89153d8566015b0efe1c5607f9056c Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Sun, 2 Jul 2023 01:00:16 -0700 Subject: [PATCH 114/184] Fix cirular imports issue --- Bot/Libs/utils/prefix.py | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/Bot/Libs/utils/prefix.py b/Bot/Libs/utils/prefix.py index 536d13d5..71d44e75 100644 --- a/Bot/Libs/utils/prefix.py +++ b/Bot/Libs/utils/prefix.py @@ -1,9 +1,10 @@ import discord from discord.ext import commands -from kumikocore import KumikoCore -async def get_prefix(bot: KumikoCore, msg: discord.Message): +# removed the type hinting bc of circular imports +# if there is a way to solve it, then it would be back +async def get_prefix(bot, msg: discord.Message): if msg.guild is None: return commands.when_mentioned_or(bot.default_prefix)(bot, msg) try: @@ -12,7 +13,7 @@ async def get_prefix(bot: KumikoCore, msg: discord.Message): # if not in the LRU cache async with bot.pool.acquire() as conn: query = """ - SELECT prefix FROM guilds WHERE id = $1; + SELECT prefix FROM guild WHERE id = $1; """ updateQuery = """ UPDATE guild From 0565f904364b62ad949ea36e633a117a6a489121 Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Sun, 2 Jul 2023 02:32:10 -0700 Subject: [PATCH 115/184] Fix prefix module + create lookup tables The lookup tables have indexes on them to help with performance. This idea was ported from Akari, which in turn was borrowed from RoboDanny. In this case, we have indexed the names of the items in the economy. There is no need for a marketplace table, so we can remove that later --- Bot/Cogs/prefix.py | 90 ++++++++++++------------- Bot/Libs/utils/prefix.py | 60 ++++++++--------- Migrations/20230612_initial_up_rev1.sql | 7 +- Migrations/20230702_rev1_up_rev2.sql | 24 +++++++ README.md | 2 + 5 files changed, 105 insertions(+), 78 deletions(-) create mode 100644 Migrations/20230702_rev1_up_rev2.sql diff --git a/Bot/Cogs/prefix.py b/Bot/Cogs/prefix.py index ab21dafa..6ee346ac 100644 --- a/Bot/Cogs/prefix.py +++ b/Bot/Cogs/prefix.py @@ -1,45 +1,45 @@ -from discord import app_commands -from discord.ext import commands -from kumikocore import KumikoCore - - -# TODO - Straight up slap an GIN index on the prefixes column -# TODO - Add a bunch more commands (add, delete, update, etc) -class Prefixes(commands.Cog): - """Kumiko's custom prefix manager! Set a custom prefix for your server!""" - - def __init__(self, bot: KumikoCore) -> None: - self.bot = bot - self.pool = self.bot.pool - - @commands.hybrid_group(name="prefixes") - async def prefixes(self, ctx: commands.Context) -> None: - """Base parent command for Prefixes - See the subcommands for more info""" - if ctx.invoked_subcommand is None: - await ctx.send_help(ctx.command) - - # TODO - Make sure that the prefixes is a list, not just one str - @prefixes.command(name="update") - @app_commands.describe(prefix="The new prefix to use") - async def updatePrefixes(self, ctx: commands.Context, prefix: str) -> None: - """Updates the prefix for your server - - Args: - ctx (commands.Context): Base context - """ - query = """ - UPDATE guild - SET column = $1 - WHERE id = $2; - """ - if ctx.guild is None: - await ctx.send("You can't set a prefix in DMs!") - return - async with self.pool.acquire() as conn: - await conn.execute(query, prefix, ctx.guild.id) - self.bot.prefixes[ctx.guild.id] = prefix - await ctx.send(f"Prefix updated to `{prefix}`") - - -async def setup(bot: KumikoCore) -> None: - await bot.add_cog(Prefixes(bot)) +from discord import app_commands +from discord.ext import commands +from kumikocore import KumikoCore + + +# TODO - Straight up slap an GIN index on the prefixes column +# TODO - Add a bunch more commands (add, delete, update, etc) +class Prefixes(commands.Cog): + """Kumiko's custom prefix manager! Set a custom prefix for your server!""" + + def __init__(self, bot: KumikoCore) -> None: + self.bot = bot + self.pool = self.bot.pool + + @commands.hybrid_group(name="prefixes") + async def prefixes(self, ctx: commands.Context) -> None: + """Base parent command for Prefixes - See the subcommands for more info""" + if ctx.invoked_subcommand is None: + await ctx.send_help(ctx.command) + + # TODO - Make sure that the prefixes is a list, not just one str + @prefixes.command(name="update") + @app_commands.describe(prefix="The new prefix to use") + async def updatePrefixes(self, ctx: commands.Context, prefix: str) -> None: + """Updates the prefix for your server + + Args: + ctx (commands.Context): Base context + """ + query = """ + UPDATE guild + SET column = $1 + WHERE id = $2; + """ + if ctx.guild is None: + await ctx.send("You can't set a prefix in DMs!") + return + async with self.pool.acquire() as conn: + await conn.execute(query, prefix, ctx.guild.id) + self.bot.prefixes[ctx.guild.id] = prefix + await ctx.send(f"Prefix updated to `{prefix}`") + + +async def setup(bot: KumikoCore) -> None: + await bot.add_cog(Prefixes(bot)) diff --git a/Bot/Libs/utils/prefix.py b/Bot/Libs/utils/prefix.py index 71d44e75..f819e457 100644 --- a/Bot/Libs/utils/prefix.py +++ b/Bot/Libs/utils/prefix.py @@ -1,30 +1,30 @@ -import discord -from discord.ext import commands - - -# removed the type hinting bc of circular imports -# if there is a way to solve it, then it would be back -async def get_prefix(bot, msg: discord.Message): - if msg.guild is None: - return commands.when_mentioned_or(bot.default_prefix)(bot, msg) - try: - return commands.when_mentioned_or(bot.prefixes[msg.guild.id])(bot, msg) - except KeyError: - # if not in the LRU cache - async with bot.pool.acquire() as conn: - query = """ - SELECT prefix FROM guild WHERE id = $1; - """ - updateQuery = """ - UPDATE guild - SET column = $1 - WHERE id = $2; - """ - fetchPrefix = await conn.fetchval(query, msg.guild.id) - if fetchPrefix: - bot.prefixes[msg.guild.id] = fetchPrefix - return commands.when_mentioned_or(bot.prefixes[msg.guild.id])(bot, msg) - else: - await conn.execute(updateQuery, bot.default_prefix, msg.guild.id) - bot.prefixes[msg.guild.id] = bot.default_prefix - return commands.when_mentioned_or(bot.prefixes[msg.guild.id])(bot, msg) +import discord +from discord.ext import commands + +# TODO - Prevent people from setting up `/` prefixes. Doesn't help +# removed the type hinting bc of circular imports +# if there is a way to solve it, then it would be back +async def get_prefix(bot, msg: discord.Message): + if msg.guild is None: + return commands.when_mentioned_or(bot.default_prefix)(bot, msg) + cachedPrefix = bot.prefixes.get(msg.guild.id) + if cachedPrefix is None: + async with bot.pool.acquire() as conn: + query = """ + SELECT prefix FROM guild WHERE id = $1; + """ + updateQuery = """ + UPDATE guild + SET prefix = $1 + WHERE id = $2; + """ + fetchPrefix = await conn.fetchval(query, msg.guild.id) + if fetchPrefix: + bot.prefixes[msg.guild.id] = fetchPrefix + return commands.when_mentioned_or(bot.prefixes[msg.guild.id])(bot, msg) + else: + await conn.execute(updateQuery, [bot.default_prefix], msg.guild.id) + bot.prefixes[msg.guild.id] = bot.default_prefix + return commands.when_mentioned_or(bot.prefixes[msg.guild.id])(bot, msg) + else: + return commands.when_mentioned_or(bot.prefixes[msg.guild.id])(bot, msg) \ No newline at end of file diff --git a/Migrations/20230612_initial_up_rev1.sql b/Migrations/20230612_initial_up_rev1.sql index e38e8383..dad6a2ab 100644 --- a/Migrations/20230612_initial_up_rev1.sql +++ b/Migrations/20230612_initial_up_rev1.sql @@ -3,7 +3,7 @@ CREATE TABLE IF NOT EXISTS guild ( id BIGINT PRIMARY KEY, - prefix VARCHAR(255) NOT NULL, + prefix VARCHAR(255)[], logs BOOLEAN DEFAULT FALSE, birthday BOOLEAN DEFAULT FALSE, local_economy BOOLEAN DEFAULT FALSE @@ -13,12 +13,13 @@ CREATE TABLE IF NOT EXISTS eco_user ( id BIGINT PRIMARY KEY, rank INT DEFAULT 0, petals INT DEFAULT 0, - date_joined timestamp WITHOUT TIME ZONE DEFAULT CURRENT_TIMESTAMP NOT NULL + created_at timestamp WITHOUT TIME ZONE DEFAULT CURRENT_TIMESTAMP NOT NULL ); CREATE TABLE IF NOT EXISTS eco_item ( id SERIAL PRIMARY KEY, user_id BIGINT, + guild_id BIGINT, name VARCHAR(255), description TEXT, price INT DEFAULT 0, @@ -31,6 +32,6 @@ CREATE TABLE IF NOT EXISTS marketplace ( guild_id BIGINT, name VARCHAR(255), description TEXT, - date_created timestamp WITHOUT TIME ZONE DEFAULT CURRENT_TIMESTAMP NOT NULL, + created_at timestamp WITHOUT TIME ZONE DEFAULT CURRENT_TIMESTAMP NOT NULL, CONSTRAINT fk_guild FOREIGN KEY (guild_id) REFERENCES guild (id) ON DELETE CASCADE ); diff --git a/Migrations/20230702_rev1_up_rev2.sql b/Migrations/20230702_rev1_up_rev2.sql new file mode 100644 index 00000000..76ee244b --- /dev/null +++ b/Migrations/20230702_rev1_up_rev2.sql @@ -0,0 +1,24 @@ +ALTER TABLE eco_user ALTER COLUMN created_at SET DEFAULT (NOW() AT TIME ZONE 'utc'); +ALTER TABLE marketplace ALTER COLUMN created_at SET DEFAULT (NOW() AT TIME ZONE 'utc'); + +ALTER TABLE guild ALTER COLUMN prefix SET DATA TYPE VARCHAR(255)[]; + +CREATE TABLE IF NOT EXISTS eco_item_lookup ( + id SERIAL PRIMARY KEY, + name TEXT, + guild_id BIGINT, + owner_id BIGINT, + created_at TIMESTAMP DEFAULT (now() AT TIME ZONE 'utc'), + item_id INTEGER REFERENCES eco_item (id) ON DELETE CASCADE ON UPDATE NO ACTION +); + +CREATE INDEX IF NOT EXISTS eco_item_name_idx ON eco_item (name); +CREATE INDEX IF NOT EXISTS eco_item_name_trgm_idx ON eco_item USING GIN (name gin_trgm_ops); +CREATE INDEX IF NOT EXISTS eco_item_name_lower_idx ON eco_item (LOWER(name)); +CREATE UNIQUE INDEX IF NOT EXISTS eco_item_uniq_idx ON eco_item (LOWER(name), guild_id); + +CREATE INDEX IF NOT EXISTS eco_item_lookup_name_idx ON eco_item_lookup (name); +CREATE INDEX IF NOT EXISTS eco_item_lookup_location_id_idx ON eco_item_lookup (guild_id); +CREATE INDEX IF NOT EXISTS eco_item_lookup_name_trgm_idx ON eco_item_lookup USING GIN (name gin_trgm_ops); +CREATE INDEX IF NOT EXISTS eco_item_lookup_name_lower_idx ON eco_item_lookup (LOWER(name)); +CREATE UNIQUE INDEX IF NOT EXISTS eco_item_lookup_uniq_idx ON eco_item_lookup (LOWER(name), guild_id); \ No newline at end of file diff --git a/README.md b/README.md index d229ef20..8e609f9f 100644 --- a/README.md +++ b/README.md @@ -37,6 +37,8 @@ And some ones that are planned: Kumiko uses both a prefixed command and slash commands. The currently supported prefixes are `>` , and `/`. +`>` is the default prefix, but this can be customized to be any custom prefix that you wish to have. For example, if you wanted to, you could set the prefix to be `?` instead. These do not change the global prefix; only on the current server where you have set it up + ## Inviting the Bot Currently under beta stages. Not ready for release yet. Currently Kumiko is under v0, which means it's beta-level software as of now, and thus should not be used in production. Kumiko is subject to breaking changes within this version. Kumiko will be ready to be invited once it reaches to v1, which is production-ready software. From 0d691a2c7b7430abee2867c10bf99ab8d9c5c169 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Mon, 3 Jul 2023 03:27:41 -0700 Subject: [PATCH 116/184] Implement a working custom prefix module --- Bot/Cogs/error-handler.py | 13 ++- Bot/Cogs/prefix.py | 101 ++++++++++++++++++------ Bot/Libs/errors/__init__.py | 2 + Bot/Libs/errors/exceptions.py | 4 + Bot/Libs/ui/prefix/__init__.py | 3 + Bot/Libs/ui/prefix/views.py | 48 +++++++++++ Bot/Libs/utils/__init__.py | 14 +++- Bot/Libs/utils/embeds.py | 29 +++++++ Bot/Libs/utils/prefix.py | 40 ++++++++-- Migrations/20230612_initial_up_rev1.sql | 11 +-- Migrations/20230702_rev1_up_rev2.sql | 3 +- Migrations/20230702_rev2_up_rev3.sql | 1 + 12 files changed, 226 insertions(+), 43 deletions(-) create mode 100644 Bot/Libs/ui/prefix/__init__.py create mode 100644 Bot/Libs/ui/prefix/views.py create mode 100644 Migrations/20230702_rev2_up_rev3.sql diff --git a/Bot/Cogs/error-handler.py b/Bot/Cogs/error-handler.py index 58eea2d6..38fd0993 100644 --- a/Bot/Cogs/error-handler.py +++ b/Bot/Cogs/error-handler.py @@ -3,7 +3,13 @@ from discord.app_commands.errors import CommandInvokeError from discord.ext import commands from kumikocore import KumikoCore -from Libs.errors import HTTPError, KumikoException, NoItemsError, NotFoundError +from Libs.errors import ( + HTTPError, + KumikoException, + NoItemsError, + NotFoundError, + ValidationError, +) from Libs.utils import Embed, ErrorEmbed @@ -135,6 +141,11 @@ async def on_command_error( f"You are missing the following argument(s): {error.param.name}" ) await ctx.send(embed=errorEmbed) + elif isinstance(error, ValidationError): + errorEmbed = ErrorEmbed() + errorEmbed.title = "Validation Error" + errorEmbed.description = str(error) + await ctx.send(embed=errorEmbed) else: errorEmbed = ErrorEmbed() errorEmbed.add_field(name="Error", value=str(error), inline=False) diff --git a/Bot/Cogs/prefix.py b/Bot/Cogs/prefix.py index 6ee346ac..c6b7e371 100644 --- a/Bot/Cogs/prefix.py +++ b/Bot/Cogs/prefix.py @@ -1,45 +1,102 @@ from discord import app_commands from discord.ext import commands +from discord.utils import utcnow from kumikocore import KumikoCore +from Libs.errors import ValidationError +from Libs.ui.prefix import DeletePrefixView +from Libs.utils import ConfirmEmbed, Embed, get_prefix # TODO - Straight up slap an GIN index on the prefixes column -# TODO - Add a bunch more commands (add, delete, update, etc) -class Prefixes(commands.Cog): +class Prefix(commands.Cog): """Kumiko's custom prefix manager! Set a custom prefix for your server!""" def __init__(self, bot: KumikoCore) -> None: self.bot = bot self.pool = self.bot.pool - @commands.hybrid_group(name="prefixes") - async def prefixes(self, ctx: commands.Context) -> None: - """Base parent command for Prefixes - See the subcommands for more info""" + @commands.hybrid_group(name="prefix") + async def prefix(self, ctx: commands.Context) -> None: if ctx.invoked_subcommand is None: await ctx.send_help(ctx.command) - # TODO - Make sure that the prefixes is a list, not just one str - @prefixes.command(name="update") - @app_commands.describe(prefix="The new prefix to use") - async def updatePrefixes(self, ctx: commands.Context, prefix: str) -> None: - """Updates the prefix for your server - - Args: - ctx (commands.Context): Base context + @commands.has_guild_permissions(manage_guild=True) + @commands.guild_only() + @prefix.command(name="update") + @app_commands.describe( + old_prefix="The old prefix to replace", new_prefix="The new prefix to use" + ) + async def updatePrefixes( + self, ctx: commands.Context, old_prefix: str, new_prefix: str + ) -> None: + """Updates the prefix for your server""" + query = """ + UPDATE guild + SET prefix = ARRAY_REPLACE(prefix, $1, $2) + WHERE id = $3; """ + guild_id = ctx.guild.id # type: ignore + if old_prefix in self.bot.prefixes[guild_id]: + async with self.pool.acquire() as conn: + await conn.execute(query, old_prefix, new_prefix, guild_id) + prefixes = self.bot.prefixes[guild_id][ + : + ] # Shallow copy the list so we can safely perform operations on it + idxSearch = [ + idx for idx, item in enumerate(prefixes) if item == old_prefix + ] + prefixes[idxSearch[0]] = new_prefix + self.bot.prefixes[guild_id] = prefixes + await ctx.send(f"Prefix updated to `{new_prefix}`") + else: + await ctx.send("The prefix is not in the list of prefixes for your server") + + @commands.has_guild_permissions(manage_guild=True) + @commands.guild_only() + @prefix.command(name="add") + @app_commands.describe(prefix="The new prefix to add") + async def addPrefixes(self, ctx: commands.Context, prefix: str) -> None: + """Adds new prefixes into your server""" + prefixes = await get_prefix(self.bot, ctx.message) + # validatePrefix(self.bot.prefixes, prefix) is False + if len(prefixes) > 10: + desc = "There was an validation issue. This is because of two reasons:\n- You have more than 10 prefixes for your server\n- Your prefix fails the validation rules" + raise ValidationError(desc) + query = """ UPDATE guild - SET column = $1 - WHERE id = $2; + SET prefix = ARRAY_APPEND(prefix, $1) + WHERE id=$2; """ - if ctx.guild is None: - await ctx.send("You can't set a prefix in DMs!") - return async with self.pool.acquire() as conn: - await conn.execute(query, prefix, ctx.guild.id) - self.bot.prefixes[ctx.guild.id] = prefix - await ctx.send(f"Prefix updated to `{prefix}`") + guildId = ctx.guild.id # type: ignore # These are all done in an guild + await conn.execute(query, prefix, guildId) + self.bot.prefixes[guildId].append(prefix) + await ctx.send(f"Added prefix: {prefix}") + + @commands.guild_only() + @prefix.command(name="info") + async def infoPrefixes(self, ctx: commands.Context) -> None: + """Displays infos about the current prefix set on your server""" + prefixes = await get_prefix(self.bot, ctx.message) + cleanedPrefixes = ", ".join([f"`{item}`" for item in prefixes]).rstrip(",") + embed = Embed() + embed.description = f"**Current prefixes**\n{cleanedPrefixes}" + embed.timestamp = utcnow() + embed.set_author(name=ctx.guild.name, icon_url=ctx.guild.icon.url) # type: ignore # LIES, LIES, AND LIES!!! + await ctx.send(embed=embed) + + @commands.has_guild_permissions(manage_guild=True) + @commands.guild_only() + @prefix.command(name="delete") + @app_commands.describe(prefix="The prefix to delete") + async def deletePrefixes(self, ctx: commands.Context, prefix: str) -> None: + """Deletes a prefix from your server""" + view = DeletePrefixView(bot=self.bot, prefix=prefix) + embed = ConfirmEmbed() + embed.description = f"Do you want to delete the following prefix: {prefix}" + await ctx.send(embed=embed, view=view) async def setup(bot: KumikoCore) -> None: - await bot.add_cog(Prefixes(bot)) + await bot.add_cog(Prefix(bot)) diff --git a/Bot/Libs/errors/__init__.py b/Bot/Libs/errors/__init__.py index 5f2d72a7..b21140be 100644 --- a/Bot/Libs/errors/__init__.py +++ b/Bot/Libs/errors/__init__.py @@ -4,12 +4,14 @@ KumikoException, NoItemsError, NotFoundError, + ValidationError, ) __all__ = [ "KumikoException", "NoItemsError", "ItemNotFoundError", + "ValidationError", "HTTPError", "NotFoundError", ] diff --git a/Bot/Libs/errors/exceptions.py b/Bot/Libs/errors/exceptions.py index b33091ef..96f2e887 100644 --- a/Bot/Libs/errors/exceptions.py +++ b/Bot/Libs/errors/exceptions.py @@ -19,6 +19,10 @@ class ItemNotFoundError(KumikoException): """Generally used if any item of the economy system is not found""" +class ValidationError(KumikoException): + """Raised when a validation of any function fails""" + + class HTTPError(KumikoException): """Raised when an HTTP request fails. diff --git a/Bot/Libs/ui/prefix/__init__.py b/Bot/Libs/ui/prefix/__init__.py new file mode 100644 index 00000000..fc7a6690 --- /dev/null +++ b/Bot/Libs/ui/prefix/__init__.py @@ -0,0 +1,3 @@ +from .views import DeletePrefixView + +__all__ = ["DeletePrefixView"] diff --git a/Bot/Libs/ui/prefix/views.py b/Bot/Libs/ui/prefix/views.py new file mode 100644 index 00000000..9af8a3eb --- /dev/null +++ b/Bot/Libs/ui/prefix/views.py @@ -0,0 +1,48 @@ +import discord +from kumikocore import KumikoCore +from Libs.utils import CancelledActionEmbed, SuccessActionEmbed + + +class DeletePrefixView(discord.ui.View): + def __init__(self, bot: KumikoCore, prefix: str) -> None: + super().__init__() + self.bot = bot + self.prefix = prefix + self.pool = self.bot.pool + + @discord.ui.button( + label="Confirm", + style=discord.ButtonStyle.green, + emoji="<:greenTick:596576670815879169>", + ) + async def confirm( + self, interaction: discord.Interaction, button: discord.ui.Button + ) -> None: + query = """ + UPDATE guild + SET prefix = ARRAY_REMOVE(prefix, $1) + WHERE id=$2; + """ + async with self.pool.acquire() as conn: + guild_id = interaction.guild.id # type: ignore # lying again + await conn.execute(query, self.prefix, guild_id) + self.bot.prefixes[guild_id].remove( + self.prefix + ) # This makes the assumption that the guild is already in the LRU cache. This is not the best - Noelle + self.clear_items() + embed = SuccessActionEmbed( + description=f"The prefix `{self.prefix}` was successfully removed" + ) + await interaction.response.edit_message(embed=embed, view=self) + + @discord.ui.button( + label="Cancel", + style=discord.ButtonStyle.red, + emoji="<:redTick:596576672149667840>", + ) + async def cancel( + self, interaction: discord.Interaction, button: discord.ui.Button + ) -> None: + self.clear_items() + embed = CancelledActionEmbed() + await interaction.response.edit_message(embed=embed, view=self) diff --git a/Bot/Libs/utils/__init__.py b/Bot/Libs/utils/__init__.py index 622f02e3..2cf4c6e7 100644 --- a/Bot/Libs/utils/__init__.py +++ b/Bot/Libs/utils/__init__.py @@ -1,8 +1,14 @@ from .backoff import backoff -from .embeds import Embed, ErrorEmbed +from .embeds import ( + CancelledActionEmbed, + ConfirmEmbed, + Embed, + ErrorEmbed, + SuccessActionEmbed, +) from .greedy_formatter import formatGreedy from .kumiko_logger import KumikoLogger -from .prefix import get_prefix +from .prefix import get_prefix, validatePrefix from .utils import encodeDatetime, parseDatetime, parseSubreddit, parseTimeStr __all__ = [ @@ -16,4 +22,8 @@ "formatGreedy", "KumikoLogger", "get_prefix", + "validatePrefix", + "ConfirmEmbed", + "SuccessActionEmbed", + "CancelledActionEmbed", ] diff --git a/Bot/Libs/utils/embeds.py b/Bot/Libs/utils/embeds.py index e1574c97..06f44a3c 100644 --- a/Bot/Libs/utils/embeds.py +++ b/Bot/Libs/utils/embeds.py @@ -9,6 +9,26 @@ def __init__(self, **kwargs): super().__init__(**kwargs) +class SuccessActionEmbed(discord.Embed): + """Kumiko's custom success action embed""" + + def __init__(self, **kwargs): + kwargs.setdefault("color", discord.Color.from_rgb(75, 181, 67)) + kwargs.setdefault("title", "Action successful") + kwargs.setdefault("description", "The action requested was successful") + super().__init__(**kwargs) + + +class CancelledActionEmbed(discord.Embed): + """Kumiko's custom confirm action embed""" + + def __init__(self, **kwargs): + kwargs.setdefault("color", discord.Color.from_rgb(255, 0, 51)) + kwargs.setdefault("title", "Action cancelled") + kwargs.setdefault("description", "The action requested was cancelled") + super().__init__(**kwargs) + + class ErrorEmbed(discord.Embed): """Kumiko's custom error embed""" @@ -20,3 +40,12 @@ def __init__(self, **kwargs): "Uh oh! It seems like the command ran into an issue! For support, please visit Kumiko's Support Server to get help!", ) super().__init__(**kwargs) + + +class ConfirmEmbed(discord.Embed): + """Kumiko's custom confirm embed""" + + def __init__(self, **kwargs): + kwargs.setdefault("color", discord.Color.from_rgb(255, 191, 0)) + kwargs.setdefault("title", "Are you sure?") + super().__init__(**kwargs) diff --git a/Bot/Libs/utils/prefix.py b/Bot/Libs/utils/prefix.py index f819e457..993bcd3c 100644 --- a/Bot/Libs/utils/prefix.py +++ b/Bot/Libs/utils/prefix.py @@ -1,12 +1,16 @@ +from typing import List + import discord -from discord.ext import commands # TODO - Prevent people from setting up `/` prefixes. Doesn't help # removed the type hinting bc of circular imports # if there is a way to solve it, then it would be back -async def get_prefix(bot, msg: discord.Message): + + +async def get_prefix(bot, msg: discord.Message) -> List[str]: if msg.guild is None: - return commands.when_mentioned_or(bot.default_prefix)(bot, msg) + return bot.default_prefix + # return commands.when_mentioned_or(bot.default_prefix)(bot, msg) cachedPrefix = bot.prefixes.get(msg.guild.id) if cachedPrefix is None: async with bot.pool.acquire() as conn: @@ -21,10 +25,34 @@ async def get_prefix(bot, msg: discord.Message): fetchPrefix = await conn.fetchval(query, msg.guild.id) if fetchPrefix: bot.prefixes[msg.guild.id] = fetchPrefix - return commands.when_mentioned_or(bot.prefixes[msg.guild.id])(bot, msg) + # return commands.when_mentioned_or(bot.prefixes[msg.guild.id])(bot, msg) + return bot.prefixes[msg.guild.id] else: await conn.execute(updateQuery, [bot.default_prefix], msg.guild.id) bot.prefixes[msg.guild.id] = bot.default_prefix - return commands.when_mentioned_or(bot.prefixes[msg.guild.id])(bot, msg) + return bot.prefixes[msg.guild.id] + # return commands.when_mentioned_or(bot.prefixes[msg.guild.id])(bot, msg) else: - return commands.when_mentioned_or(bot.prefixes[msg.guild.id])(bot, msg) \ No newline at end of file + return bot.prefixes[msg.guild.id] + # return commands.when_mentioned_or(bot.prefixes[msg.guild.id])(bot, msg) + + +def validatePrefix(prefixes: List[str], new_prefix: str) -> bool: + """Validates whether the prefix given is valid or not. + + The rules for the prefix being valid goes as follows: + + 1. The new prefix must not be in the prefixes list + 2. The new prefix cannot be "/". + a. If a prefix containing "/" is followed with another character (eg "/e"), this is considered valid + + Args: + prefixes (List[str]): The list of prefixes associated with the guild. This is usually found within the prefix cache + new_prefix (str): The new prefix to validate + + Returns: + bool: Whether the prefix is valid or not + """ + return new_prefix in prefixes or ( + new_prefix.startswith("/") and len(new_prefix) == 1 + ) diff --git a/Migrations/20230612_initial_up_rev1.sql b/Migrations/20230612_initial_up_rev1.sql index dad6a2ab..f5a3cf56 100644 --- a/Migrations/20230612_initial_up_rev1.sql +++ b/Migrations/20230612_initial_up_rev1.sql @@ -25,13 +25,4 @@ CREATE TABLE IF NOT EXISTS eco_item ( price INT DEFAULT 0, amount INT DEFAULT 0, CONSTRAINT fk_user FOREIGN KEY (user_id) REFERENCES eco_user (id) ON DELETE CASCADE -); - -CREATE TABLE IF NOT EXISTS marketplace ( - id SERIAL PRIMARY KEY, - guild_id BIGINT, - name VARCHAR(255), - description TEXT, - created_at timestamp WITHOUT TIME ZONE DEFAULT CURRENT_TIMESTAMP NOT NULL, - CONSTRAINT fk_guild FOREIGN KEY (guild_id) REFERENCES guild (id) ON DELETE CASCADE -); +); \ No newline at end of file diff --git a/Migrations/20230702_rev1_up_rev2.sql b/Migrations/20230702_rev1_up_rev2.sql index 76ee244b..ef39f37b 100644 --- a/Migrations/20230702_rev1_up_rev2.sql +++ b/Migrations/20230702_rev1_up_rev2.sql @@ -1,7 +1,6 @@ ALTER TABLE eco_user ALTER COLUMN created_at SET DEFAULT (NOW() AT TIME ZONE 'utc'); -ALTER TABLE marketplace ALTER COLUMN created_at SET DEFAULT (NOW() AT TIME ZONE 'utc'); -ALTER TABLE guild ALTER COLUMN prefix SET DATA TYPE VARCHAR(255)[]; +ALTER TABLE guild ALTER COLUMN prefix SET DATA TYPE VARCHAR(255)[3]; CREATE TABLE IF NOT EXISTS eco_item_lookup ( id SERIAL PRIMARY KEY, diff --git a/Migrations/20230702_rev2_up_rev3.sql b/Migrations/20230702_rev2_up_rev3.sql new file mode 100644 index 00000000..85c27fcc --- /dev/null +++ b/Migrations/20230702_rev2_up_rev3.sql @@ -0,0 +1 @@ +ALTER TABLE guild ADD COLUMN local_economy_name VARCHAR(255) DEFAULT 'Server Economy'; \ No newline at end of file From 408863ed0039a0909493df031a2aede5bb1bc74c Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Mon, 3 Jul 2023 04:11:14 -0700 Subject: [PATCH 117/184] Cleanup code + implement async context manager for kumikocpm And also address the elephant in the room --- Bot/Libs/cache/__init__.py | 4 -- Bot/Libs/cache/cp_manager.py | 42 ++++++++------ Bot/Libs/cache/decorators.py | 54 ++++++++++++------ Bot/Libs/cache/global_cp.py | 13 ----- Bot/Libs/cache/mem_cache.py | 68 ----------------------- Bot/Libs/cache/redis_cache.py | 5 -- Bot/Libs/economy/cache_utils.py | 9 ++- Bot/Libs/utils/__init__.py | 2 - Bot/Libs/utils/backoff.py | 19 ------- Bot/Libs/utils/redis/__init__.py | 4 +- Bot/Libs/utils/redis/connections.py | 60 +------------------- Bot/kumikobot.py | 11 +++- Bot/kumikocore.py | 16 +++++- codecov.yml | 4 +- tests/db/test_db_conn.py | 26 ++++++--- tests/exceptions/test_exceptions.py | 10 ++++ tests/redis/test_cache_deco.py | 22 +++++--- tests/redis/test_global_cache.py | 21 +++++-- tests/redis/test_mem_cache.py | 55 ------------------ tests/redis/test_redis_conn.py | 19 ++----- tests/redis/test_redis_conn_pool_cache.py | 47 ---------------- tests/utils/test_backoff.py | 30 ---------- 22 files changed, 159 insertions(+), 382 deletions(-) delete mode 100644 Bot/Libs/cache/global_cp.py delete mode 100644 Bot/Libs/cache/mem_cache.py delete mode 100644 Bot/Libs/utils/backoff.py delete mode 100644 tests/redis/test_mem_cache.py delete mode 100644 tests/redis/test_redis_conn_pool_cache.py delete mode 100644 tests/utils/test_backoff.py diff --git a/Bot/Libs/cache/__init__.py b/Bot/Libs/cache/__init__.py index 5acb5fb7..301f3c19 100644 --- a/Bot/Libs/cache/__init__.py +++ b/Bot/Libs/cache/__init__.py @@ -1,16 +1,12 @@ from .cp_manager import KumikoCPManager from .decorators import cache, cacheJson -from .global_cp import kumikoCP from .key_builder import CommandKeyBuilder -from .mem_cache import MemoryCache from .redis_cache import KumikoCache __all__ = [ - "MemoryCache", "CommandKeyBuilder", "KumikoCache", "KumikoCPManager", - "kumikoCP", "cache", "cacheJson", ] diff --git a/Bot/Libs/cache/cp_manager.py b/Bot/Libs/cache/cp_manager.py index d9f0706c..086209fd 100644 --- a/Bot/Libs/cache/cp_manager.py +++ b/Bot/Libs/cache/cp_manager.py @@ -1,30 +1,38 @@ -from typing import Optional +from types import TracebackType +from typing import Optional, Type, TypeVar from redis.asyncio.connection import ConnectionPool +from yarl import URL + +BE = TypeVar("BE", bound=BaseException) class KumikoCPManager: - """Redis connection pool manager""" + def __init__(self, uri: str, max_size: int = 20) -> None: + self.uri = uri + self.max_size = max_size + self.connPool = None - def __init__( - self, host: str = "127.0.0.1", port: int = 6379, password: Optional[str] = None, uri: Optional[str] = None + async def __aenter__(self) -> ConnectionPool: + return self.createPool() + + async def __aexit__( + self, + exc_type: Optional[Type[BE]], + exc: Optional[BE], + traceback: Optional[TracebackType], ) -> None: - self.host = host - self.port = port - self.password = password - self.connPool = None - self.uri = uri + if self.connPool is not None: + await self.connPool.disconnect() - def createConnPool(self) -> ConnectionPool: - if self.uri is not None: - self.connPool = ConnectionPool( - host=self.host, port=self.port, password=self.password, db=0 - ) - return self.connPool - self.connPool = ConnectionPool.from_url(self.uri) + def createPool(self) -> ConnectionPool: + completeURI = URL(self.uri) % {"decode_responses": "True"} + self.connPool = ConnectionPool(max_connections=self.max_size).from_url( + str(completeURI) + ) return self.connPool def getConnPool(self) -> ConnectionPool: if not self.connPool: - return self.createConnPool() + return self.createPool() return self.connPool diff --git a/Bot/Libs/cache/decorators.py b/Bot/Libs/cache/decorators.py index 436722cc..a22e42a3 100644 --- a/Bot/Libs/cache/decorators.py +++ b/Bot/Libs/cache/decorators.py @@ -1,6 +1,6 @@ import uuid from functools import wraps -from typing import Any, Callable, Union +from typing import Any, Callable, Optional, Union from redis.asyncio.connection import ConnectionPool @@ -17,26 +17,35 @@ class cache: ttl (int, optional): TTL (Time-To-Live). Defaults to 30. """ - def __init__(self, connection_pool: ConnectionPool, ttl: int = 30): - self.connection_pool = connection_pool + def __init__(self, key: Optional[str] = None, ttl: int = 30): + self.key = key self.ttl = ttl def __call__(self, func: Callable, *args: Any, **kwargs: Any): @wraps(func) - async def wrapper(id: int, *args: Any, **kwargs: Any): - return await self.deco(func, id, *args, **kwargs) + async def wrapper( + id: int, redis_pool: ConnectionPool, *args: Any, **kwargs: Any + ): + return await self.deco(func, id, redis_pool, *args, **kwargs) return wrapper - async def deco(self, func: Callable, id: Union[int, None], *args, **kwargs): - res = await func(id, *args, **kwargs) - if res is None: + async def deco( + self, + func: Callable, + id: Union[int, None], + redis_pool: ConnectionPool, + *args, + **kwargs + ): + res = await func(id, redis_pool, *args, **kwargs) + if isinstance(res, str) is False: return None - cache = KumikoCache(connection_pool=self.connection_pool) + cache = KumikoCache(connection_pool=redis_pool) key = CommandKeyBuilder( prefix="cache", namespace="kumiko", - id=id if id is not None else uuid.uuid4(), + id=id or self.key or uuid.uuid4(), # type: ignore command=func.__name__, ) @@ -58,26 +67,35 @@ class cacheJson: Defaults to 30. """ - def __init__(self, connection_pool: ConnectionPool, ttl: int = 30): - self.connection_pool = connection_pool + def __init__(self, key: Optional[str] = None, ttl: int = 30): + self.key = key self.ttl = ttl def __call__(self, func: Callable, *args: Any, **kwargs: Any): @wraps(func) - async def wrapper(id: int, *args: Any, **kwargs: Any): - return await self.deco(func, id, *args, **kwargs) + async def wrapper( + id: int, redis_pool: ConnectionPool, *args: Any, **kwargs: Any + ): + return await self.deco(func, id, redis_pool, *args, **kwargs) return wrapper - async def deco(self, func: Callable, id: Union[int, None], *args, **kwargs): + async def deco( + self, + func: Callable, + id: Union[int, None], + redis_pool: ConnectionPool, + *args, + **kwargs + ): res = await func(id, *args, **kwargs) - if res is None: + if isinstance(res, dict) is False: return None - cache = KumikoCache(connection_pool=self.connection_pool) + cache = KumikoCache(connection_pool=redis_pool) key = CommandKeyBuilder( prefix="cache", namespace="kumiko", - id=id if id is not None else uuid.uuid4(), + id=id or self.key or uuid.uuid4(), # type: ignore command=func.__name__, ) diff --git a/Bot/Libs/cache/global_cp.py b/Bot/Libs/cache/global_cp.py deleted file mode 100644 index 117dba94..00000000 --- a/Bot/Libs/cache/global_cp.py +++ /dev/null @@ -1,13 +0,0 @@ -import os -from pathlib import Path - -from dotenv import load_dotenv -from Libs.cache import KumikoCPManager - -path = Path(__file__).parents[2].joinpath(".env") - -load_dotenv(dotenv_path=path) - -REDIS_URI = os.environ["REDIS_URI"] - -kumikoCP: KumikoCPManager = KumikoCPManager(uri=REDIS_URI) diff --git a/Bot/Libs/cache/mem_cache.py b/Bot/Libs/cache/mem_cache.py deleted file mode 100644 index 57cd9ac6..00000000 --- a/Bot/Libs/cache/mem_cache.py +++ /dev/null @@ -1,68 +0,0 @@ -from typing import Any, Dict, List - - -class MemoryCache: - """Synchronous memory cache implementation based off of aiocache""" - - def __init__(self): - self._cache: Dict[str, Any] = {} - - def get(self, key: str) -> Any: - """Gets a value from the cache - - Args: - key (str): The key to use - - Returns: - Any: The value from the cache - """ - return self._cache.get(key) - - def getAll(self) -> List[Any]: - """Gets all values from the cache - - Returns: - List[Any]: A list of all of the values - """ - return list(self._cache.values()) - - def set(self, key: str, value: Any) -> Any: - """Sets a value in the cache - - Args: - key (str): The key to use - value (Any): The value to set - - Returns: - Any: The set value from the cache - """ - self._cache[key] = value - return self._cache[key] - - def add(self, key: str, value: Any) -> Any: - """Adds a value to the cache if it doesn't exist - - Args: - key (str): The key to use - value (Any): The value to set - - Raises: - ValueError: If the key already exists - - Returns: - Any: The set value from the cache - """ - if key in self._cache: - raise ValueError(f"Key {key} already exists. Please use .set to update it") - return self.set(key=key, value=value) - - def delete(self, key: str) -> Dict[str, Any]: - """Deletes a key from the cache - - Args: - key (str): The key to delete - - Returns: - Dict[str, Any]: The deleted key-value pair - """ - return self._cache.pop(key, None) diff --git a/Bot/Libs/cache/redis_cache.py b/Bot/Libs/cache/redis_cache.py index f35679b4..d2c9d02e 100644 --- a/Bot/Libs/cache/redis_cache.py +++ b/Bot/Libs/cache/redis_cache.py @@ -30,7 +30,6 @@ async def setBasicCache( ) conn: redis.Redis = redis.Redis(connection_pool=self.connection_pool) await conn.set(name=key if key is not None else defaultKey, value=value, ex=ttl) - await conn.close() async def getBasicCache(self, key: str) -> Union[str, None]: """Gets the command cache from Redis @@ -40,7 +39,6 @@ async def getBasicCache(self, key: str) -> Union[str, None]: """ conn: redis.Redis = redis.Redis(connection_pool=self.connection_pool) res = await conn.get(key) - await conn.close() return res async def setJSONCache(self, key: str, value: Dict[str, Any], ttl: int = 5) -> None: @@ -54,7 +52,6 @@ async def setJSONCache(self, key: str, value: Dict[str, Any], ttl: int = 5) -> N client: redis.Redis = redis.Redis(connection_pool=self.connection_pool) await client.json().set(name=key, path="$", obj=encodeDatetime(value)) await client.expire(name=key, time=ttl) - await client.close() async def getJSONCache(self, key: str) -> Union[str, None]: """Gets the JSON cache on Redis @@ -67,7 +64,6 @@ async def getJSONCache(self, key: str) -> Union[str, None]: """ client: redis.Redis = redis.Redis(connection_pool=self.connection_pool) value = await client.json().get(name=key) - await client.close() if value is None: return None return value @@ -83,5 +79,4 @@ async def cacheExists(self, key: str) -> bool: """ client: redis.Redis = redis.Redis(connection_pool=self.connection_pool) keyExists = await client.exists(key) >= 1 - await client.close() return True if keyExists else False diff --git a/Bot/Libs/economy/cache_utils.py b/Bot/Libs/economy/cache_utils.py index 06e7ca56..a8822bcd 100644 --- a/Bot/Libs/economy/cache_utils.py +++ b/Bot/Libs/economy/cache_utils.py @@ -2,12 +2,15 @@ from prisma.models import User from prisma.types import UserInclude +from redis.asyncio.connection import ConnectionPool -from ..cache import cacheJson, kumikoCP +from ..cache import cacheJson -@cacheJson(connection_pool=kumikoCP.getConnPool()) -async def getUser(id: int, includes: UserInclude) -> Union[Dict, None]: +@cacheJson() +async def getUser( + id: int, redis_pool: ConnectionPool, includes: UserInclude +) -> Union[Dict, None]: """[Coroutine] Helper coroutine to obtain a user's profile from the database For reducing the latency for accessing the data, this helper coroutine is cached on Redis (w/ RedisJSON). Also note that this coroutine expects that the Prisma query engine and database are already connected. diff --git a/Bot/Libs/utils/__init__.py b/Bot/Libs/utils/__init__.py index 2cf4c6e7..6cbc7628 100644 --- a/Bot/Libs/utils/__init__.py +++ b/Bot/Libs/utils/__init__.py @@ -1,4 +1,3 @@ -from .backoff import backoff from .embeds import ( CancelledActionEmbed, ConfirmEmbed, @@ -12,7 +11,6 @@ from .utils import encodeDatetime, parseDatetime, parseSubreddit, parseTimeStr __all__ = [ - "backoff", "parseDatetime", "encodeDatetime", "Embed", diff --git a/Bot/Libs/utils/backoff.py b/Bot/Libs/utils/backoff.py deleted file mode 100644 index 9047697e..00000000 --- a/Bot/Libs/utils/backoff.py +++ /dev/null @@ -1,19 +0,0 @@ -import random - - -def backoff(backoff_sec: int = 5, backoff_sec_index: int = 0) -> float: - """Helper function to calculate backoff time (exponential) - - Args: - backoff_sec (int, optional): The init second to use. Defaults to 5. - backoff_sec_index (int, optional): The index to use. Defaults to 0. - - Returns: - float: Backoff time (seconds) - """ - sleepAmt = backoff_sec * 2**backoff_sec_index + random.uniform( # nosec - 0, 1 - ) # nosec - if sleepAmt > 60: - return float(60) - return sleepAmt diff --git a/Bot/Libs/utils/redis/__init__.py b/Bot/Libs/utils/redis/__init__.py index cd02a9bb..d6d53d20 100644 --- a/Bot/Libs/utils/redis/__init__.py +++ b/Bot/Libs/utils/redis/__init__.py @@ -1,3 +1,3 @@ -from .connections import pingRedis, redisCheck, ensureOpenRedisConn +from .connections import ensureOpenRedisConn -__all__ = ["pingRedis", "redisCheck", "ensureOpenRedisConn"] +__all__ = ["ensureOpenRedisConn"] diff --git a/Bot/Libs/utils/redis/connections.py b/Bot/Libs/utils/redis/connections.py index 78e5f7e4..74fcff45 100644 --- a/Bot/Libs/utils/redis/connections.py +++ b/Bot/Libs/utils/redis/connections.py @@ -1,30 +1,12 @@ -import asyncio import logging -from typing import Union import redis.asyncio as redis -from Libs.cache import kumikoCP from redis.asyncio.connection import ConnectionPool -from redis.exceptions import ConnectionError, TimeoutError - -from ..backoff import backoff logger = logging.getLogger("discord") -async def pingRedis(connection_pool: ConnectionPool) -> bool: - """Pings the redis server to ensure that it is alive - - Args: - connection_pool (ConnectionPool): ConnectionPool object to use - - Returns: - bool: Whether the Redis server is alive or not - """ - r: redis.Redis = redis.Redis(connection_pool=connection_pool, socket_timeout=10.0) - return await r.ping() - -async def ensureOpenRedisConn() -> bool: +async def ensureOpenRedisConn(redis_pool: ConnectionPool) -> bool: """Pings the Redis server to check if it's open or not Args: @@ -33,48 +15,10 @@ async def ensureOpenRedisConn() -> bool: Returns: bool: Whether the server is up or not """ - connPool = kumikoCP.getConnPool() - r: redis.Redis = redis.Redis(connection_pool=connPool) + r: redis.Redis = redis.Redis(connection_pool=redis_pool) resultPing = await r.ping() if resultPing: logger.info("Sucessfully connected to the Redis server") return True logger.error("Failed to connect to the Redis server - Restart Kumiko to reconnect") return False - - - -async def redisCheck( - backoff_sec: int = 15, - backoff_index: int = 0, -) -> Union[bool, None]: - """Integration method to check if the Redis server is alive - - Also sets up the conn pool cache. This is handled recursively actually. - There is a base case of 5 so the recursion only goes 5 calls deep on the stack. This is to prevent infinite calls on the stack from piling up. - - Args: - backoff_sec (int, optional): Backoff time in seconds. Defaults to 15. - backoff_index (int, optional): Backoff index. This is used privately Defaults to 0. - - Returns: - Union[Literal[True], None]: Returns True if the Redis server is alive. Returns None if the coroutine is in a recursive loop. - """ - try: - connPool = kumikoCP.getConnPool() - res = await pingRedis(connection_pool=connPool) - if backoff_index == 5: - logger.error("Unable to connect to Redis server") - return False - if res is True: - logger.info("Successfully connected to Redis server") - return True - except (ConnectionError, TimeoutError): - backoffTime = backoff(backoff_sec=backoff_sec, backoff_sec_index=backoff_index) - logger.error( - f"Failed to connect to Redis server - Restarting connection in {int(backoffTime)} seconds" - ) - await asyncio.sleep(backoffTime) - await redisCheck( - backoff_index=backoff_index + 1, - ) diff --git a/Bot/kumikobot.py b/Bot/kumikobot.py index f286a5d4..c7986f52 100644 --- a/Bot/kumikobot.py +++ b/Bot/kumikobot.py @@ -1,29 +1,34 @@ import os +import asyncpg import discord from aiohttp import ClientSession from anyio import run from dotenv import load_dotenv from kumikocore import KumikoCore +from Libs.cache import KumikoCPManager from Libs.utils import KumikoLogger -import asyncpg + load_dotenv() KUMIKO_TOKEN = os.environ["DEV_BOT_TOKEN"] DEV_MODE = os.getenv("DEV_MODE") in ("True", "TRUE") POSTGRES_URI = os.environ["POSTGRES_URI"] +REDIS_URI = os.environ["REDIS_URI"] intents = discord.Intents.default() intents.message_content = True - async def main() -> None: - async with ClientSession() as session, asyncpg.create_pool(dsn=POSTGRES_URI, command_timeout=60, max_size=20, min_size=20) as pool: + async with ClientSession() as session, asyncpg.create_pool( + dsn=POSTGRES_URI, command_timeout=60, max_size=20, min_size=20 + ) as pool, KumikoCPManager(uri=REDIS_URI, max_size=25) as redis_pool: async with KumikoCore( intents=intents, session=session, pool=pool, + redis_pool=redis_pool, dev_mode=DEV_MODE, ) as bot: await bot.start(KUMIKO_TOKEN) diff --git a/Bot/kumikocore.py b/Bot/kumikocore.py index a9048fc9..4e52fb06 100644 --- a/Bot/kumikocore.py +++ b/Bot/kumikocore.py @@ -11,6 +11,7 @@ from Libs.utils.postgresql import ensureOpenPostgresConn from Libs.utils.redis import ensureOpenRedisConn from lru import LRU +from redis.asyncio.connection import ConnectionPool # Some weird import logic to ensure that watchfiles is there _fsw = True @@ -28,6 +29,7 @@ def __init__( intents: discord.Intents, session: ClientSession, pool: asyncpg.Pool, + redis_pool: ConnectionPool, lru_size: int = 50, dev_mode: bool = False, *args, @@ -45,6 +47,7 @@ def __init__( self.lru_size = lru_size self._session = session self._pool = pool + self._redis_pool = redis_pool self._prefixes: LRU = LRU(self.lru_size) self.default_prefix = ">" self.logger: logging.Logger = logging.getLogger("kumikobot") @@ -62,13 +65,22 @@ def session(self) -> ClientSession: def pool(self) -> asyncpg.Pool: """A global object managed throughout the lifetime of Kumiko - Holds the asyncpg + Holds the asyncpg pool for connections Returns: asyncpg.Pool: asyncpg connection pool """ return self._pool + @property + def redis_pool(self) -> ConnectionPool: + """A global object managed throughout the lifetime of Kumiko + + Returns: + ConnectionPool: Redis connection pool + """ + return self._redis_pool + # It is preffered in this case to keep an LRU cache instead of a regular Dict cache # For example, if an running instance keeps 100 entries ({guild_id: prefix}) # then this would take up too much memory. @@ -106,7 +118,7 @@ async def setup_hook(self) -> None: await self.load_extension(f"{cog.parent.name}.{cog.name[:-3]}") self.loop.create_task(ensureOpenPostgresConn(self._pool)) - self.loop.create_task(ensureOpenRedisConn()) + self.loop.create_task(ensureOpenRedisConn(self._redis_pool)) if self.dev_mode is True and _fsw is True: self.logger.info("Dev mode is enabled. Loading Jishaku and FSWatcher") diff --git a/codecov.yml b/codecov.yml index 8ab53c34..e5a0a241 100644 --- a/codecov.yml +++ b/codecov.yml @@ -1,4 +1,6 @@ ignore: - "Bot/Libs/ui/**" - "Bot/Libs/utils/help/**" - - "Bot/Libs/utils/pages/**" \ No newline at end of file + - "Bot/Libs/utils/pages/**" + - "Bot/Libs/utils/kumiko_logger.py" + - "Bot/Libs/utils/embeds.py" \ No newline at end of file diff --git a/tests/db/test_db_conn.py b/tests/db/test_db_conn.py index bc2e54df..eae96412 100644 --- a/tests/db/test_db_conn.py +++ b/tests/db/test_db_conn.py @@ -1,17 +1,29 @@ +import os import sys from pathlib import Path -from prisma.utils import async_run +import pytest +from dotenv import load_dotenv path = Path(__file__).parents[2].joinpath("Bot") sys.path.append(str(path)) +load_dotenv() -from Libs.utils.postgresql import PrismaSessionManager -from prisma.models import User +import asyncpg +from Libs.utils.postgresql import ensureOpenPostgresConn -def test_prisma_client_session_manager(): - with PrismaSessionManager(): - res = async_run(User.prisma().find_first(where={"id": 454357482102587393})) - assert (res is None) or (isinstance(res, User)) # nosec +@pytest.fixture(scope="session") +def get_uri(): + pg_uri = os.getenv("POSTGRES_URI") + if pg_uri is None: + return "postgresql://postgres:postgres@localhost:5432/test" + return pg_uri + + +@pytest.mark.asyncio +async def test_open_postgres_conn(get_uri): + async with asyncpg.create_pool(dsn=get_uri) as pool: + res = await ensureOpenPostgresConn(conn_pool=pool) + assert res is True diff --git a/tests/exceptions/test_exceptions.py b/tests/exceptions/test_exceptions.py index 28f0e8e2..71feb513 100644 --- a/tests/exceptions/test_exceptions.py +++ b/tests/exceptions/test_exceptions.py @@ -12,6 +12,7 @@ KumikoException, NoItemsError, NotFoundError, + ValidationError, ) @@ -64,3 +65,12 @@ def test_not_found_error(): and (e.value.status == 404) and ("Resource or endpoint not found" in str(e.value)) ) + + +def test_validation_error(): + with pytest.raises(ValidationError) as e: + raise ValidationError("There is an validation error") + + assert (e.type == ValidationError) and ( + "There is an validation error" in str(e.value) + ) diff --git a/tests/redis/test_cache_deco.py b/tests/redis/test_cache_deco.py index 844b7864..f9bab76f 100644 --- a/tests/redis/test_cache_deco.py +++ b/tests/redis/test_cache_deco.py @@ -14,12 +14,16 @@ async def test_cache_deco(): connPool = ConnectionPool(max_connections=25) - @cache(connection_pool=connPool) - async def testFunc(id=1235): + @cache() + async def testFunc( + id=1235, redis_pool=ConnectionPool.from_url("redis://localhost:6379/0") + ): return "Hello World" - res = await testFunc(1235) - assert (await testFunc(1235) == "Hello World".encode("utf-8")) and isinstance( + res = await testFunc(1235, connPool) + assert ( + await testFunc(1235, connPool) == "Hello World".encode("utf-8") + ) and isinstance( res, str ) # nosec @@ -28,13 +32,15 @@ async def testFunc(id=1235): async def test_cache_deco_json(): connPool = ConnectionPool(max_connections=25) - @cacheJson(connection_pool=connPool) - async def testFuncJSON(id=182348478): + @cacheJson() + async def testFuncJSON( + id=182348478, redis_pool=ConnectionPool.from_url("redis://localhost:6379/0") + ): return {"message": "Hello World"} - res = await testFuncJSON(182348478) + res = await testFuncJSON(182348478, connPool) assert ( - await testFuncJSON(182348478) == {"message": "Hello World"} + await testFuncJSON(182348478, connPool) == {"message": "Hello World"} ) and isinstance( # nosec res, dict ) diff --git a/tests/redis/test_global_cache.py b/tests/redis/test_global_cache.py index 22a84f7d..d837c385 100644 --- a/tests/redis/test_global_cache.py +++ b/tests/redis/test_global_cache.py @@ -4,15 +4,26 @@ path = Path(__file__).parents[2].joinpath("Bot") sys.path.append(str(path)) -from Libs.cache import kumikoCP +import pytest +from Libs.cache import KumikoCPManager from redis.asyncio.connection import ConnectionPool +REDIS_URI = "redis://localhost:6379/0" -def test_get_cp(): - connPool = kumikoCP.getConnPool() - assert isinstance(connPool, ConnectionPool) + +@pytest.mark.asyncio +async def test_cpm(): + async with KumikoCPManager(uri=REDIS_URI) as cpm: + assert isinstance(cpm, ConnectionPool) def test_creation_cp(): - connPool = kumikoCP.createConnPool() + kumikoCP = KumikoCPManager(uri=REDIS_URI) + connPool = kumikoCP.createPool() + assert isinstance(connPool, ConnectionPool) + + +def test_get_cp(): + kumikoCP = KumikoCPManager(uri=REDIS_URI) + connPool = kumikoCP.getConnPool() assert isinstance(connPool, ConnectionPool) diff --git a/tests/redis/test_mem_cache.py b/tests/redis/test_mem_cache.py deleted file mode 100644 index d1f4014b..00000000 --- a/tests/redis/test_mem_cache.py +++ /dev/null @@ -1,55 +0,0 @@ -import sys -from pathlib import Path - -import pytest - -path = Path(__file__).parents[2].joinpath("Bot") -sys.path.append(str(path)) - -from Libs.cache import MemoryCache -from redis.connection import ConnectionPool - - -@pytest.fixture(autouse=True, scope="session") -def load_conn_pool() -> ConnectionPool: - return ConnectionPool().from_url("redis://localhost:6379/0") - - -def test_mem_cache_set(load_conn_pool): - memCache = MemoryCache() - memCache.set(key="main", value=load_conn_pool) - res = memCache.get(key="main") - assert isinstance(res, ConnectionPool) # nosec - - -def test_mem_cache_add(load_conn_pool): - memCache = MemoryCache() - memCache.add(key="main4", value=load_conn_pool) - res = memCache.get(key="main4") - assert isinstance(res, ConnectionPool) # nosec - - -def test_mem_cache_add_error(load_conn_pool): - with pytest.raises(ValueError) as execinfo: - memCache = MemoryCache() - memCache.add(key="main", value=load_conn_pool) - memCache.add(key="main", value=load_conn_pool) - assert ( # nosec - str(execinfo.value) - == "Key main already exists. Please use .set to update it" # nosec - ) # nosec - - -def test_mem_cache_delete_return(load_conn_pool): - memCache = MemoryCache() - memCache.set(key="main3", value=load_conn_pool) - res = memCache.delete(key="main3") - assert isinstance(res, ConnectionPool) # nosec - - -def test_mem_cache_delete(load_conn_pool): - memCache = MemoryCache() - memCache.set(key="main2", value=load_conn_pool) - memCache.delete(key="main2") - currCache = memCache.getAll() - assert len(currCache) == 0 # nosec diff --git a/tests/redis/test_redis_conn.py b/tests/redis/test_redis_conn.py index e91384b2..994e44f8 100644 --- a/tests/redis/test_redis_conn.py +++ b/tests/redis/test_redis_conn.py @@ -7,22 +7,11 @@ path = Path(__file__).parents[2].joinpath("Bot") sys.path.append(str(path)) -from Libs.cache import MemoryCache -from Libs.utils.redis import pingRedis, redisCheck +from Libs.utils.redis import ensureOpenRedisConn @pytest.mark.asyncio -async def test_redis_ping(): - memCache = MemoryCache() - memCache.add( - key="main", value=ConnectionPool().from_url("redis://localhost:6379/0") - ) - connPool = memCache.get(key="main") - res = await pingRedis(connection_pool=connPool) - assert res is True # nosec - - -@pytest.mark.asyncio -async def test_redis_check(): - res = await redisCheck() +async def test_open_conn(): + connPool = ConnectionPool().from_url("redis://localhost:6379/0") + res = await ensureOpenRedisConn(redis_pool=connPool) assert res is True # nosec diff --git a/tests/redis/test_redis_conn_pool_cache.py b/tests/redis/test_redis_conn_pool_cache.py deleted file mode 100644 index 26a5889f..00000000 --- a/tests/redis/test_redis_conn_pool_cache.py +++ /dev/null @@ -1,47 +0,0 @@ -import sys -from pathlib import Path - -import redis - -path = Path(__file__).parents[2].joinpath("Bot") -sys.path.append(str(path)) - -from Libs.cache import MemoryCache -from redis.connection import ConnectionPool - - -def test_pool_mem_cache_add(): - connPool = ConnectionPool(max_connections=25) - memCache = MemoryCache() - memCache.add(key="conn1", value=connPool) - assert isinstance(memCache.get(key="conn1"), ConnectionPool) # nosec - - -def test_pool_mem_cache_delete(): - connPool = ConnectionPool(max_connections=25) - memCache = MemoryCache() - memCache.add(key="conn1", value=connPool) - memCache.delete(key="conn1") - assert memCache.get(key="conn1") is None # nosec - - -def test_pool_mem_cache_set(): - connPool = ConnectionPool(max_connections=25) - memCache = MemoryCache() - memCache.set(key="conn2", value=connPool) - memCache.set(key="conn1", value=connPool) - assert ( # nosec - memCache.get(key="conn1") is not None and memCache.get(key="conn2") is not None - ) - - -def test_pool_mem_integration(): - connPool = ConnectionPool(max_connections=25) - memCache = MemoryCache() - memCache.add(key="conn1", value=connPool) - currPool = memCache.get(key="conn1") - r = redis.Redis(connection_pool=currPool) - r.set("foo", "bar") - res = r.get("foo") - r.close() - assert res == b"bar" # nosec diff --git a/tests/utils/test_backoff.py b/tests/utils/test_backoff.py deleted file mode 100644 index c164c576..00000000 --- a/tests/utils/test_backoff.py +++ /dev/null @@ -1,30 +0,0 @@ -import sys -from pathlib import Path - -import pytest - -path = Path(__file__).parents[2].joinpath("Bot") -sys.path.append(str(path)) - -from Libs.utils import backoff - - -@pytest.fixture(scope="session") -def backoff_values(): - return (5, 0) - - -def test_backoff(backoff_values): - backoff_sec, backoff_sec_index = backoff_values - sleepAmt = backoff(backoff_sec, backoff_sec_index) - assert sleepAmt <= 6.0 and sleepAmt >= 5.0 # nosec - - -def test_backoff_loop(backoff_values): - backoff_sec, backoff_sec_index = backoff_values - backoffTime = 0 - for _ in range(5): - backoffTime = backoff(backoff_sec, backoff_sec_index) - backoff_sec_index += 1 - - assert backoffTime == 60.0 # nosec From 7973369680a6aa665d75747f03afd6eb4e00429a Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Mon, 3 Jul 2023 04:15:06 -0700 Subject: [PATCH 118/184] Fix the tests running on gh actions --- .github/workflows/tests.yml | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/.github/workflows/tests.yml b/.github/workflows/tests.yml index 82a5aa81..4c5cc09c 100644 --- a/.github/workflows/tests.yml +++ b/.github/workflows/tests.yml @@ -10,10 +10,11 @@ on: - dev env: - DATABASE_URL: postgresql://postgres:postgres@localhost:5432/postgres + POSTGRES_URI: postgresql://postgres:postgres@localhost:5432/postgres REDIS_HOST: localhost REDIS_PORT: 6379 REDIS_PASSWORD: kumiko + REDIS_URI: redis://localhost:6379/0 jobs: From db27fee105db0f82bbf793c807a6a5304e840786 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Mon, 3 Jul 2023 04:19:30 -0700 Subject: [PATCH 119/184] I do not need Prisma, Jon --- noxfile.py | 4 ---- 1 file changed, 4 deletions(-) diff --git a/noxfile.py b/noxfile.py index 688c649a..a3620fbb 100644 --- a/noxfile.py +++ b/noxfile.py @@ -4,7 +4,6 @@ @nox.session(python="3.11") def test311(session: nox.Session): session.run_always("poetry", "install", "--with", "test", external=True) - session.run_always("poetry", "run", "prisma", "db", "push", external=True) session.run( "poetry", "run", @@ -19,7 +18,6 @@ def test311(session: nox.Session): @nox.session(python="3.10") def test310(session: nox.Session): session.run_always("poetry", "install", "--with", "test", external=True) - session.run_always("poetry", "run", "prisma", "db", "push", external=True) session.run( "poetry", "run", @@ -34,7 +32,6 @@ def test310(session: nox.Session): @nox.session(python="3.9") def test39(session: nox.Session): session.run_always("poetry", "install", "--with", "test", external=True) - session.run_always("poetry", "run", "prisma", "db", "push", external=True) session.run( "poetry", "run", @@ -49,7 +46,6 @@ def test39(session: nox.Session): @nox.session(python="3.8") def test38(session: nox.Session): session.run_always("poetry", "install", "--with", "test", external=True) - session.run_always("poetry", "run", "prisma", "db", "push", external=True) session.run( "poetry", "run", From 504123a6b0e2449372d04438b12f9a0f19d703f2 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Mon, 3 Jul 2023 18:11:55 +0000 Subject: [PATCH 120/184] [pip](deps): Bump prisma from 0.9.0 to 0.9.1 (#367) Bumps [prisma](https://github.com/RobertCraigie/prisma-client-py) from 0.9.0 to 0.9.1. - [Release notes](https://github.com/RobertCraigie/prisma-client-py/releases) - [Commits](https://github.com/RobertCraigie/prisma-client-py/compare/v0.9.0...v0.9.1) --- updated-dependencies: - dependency-name: prisma dependency-type: direct:production update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 10 +++++----- pyproject.toml | 2 +- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/poetry.lock b/poetry.lock index 24bede14..27da1f38 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2247,13 +2247,13 @@ virtualenv = ">=20.10.0" [[package]] name = "prisma" -version = "0.9.0" +version = "0.9.1" description = "Prisma Client Python is an auto-generated and fully type-safe database client" optional = false python-versions = ">=3.7.0" files = [ - {file = "prisma-0.9.0-py3-none-any.whl", hash = "sha256:bff4b239faeb5d427e8337eadc6fe2d2e2ee4f82e30048fd7de46f8aaf9ef07d"}, - {file = "prisma-0.9.0.tar.gz", hash = "sha256:1f9321efc099401995067d921cab848f5a82cd64ecdb5924fa91fb2f1379897f"}, + {file = "prisma-0.9.1-py3-none-any.whl", hash = "sha256:a59447cee28cb04a6c480f875d50bb1a1c1661013a81d3145114d39fd53a806c"}, + {file = "prisma-0.9.1.tar.gz", hash = "sha256:c8a58845833890da931f0d04719ae6506dc86f018b46bb3084402d0d38af8e23"}, ] [package.dependencies] @@ -2261,7 +2261,7 @@ click = ">=7.1.2" httpx = ">=0.19.0" jinja2 = ">=2.11.2" nodeenv = "*" -pydantic = ">=1.8.0" +pydantic = ">=1.8.0,<2.0.0" python-dotenv = ">=0.12.0" tomlkit = "*" typing-extensions = ">=4.0.1" @@ -3381,4 +3381,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "ba19565aba6b3b84495dcbce3d8a4b0032da29d47d5007e0ae8e34485be6f166" +content-hash = "07126d4912e0238ad6e578192cb34c5610dd91d387af4b1db4e301e86e35bea6" diff --git a/pyproject.toml b/pyproject.toml index 9ef404ef..8646f92f 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -15,7 +15,7 @@ asyncpraw = "^7.7.0" uvloop = "^0.17.0" gql = { extras = ["aiohttp"], version = "^3.4.1" } better-ipc = "^2.0.3" -prisma = "^0.9.0" +prisma = "^0.9.1" redis = {extras = ["hiredis"], version = "^4.6.0"} ciso8601 = "^2.3.0" faust-cchardet = "^2.1.18" From 4ddae0ec738e765eaa3a76a7972c19ef3f8d28f8 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Mon, 3 Jul 2023 13:56:17 -0700 Subject: [PATCH 121/184] Removing the need for Prisma --- .github/workflows/lint.yml | 36 +++++++--------- .github/workflows/tests.yml | 3 -- .gitignore | 5 ++- Bot/Libs/economy/cache_utils.py | 23 +++++++--- Bot/Libs/utils/postgresql/ctx.py | 32 -------------- Docker/start.sh | 54 ----------------------- schema.prisma | 74 -------------------------------- 7 files changed, 36 insertions(+), 191 deletions(-) delete mode 100644 Bot/Libs/utils/postgresql/ctx.py delete mode 100644 schema.prisma diff --git a/.github/workflows/lint.yml b/.github/workflows/lint.yml index e18ecae5..f0b8eae8 100644 --- a/.github/workflows/lint.yml +++ b/.github/workflows/lint.yml @@ -8,27 +8,27 @@ on: branches: - dev -env: - DATABASE_URL: postgresql://postgres:postgres@localhost:5432/postgres +# env: +# DATABASE_URL: postgresql://postgres:postgres@localhost:5432/postgres jobs: Analyze: runs-on: ubuntu-latest - services: - postgres: - image: postgres:15 - env: - POSTGRES_USER: postgres - POSTGRES_PASSWORD: postgres - POSTGRES_DB: postgres - ports: - - 5432:5432 - options: >- - --health-cmd pg_isready - --health-interval 10s - --health-timeout 5s - --health-retries 5 + # services: + # postgres: + # image: postgres:15 + # env: + # POSTGRES_USER: postgres + # POSTGRES_PASSWORD: postgres + # POSTGRES_DB: postgres + # ports: + # - 5432:5432 + # options: >- + # --health-cmd pg_isready + # --health-interval 10s + # --health-timeout 5s + # --health-retries 5 strategy: fail-fast: false @@ -60,10 +60,6 @@ jobs: run: | poetry install --with dev - - name: Generate Prisma Client - run: | - poetry run prisma db push - - name: Run Pyright run: | poetry run pyright Bot diff --git a/.github/workflows/tests.yml b/.github/workflows/tests.yml index 4c5cc09c..de016572 100644 --- a/.github/workflows/tests.yml +++ b/.github/workflows/tests.yml @@ -11,9 +11,6 @@ on: env: POSTGRES_URI: postgresql://postgres:postgres@localhost:5432/postgres - REDIS_HOST: localhost - REDIS_PORT: 6379 - REDIS_PASSWORD: kumiko REDIS_URI: redis://localhost:6379/0 diff --git a/.gitignore b/.gitignore index cac5caf9..fd054975 100644 --- a/.gitignore +++ b/.gitignore @@ -169,4 +169,7 @@ cython_debug/ .dccache # Testing scripts -test-scripts/ \ No newline at end of file +test-scripts/ + +# Ruff cache +.ruff_cache/ \ No newline at end of file diff --git a/Bot/Libs/economy/cache_utils.py b/Bot/Libs/economy/cache_utils.py index a8822bcd..0950e06d 100644 --- a/Bot/Libs/economy/cache_utils.py +++ b/Bot/Libs/economy/cache_utils.py @@ -1,26 +1,35 @@ from typing import Dict, Union -from prisma.models import User -from prisma.types import UserInclude +import asyncpg from redis.asyncio.connection import ConnectionPool from ..cache import cacheJson +# TODO - Add an join for the items owned @cacheJson() async def getUser( - id: int, redis_pool: ConnectionPool, includes: UserInclude + id: int, redis_pool: ConnectionPool, pool: asyncpg.Pool ) -> Union[Dict, None]: """[Coroutine] Helper coroutine to obtain a user's profile from the database - For reducing the latency for accessing the data, this helper coroutine is cached on Redis (w/ RedisJSON). Also note that this coroutine expects that the Prisma query engine and database are already connected. + For reducing the latency for accessing the data, this helper coroutine is cached on Redis (w/ RedisJSON). Args: id (int): User ID to use to search up the user - includes (UserInclude, optional): Which schemas to include (for 1-n relations) Note that it must be a dict containing the column, and to include it or not. + redis_pool (ConnectionPool): Redis connection pool to use + pool (asyncpg.Pool): Asyncpg pool Returns: Union[Dict, None]: The user's profile, or None if the user is not found """ - user = await User.prisma().find_unique(where={"id": id}, include=includes) - return user.dict() if user is not None else None + query = """ + SELECT rank, petals, created_at + FROM eco_user + WHERE id=$1; + """ + async with pool.acquire() as conn: + user = await conn.fetchval(query, id) + if user is None: + return None + return dict(user) diff --git a/Bot/Libs/utils/postgresql/ctx.py b/Bot/Libs/utils/postgresql/ctx.py deleted file mode 100644 index 1037e2db..00000000 --- a/Bot/Libs/utils/postgresql/ctx.py +++ /dev/null @@ -1,32 +0,0 @@ -import logging -from types import TracebackType -from typing import Optional, Type, TypeVar - -from prisma import Prisma -from prisma.utils import async_run - -BE = TypeVar("BE", bound=BaseException) - -logger = logging.getLogger("discord") or logging.getLogger(__name__) - - -class PrismaSessionManager: - """Context manager for managing Prisma Sessions""" - - def __init__(self) -> None: - self.self = self - self.db = Prisma(auto_register=True) - - def __enter__(self) -> None: - async_run(self.db.connect()) - logger.info("Successfully connected to PostgreSQL database") - - def __exit__( - self, - exc_type: Optional[Type[BE]], - exc: Optional[BE], - traceback: Optional[TracebackType], - ) -> None: - if self.db.is_connected() is True: - async_run(self.db.disconnect()) - logging.info("Safely disconnected from PostgreSQL database") diff --git a/Docker/start.sh b/Docker/start.sh index 18b9a7a2..d3a319b1 100644 --- a/Docker/start.sh +++ b/Docker/start.sh @@ -1,59 +1,5 @@ #!/usr/bin/env bash -# if [[ -v KUMIKO_TOKEN ]]; then -# echo "KUMIKO_TOKEN=${KUMIKO_TOKEN}" >> /Kumiko/Bot/.env -# else -# echo "Missing Kumiko's bot token! KUMIKO_TOKEN environment variable is not set." -# exit 1; -# fi - -# Testing bot token -# Not needed in production -# if [[ -v DEV_BOT_TOKEN ]]; then -# echo "DEV_BOT_TOKEN=${DEV_BOT_TOKEN}" >> /Kumiko/Bot/.env -# fi - -# API Keys -# GitHub -# if [[ -v GITHUB_API_ACCESS_TOKEN ]]; then -# echo "GitHub_API_Access_Token=${GITHUB_API_ACCESS_TOKEN}" >> /Kumiko/Bot/.env -# else -# echo "Missing GitHub API token! GITHUB_API_ACCESS_TOKEN environment variable is not set." -# fi -# # Reddit ID -# if [[ -v REDDIT_ID ]]; then -# echo "Reddit_ID=${REDDIT_ID}" >> /Kumiko/Bot/.env -# else -# echo "Missing Reddit ID! REDDIT_ID environment variable is not set." -# fi -# # Reddit Secret -# if [[ -v REDDIT_SECRET ]]; then -# echo "Reddit_Secret=${REDDIT_SECRET}" >> /Kumiko/Bot/.env -# else -# echo "Missing Reddit secret! REDDIT_SECRET environment variable is not set." -# fi -# # Tenor -# if [[ -v TENOR_API_KEY ]]; then -# echo "Kumiko_Tenor_API_Key=${TENOR_API_KEY}" >> /Kumiko/Bot/.env -# else -# echo "Missing Tenor API key! TENOR_API_KEY environment variable is not set." -# fi -# YouTube - -# if [[ -v IPC_SECRET_KEY ]]; then -# echo "IPC_SECRET_KEY=${IPC_SECRET_KEY}" >> /Kumiko/Bot/.env -# else -# echo "Missing IPC_Secret_Key env var! IPC_Secret_Key environment variable is not set." -# exit 1; -# fi - -# if [[ -v DATABASE_URL ]]; then -# echo "DATABASE_URL=${DATABASE_URL}" >> /Kumiko/Bot/.env -# else -# echo "Missing DATABASE_URL env var! DATABASE_URL environment variable is not set." -# exit 1; -# fi - KUMIKO_FIRST_START_CHECK="KUMIKO_FIRST_START" if [ ! -f $KUMIKO_FIRST_START_CHECK ]; then diff --git a/schema.prisma b/schema.prisma deleted file mode 100644 index c0b68735..00000000 --- a/schema.prisma +++ /dev/null @@ -1,74 +0,0 @@ -datasource db { - provider = "postgresql" - url = env("DATABASE_URL") -} - -generator client { - provider = "prisma-client-py" - recursive_type_depth = 5 -} - -model Guild { - id BigInt @id @unique - prefix String @default(">") - logs Boolean @default(false) - birthday Boolean @default(false) - local_economy Boolean @default(false) -} - -model User { - id BigInt @id @unique - name String - rank Int @default(0) - petals Int @default(0) - date_joined DateTime @default(now()) - marketplace Marketplace? // A user can also optionally own a marketplace - user_inv MItem[] // Give the user a default inventory that has one item that is worth 0 petals - // quests Quest[] // This default quest may be used to get the user to explore the marketplace - // QuestClaimer QuestClaimer? // A user can only claim one quest -} - -model MItem { - id String @id @default(uuid()) - marketplace Marketplace @relation(fields: [marketplace_id], references: [id]) - marketplace_id String - user User? @relation(fields: [userId], references: [id]) - userId BigInt? - name String - description String @db.Text - price Float -} - -model Marketplace { - id String @id @default(uuid()) - name String - description String @db.Text - date_created DateTime @default(now()) - owner User @relation(fields: [owner_id], references: [id]) - owner_id BigInt @unique - items MItem[] -} - -// model QuestClaimer { -// id BigInt @id @unique -// user User @relation(fields: [user_id], references: [id]) -// user_id BigInt @unique -// claimed_at DateTime -// quest Quest[] -// } - -// model Quest { -// id String @id @default(uuid()) -// author User @relation(fields: [author_id], references: [id]) -// author_id BigInt -// claimer QuestClaimer @relation(fields: [claimer_id], references: [id]) -// claimer_id BigInt -// name String -// description String @db.Text -// reward Int @default(0) -// active Boolean @default(true) -// claimed Boolean @default(false) -// date_created DateTime @default(now()) -// date_completed DateTime? -// end_datetime DateTime? -// } From 226d83e104270c0b7133ab1efdf4670bad324c62 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Mon, 3 Jul 2023 14:10:41 -0700 Subject: [PATCH 122/184] Fix cache deco bug --- Bot/Libs/cache/decorators.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Bot/Libs/cache/decorators.py b/Bot/Libs/cache/decorators.py index a22e42a3..ba4e1c3e 100644 --- a/Bot/Libs/cache/decorators.py +++ b/Bot/Libs/cache/decorators.py @@ -40,7 +40,7 @@ async def deco( ): res = await func(id, redis_pool, *args, **kwargs) if isinstance(res, str) is False: - return None + return res cache = KumikoCache(connection_pool=redis_pool) key = CommandKeyBuilder( prefix="cache", @@ -90,7 +90,7 @@ async def deco( ): res = await func(id, *args, **kwargs) if isinstance(res, dict) is False: - return None + return res cache = KumikoCache(connection_pool=redis_pool) key = CommandKeyBuilder( prefix="cache", From a2f43f89617dd1557508d2aff89f4351c3fa96ef Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Mon, 3 Jul 2023 14:11:55 -0700 Subject: [PATCH 123/184] unload cog-ext cog --- Bot/{Cogs => unloaded_cogs}/cogs-ext.py | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename Bot/{Cogs => unloaded_cogs}/cogs-ext.py (100%) diff --git a/Bot/Cogs/cogs-ext.py b/Bot/unloaded_cogs/cogs-ext.py similarity index 100% rename from Bot/Cogs/cogs-ext.py rename to Bot/unloaded_cogs/cogs-ext.py From ca10b07467368fd9a88a49f21c89f8f910f1c837 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Mon, 3 Jul 2023 19:33:56 -0700 Subject: [PATCH 124/184] Add Discord API events handler --- Bot/Cogs/events-handler.py | 32 ++++++++++++++++++++++++++++++++ Bot/kumikobot.py | 1 + 2 files changed, 33 insertions(+) create mode 100644 Bot/Cogs/events-handler.py diff --git a/Bot/Cogs/events-handler.py b/Bot/Cogs/events-handler.py new file mode 100644 index 00000000..4779649b --- /dev/null +++ b/Bot/Cogs/events-handler.py @@ -0,0 +1,32 @@ +import discord +from discord.ext import commands +from kumikocore import KumikoCore + + +class EventsHandler(commands.Cog): + """Cog for handling discord api events""" + + def __init__(self, bot: KumikoCore) -> None: + self.bot = bot + self.pool = self.bot.pool + + @commands.Cog.listener() + async def on_guild_join(self, guild: discord.Guild) -> None: + existsQuery = "SELECT EXISTS(SELECT 1 FROM guild WHERE id = $1);" + async with self.pool.acquire() as conn: + async with conn.transaction(): + exists = await conn.fetchval(existsQuery, guild.id) + if not exists: + await conn.execute("INSERT INTO guild (id) VALUES ($1)", guild.id) + self.bot.prefixes[guild.id] = [self.bot.default_prefix] + + @commands.Cog.listener() + async def on_guild_remove(self, guild: discord.Guild) -> None: + async with self.pool.acquire() as conn: + async with conn.transaction(): + await conn.execute("DELETE FROM guild WHERE id = $1", guild.id) + self.bot.prefixes[guild.id] = self.bot.default_prefix + + +async def setup(bot: KumikoCore) -> None: + await bot.add_cog(EventsHandler(bot)) diff --git a/Bot/kumikobot.py b/Bot/kumikobot.py index c7986f52..fbaaa1df 100644 --- a/Bot/kumikobot.py +++ b/Bot/kumikobot.py @@ -18,6 +18,7 @@ intents = discord.Intents.default() intents.message_content = True +intents.members = True async def main() -> None: From 0014b87ad8bc68f46a38ade0c4a6b1a11120bcdc Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Mon, 3 Jul 2023 19:47:07 -0700 Subject: [PATCH 125/184] [skip ci] Cleanup --- .env-dev-example | 46 -------------------------- Envs/dev.env | 32 ++++++++++++++++++ .env-docker-example => Envs/docker.env | 14 ++++---- 3 files changed, 39 insertions(+), 53 deletions(-) delete mode 100644 .env-dev-example create mode 100644 Envs/dev.env rename .env-docker-example => Envs/docker.env (74%) diff --git a/.env-dev-example b/.env-dev-example deleted file mode 100644 index 8fedcb5b..00000000 --- a/.env-dev-example +++ /dev/null @@ -1,46 +0,0 @@ -################################################################## -# Kumiko's Dev Example ENV # -# Replace the values with the appropriate values # -################################################################## - -# More than likely you will not need to use the prod token for testing -# In some cases where Kumiko is near prod, this will get used instead -Kumiko_Token = "Prod-Bot-Token" - -# This is where your main bot token for testing should go. -Dev_Bot_Token = "Dev-Bot-Token" - -# Rin's API Keys -# These are used with Rin's services, and if you do plan on using these, then get the keys for them -# THESE WILL BREAK THE COMMANDS IF YOU DO NOT HAVE THE KEYS HERE -GitHub_API_Access_Token = "key" -Reddit_ID = "id" -Reddit_Secret = "secret" -Kumiko_Tenor_API_Key = "tenor_api_key" -Twitter_Bearer_Token = "twitter_bearer_token" -YouTube_API_Key = "yt_api_key" - -# IPC Secret Key -# This is used to communicate with the IPC server -IPC_Secret_Key = "key" - -# Dev Database Credentials - For PostgreSQL -# Set Postgres_Username and Postgres_Kumiko_Database to the same values -# WITHOUT THESE SET, THE ECONOMY SYSTEM WILL NOT WORK AND WILL BREAK -Postgres_Password = "password" -Postgres_Username = "bot" -Postgres_Server_IP = "host" -Postgres_Port = "5432" -Postgres_Kumiko_Database = "bot" - -# Dev Database Credentials - For MongoDB -# WITHOUT THESE SET, THE ECONOMY SYSTEM WILL NOT WORK AND WILL BREAK -MongoDB_Password = "password" -MongoDB_Username = "bot" -MongoDB_Server_IP = "host" -MongoDB_Server_Port = "27017" - -# Dev Database Credentials - For Redis -# WITHOUT THESE SET, THE ECONOMY SYSTEM WILL NOT WORK AND WILL BREAK -Redis_Server_IP = "host" -Redis_Port = "6379" \ No newline at end of file diff --git a/Envs/dev.env b/Envs/dev.env new file mode 100644 index 00000000..f6983a84 --- /dev/null +++ b/Envs/dev.env @@ -0,0 +1,32 @@ +################################################################## +# Kumiko's Dev Example ENV # +# Replace the values with the appropriate values # +################################################################## + +# More than likely you will not need to use the prod token for testing +# In some cases where Kumiko is near prod, this will get used instead +KUMIKO_TOKEN=token + +# Dev bot token +DEV_BOT_TOKEN=token +DEV_MODE=True + +# For the migrations system +# DO NOT TOUCH THIS UNLESS IT IS TO UPGRADE +TARGET_REVISION=rev3 + +# Search Cog API Keys +# THESE WILL BREAK THE COMMANDS IF YOU DO NOT HAVE THE KEYS HERE +GITHUB_API_KEY=key +REDDIT_ID=key +REDDIT_SECRET=key +TENOR_API_KEY=key + +# IPC Secret Key +# This is used to communicate with the IPC server +IPC_SECRET_KEY=key +IPC_HOST=0.0.0.0 + +# Dev Database Credentials - For PostgreSQL and Redis +POSTGRES_URI=postgres://user:password@localhost:5432/user +REDIS_URI=redis://localhost:6379/0 \ No newline at end of file diff --git a/.env-docker-example b/Envs/docker.env similarity index 74% rename from .env-docker-example rename to Envs/docker.env index 25fd330e..7b5746ca 100644 --- a/.env-docker-example +++ b/Envs/docker.env @@ -10,18 +10,18 @@ KUMIKO_TOKEN=token # If you are using the development builds, use the token that you wish to use for the dev bot. DEV_BOT_TOKEN=token -# Rin's API Keys + Access Tokens +TARGET_REVISION=rev3 GITHUB_API_ACCESS_TOKEN=apiKey REDDIT_ID=apiKey REDDIT_SECRET=apiKey TENOR_API_KEY=apiKey -YOUTUBE_API_KEY=apiKey -# IPC Server Key IPC_SECRET_KEY=key +IPC_HOST=some_ip_address -DATABASE_URL=postgresql://user:password@host:port/database +POSTGRES_PASSWORD=password +POSTGRES_USER=postgres +POSTGRES_DB=postgres -# Redis Credentials -REDIS_IP=ip -REDIS_PORT=port \ No newline at end of file +POSTGRES_URI=postgresql://user:password@host:port/database +REDIS_URI=redis://localhost:6379/0 \ No newline at end of file From 45df629e3e0a7325b8bcb94b802485162dfb816e Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Tue, 4 Jul 2023 01:58:32 -0700 Subject: [PATCH 126/184] [skip ci] Update requirements.txt for docs --- Kumiko-Docs/requirements.txt | 42 ++++++++++++++++++------------------ 1 file changed, 21 insertions(+), 21 deletions(-) diff --git a/Kumiko-Docs/requirements.txt b/Kumiko-Docs/requirements.txt index e3355692..3117b777 100644 --- a/Kumiko-Docs/requirements.txt +++ b/Kumiko-Docs/requirements.txt @@ -1,42 +1,42 @@ alabaster==0.7.13 ; python_version >= "3.8" and python_version < "4.0" babel==2.12.1 ; python_version >= "3.8" and python_version < "4.0" beautifulsoup4==4.12.2 ; python_version >= "3.8" and python_version < "4.0" -certifi==2022.12.7 ; python_version >= "3.8" and python_version < "4" -charset-normalizer==3.1.0 ; python_version >= "3.8" and python_version < "4" +certifi==2023.5.7 ; python_version >= "3.8" and python_version < "4.0" +charset-normalizer==3.1.0 ; python_version >= "3.8" and python_version < "4.0" colorama==0.4.6 ; python_version >= "3.8" and python_version < "4.0" -contourpy==1.0.7 ; python_version >= "3.8" and python_version < "4.0" +contourpy==1.1.0 ; python_version >= "3.8" and python_version < "4.0" cycler==0.11.0 ; python_version >= "3.8" and python_version < "4.0" -docutils==0.19 ; python_version >= "3.8" and python_version < "4.0" -fonttools==4.39.3 ; python_version >= "3.8" and python_version < "4.0" -furo==2023.3.27 ; python_version >= "3.8" and python_version < "4.0" -idna==3.4 ; python_version >= "3.8" and python_version < "4" +docutils==0.20.1 ; python_version >= "3.8" and python_version < "4.0" +fonttools==4.40.0 ; python_version >= "3.8" and python_version < "4.0" +furo==2023.5.20 ; python_version >= "3.8" and python_version < "4.0" +idna==3.4 ; python_version >= "3.8" and python_version < "4.0" imagesize==1.4.1 ; python_version >= "3.8" and python_version < "4.0" -importlib-metadata==6.1.0 ; python_version >= "3.8" and python_version < "3.10" +importlib-metadata==6.7.0 ; python_version >= "3.8" and python_version < "3.10" importlib-resources==5.12.0 ; python_version >= "3.8" and python_version < "3.10" jinja2==3.1.2 ; python_version >= "3.8" and python_version < "4.0" kiwisolver==1.4.4 ; python_version >= "3.8" and python_version < "4.0" livereload==2.6.3 ; python_version >= "3.8" and python_version < "4.0" -markdown-it-py==2.2.0 ; python_version >= "3.8" and python_version < "4.0" -markupsafe==2.1.2 ; python_version >= "3.8" and python_version < "4.0" +markdown-it-py==3.0.0 ; python_version >= "3.8" and python_version < "4.0" +markupsafe==2.1.3 ; python_version >= "3.8" and python_version < "4.0" matplotlib==3.7.1 ; python_version >= "3.8" and python_version < "4.0" -mdit-py-plugins==0.3.5 ; python_version >= "3.8" and python_version < "4.0" +mdit-py-plugins==0.4.0 ; python_version >= "3.8" and python_version < "4.0" mdurl==0.1.2 ; python_version >= "3.8" and python_version < "4.0" -myst-parser==1.0.0 ; python_version >= "3.8" and python_version < "4.0" -numpy==1.24.2 ; python_version >= "3.8" and python_version < "4.0" -packaging==22.0 ; python_version >= "3.8" and python_version < "4.0" +myst-parser==2.0.0 ; python_version >= "3.8" and python_version < "4.0" +numpy==1.24.4 ; python_version >= "3.8" and python_version < "4.0" +packaging==23.1 ; python_version >= "3.8" and python_version < "4.0" pillow==9.5.0 ; python_version >= "3.8" and python_version < "4.0" -pygments==2.15.0 ; python_version >= "3.8" and python_version < "4.0" -pyparsing==3.0.9 ; python_version >= "3.8" and python_version < "4.0" +pygments==2.15.1 ; python_version >= "3.8" and python_version < "4.0" +pyparsing==3.1.0 ; python_version >= "3.8" and python_version < "4.0" python-dateutil==2.8.2 ; python_version >= "3.8" and python_version < "4.0" pytz==2023.3 ; python_version >= "3.8" and python_version < "3.9" pyyaml==6.0 ; python_version >= "3.8" and python_version < "4.0" -requests==2.28.2 ; python_version >= "3.8" and python_version < "4" +requests==2.31.0 ; python_version >= "3.8" and python_version < "4.0" six==1.16.0 ; python_version >= "3.8" and python_version < "4.0" snowballstemmer==2.2.0 ; python_version >= "3.8" and python_version < "4.0" soupsieve==2.4.1 ; python_version >= "3.8" and python_version < "4.0" sphinx-autobuild==2021.3.14 ; python_version >= "3.8" and python_version < "4.0" sphinx-basic-ng==1.0.0b1 ; python_version >= "3.8" and python_version < "4.0" -sphinx==6.1.3 ; python_version >= "3.8" and python_version < "4.0" +sphinx==7.0.1 ; python_version >= "3.8" and python_version < "4.0" sphinxcontrib-applehelp==1.0.4 ; python_version >= "3.8" and python_version < "4.0" sphinxcontrib-devhelp==1.0.2 ; python_version >= "3.8" and python_version < "4.0" sphinxcontrib-htmlhelp==2.0.1 ; python_version >= "3.8" and python_version < "4.0" @@ -44,6 +44,6 @@ sphinxcontrib-jsmath==1.0.1 ; python_version >= "3.8" and python_version < "4.0" sphinxcontrib-qthelp==1.0.3 ; python_version >= "3.8" and python_version < "4.0" sphinxcontrib-serializinghtml==1.1.5 ; python_version >= "3.8" and python_version < "4.0" sphinxext-opengraph==0.8.2 ; python_version >= "3.8" and python_version < "4.0" -tornado==6.2 ; python_version >= "3.8" and python_version < "4.0" -urllib3==1.26.14 ; python_version >= "3.8" and python_version < "4" -zipp==3.15.0 ; python_version >= "3.8" and python_version < "3.10" +tornado==6.3.2 ; python_version >= "3.8" and python_version < "4.0" +urllib3==2.0.3 ; python_version >= "3.8" and python_version < "4.0" +zipp==3.15.0 ; python_version >= "3.8" and python_version < "3.10" \ No newline at end of file From 18fddf39c4d6e9de73b96a7f62d45dc936fef922 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Tue, 4 Jul 2023 03:01:05 -0700 Subject: [PATCH 127/184] [skip ci] Add new methods to run Kumiko into the docs --- .../source/guides/dev/requirements.rst | 11 +--- Kumiko-Docs/source/guides/dev/setup.rst | 54 +++++++++++++++-- Kumiko-Docs/source/guides/user/trying-out.rst | 58 ++++++++++++++++++- 3 files changed, 107 insertions(+), 16 deletions(-) diff --git a/Kumiko-Docs/source/guides/dev/requirements.rst b/Kumiko-Docs/source/guides/dev/requirements.rst index 33d60477..8d75a089 100644 --- a/Kumiko-Docs/source/guides/dev/requirements.rst +++ b/Kumiko-Docs/source/guides/dev/requirements.rst @@ -24,18 +24,11 @@ Debian/Ubuntu .. code-block:: bash - sudo apt-get install libffi-dev python3-dev libnacl-dev libopus-dev libopus0 \ + sudo apt-get install libffi-dev python3-dev libnacl-dev libopus-dev \ libopusenc-dev build-essentials libssl-dev curl wget git -RHEL/CentOS/Fedora 22 or below -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ -.. code-block:: bash - - sudo yum install make gcc libffi-devel python-devel \ - openssl-devel opus-devel opus curl wget git - -Fedora 23+ +Fedora ^^^^^^^^^^ .. code-block:: bash diff --git a/Kumiko-Docs/source/guides/dev/setup.rst b/Kumiko-Docs/source/guides/dev/setup.rst index b297016b..5d4c3c88 100644 --- a/Kumiko-Docs/source/guides/dev/setup.rst +++ b/Kumiko-Docs/source/guides/dev/setup.rst @@ -22,28 +22,70 @@ Local Setup .. code-block:: bash - poetry install --with=dev,test + poetry install --with=dev,test,docs + +3. Copy the ENV files into the correct places + + .. code-block:: bash + + cp Envs/dev.env Bot/.env \ + cp Envs/docker.env .env + +4. Edit the ``.env`` file placed in the root of the repo and in the ``Bot`` folder to include any credentials needed for the bot to run + .. code-block:: bash + + # THIS IS ONLY AN EXAMPLE + POSTGRES_PASSWORD=... + POSTGRES_USER=... + POSTGRES_URI=postgres://user:somepass@localhost:5432/somedb + -3. Start the Docker Compose stack +5. Start the Docker Compose stack .. code-block:: bash sudo docker compose -f docker-compose-dev.yml up -d -4. Run the database migrations +6. Enable the PostgreSQL extension ``pg_trgm`` + + .. code-block:: sql + + CREATE EXTENSION pg_trgm; + +7. Run the database migrations .. code-block:: bash - poetry run prisma db push + python migrations-runner.py Vagrant ------- -Kumiko also supports using Vagrant as a development environment. In order to use Vagrant, you will need Oracle VirtualBox or VMWare Workstation installed on your machine. Once installed and properly configured, you can just run ``vagrant up`` to provision and start it up, and connect to it by SSH or by VSCode. +Kumiko also supports using Vagrant as a development environment. + +.. note:: + + The Ansible playbook only sets up the environment which includes everything needed to get started. There is still a layer of manual configuration that needs to be done. The Ansible playbook installs PostgreSQL, Redis, Python and Poetry into the VM, and also sets up the repo for development. There is no need to use Docker since PostgreSQL and Redis are installed natively into the system. + +Requirements +^^^^^^^^^^^^ + +* Vagrant (w/ `VirtualBox WSL2 plugin `_) +* WSL2 +* Ansible (installed on WSL2 (you will need to execute the vagrant commands in WSL2)) + +Ansible roles needed: + +* ``geerlingguy.postgresql`` +* ``geerlingguy.redis`` +* ``staticdev.pyenv`` + + +In order to use Vagrant, you will need Oracle VirtualBox or VMWare Workstation installed on your machine. Once installed and properly configured, you can just run ``vagrant up`` (in your WSL2 or Linux environment) to provision and start it up, and connect to it by SSH or by VSCode. Environment Variables --------------------- -Kumiko v0.7+ includes an development mode feature, which will set up jishaku and a custom FS watcher. Later on, there may be more development features that will be included. Make sure you first install the dev dependencies first! And in order to enable it, set an environment variable called ``DEV_MODE`` to ``True``. \ No newline at end of file +Kumiko v0.7+ includes an development mode feature, which will set up jishaku and a custom FS watcher. The FS (File System) watcher is just like HMR (Hot Module Replacements). Once you press Ctrl+s in your cog, it will automatically reload it so the code executed is changed. Later on, there may be more development features that will be included. Make sure you first install the dev dependencies first! And in order to enable it, set an environment variable called ``DEV_MODE`` to ``True``. \ No newline at end of file diff --git a/Kumiko-Docs/source/guides/user/trying-out.rst b/Kumiko-Docs/source/guides/user/trying-out.rst index c3eb8dd5..c8881f4f 100644 --- a/Kumiko-Docs/source/guides/user/trying-out.rst +++ b/Kumiko-Docs/source/guides/user/trying-out.rst @@ -14,7 +14,7 @@ Prerequisites Standalone Requirements ^^^^^^^^^^^^^^^^^^^^^^^ -If you are running Kumiko on a standalone machine (w/o Docker Compose), you will need to install the following: +If you are running Kumiko on a standalone machine (w/o Docker Compose or using Systemd), you will need to install the following: - `PostgreSQL `_ - `Redis Stack `_ (or Redis w/ RedisJSON and RedisSearch modules loaded) @@ -54,6 +54,62 @@ Standalone (Docker CLI) sudo docker run -d --env-file .env --name Kumiko no767/kumiko:latest +Standalone (Systemd) +-------------------- + +**Before you start, ensure that you have PostgreSQL and Redis correctly configured and is running** + +1. Clone the repo + + .. code-block:: bash + + git clone https://github.com/No767/Kumiko.git && cd Kumiko + + + Or if you have the `gh` cli tool installed: + + .. code-block:: bash + + gh repo clone No767/Kumiko + + .. note:: + + By default, this will clone the dev branch. For stable releases, run ``git checkout master`` to checkout into stable releases (or checkout the latest tag) + +2. Set up the prod ENV file. During this step, please also fill your credentials in the ENV file + + .. code-block:: bash + + cp Envs/prod.env Bot/.env + +2. Create an systemd service file. This is an example, and you will need to edit it to point to the correct directory and user. + + .. code-block:: ini + + [Unit] + Description=Kumiko + After=network-online.target + Requires=postgresql.service + + [Service] + Type=simple + WorkingDirectory=/your/bots/directory + ExecStart=/usr/bin/python3 /your/bots/directory/Bot/kumikobot.py + User=username + Restart=on-failure + EnvironmentFile=/your/bots/directory/Bot/.env + + [Install] + WantedBy=multi-user.target + +3. Test whether you have everything set up. If you have ``make`` installed, you can run ``make prod-run`` in order to run the bot. Otherwise, just run ``kumikobot.py`` + +4. Run and enable the systemd service. + + .. code-block:: bash + + sudo systemctl enable --now kumiko + Docker Compose -------------- From fd85615a6ab36a4e1a671a131bb12c832d9fa66b Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Tue, 4 Jul 2023 03:08:32 -0700 Subject: [PATCH 128/184] [skip ci] Add Ansible playbooks --- .gitignore | 7 +++- Vagrantfile | 13 +++---- playbook.yml | 105 +++++++++++++++++++++++++++++++++++++++++++++++++++ postgres.yml | 5 +++ 4 files changed, 120 insertions(+), 10 deletions(-) create mode 100644 playbook.yml create mode 100644 postgres.yml diff --git a/.gitignore b/.gitignore index fd054975..b632800a 100644 --- a/.gitignore +++ b/.gitignore @@ -159,8 +159,11 @@ cython_debug/ # option (not recommended) you can uncomment the following to ignore the entire idea folder. .idea/ -# Vagrant project cache files -.vagrant +# Vagrant project cache files and others +.vagrant/ +inventory.yml +inv.yml + # VSC .vscode/ diff --git a/Vagrantfile b/Vagrantfile index 796eb9e5..57b40e01 100644 --- a/Vagrantfile +++ b/Vagrantfile @@ -5,13 +5,10 @@ Vagrant.configure("2") do |config| config.vm.define "kumiko_dev" config.vm.box = "generic/ubuntu2204" config.vm.synced_folder ".", "/home/vagrant/Kumiko", create: true - # config.vm.provision "ansible" do |ansible| - # ansible.verbose = "v" - # ansible.playbook = "playbook.yml" - # ansible.groups = { - # "dev" => ["kumiko_dev"] - # } - # end - config.vm.provision "shell", path: "scripts/vagrant-dev-provision.sh" + config.vm.provision "ansible" do |ansible| + ansible.verbose = "v" + ansible.playbook = "playbook.yml" + ansible.ask_become_pass = true + end end diff --git a/playbook.yml b/playbook.yml new file mode 100644 index 00000000..4de99c4f --- /dev/null +++ b/playbook.yml @@ -0,0 +1,105 @@ +- name: Setup PostgreSQL and Redis + hosts: dev + become: yes + become_method: sudo + roles: + - role: geerlingguy.postgresql + - role: geerlingguy.redis + +- name: Setup Python and Poetry + hosts: dev + roles: + - role: staticdev.pyenv + +- name: Install any dependecies + hosts: dev + become: yes + become_method: sudo + tasks: + - name: Install dependencies + ansible.builtin.apt: + update_cache: yes + pkg: + - curl + - libffi-dev + - git + - libnacl-dev + - libopus-dev + - python3-dev + +- name: Compile Python and install Poetry + hosts: dev + vars: + virtualenvs_inproject: true + virtualenvs_prefer_active_python: true + python_version: 3.11.4 + environment: + PATH: "{{ ansible_env.HOME }}/pyenv/bin:{{ ansible_env.PATH }}" + tasks: + - name: Install Python + ansible.builtin.shell: pyenv install "{{ python_version }}" -v + - name: Set global Python version + ansible.builtin.shell: pyenv global "{{ python_version }}" + - name: Rehash pyenv + ansible.builtin.shell: pyenv rehash + +- name: Setup Poetry + hosts: dev + vars: + virtualenvs_inproject: true + virtualenvs_prefer_active_python: true + tasks: + - name: Install Poetry # noqa command-instead-of-module + ansible.builtin.shell: curl -sSL https://install.python-poetry.org | python3 - + args: + creates: "{{ ansible_env.HOME }}/.local/bin/poetry" + + - name: Check Poetry virtualenvs.in-project config + ansible.builtin.command: ~/.local/bin/poetry config virtualenvs.in-project + register: poetry_in_project + changed_when: false + when: virtualenvs_inproject + + - name: Configure Poetry virtualenvs.in-project + ansible.builtin.command: ~/.local/bin/poetry config virtualenvs.in-project true + when: virtualenvs_inproject and poetry_in_project.stdout != "true" + + - name: Check Poetry virtualenvs.prefer-active-python config + ansible.builtin.command: ~/.local/bin/poetry config virtualenvs.prefer-active-python + register: poetry_prefer_active_python + changed_when: false + when: virtualenvs_prefer_active_python + + - name: Configure Poetry virtualenvs.prefer-active-python + ansible.builtin.command: ~/.local/bin/poetry config virtualenvs.prefer-active-python true + when: virtualenvs_prefer_active_python and poetry_prefer_active_python.stdout != "true" + +- name: Setup Kumiko repo + hosts: dev + vars: + kumiko_home: "{{ lookup('env', 'HOME') }}/Kumiko" + local_bin: "$PATH:{{ ansible_env.HOME }}/.local/bin:{{ ansible_env.HOME }}/pyenv/bin" + python_version: 3.11.4 + tasks: + - name: Ensure that local bin is in path + ansible.builtin.shell: | + export PATH={{ local_bin }} + echo export PATH={{ local_bin }} >> {{ ansible_env.HOME }}/.bashrc + - name: Clone Kumiko repo + ansible.builtin.git: + repo: "https://github.com/No767/Kumiko.git" + dest: "{{ kumiko_home }}" + version: dev + - name: Use local python version + ansible.builtin.shell: pyenv local {{ python_version }} + - name: Install Poetry dependencies + ansible.builtin.shell: | + poetry env use {{ python_version }} + poetry install + args: + chdir: "{{ kumiko_home }}" + - name: Setup Dev ENV file + ansible.builtin.shell: cp Envs/dev.env Bot/.env + args: + chdir: "{{ kumiko_home }}" + \ No newline at end of file diff --git a/postgres.yml b/postgres.yml new file mode 100644 index 00000000..b18c8d6b --- /dev/null +++ b/postgres.yml @@ -0,0 +1,5 @@ +postgresql_databases: + - name: kumiko +postgresql_users: + - name: kumiko + password: somepass # SET THE PASSWORD HERE! \ No newline at end of file From 1e4597a09d86cdabe047e3eeeb83e988871d8fb3 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Tue, 4 Jul 2023 03:11:30 -0700 Subject: [PATCH 129/184] [skip ci] Add prod envs --- Envs/prod.env | 28 ++++++++++++++++++++++++++++ 1 file changed, 28 insertions(+) create mode 100644 Envs/prod.env diff --git a/Envs/prod.env b/Envs/prod.env new file mode 100644 index 00000000..225cd0c9 --- /dev/null +++ b/Envs/prod.env @@ -0,0 +1,28 @@ +################################################################## +# Kumiko's Prod Example ENV # +# Replace the values with the appropriate values # +################################################################## + +# More than likely you will not need to use the prod token for testing +# In some cases where Kumiko is near prod, this will get used instead +KUMIKO_TOKEN=token + +# For the migrations system +# DO NOT TOUCH THIS UNLESS IT IS TO UPGRADE +TARGET_REVISION=rev3 + +# Search Cog API Keys +# THESE WILL BREAK THE COMMANDS IF YOU DO NOT HAVE THE KEYS HERE +GITHUB_API_KEY=key +REDDIT_ID=key +REDDIT_SECRET=key +TENOR_API_KEY=key + +# IPC Secret Key +# This is used to communicate with the IPC server +IPC_SECRET_KEY=key +IPC_HOST=127.0.0.1 + +# Prod Database Credentials - For PostgreSQL and Redis +POSTGRES_URI=postgres://user:password@localhost:5432/user +REDIS_URI=redis://localhost:6379/0 \ No newline at end of file From 96b221a8200408395694f2bf3c5aa8647aeb04cf Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Tue, 4 Jul 2023 03:14:20 -0700 Subject: [PATCH 130/184] Remove prisma --- poetry.lock | 134 +------------------------------------------------ pyproject.toml | 1 - 2 files changed, 1 insertion(+), 134 deletions(-) diff --git a/poetry.lock b/poetry.lock index c78d3638..7a74fba3 100644 --- a/poetry.lock +++ b/poetry.lock @@ -1319,17 +1319,6 @@ files = [ {file = "graphql_core-3.2.3-py3-none-any.whl", hash = "sha256:5766780452bd5ec8ba133f8bf287dc92713e3868ddd83aee4faab9fc3e303dc3"}, ] -[[package]] -name = "h11" -version = "0.14.0" -description = "A pure-Python, bring-your-own-I/O implementation of HTTP/1.1" -optional = false -python-versions = ">=3.7" -files = [ - {file = "h11-0.14.0-py3-none-any.whl", hash = "sha256:e3fe4ac4b851c468cc8363d500db52c2ead036020723024a109d37346efaa761"}, - {file = "h11-0.14.0.tar.gz", hash = "sha256:8f19fbbe99e72420ff35c00b27a34cb9937e902a8b810e2c88300c6f0a3b699d"}, -] - [[package]] name = "hiredis" version = "2.2.3" @@ -1428,50 +1417,6 @@ files = [ {file = "hiredis-2.2.3.tar.gz", hash = "sha256:e75163773a309e56a9b58165cf5a50e0f84b755f6ff863b2c01a38918fe92daa"}, ] -[[package]] -name = "httpcore" -version = "0.17.2" -description = "A minimal low-level HTTP client." -optional = false -python-versions = ">=3.7" -files = [ - {file = "httpcore-0.17.2-py3-none-any.whl", hash = "sha256:5581b9c12379c4288fe70f43c710d16060c10080617001e6b22a3b6dbcbefd36"}, - {file = "httpcore-0.17.2.tar.gz", hash = "sha256:125f8375ab60036db632f34f4b627a9ad085048eef7cb7d2616fea0f739f98af"}, -] - -[package.dependencies] -anyio = ">=3.0,<5.0" -certifi = "*" -h11 = ">=0.13,<0.15" -sniffio = "==1.*" - -[package.extras] -http2 = ["h2 (>=3,<5)"] -socks = ["socksio (==1.*)"] - -[[package]] -name = "httpx" -version = "0.24.1" -description = "The next generation HTTP client." -optional = false -python-versions = ">=3.7" -files = [ - {file = "httpx-0.24.1-py3-none-any.whl", hash = "sha256:06781eb9ac53cde990577af654bd990a4949de37a28bdb4a230d434f3a30b9bd"}, - {file = "httpx-0.24.1.tar.gz", hash = "sha256:5853a43053df830c20f8110c5e69fe44d035d850b2dfe795e196f00fdb774bdd"}, -] - -[package.dependencies] -certifi = "*" -httpcore = ">=0.15.0,<0.18.0" -idna = "*" -sniffio = "*" - -[package.extras] -brotli = ["brotli", "brotlicffi"] -cli = ["click (==8.*)", "pygments (==2.*)", "rich (>=10,<14)"] -http2 = ["h2 (>=3,<5)"] -socks = ["socksio (==1.*)"] - [[package]] name = "identify" version = "2.5.24" @@ -2429,31 +2374,6 @@ nodeenv = ">=0.11.1" pyyaml = ">=5.1" virtualenv = ">=20.10.0" -[[package]] -name = "prisma" -version = "0.9.0" -description = "Prisma Client Python is an auto-generated and fully type-safe database client" -optional = false -python-versions = ">=3.7.0" -files = [ - {file = "prisma-0.9.0-py3-none-any.whl", hash = "sha256:bff4b239faeb5d427e8337eadc6fe2d2e2ee4f82e30048fd7de46f8aaf9ef07d"}, - {file = "prisma-0.9.0.tar.gz", hash = "sha256:1f9321efc099401995067d921cab848f5a82cd64ecdb5924fa91fb2f1379897f"}, -] - -[package.dependencies] -click = ">=7.1.2" -httpx = ">=0.19.0" -jinja2 = ">=2.11.2" -nodeenv = "*" -pydantic = ">=1.8.0" -python-dotenv = ">=0.12.0" -tomlkit = "*" -typing-extensions = ">=4.0.1" - -[package.extras] -all = ["nodejs-bin"] -node = ["nodejs-bin"] - [[package]] name = "pycares" version = "4.3.0" @@ -2532,58 +2452,6 @@ files = [ {file = "pycparser-2.21.tar.gz", hash = "sha256:e644fdec12f7872f86c58ff790da456218b10f863970249516d60a5eaca77206"}, ] -[[package]] -name = "pydantic" -version = "1.10.9" -description = "Data validation and settings management using python type hints" -optional = false -python-versions = ">=3.7" -files = [ - {file = "pydantic-1.10.9-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:e692dec4a40bfb40ca530e07805b1208c1de071a18d26af4a2a0d79015b352ca"}, - {file = "pydantic-1.10.9-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:3c52eb595db83e189419bf337b59154bdcca642ee4b2a09e5d7797e41ace783f"}, - {file = "pydantic-1.10.9-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:939328fd539b8d0edf244327398a667b6b140afd3bf7e347cf9813c736211896"}, - {file = "pydantic-1.10.9-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:b48d3d634bca23b172f47f2335c617d3fcb4b3ba18481c96b7943a4c634f5c8d"}, - {file = "pydantic-1.10.9-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:f0b7628fb8efe60fe66fd4adadd7ad2304014770cdc1f4934db41fe46cc8825f"}, - {file = "pydantic-1.10.9-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:e1aa5c2410769ca28aa9a7841b80d9d9a1c5f223928ca8bec7e7c9a34d26b1d4"}, - {file = "pydantic-1.10.9-cp310-cp310-win_amd64.whl", hash = "sha256:eec39224b2b2e861259d6f3c8b6290d4e0fbdce147adb797484a42278a1a486f"}, - {file = "pydantic-1.10.9-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:d111a21bbbfd85c17248130deac02bbd9b5e20b303338e0dbe0faa78330e37e0"}, - {file = "pydantic-1.10.9-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:2e9aec8627a1a6823fc62fb96480abe3eb10168fd0d859ee3d3b395105ae19a7"}, - {file = "pydantic-1.10.9-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:07293ab08e7b4d3c9d7de4949a0ea571f11e4557d19ea24dd3ae0c524c0c334d"}, - {file = "pydantic-1.10.9-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:7ee829b86ce984261d99ff2fd6e88f2230068d96c2a582f29583ed602ef3fc2c"}, - {file = "pydantic-1.10.9-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:4b466a23009ff5cdd7076eb56aca537c745ca491293cc38e72bf1e0e00de5b91"}, - {file = "pydantic-1.10.9-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:7847ca62e581e6088d9000f3c497267868ca2fa89432714e21a4fb33a04d52e8"}, - {file = "pydantic-1.10.9-cp311-cp311-win_amd64.whl", hash = "sha256:7845b31959468bc5b78d7b95ec52fe5be32b55d0d09983a877cca6aedc51068f"}, - {file = "pydantic-1.10.9-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:517a681919bf880ce1dac7e5bc0c3af1e58ba118fd774da2ffcd93c5f96eaece"}, - {file = "pydantic-1.10.9-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:67195274fd27780f15c4c372f4ba9a5c02dad6d50647b917b6a92bf00b3d301a"}, - {file = "pydantic-1.10.9-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:2196c06484da2b3fded1ab6dbe182bdabeb09f6318b7fdc412609ee2b564c49a"}, - {file = "pydantic-1.10.9-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:6257bb45ad78abacda13f15bde5886efd6bf549dd71085e64b8dcf9919c38b60"}, - {file = "pydantic-1.10.9-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:3283b574b01e8dbc982080d8287c968489d25329a463b29a90d4157de4f2baaf"}, - {file = "pydantic-1.10.9-cp37-cp37m-win_amd64.whl", hash = "sha256:5f8bbaf4013b9a50e8100333cc4e3fa2f81214033e05ac5aa44fa24a98670a29"}, - {file = "pydantic-1.10.9-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:b9cd67fb763248cbe38f0593cd8611bfe4b8ad82acb3bdf2b0898c23415a1f82"}, - {file = "pydantic-1.10.9-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:f50e1764ce9353be67267e7fd0da08349397c7db17a562ad036aa7c8f4adfdb6"}, - {file = "pydantic-1.10.9-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:73ef93e5e1d3c8e83f1ff2e7fdd026d9e063c7e089394869a6e2985696693766"}, - {file = "pydantic-1.10.9-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:128d9453d92e6e81e881dd7e2484e08d8b164da5507f62d06ceecf84bf2e21d3"}, - {file = "pydantic-1.10.9-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:ad428e92ab68798d9326bb3e5515bc927444a3d71a93b4a2ca02a8a5d795c572"}, - {file = "pydantic-1.10.9-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:fab81a92f42d6d525dd47ced310b0c3e10c416bbfae5d59523e63ea22f82b31e"}, - {file = "pydantic-1.10.9-cp38-cp38-win_amd64.whl", hash = "sha256:963671eda0b6ba6926d8fc759e3e10335e1dc1b71ff2a43ed2efd6996634dafb"}, - {file = "pydantic-1.10.9-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:970b1bdc6243ef663ba5c7e36ac9ab1f2bfecb8ad297c9824b542d41a750b298"}, - {file = "pydantic-1.10.9-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:7e1d5290044f620f80cf1c969c542a5468f3656de47b41aa78100c5baa2b8276"}, - {file = "pydantic-1.10.9-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:83fcff3c7df7adff880622a98022626f4f6dbce6639a88a15a3ce0f96466cb60"}, - {file = "pydantic-1.10.9-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:0da48717dc9495d3a8f215e0d012599db6b8092db02acac5e0d58a65248ec5bc"}, - {file = "pydantic-1.10.9-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:0a2aabdc73c2a5960e87c3ffebca6ccde88665616d1fd6d3db3178ef427b267a"}, - {file = "pydantic-1.10.9-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:9863b9420d99dfa9c064042304868e8ba08e89081428a1c471858aa2af6f57c4"}, - {file = "pydantic-1.10.9-cp39-cp39-win_amd64.whl", hash = "sha256:e7c9900b43ac14110efa977be3da28931ffc74c27e96ee89fbcaaf0b0fe338e1"}, - {file = "pydantic-1.10.9-py3-none-any.whl", hash = "sha256:6cafde02f6699ce4ff643417d1a9223716ec25e228ddc3b436fe7e2d25a1f305"}, - {file = "pydantic-1.10.9.tar.gz", hash = "sha256:95c70da2cd3b6ddf3b9645ecaa8d98f3d80c606624b6d245558d202cd23ea3be"}, -] - -[package.dependencies] -typing-extensions = ">=4.2.0" - -[package.extras] -dotenv = ["python-dotenv (>=0.10.4)"] -email = ["email-validator (>=1.0.3)"] - [[package]] name = "pygments" version = "2.15.1" @@ -3550,4 +3418,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "54d9a344c37971fe437d4e6f4b23712bc7845ce5308289c25f2fb39734367127" +content-hash = "62f0c3e74f19f113ca786d5af940c3353316260b2d5f8be43c7516d3aa982e92" diff --git a/pyproject.toml b/pyproject.toml index 3dac8086..1eaf4d25 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -15,7 +15,6 @@ asyncpraw = "^7.7.0" uvloop = "^0.17.0" gql = { extras = ["aiohttp"], version = "^3.4.1" } better-ipc = "^2.0.3" -prisma = "^0.9.0" redis = {extras = ["hiredis"], version = "^4.6.0"} ciso8601 = "^2.3.0" faust-cchardet = "^2.1.18" From ecaea6d21e17897c970320ab9974d5fdac181556 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Tue, 4 Jul 2023 03:52:27 -0700 Subject: [PATCH 131/184] Update workflows + changelog --- .github/workflows/docker-build.yml | 20 ++-- .github/workflows/snyk.yml | 4 +- changelog.md | 147 ++++++++++++++++++++--------- 3 files changed, 112 insertions(+), 59 deletions(-) diff --git a/.github/workflows/docker-build.yml b/.github/workflows/docker-build.yml index 2f5cd5a4..bf15f713 100644 --- a/.github/workflows/docker-build.yml +++ b/.github/workflows/docker-build.yml @@ -24,16 +24,16 @@ jobs: images: | ghcr.io/no767/kumiko tags: | - type=semver,pattern={{raw}},suffix=-bullseye - type=semver,pattern={{version}},suffix=-bullseye - type=semver,pattern={{major}}.{{minor}},suffix=-bullseye - type=semver,pattern={{major}},suffix=-bullseye + type=semver,pattern={{raw}},suffix=-bookworm + type=semver,pattern={{version}},suffix=-bookworm + type=semver,pattern={{major}}.{{minor}},suffix=-bookworm + type=semver,pattern={{major}},suffix=-bookworm type=semver,pattern={{raw}} type=semver,pattern={{version}} type=semver,pattern={{major}}.{{minor}} type=semver,pattern={{major}} type=edge,branch=dev - type=edge,branch=dev,suffix=-bullseye + type=edge,branch=dev,suffix=-bookworm - name: Setup Docker Buildx id: buildx @@ -84,16 +84,16 @@ jobs: images: | no767/kumiko tags: | - type=semver,pattern={{raw}},suffix=-bullseye - type=semver,pattern={{version}},suffix=-bullseye - type=semver,pattern={{major}}.{{minor}},suffix=-bullseye - type=semver,pattern={{major}},suffix=-bullseye + type=semver,pattern={{raw}},suffix=-bookworm + type=semver,pattern={{version}},suffix=-bookworm + type=semver,pattern={{major}}.{{minor}},suffix=-bookworm + type=semver,pattern={{major}},suffix=-bookworm type=semver,pattern={{raw}} type=semver,pattern={{version}} type=semver,pattern={{major}}.{{minor}} type=semver,pattern={{major}} type=edge,branch=dev - type=edge,branch=dev,suffix=-bullseye + type=edge,branch=dev,suffix=-bookworm - name: Setup Docker Buildx id: buildx diff --git a/.github/workflows/snyk.yml b/.github/workflows/snyk.yml index 14543e32..7d40aaad 100644 --- a/.github/workflows/snyk.yml +++ b/.github/workflows/snyk.yml @@ -17,10 +17,10 @@ jobs: uses: actions/setup-python@v4.6.1 with: python-version: '3.11' - - name: Set up Node.js 18 + - name: Set up Node.js 20 uses: actions/setup-node@v3.6.0 with: - node-version: '18' + node-version: '20' - name: Install Snyk CLI run: | npm install --location=global snyk@latest diff --git a/changelog.md b/changelog.md index 7de76ae0..926ae3f8 100644 --- a/changelog.md +++ b/changelog.md @@ -1,62 +1,115 @@ -# ✨ Kumiko v0.7.0 ✨ +# ✨ Kumiko v0.9.0 ✨ -This release is the foundation for v0.8.x. This release implements almost everything back (excluding the advanced moderation features, and economy system) from previous versions of Kumiko, and now Kumiko is migrated to Discord.py (sorry Pycord devs). The economy system and improved moderation commands will be coming in v0.8.x instead. There might be some that might have been missed, so if you want to see the full list of changes, please see the changes here: [`v0.6.0...v0.7.x`](https://github.com/No767/Kumiko/compare/v0.6.0...v0.7.0) +More reworks of literally everything... This release migrates from Prisma to pure SQL (asyncpg), and fully stabilities the repo to use discord.py instead of Pycord. Nearly all of the planned features are implemented in this release, except the economy module. +For the full list of changes, please see them here: [`v0.8.x...v0.9.0`](https://github.com/No767/Kumiko/compare/v0.8.0...v0.9.0) ## :boom: Breaking Changes :boom: -- Literally rewrote Kumiko from the ground up to use Discord.py instead of Pycord. Expect a ton of things to be broken -- A ton of cogs, and commands have been either moved or deleted since v0.6.x. Please consider resyncing your commands with the include dev-tool cog (or by activating jishaku) +- All of the SQL queries have been rewritten to use SQL w/ asyncpg instead of Prisma +- A ton of cogs, and commands have been either moved or deleted since v0.8.x. Please consider resyncing your commands with the include dev-tool cog (or by activating jishaku) ## ✨ TD;LR -- Migrated from Pycord to Discord.py. Literally this took way too long -- Kumiko now supports both prefixed and slash commands (default prefix is `>`) -- Migration from Coredis to Redis-py, and migration from Tortoise ORM to Prisma -- Kumiko is now properly type hinted/statically typed now. +- Migration from Prisma to asyncpg +- Kumiko now supports custom prefixes (max is 10). The default that will be set is `>` +- asyncpg-trek migration system +- Kumiko's logging module has been implemented +- Docs has been merged into one repo (https://kumiko.readthedocs.io/en/latest/index.html) ## 🛠️ Changes -- RedisCheck is now fully recursive -- Properly implemented static type checking -- Improved DB connections via DB cog -- Migrate searches cog to dpy -- Spilt Reddit and GitHub commands to their respective cogs -- Use `@app_commands.describe` to describe the slash command inputs. Removed the docstring args bc it was conflicting w/ the help cmd -- Now using a singleton object for storing Redis connection pools. (Known as the KumikoCPM) -- Improved the Vagrantfile (possible Ansible provisioning in the future) -- Using orjson for parsing JSON instead of pysimdjson or cysimdjson +- Allow actions commands to greedily consume users to mention +- Replaced RedisCheck with an simple ping check (`ensureOpenRedisConn`) +- Replace all Prisma related code with asyncpg code +- Reuse AIOHTTP `ClientSession`, `asyncpg.Pool`, `redis.asyncio.connection.ConnectionPool`, and `LRU` objects throughout the lifecycle of the bot +- Hide `.python-version` file from the repo +- Expect `id` and `redis_pool` args to be in an function when using `@cache` or `@cacheJson` decos +- Update docs to add new instructions for hosting, and new requirements +- Don't stack context managers, but rather spawn 3 new ones in one go (this is recommended instead) +- Update Dockerfile to use Debian 12 (Bookworm) +- Use `Embed.timestamp` for some embeds to show timestamps +- Replaced `.gitignore` with a proper one from GitHub -## ✨ Additions -- Context manager for Prisma sessions - Useful for debugging and testing -- Recursive RedisCheck coroutine - Actually now cleans up the stack calls for once (thanks to a base case) -- Vasic help command - Will be improved in v0.8.x -- New unit tests -- Pagination - Taken from Rapptz's (Danny) RoboDanny bot, and improved to work w/ Kumiko -- EmbedListSource for paginating embeds -- TextSources, and ListSources for paginating text and lists -- Actions cog - Replacement for the UwU Cog -- Error Handler cog - Now uses custom exceptions -- exceptions and utils (including datetime parsing utils, and much much more) -- Dev Mode - It's an environment variable that toggles the dev mode. This is useful for testing, and debugging Kumiko (includes Jishaku and a custom extension reloader) +## ✨ Additions +- Migrations system using asyncpg-trek +- SQL migrations +- SQL based code to replace Prisma +- Context manager based logging system +- Custom prefix module (aka Kumiko supports custom prefixes for guilds) +- Ansible playbooks, proper Vagrant config +- Discord API events handler, custom dispatch events +- Prefix utils +- Better logging system +- Ping checks to ensure that the connections are open for PostgreSQL and Redis +- Docs merged into one repo - this repo ## ➖ Removals -- MsgPack Serialization -- Literally all of the cogs from v0.6.x -- Removed python-dateutil, numpy, pytimeparse, aiocache, ormsgpack, and pysimdjson (yay no C compilations anymore) -- Old libs -- Pycord itself -- Builtlins cache in favor of KumikoCPM +- Global KumikoCPM variable in favor of having it stored during runtime instead +- Old economy packages +- cog-ext module +- Prisma along with other unused libs # ⬆️ Dependabot Updates -- \[Actions](deps)\: Bump actions/cache from 3.3.0 to 3.3.1 (#282) (@dependabot) -- \[pip](deps-dev)\: Bump pyright from 1.1.298 to 1.1.299 (#283) (@dependabot) -- \[pip](deps-dev)\: Bump pre-commit from 3.1.1 to 3.2.0 (#284) (@dependabot) -- \[pip](deps)\: Bump redis from 4.5.1 to 4.5.2 (#285) (@dependabot) -- \[pip](deps-dev)\: Bump pytest-asyncio from 0.20.3 to 0.21.0 (#286) (@\dependabot) -- \[pip](deps)\: Bump orjson from 3.8.7 to 3.8.8 (#288) (@dependabot) -- \[pip](deps-dev)\: Bump pyright from 1.1.299 to 1.1.300 (#289) (@dependabot) -- \[pip](deps)\: Bump redis from 4.5.2 to 4.5.3 (#290) (@dependabot) -- \[pip](deps-dev)\: Bump pre-commit from 3.2.0 to 3.2.1 (#291) (@dependabot) -- \[pip](deps)\: Bump orjson from 3.8.8 to 3.8.9 (#293) (@dependabot) -- \[pip](deps-dev)\: Bump pyright from 1.1.300 to 1.1.301 (#294) (@dependabot) -- \[pip](deps)\: Bump redis from 4.5.3 to 4.5.4 (#295) (@dependabot) +- \[pip](deps-dev)\: Bump pre-commit from 3.2.1 to 3.2.2 (#300) (@dependabot) +- \[pip](deps-dev)\: Bump pyright from 1.1.301 to 1.1.302 (#301) (@dependabot) +- \[pip](deps-dev)\: Bump pytest from 7.2.2 to 7.3.0 (#302) (@dependabot) +- \[pip](deps)\: Bump orjson from 3.8.9 to 3.8.10 (#303) (@dependabot) +- \[pip](deps-dev)\: Bump pytest from 7.3.0 to 7.3.1 (#304) (@dependabot) +- \[pip](deps-dev)\: Bump pyright from 1.1.302 to 1.1.303 (#305) (@dependabot) +- \[pip](deps-dev)\: Bump ruff from 0.0.261 to 0.0.262 (#306) (@dependabot) +- \[Actions](deps)\: Bump actions/setup-python from 4.5.0 to 4.6.0 (#307) (@dependabot) +- \[pip](deps-dev)\: Bump pyright from 1.1.303 to 1.1.304 (#308) (@dependabot) +- \[pip](deps-dev)\: Bump sphinx from 6.1.3 to 6.2.0 (#310) (@dependabot) +- \[pip](deps-dev)\: Bump nox from 2022.11.21 to 2023.4.22 (@dependabot) +- \[pip](deps-dev)\: Bump sphinx from 6.2.0 to 6.2.1 (#312) (@dependabot) +- \[pip](deps-dev)\: Bump ruff from 0.0.262 to 0.0.263 (#313) (@dependabot) +- \[pip](deps-dev)\: Bump pyright from 1.1.304 to 1.1.305 (#314) (@dependabot) +- \[pip](deps)\: Bump orjson from 3.8.10 to 3.8.11 (#315) (@dependabot) +- \[pip](deps)\: Bump discord-py from 2.2.2 to 2.2.3 (#316) (@dependabot) +- \[pip](deps-dev)\: Bump pre-commit from 3.2.2 to 3.3.0 (#317) (@dependabot) +- \[pip](deps-dev)\: Bump pre-commit from 3.3.0 to 3.3.1 (#318) (@dependabot) +- \[pip](deps-dev)\: Bump ruff from 0.0.263 to 0.0.264 (#319) (@dependabot) +- \[pip](deps-dev)\: Bump pyright from 1.1.305 to 1.1.306 (#320) (@dependabot) +- \[pip](deps-dev)\: Bump ruff from 0.0.264 to 0.0.265 (#321) (@dependabot) +- \[pip](deps)\: Bump orjson from 3.8.11 to 3.8.12 (#322) (@dependabot) +- \[pip](deps)\: Bump redis from 4.5.4 to 4.5.5 (#324) (@dependabot) +- \[pip](deps)\: Bump gql from 3.4.0 to 3.4.1 (#323) (@dependabot) +- \[pip](deps-dev)\: Bump pyright from 1.1.306 to 1.1.307 (#325) (@dependabot) +- \[pip](deps-dev)\: Bump pyright from 1.1.307 to 1.1.308 (#326) (@dependabot) +- \[pip](deps-dev)\: Bump ruff from 0.0.265 to 0.0.267 (#327) (@dependabot) +- \[pip](deps-dev)\: Bump pyright from 1.1.308 to 1.1.309 (#328) (@dependabot) +- \[pip](deps-dev)\: Bump pre-commit from 3.3.1 to 3.3.2 (#329) (@dependabot) +- \[pip](deps-dev)\: Bump ruff from 0.0.267 to 0.0.269 (#330) (@dependabot) +- \[pip](deps-dev)\: Bump furo from 2023.3.27 to 2023.5.20 (#331) (@dependabot) +- \[pip](security)\: Bump requests from 2.28.2 to 2.31.0 (#332) (@dependabot) +- \[Actions](deps)\: Bump actions/setup-python from 4.6.0 to 4.6.1 (#333) (@dependabot) +- \[pip](deps)\: Bump orjson from 3.8.12 to 3.8.13 (#334) (@dependabot) +- \[pip](security)\: Bump tornado from 6.2 to 6.3.2 (#336) (@dependabot) +- \[pip](deps-dev)\: Bump pyright from 1.1.309 to 1.1.310 (#337) (@dependabot) +- \[pip](deps-dev)\: Bump pytest-cov from 4.0.0 to 4.1.0 (#335) (@dependabot) +- \[pip](deps-dev)\: Bump ruff from 0.0.269 to 0.0.270 (#338) (@dependabot) +- \[pip](deps)\: Bump orjson from 3.8.13 to 3.8.14 (#339) (@dependabot) +- \[pip](deps-dev)\: Bump pyright from 1.1.310 to 1.1.311 (#340) (@dependabot) +- \[pip](deps)\: Bump orjson from 3.8.14 to 3.9.0 (#341) (@dependabot) +- \[pip](deps-dev)\: Bump pyinstrument from 4.4.0 to 4.5.0 (#342) (@dependabot) +- \[pip](deps-dev)\: Bump ruff from 0.0.270 to 0.0.271 (#343) (@dependabot) +- \[pip](deps-dev)\: Bump pyright from 1.1.311 to 1.1.313 (#344) (@dependabot) +- \[pip](deps-dev)\: Bump ruff from 0.0.271 to 0.0.272 (#345) (@dependabot) +- \[Actions](deps)\: Bump docker/build-push-action from 4.0.0 to 4.1.0 (#346) (@dependabot) +- \[pip](deps)\: Bump orjson from 3.9.0 to 3.9.1 (#347) (@dependabot) +- \[pip](deps-dev)\: Bump pytest from 7.3.1 to 7.3.2 (#348) (@dependabot) +- \[pip](deps)\: Bump prisma from 0.8.2 to 0.9.0 (#349) (@dependabot) +- \[pip](deps)\: Bump discord-py from 2.2.3 to 2.3.0 (#350) (@dependabot) +- \[Actions](deps)\: Bump docker/build-push-action from 4.1.0 to 4.1.1 (#352) (@dependabot) +- \[pip](deps-dev)\: Bump myst-parser from 1.0.0 to 2.0.0 (@dependabot) +- \[pip](deps-dev)\: Bump pre-commit from 3.3.2 to 3.3.3 (#354) (@dependabot) +- \[pip](deps-dev)\: Bump pyright from 1.1.313 to 1.1.314 (#356) (@dependabot) +- \[pip](deps-dev)\: Bump sphinx from 6.2.1 to 7.0.1 (@dependabot) +- \[pip](deps-dev)\: Bump pyright from 1.1.314 to 1.1.315 (#357) (@dependabot) +- \[pip](deps-dev)\: Bump ruff from 0.0.272 to 0.0.274 (#358) (@dependabot) +- \[pip](deps-dev)\: Bump ruff from 0.0.274 to 0.0.275 (#359) (@dependabot) +- \[pip](deps-dev)\: Bump pytest from 7.3.2 to 7.4.0 (#360) (@dependabot) +- \[pip](deps)\: Bump discord-py from 2.3.0 to 2.3.1 (#361) (@dependabot) +- \[pip](deps)\: Bump redis from 4.5.5 to 4.6.0 (#363) (@dependabot) +- \[pip](deps-dev)\: Bump pyright from 1.1.315 to 1.1.316 (#362) (@dependabot) +- \[pip](deps)\: Bump prisma from 0.9.0 to 0.9.1 (#367) (@dependabot) From b402b2e46336db2685340ae04aae57eee957b89e Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Tue, 4 Jul 2023 04:04:53 -0700 Subject: [PATCH 132/184] Slience Prisma --- Bot/Libs/ui/economy/views.py | 2 +- Bot/unloaded_cogs/economy.py | 2 +- Bot/unloaded_cogs/socket-events.py | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/Bot/Libs/ui/economy/views.py b/Bot/Libs/ui/economy/views.py index 0e50cc81..ae04e3cc 100644 --- a/Bot/Libs/ui/economy/views.py +++ b/Bot/Libs/ui/economy/views.py @@ -1,6 +1,6 @@ import discord from Libs.utils import Embed -from prisma.models import User +from prisma.models import User # type: ignore class RegisterView(discord.ui.View): diff --git a/Bot/unloaded_cogs/economy.py b/Bot/unloaded_cogs/economy.py index 2f6c0533..c4a37c88 100644 --- a/Bot/unloaded_cogs/economy.py +++ b/Bot/unloaded_cogs/economy.py @@ -4,7 +4,7 @@ from Libs.economy import getUser from Libs.ui.economy import RegisterView from Libs.utils import Embed, parseDatetime -from prisma.models import User +from prisma.models import User # type: ignore class Economy(commands.Cog): diff --git a/Bot/unloaded_cogs/socket-events.py b/Bot/unloaded_cogs/socket-events.py index 657ece2d..00acbf41 100644 --- a/Bot/unloaded_cogs/socket-events.py +++ b/Bot/unloaded_cogs/socket-events.py @@ -1,7 +1,7 @@ import discord from discord.ext import commands from kumikocore import KumikoCore -from prisma.models import Guild +from prisma.models import Guild # type: ignore class SocketEvents(commands.Cog): From 4b35d82168ba59fbbdb127546c35de06b1202a63 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 4 Jul 2023 18:24:59 +0000 Subject: [PATCH 133/184] [pip](deps-dev): Bump ruff from 0.0.275 to 0.0.276 (#370) Bumps [ruff](https://github.com/astral-sh/ruff) from 0.0.275 to 0.0.276. - [Release notes](https://github.com/astral-sh/ruff/releases) - [Changelog](https://github.com/astral-sh/ruff/blob/main/BREAKING_CHANGES.md) - [Commits](https://github.com/astral-sh/ruff/compare/v0.0.275...v0.0.276) --- updated-dependencies: - dependency-name: ruff dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 38 +++++++++++++++++++------------------- pyproject.toml | 2 +- 2 files changed, 20 insertions(+), 20 deletions(-) diff --git a/poetry.lock b/poetry.lock index 27da1f38..8e7397c7 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2739,28 +2739,28 @@ idna2008 = ["idna"] [[package]] name = "ruff" -version = "0.0.275" +version = "0.0.276" description = "An extremely fast Python linter, written in Rust." optional = false python-versions = ">=3.7" files = [ - {file = "ruff-0.0.275-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:5e6554a072e7ce81eb6f0bec1cebd3dcb0e358652c0f4900d7d630d61691e914"}, - {file = "ruff-0.0.275-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:1cc599022fe5ffb143a965b8d659eb64161ab8ab4433d208777eab018a1aab67"}, - {file = "ruff-0.0.275-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:5206fc1cd8c1c1deadd2e6360c0dbcd690f1c845da588ca9d32e4a764a402c60"}, - {file = "ruff-0.0.275-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:0c4e6468da26f77b90cae35319d310999f471a8c352998e9b39937a23750149e"}, - {file = "ruff-0.0.275-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:0dbdea02942131dbc15dd45f431d152224f15e1dd1859fcd0c0487b658f60f1a"}, - {file = "ruff-0.0.275-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:22efd9f41af27ef8fb9779462c46c35c89134d33e326c889971e10b2eaf50c63"}, - {file = "ruff-0.0.275-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:2c09662112cfa22d7467a19252a546291fd0eae4f423e52b75a7a2000a1894db"}, - {file = "ruff-0.0.275-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:80043726662144876a381efaab88841c88e8df8baa69559f96b22d4fa216bef1"}, - {file = "ruff-0.0.275-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5859ee543b01b7eb67835dfd505faa8bb7cc1550f0295c92c1401b45b42be399"}, - {file = "ruff-0.0.275-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:c8ace4d40a57b5ea3c16555f25a6b16bc5d8b2779ae1912ce2633543d4e9b1da"}, - {file = "ruff-0.0.275-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:8347fc16aa185aae275906c4ac5b770e00c896b6a0acd5ba521f158801911998"}, - {file = "ruff-0.0.275-py3-none-musllinux_1_2_i686.whl", hash = "sha256:ec43658c64bfda44fd84bbea9da8c7a3b34f65448192d1c4dd63e9f4e7abfdd4"}, - {file = "ruff-0.0.275-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:508b13f7ca37274cceaba4fb3ea5da6ca192356323d92acf39462337c33ad14e"}, - {file = "ruff-0.0.275-py3-none-win32.whl", hash = "sha256:6afb1c4422f24f361e877937e2a44b3f8176774a476f5e33845ebfe887dd5ec2"}, - {file = "ruff-0.0.275-py3-none-win_amd64.whl", hash = "sha256:d9b264d78621bf7b698b6755d4913ab52c19bd28bee1a16001f954d64c1a1220"}, - {file = "ruff-0.0.275-py3-none-win_arm64.whl", hash = "sha256:a19ce3bea71023eee5f0f089dde4a4272d088d5ac0b675867e074983238ccc65"}, - {file = "ruff-0.0.275.tar.gz", hash = "sha256:a63a0b645da699ae5c758fce19188e901b3033ec54d862d93fcd042addf7f38d"}, + {file = "ruff-0.0.276-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:c150912b8ebde843c10b33db90705d4fee48db6f05441e5d143be9f4c2f35df5"}, + {file = "ruff-0.0.276-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:5e9cd7238d34f24d7ccfadcce4dc6807b8c5a390f547dd7236d06488d9d6f40f"}, + {file = "ruff-0.0.276-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:fc7dc557cc3fa2a03a88e99425ceee91429cc7432e5a41087850c1629294faed"}, + {file = "ruff-0.0.276-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:13e5983836ae383c04de213954da731f14ea884aaf74467abc47e1d79d8cf1b7"}, + {file = "ruff-0.0.276-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:4ac65df96be3e2f4b10bc97bbb624152281611b06ef1068d5bb064b7ad35d800"}, + {file = "ruff-0.0.276-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:d070a64de4affd17e006d6986ef25601dbbc6b373844ece5396c33900f8b8563"}, + {file = "ruff-0.0.276-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:2edcd6948a21fa7fb4594094da37a1aa1d205b7abaa718bd27d48ba1d7977348"}, + {file = "ruff-0.0.276-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:57c49b525d8ca3838d8b614f42e342077bed95aedd9fe6e6ec419f39320c214e"}, + {file = "ruff-0.0.276-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5980960a748ada3ddfe4ea7ff3a01b9113c456a14cb1a39b4c30783012d4cba6"}, + {file = "ruff-0.0.276-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:12be4f007114cf5ed1242e522762651539521ec32ae0210cc4b8dfe434a872f0"}, + {file = "ruff-0.0.276-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:6ed8fc729b3e7b9f20a4e2aa6f24c798b06912f8a94cb3e8fd590eba055780df"}, + {file = "ruff-0.0.276-py3-none-musllinux_1_2_i686.whl", hash = "sha256:735d724031212c2ab63fafdea49d4581ae866a1180d06c29b0b5481228ca6bb9"}, + {file = "ruff-0.0.276-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:100ad9055d50977c2b4ab3de0db62d6e525bcd4aafbb660a842733bdbf650be9"}, + {file = "ruff-0.0.276-py3-none-win32.whl", hash = "sha256:1b34a3673b2e5d97df8f7f04090c0b74e9ae6d3d172921d0e0781192954afddf"}, + {file = "ruff-0.0.276-py3-none-win_amd64.whl", hash = "sha256:02deadc0f6abead6cc2d38ddd7100a52aba27a0d90315facaa44b8b4acdba162"}, + {file = "ruff-0.0.276-py3-none-win_arm64.whl", hash = "sha256:a6bd5b53ac689a43c7afc45bd574a7b3efe0ceb192e26e95a055c770ef2045b9"}, + {file = "ruff-0.0.276.tar.gz", hash = "sha256:d456c86eb6ce9225507f24fcc7bf72fa031bb7cc750023310e62889bf4ad4b6a"}, ] [[package]] @@ -3381,4 +3381,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "07126d4912e0238ad6e578192cb34c5610dd91d387af4b1db4e301e86e35bea6" +content-hash = "8b21561737cfcd5f0c525214f57ba7a91f86455ec55ab1450dfce4a2915658d8" diff --git a/pyproject.toml b/pyproject.toml index 8646f92f..741ec308 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -35,7 +35,7 @@ pyinstrument = "^4.5.0" pyright = "^1.1.316" watchfiles = "^0.19.0" jishaku = "^2.5.1" -ruff = "^0.0.275" +ruff = "^0.0.276" [tool.poetry.group.docs.dependencies] From 927eb6dee61ee50d9620d11cf0e3bdadfb1163c2 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Wed, 5 Jul 2023 02:03:10 -0700 Subject: [PATCH 134/184] Implement enable/disable and info commands for events log --- Bot/Cogs/dev-tools.py | 12 +++ Bot/Cogs/events-handler.py | 21 ++++- Bot/Cogs/events-log.py | 71 ++++++++++++++++ Bot/Libs/ui/events_log/__init__.py | 3 + Bot/Libs/ui/events_log/views.py | 121 +++++++++++++++++++++++++++ Bot/Libs/utils/__init__.py | 4 + Bot/Libs/utils/embeds.py | 19 +++++ Migrations/20230702_rev2_up_rev3.sql | 11 ++- Vagrantfile | 3 +- 9 files changed, 262 insertions(+), 3 deletions(-) create mode 100644 Bot/Cogs/events-log.py create mode 100644 Bot/Libs/ui/events_log/__init__.py create mode 100644 Bot/Libs/ui/events_log/views.py diff --git a/Bot/Cogs/dev-tools.py b/Bot/Cogs/dev-tools.py index 0c2fdd09..56138d03 100644 --- a/Bot/Cogs/dev-tools.py +++ b/Bot/Cogs/dev-tools.py @@ -56,6 +56,18 @@ async def sync( await ctx.send(f"Synced the tree to {ret}/{len(guilds)}.") + @commands.hybrid_command(name="dispatch") + @commands.guild_only() + @commands.is_owner() + async def dispatch_event(self, ctx: commands.Context) -> None: + """Dispatches an custom event + + Args: + ctx (commands.Context): _description_ + """ + self.bot.dispatch("log", ctx.author) + await ctx.send("Dispatched event") + async def setup(bot: KumikoCore): await bot.add_cog(DevTools(bot)) diff --git a/Bot/Cogs/events-handler.py b/Bot/Cogs/events-handler.py index 4779649b..440ffe6e 100644 --- a/Bot/Cogs/events-handler.py +++ b/Bot/Cogs/events-handler.py @@ -13,11 +13,15 @@ def __init__(self, bot: KumikoCore) -> None: @commands.Cog.listener() async def on_guild_join(self, guild: discord.Guild) -> None: existsQuery = "SELECT EXISTS(SELECT 1 FROM guild WHERE id = $1);" + insertQuery = """ + INSERT INTO guild (id) VALUES ($1); + INSERT INTO logging_config (guild_id) VALUES ($1); + """ async with self.pool.acquire() as conn: async with conn.transaction(): exists = await conn.fetchval(existsQuery, guild.id) if not exists: - await conn.execute("INSERT INTO guild (id) VALUES ($1)", guild.id) + await conn.execute(insertQuery, guild.id) self.bot.prefixes[guild.id] = [self.bot.default_prefix] @commands.Cog.listener() @@ -27,6 +31,21 @@ async def on_guild_remove(self, guild: discord.Guild) -> None: await conn.execute("DELETE FROM guild WHERE id = $1", guild.id) self.bot.prefixes[guild.id] = self.bot.default_prefix + # @commands.Cog.listener() + # async def on_member_join(self, member: discord.Member) -> None: + + # @commands.Cog.listener() + # async def on_log(self, member: discord.Member) -> None: + # channel = member.guild.get_channel(1125898205327007774) + # if isinstance(channel, discord.TextChannel): + # embed = JoinEmbed() + # # embed.set_author(name="Member Joined", icon_url=member.display_avatar.url) + # embed.title = "Member Joined" + # embed.set_thumbnail(url=member.display_avatar.url) + # embed.description = f"{member.mention} {member.global_name}" + # await channel.send(embed=embed) + # # await channel.send("hello") + async def setup(bot: KumikoCore) -> None: await bot.add_cog(EventsHandler(bot)) diff --git a/Bot/Cogs/events-log.py b/Bot/Cogs/events-log.py new file mode 100644 index 00000000..20fa32a4 --- /dev/null +++ b/Bot/Cogs/events-log.py @@ -0,0 +1,71 @@ +from discord.ext import commands +from kumikocore import KumikoCore +from Libs.ui.events_log import RegisterView, UnregisterView +from Libs.utils import ConfirmEmbed, Embed + + +class EventsLog(commands.Cog): + """Events logging module - Optional module to log member joins and others""" + + def __init__(self, bot: KumikoCore) -> None: + self.bot = bot + self.pool = self.bot.pool + + @commands.hybrid_group(name="logs") + async def logs(self, ctx: commands.Context) -> None: + if ctx.invoked_subcommand is None: + await ctx.send_help(ctx.command) + + @commands.has_guild_permissions(manage_guild=True) + @commands.guild_only() + @logs.command(name="enable") + async def enableLogs(self, ctx: commands.Context) -> None: + """Registers and enables events logging on the server""" + registerInfo = "In order to get started, **only** select one of the options within the dropdown menu in order to set it.\nOnce you are done, click the finish button." + embed = Embed(title="Registration Info") + embed.description = registerInfo + view = RegisterView(pool=self.pool) + await ctx.send(embed=embed, view=view) + + @commands.has_guild_permissions(manage_guild=True) + @commands.guild_only() + @logs.command(name="disable") + async def disableLogs(self, ctx: commands.Context) -> None: + """Disables and unregisters the events logging on the server""" + view = UnregisterView(pool=self.pool) + embed = ConfirmEmbed() + embed.description = "You are about to disable and unregister the events logging feature on Kumiko. Press Confirm to confirm your action." + await ctx.send(embed=embed, view=view) + + @commands.has_guild_permissions(manage_guild=True) + @commands.guild_only() + @logs.command(name="info") + async def logInfo(self, ctx: commands.Context) -> None: + """Displays info about the events logging module""" + query = """ + SELECT guild.id, guild.logs, logging_config.channel_id, logging_config.member_events, logging_config.mod_events, logging_config.eco_events + FROM guild + INNER JOIN logging_config + ON guild.id = logging_config.guild_id + WHERE guild.id = $1; + """ + guild_id = ctx.guild.id # type: ignore + async with self.pool.acquire() as conn: + result = await conn.fetchrow(query, guild_id) + embed = Embed() + embed.set_author(name="Events Logging Info", icon_url=ctx.guild.icon.url) # type: ignore + embed.description = f"**Enabled?:** {result['logs']}\n**Events Logging Channel:** <#{result['channel_id']}>" + embed.add_field( + name="Member Events", value=f"Enabled?: **{result['member_events']}**" + ) + embed.add_field( + name="Mod Events", value=f"Enabled?: **{result['mod_events']}**" + ) + embed.add_field( + name="Eco Events", value=f"Enabled?: **{result['eco_events']}**" + ) + await ctx.send(embed=embed) + + +async def setup(bot: KumikoCore) -> None: + await bot.add_cog(EventsLog(bot)) diff --git a/Bot/Libs/ui/events_log/__init__.py b/Bot/Libs/ui/events_log/__init__.py new file mode 100644 index 00000000..ebca55ab --- /dev/null +++ b/Bot/Libs/ui/events_log/__init__.py @@ -0,0 +1,3 @@ +from .views import RegisterView, UnregisterView + +__all__ = ["RegisterView", "UnregisterView"] diff --git a/Bot/Libs/ui/events_log/views.py b/Bot/Libs/ui/events_log/views.py new file mode 100644 index 00000000..f4f6517f --- /dev/null +++ b/Bot/Libs/ui/events_log/views.py @@ -0,0 +1,121 @@ +import asyncpg +import discord +from Libs.utils import ErrorEmbed, SuccessActionEmbed + + +class RegisterView(discord.ui.View): + def __init__(self, pool: asyncpg.Pool) -> None: + super().__init__() + self.pool = pool + + @discord.ui.select( + cls=discord.ui.ChannelSelect, channel_types=[discord.ChannelType.text] + ) + async def select_channels( + self, interaction: discord.Interaction, select: discord.ui.ChannelSelect + ) -> None: + query = """ + WITH guild_update AS ( + UPDATE guild + SET logs = $3 + WHERE id = $1 + RETURNING id + ) + INSERT INTO logging_config (channel_id, guild_id) + VALUES ($2, (SELECT id FROM guild_update)) + ON CONFLICT (guild_id) DO + UPDATE SET channel_id = excluded.channel_id; + """ + async with self.pool.acquire() as conn: + guildId = interaction.guild.id # type: ignore + tr = conn.transaction() + await tr.start() + + try: + await conn.execute(query, guildId, select.values[0].id, True) + except asyncpg.UniqueViolationError: + await tr.rollback() + await interaction.response.send_message("There are duplicate records") + except: + await tr.rollback() + await interaction.response.send_message("Could not create records.") + else: + await tr.commit() + await interaction.response.send_message( + f"Successfully set the logging channel to {select.values[0].mention}" + ) + + @discord.ui.button(label="Finish", style=discord.ButtonStyle.green) + async def button_quit( + self, interaction: discord.Interaction, button: discord.ui.Button + ) -> None: + await interaction.response.defer() + await interaction.delete_original_response() + self.stop() + + +class UnregisterView(discord.ui.View): + def __init__(self, pool: asyncpg.Pool) -> None: + super().__init__() + self.pool = pool + + @discord.ui.button( + label="Confirm", + style=discord.ButtonStyle.green, + emoji="<:greenTick:596576670815879169>", + ) + async def confirm( + self, interaction: discord.Interaction, button: discord.ui.Button + ) -> None: + query = """ + WITH guild_update AS ( + UPDATE guild + SET logs = $2 + WHERE id = $1 + RETURNING id + ) + DELETE FROM logging_config WHERE guild_id = (SELECT id FROM guild_update); + """ + async with self.pool.acquire() as conn: + guildId = interaction.guild.id # type: ignore + + tr = conn.transaction() + await tr.start() + + try: + await conn.execute(query, guildId, False) + except asyncpg.UniqueViolationError: + await tr.rollback() + self.clear_items() + uniqueViolationEmbed = ErrorEmbed( + description="There are duplicate records" + ) + await interaction.response.edit_message( + embed=uniqueViolationEmbed, view=self + ) + except: + await tr.rollback() + self.clear_items() + failedEmbed = ErrorEmbed( + description="Could not update or delete records" + ) + await interaction.response.edit_message(embed=failedEmbed, view=self) + else: + await tr.commit() + self.clear_items() + successEmbed = SuccessActionEmbed() + successEmbed.description = "Disabled and cleared all logging configs" + + await interaction.response.edit_message(embed=successEmbed, view=self) + + @discord.ui.button( + label="Cancel", + style=discord.ButtonStyle.red, + emoji="<:redTick:596576672149667840>", + ) + async def cancel( + self, interaction: discord.Interaction, button: discord.ui.Button + ) -> None: + await interaction.response.defer() + await interaction.delete_original_response() + self.stop() diff --git a/Bot/Libs/utils/__init__.py b/Bot/Libs/utils/__init__.py index 6cbc7628..c8bc4cff 100644 --- a/Bot/Libs/utils/__init__.py +++ b/Bot/Libs/utils/__init__.py @@ -3,6 +3,8 @@ ConfirmEmbed, Embed, ErrorEmbed, + JoinEmbed, + LeaveEmbed, SuccessActionEmbed, ) from .greedy_formatter import formatGreedy @@ -24,4 +26,6 @@ "ConfirmEmbed", "SuccessActionEmbed", "CancelledActionEmbed", + "JoinEmbed", + "LeaveEmbed", ] diff --git a/Bot/Libs/utils/embeds.py b/Bot/Libs/utils/embeds.py index 06f44a3c..63f80262 100644 --- a/Bot/Libs/utils/embeds.py +++ b/Bot/Libs/utils/embeds.py @@ -1,4 +1,5 @@ import discord +from discord.utils import utcnow class Embed(discord.Embed): @@ -49,3 +50,21 @@ def __init__(self, **kwargs): kwargs.setdefault("color", discord.Color.from_rgb(255, 191, 0)) kwargs.setdefault("title", "Are you sure?") super().__init__(**kwargs) + + +class JoinEmbed(discord.Embed): + """Kumiko's custom join embed""" + + def __init__(self, **kwargs): + kwargs.setdefault("color", discord.Color.from_rgb(127, 255, 0)) + kwargs.setdefault("timestamp", utcnow()) + super().__init__(**kwargs) + + +class LeaveEmbed(discord.Embed): + """Kumiko's custom leave embed""" + + def __init__(self, **kwargs): + kwargs.setdefault("color", discord.Color.from_rgb(255, 0, 51)) + kwargs.setdefault("timestamp", utcnow()) + super().__init__(**kwargs) diff --git a/Migrations/20230702_rev2_up_rev3.sql b/Migrations/20230702_rev2_up_rev3.sql index 85c27fcc..72b32db1 100644 --- a/Migrations/20230702_rev2_up_rev3.sql +++ b/Migrations/20230702_rev2_up_rev3.sql @@ -1 +1,10 @@ -ALTER TABLE guild ADD COLUMN local_economy_name VARCHAR(255) DEFAULT 'Server Economy'; \ No newline at end of file +ALTER TABLE guild ADD COLUMN local_economy_name VARCHAR(255) DEFAULT 'Server Economy'; + +CREATE TABLE IF NOT EXISTS logging_config ( + id SERIAL PRIMARY KEY, + channel_id BIGINT, + member_events BOOLEAN DEFAULT TRUE, + mod_events BOOLEAN DEFAULT TRUE, + eco_events BOOLEAN DEFAULT FALSE, + guild_id BIGINT UNIQUE (guild_id) REFERENCES guild (id) ON DELETE CASCADE ON UPDATE NO ACTION +); \ No newline at end of file diff --git a/Vagrantfile b/Vagrantfile index 57b40e01..442c2544 100644 --- a/Vagrantfile +++ b/Vagrantfile @@ -5,10 +5,11 @@ Vagrant.configure("2") do |config| config.vm.define "kumiko_dev" config.vm.box = "generic/ubuntu2204" config.vm.synced_folder ".", "/home/vagrant/Kumiko", create: true + config.vm.network "private_network", ip: "192.168.40.0/21" config.vm.provision "ansible" do |ansible| ansible.verbose = "v" ansible.playbook = "playbook.yml" ansible.ask_become_pass = true end -end +end \ No newline at end of file From 69a0db0a7f10d0b75b4268e11e7a811a7a85dc92 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Wed, 5 Jul 2023 02:05:59 -0700 Subject: [PATCH 135/184] [skip ci] Update changelog --- changelog.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/changelog.md b/changelog.md index 926ae3f8..3f2b011c 100644 --- a/changelog.md +++ b/changelog.md @@ -13,7 +13,7 @@ For the full list of changes, please see them here: [`v0.8.x...v0.9.0`](https:// - Migration from Prisma to asyncpg - Kumiko now supports custom prefixes (max is 10). The default that will be set is `>` - asyncpg-trek migration system -- Kumiko's logging module has been implemented +- Kumiko's EventsLog module has been implemented - Docs has been merged into one repo (https://kumiko.readthedocs.io/en/latest/index.html) ## 🛠️ Changes @@ -39,7 +39,7 @@ For the full list of changes, please see them here: [`v0.8.x...v0.9.0`](https:// - Ansible playbooks, proper Vagrant config - Discord API events handler, custom dispatch events - Prefix utils -- Better logging system +- EventsLog module - Ping checks to ensure that the connections are open for PostgreSQL and Redis - Docs merged into one repo - this repo From 78de8d9668f68dac3e9bccde3aeae269e291faaf Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Wed, 5 Jul 2023 03:02:43 -0700 Subject: [PATCH 136/184] Again stealing code from RDanny --- Bot/Libs/utils/help/kumiko_help_paginated.py | 523 +++++++++++++++---- 1 file changed, 409 insertions(+), 114 deletions(-) diff --git a/Bot/Libs/utils/help/kumiko_help_paginated.py b/Bot/Libs/utils/help/kumiko_help_paginated.py index 4381d59f..169672f2 100644 --- a/Bot/Libs/utils/help/kumiko_help_paginated.py +++ b/Bot/Libs/utils/help/kumiko_help_paginated.py @@ -1,140 +1,435 @@ -import contextlib -from typing import List, Mapping, Optional +import itertools +from typing import Any, Optional, Union -from discord.ext import commands -from Libs.utils import Embed -from Libs.utils.pages import FieldPageSource, KumikoPages +import discord +from discord.ext import commands, menus +from Libs.utils.pages import KumikoPages + +# class BotCategories(discord.ui.Select): +# def __init__(self, cogs: List[commands.Cog]) -> None: +# options = [ +# discord.SelectOption(label=cog.qualified_name or "No", description=cog.description) +# for cog in cogs if cog.qualified_name not in ["DevTools", "ErrorHandler", "IPCServer"] +# ] +# super().__init__(placeholder="Select a category...", options=options) + +# async def callback(self, interaction: discord.Interaction): + + +class GroupHelpPageSource(menus.ListPageSource): + def __init__( + self, + group: Union[commands.Group, commands.Cog], + entries: list[commands.Command], + *, + prefix: str, + ): + super().__init__(entries=entries, per_page=6) + self.group: Union[commands.Group, commands.Cog] = group + self.prefix: str = prefix + self.title: str = f"{self.group.qualified_name} Commands" + self.description: str = self.group.description + + async def format_page(self, menu: KumikoPages, commands: list[commands.Command]): + embed = discord.Embed( + title=self.title, + description=self.description, + colour=discord.Colour(0xA8B9CD), + ) + + for command in commands: + signature = f"{command.qualified_name} {command.signature}" + embed.add_field( + name=signature, + value=command.short_doc or "No help given...", + inline=False, + ) + + maximum = self.get_max_pages() + if maximum > 1: + embed.set_author( + name=f"Page {menu.current_page + 1}/{maximum} ({len(self.entries)} commands)" + ) + + embed.set_footer( + text=f'Use "{self.prefix}help command" for more info on a command.' + ) + return embed + + +class HelpSelectMenu(discord.ui.Select["HelpMenu"]): + def __init__(self, entries: dict[commands.Cog, list[commands.Command]], bot): + super().__init__( + placeholder="Select a category...", + min_values=1, + max_values=1, + row=0, + ) + self.commands: dict[commands.Cog, list[commands.Command]] = entries + self.bot = bot + self.__fill_options() + + def __fill_options(self) -> None: + self.add_option( + label="Index", + emoji="\N{WAVING HAND SIGN}", + value="__index", + description="The help page showing how to use the bot.", + ) + for cog, commands in self.commands.items(): + if not commands: + continue + description = cog.description.split("\n", 1)[0] or None + emoji = getattr(cog, "display_emoji", None) + self.add_option( + label=cog.qualified_name, + value=cog.qualified_name, + description=description, + emoji=emoji, + ) + + async def callback(self, interaction: discord.Interaction): + assert self.view is not None + value = self.values[0] + if value == "__index": + await self.view.rebind(FrontPageSource(), interaction) + else: + cog = self.bot.get_cog(value) + if cog is None: + await interaction.response.send_message( + "Somehow this category does not exist?", ephemeral=True + ) + return + + commands = self.commands[cog] + if not commands: + await interaction.response.send_message( + "This category has no commands for you", ephemeral=True + ) + return + + source = GroupHelpPageSource( + cog, commands, prefix=self.view.ctx.clean_prefix + ) + await self.view.rebind(source, interaction) + + +class HelpMenu(KumikoPages): + def __init__(self, source: menus.PageSource, ctx: commands.Context): + super().__init__(source, ctx=ctx, compact=True) + + def add_categories( + self, commands: dict[commands.Cog, list[commands.Command]] + ) -> None: + self.clear_items() + self.add_item(HelpSelectMenu(commands, self.ctx.bot)) + self.fill_items() + + async def rebind( + self, source: menus.PageSource, interaction: discord.Interaction + ) -> None: + self.source = source + self.current_page = 0 + + await self.source._prepare_once() + page = await self.source.get_page(0) + kwargs = await self._get_kwargs_from_page(page) + self._update_labels(0) + await interaction.response.edit_message(**kwargs, view=self) + + +class FrontPageSource(menus.PageSource): + def is_paginating(self) -> bool: + # This forces the buttons to appear even in the front page + return True + + def get_max_pages(self) -> Optional[int]: + # There's only one actual page in the front page + # However we need at least 2 to show all the buttons + return 2 + + async def get_page(self, page_number: int) -> Any: + # The front page is a dummy + self.index = page_number + return self + + def format_page(self, menu: HelpMenu, page: Any): + embed = discord.Embed(title="Bot Help", colour=discord.Colour(0xA8B9CD)) + embed.description = "help" + # embed.description = inspect.cleandoc( + # f""" + # Hello! Welcome to the help page. + + # Use "{menu.ctx.clean_prefix}help command" for more info on a command. + # Use "{menu.ctx.clean_prefix}help category" for more info on a category. + # Use the dropdown menu below to select a category. + # """ + # ) + + # embed.add_field( + # name='Support Server', + # value='For more help, consider joining the official server over at https://discord.gg/DWEaqMy', + # inline=False, + # ) + + # created_at = time.format_dt(menu.ctx.bot.user.created_at, 'F') + # if self.index == 0: + # embed.add_field( + # name='Who are you?', + # value=( + # "I'm a bot made by Danny#0007. I'm the oldest running Discord bot! I've been running since " + # f'{created_at}. I have features such as moderation, tags, starboard, and more. You can get more ' + # 'information on my commands by using the dropdown below.\n\n' + # "I'm also open source. You can see my code on [GitHub](https://github.com/Rapptz/RoboDanny)!" + # ), + # inline=False, + # ) + # elif self.index == 1: + # entries = ( + # ('', 'This means the argument is __**required**__.'), + # ('[argument]', 'This means the argument is __**optional**__.'), + # ('[A|B]', 'This means that it can be __**either A or B**__.'), + # ( + # '[argument...]', + # 'This means you can have multiple arguments.\n' + # 'Now that you know the basics, it should be noted that...\n' + # '__**You do not type in the brackets!**__', + # ), + # ) + + # embed.add_field(name='How do I use this bot?', value='Reading the bot signature is pretty simple.') + + # for name, value in entries: + # embed.add_field(name=name, value=value, inline=False) + + return embed class KumikoHelpPaginated(commands.HelpCommand): - def __init__(self) -> None: + context: commands.Context + + def __init__(self): super().__init__( command_attrs={ - "help": "The help command for the bot", "cooldown": commands.CooldownMapping.from_cooldown( - 1, 3.0, commands.BucketType.user + 1, 3.0, commands.BucketType.member ), - "aliases": ["commands"], + "help": "Shows help about the bot, a command, or a category", } ) - async def send(self, **kwargs) -> None: - """a shortcut to sending to get_destination""" - await self.get_destination().send(**kwargs) + async def on_help_command_error( + self, ctx: commands.Context, error: commands.CommandError + ): + if isinstance(error, commands.CommandInvokeError): + # Ignore missing permission errors + if ( + isinstance(error.original, discord.HTTPException) + and error.original.code == 50013 + ): + return - async def help_embed( - self, title: str, description: str, commands: List[commands.Command] - ) -> None: - """The default help embed builder - - Mainly used so we don't repeat ourselves when building help embeds - - Args: - title (str): The title of the embed. Usually the name of the cog, group, etc - description (str): The description of the embed. Usually the desc of the cog or group - commands (List[commands.Command]): List of commands - """ - filteredCommands = await self.filter_commands(commands) - fieldSource = [ - (self.get_command_signature(command), command.help or "No help found...") - for command in filteredCommands - ] - sources = FieldPageSource( - entries=fieldSource, - per_page=6, - inline=True, - clear_description=False, - title=title or "No", - description=description or "No help found...", + await ctx.send(str(error.original)) + + def get_command_signature(self, command: commands.Command) -> str: + parent = command.full_parent_name + if len(command.aliases) > 0: + aliases = "|".join(command.aliases) + fmt = f"[{command.name}|{aliases}]" + if parent: + fmt = f"{parent} {fmt}" + alias = fmt + else: + alias = command.name if not parent else f"{parent} {command.name}" + return f"{alias} {command.signature}" + + async def send_bot_help(self, mapping): + bot = self.context.bot + + def key(command) -> str: + cog = command.cog + return cog.qualified_name if cog else "\U0010ffff" + + entries: list[commands.Command] = await self.filter_commands( + bot.commands, sort=True, key=key ) - pages = KumikoPages(source=sources, ctx=self.context) - await pages.start() - async def send_bot_help( - self, mapping: Mapping[Optional[commands.Cog], List[commands.Command]] - ) -> None: - """Generates the help embed when the default help command is called - - Args: - mapping (Mapping[Optional[commands.Cog], List[commands.Command]]): Mapping of cogs to commands - """ - ctx = self.context - embed = Embed(title=f"{ctx.me.display_name} Help") - embed.set_thumbnail(url=ctx.me.display_avatar) - embed.description = f"{ctx.me.display_name} is a multipurpose bot built with freedom and choice in mind." - usable = 0 - - for ( - cog, - cmds, - ) in mapping.items(): # iterating through our mapping of cog: commands - if filtered_commands := await self.filter_commands(cmds): - # if no commands are usable in this category, we don't want to display it - amount_commands = len(filtered_commands) - usable += amount_commands - if cog: # getting attributes dependent on if a cog exists or not - name = cog.qualified_name - description = cog.description or "No description" - else: - name = "No" - description = "Commands with no category" - - embed.add_field( - name=f"{name} Category [{amount_commands}]", value=description - ) + all_commands: dict[commands.Cog, list[commands.Command]] = {} + for name, children in itertools.groupby(entries, key=key): + if name == "\U0010ffff": + continue - # embed.description = f"{len(ctx.commands)} commands | {usable} usable" + cog = bot.get_cog(name) + assert cog is not None + all_commands[cog] = sorted(children, key=lambda c: c.qualified_name) - await self.send(embed=embed) + menu = HelpMenu(FrontPageSource(), ctx=self.context) + menu.add_categories(all_commands) + await menu.start() - async def send_command_help(self, command: commands.Command) -> None: - """Triggers when a `help ` is called + async def send_cog_help(self, cog): + entries = await self.filter_commands(cog.get_commands(), sort=True) + menu = HelpMenu( + GroupHelpPageSource(cog, entries, prefix=self.context.clean_prefix), + ctx=self.context, + ) + await menu.start() - Args: - command (commands.Command): The command to get help for - """ - signature = self.get_command_signature( - command - ) # get_command_signature gets the signature of a command in [optional] - embed = Embed(title=signature, description=command.help or "No help found...") + def common_command_formatting(self, embed_like, command): + embed_like.title = self.get_command_signature(command) + if command.description: + embed_like.description = f"{command.description}\n\n{command.help}" + else: + embed_like.description = command.help or "No help found..." - if cog := command.cog: - embed.add_field(name="Category", value=cog.qualified_name) + async def send_command_help(self, command): + # No pagination necessary for a single command. + embed = discord.Embed(colour=discord.Colour(0xA8B9CD)) + self.common_command_formatting(embed, command) + await self.context.send(embed=embed) - can_run = "No" - # command.can_run to test if the cog is usable - with contextlib.suppress(commands.CommandError): - if await command.can_run(self.context): - can_run = "Yes" + async def send_group_help(self, group): + subcommands = group.commands + if len(subcommands) == 0: + return await self.send_command_help(group) - embed.add_field(name="Usable", value=can_run) + entries = await self.filter_commands(subcommands, sort=True) + if len(entries) == 0: + return await self.send_command_help(group) - if command._buckets and ( - cooldown := command._buckets._cooldown - ): # use of internals to get the cooldown of the command - embed.add_field( - name="Cooldown", - value=f"{cooldown.rate} per {cooldown.per:.0f} seconds", - ) + source = GroupHelpPageSource(group, entries, prefix=self.context.clean_prefix) + self.common_command_formatting(source, group) + menu = HelpMenu(source, ctx=self.context) + await menu.start() - await self.send(embed=embed) + # def __init__(self) -> None: + # super().__init__( + # command_attrs={ + # "help": "The help command for the bot", + # "cooldown": commands.CooldownMapping.from_cooldown( + # 1, 3.0, commands.BucketType.user + # ), + # "aliases": ["commands"], + # } + # ) - async def send_cog_help(self, cog: commands.Cog) -> None: - """Send the help command when a `help ` is called + # async def send(self, **kwargs) -> None: + # """a shortcut to sending to get_destination""" + # await self.get_destination().send(**kwargs) - Args: - cog (commands.Cog): The cog requested - """ - title = cog.qualified_name or "No" - await self.help_embed( - title=f"{title} Category", - description=cog.description, - commands=cog.get_commands(), - ) + # async def help_embed( + # self, title: str, description: str, commands: List[commands.Command] + # ) -> None: + # """The default help embed builder - async def send_group_help(self, group): - """triggers when a `help ` is called""" - title = self.get_command_signature(group) - await self.help_embed( - title=title, description=group.help, commands=group.commands - ) + # Mainly used so we don't repeat ourselves when building help embeds + + # Args: + # title (str): The title of the embed. Usually the name of the cog, group, etc + # description (str): The description of the embed. Usually the desc of the cog or group + # commands (List[commands.Command]): List of commands + # """ + # filteredCommands = await self.filter_commands(commands) + # fieldSource = [ + # (self.get_command_signature(command), command.help or "No help found...") + # for command in filteredCommands + # ] + # sources = FieldPageSource( + # entries=fieldSource, + # per_page=5, + # inline=False, + # clear_description=False, + # title=title or "No", + # description=description or "No help found...", + # ) + # pages = KumikoPages(source=sources, ctx=self.context) + # await pages.start() + + # async def send_bot_help( + # self, mapping: Mapping[Optional[commands.Cog], List[commands.Command]] + # ) -> None: + # """Generates the help embed when the default help command is called + + # Args: + # mapping (Mapping[Optional[commands.Cog], List[commands.Command]]): Mapping of cogs to commands + # """ + # ctx = self.context + # embed = Embed(title=f"{ctx.me.display_name} Help") + # embed.set_thumbnail(url=ctx.me.display_avatar) + # embed.description = f"{ctx.me.display_name} is a multipurpose bot built with freedom and choice in mind." + # usable = 0 + + # for ( + # cog, + # cmds, + # ) in mapping.items(): # iterating through our mapping of cog: commands + # if filtered_commands := await self.filter_commands(cmds): + # # if no commands are usable in this category, we don't want to display it + # amount_commands = len(filtered_commands) + # usable += amount_commands + # if cog: # getting attributes dependent on if a cog exists or not + # name = cog.qualified_name + # description = cog.description or "No description" + # else: + # name = "No" + # description = "Commands with no category" + + # embed.add_field( + # name=f"{name} Category [{amount_commands}]", value=description + # ) + + # # embed.description = f"{len(ctx.commands)} commands | {usable} usable" + + # await self.send(embed=embed) + + # async def send_command_help(self, command: commands.Command) -> None: + # """Triggers when a `help ` is called + + # Args: + # command (commands.Command): The command to get help for + # """ + # signature = self.get_command_signature( + # command + # ) # get_command_signature gets the signature of a command in [optional] + # embed = Embed(title=signature, description=command.help or "No help found...") + + # if cog := command.cog: + # embed.add_field(name="Category", value=cog.qualified_name) + + # can_run = "No" + # # command.can_run to test if the cog is usable + # with contextlib.suppress(commands.CommandError): + # if await command.can_run(self.context): + # can_run = "Yes" + + # embed.add_field(name="Usable", value=can_run) + + # if command._buckets and ( + # cooldown := command._buckets._cooldown + # ): # use of internals to get the cooldown of the command + # embed.add_field( + # name="Cooldown", + # value=f"{cooldown.rate} per {cooldown.per:.0f} seconds", + # ) + + # await self.send(embed=embed) + + # async def send_cog_help(self, cog: commands.Cog) -> None: + # """Send the help command when a `help ` is called + + # Args: + # cog (commands.Cog): The cog requested + # """ + # title = cog.qualified_name or "No" + # await self.help_embed( + # title=f"{title} Category", + # description=cog.description, + # commands=cog.get_commands(), + # ) + + # async def send_group_help(self, group): + # """triggers when a `help ` is called""" + # title = self.get_command_signature(group) + # await self.help_embed( + # title=title, description=group.help, commands=group.commands + # ) From 4ee1d21dae3d01d8081dc1bb5b276c6f89e24c26 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 5 Jul 2023 18:21:21 +0000 Subject: [PATCH 137/184] [pip](deps-dev): Bump ruff from 0.0.276 to 0.0.277 (#371) Bumps [ruff](https://github.com/astral-sh/ruff) from 0.0.276 to 0.0.277. - [Release notes](https://github.com/astral-sh/ruff/releases) - [Changelog](https://github.com/astral-sh/ruff/blob/main/BREAKING_CHANGES.md) - [Commits](https://github.com/astral-sh/ruff/compare/v0.0.276...v0.0.277) --- updated-dependencies: - dependency-name: ruff dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 38 +++++++++++++++++++------------------- pyproject.toml | 2 +- 2 files changed, 20 insertions(+), 20 deletions(-) diff --git a/poetry.lock b/poetry.lock index 8e7397c7..8a523fd5 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2739,28 +2739,28 @@ idna2008 = ["idna"] [[package]] name = "ruff" -version = "0.0.276" +version = "0.0.277" description = "An extremely fast Python linter, written in Rust." optional = false python-versions = ">=3.7" files = [ - {file = "ruff-0.0.276-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:c150912b8ebde843c10b33db90705d4fee48db6f05441e5d143be9f4c2f35df5"}, - {file = "ruff-0.0.276-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:5e9cd7238d34f24d7ccfadcce4dc6807b8c5a390f547dd7236d06488d9d6f40f"}, - {file = "ruff-0.0.276-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:fc7dc557cc3fa2a03a88e99425ceee91429cc7432e5a41087850c1629294faed"}, - {file = "ruff-0.0.276-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:13e5983836ae383c04de213954da731f14ea884aaf74467abc47e1d79d8cf1b7"}, - {file = "ruff-0.0.276-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:4ac65df96be3e2f4b10bc97bbb624152281611b06ef1068d5bb064b7ad35d800"}, - {file = "ruff-0.0.276-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:d070a64de4affd17e006d6986ef25601dbbc6b373844ece5396c33900f8b8563"}, - {file = "ruff-0.0.276-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:2edcd6948a21fa7fb4594094da37a1aa1d205b7abaa718bd27d48ba1d7977348"}, - {file = "ruff-0.0.276-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:57c49b525d8ca3838d8b614f42e342077bed95aedd9fe6e6ec419f39320c214e"}, - {file = "ruff-0.0.276-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5980960a748ada3ddfe4ea7ff3a01b9113c456a14cb1a39b4c30783012d4cba6"}, - {file = "ruff-0.0.276-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:12be4f007114cf5ed1242e522762651539521ec32ae0210cc4b8dfe434a872f0"}, - {file = "ruff-0.0.276-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:6ed8fc729b3e7b9f20a4e2aa6f24c798b06912f8a94cb3e8fd590eba055780df"}, - {file = "ruff-0.0.276-py3-none-musllinux_1_2_i686.whl", hash = "sha256:735d724031212c2ab63fafdea49d4581ae866a1180d06c29b0b5481228ca6bb9"}, - {file = "ruff-0.0.276-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:100ad9055d50977c2b4ab3de0db62d6e525bcd4aafbb660a842733bdbf650be9"}, - {file = "ruff-0.0.276-py3-none-win32.whl", hash = "sha256:1b34a3673b2e5d97df8f7f04090c0b74e9ae6d3d172921d0e0781192954afddf"}, - {file = "ruff-0.0.276-py3-none-win_amd64.whl", hash = "sha256:02deadc0f6abead6cc2d38ddd7100a52aba27a0d90315facaa44b8b4acdba162"}, - {file = "ruff-0.0.276-py3-none-win_arm64.whl", hash = "sha256:a6bd5b53ac689a43c7afc45bd574a7b3efe0ceb192e26e95a055c770ef2045b9"}, - {file = "ruff-0.0.276.tar.gz", hash = "sha256:d456c86eb6ce9225507f24fcc7bf72fa031bb7cc750023310e62889bf4ad4b6a"}, + {file = "ruff-0.0.277-py3-none-macosx_10_7_x86_64.whl", hash = "sha256:3250b24333ef419b7a232080d9724ccc4d2da1dbbe4ce85c4caa2290d83200f8"}, + {file = "ruff-0.0.277-py3-none-macosx_10_9_x86_64.macosx_11_0_arm64.macosx_10_9_universal2.whl", hash = "sha256:3e60605e07482183ba1c1b7237eca827bd6cbd3535fe8a4ede28cbe2a323cb97"}, + {file = "ruff-0.0.277-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:7baa97c3d7186e5ed4d5d4f6834d759a27e56cf7d5874b98c507335f0ad5aadb"}, + {file = "ruff-0.0.277-py3-none-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:74e4b206cb24f2e98a615f87dbe0bde18105217cbcc8eb785bb05a644855ba50"}, + {file = "ruff-0.0.277-py3-none-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:479864a3ccd8a6a20a37a6e7577bdc2406868ee80b1e65605478ad3b8eb2ba0b"}, + {file = "ruff-0.0.277-py3-none-manylinux_2_17_ppc64.manylinux2014_ppc64.whl", hash = "sha256:468bfb0a7567443cec3d03cf408d6f562b52f30c3c29df19927f1e0e13a40cd7"}, + {file = "ruff-0.0.277-py3-none-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:f32ec416c24542ca2f9cc8c8b65b84560530d338aaf247a4a78e74b99cd476b4"}, + {file = "ruff-0.0.277-py3-none-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:14a7b2f00f149c5a295f188a643ac25226ff8a4d08f7a62b1d4b0a1dc9f9b85c"}, + {file = "ruff-0.0.277-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:a9879f59f763cc5628aa01c31ad256a0f4dc61a29355c7315b83c2a5aac932b5"}, + {file = "ruff-0.0.277-py3-none-musllinux_1_2_aarch64.whl", hash = "sha256:f612e0a14b3d145d90eb6ead990064e22f6f27281d847237560b4e10bf2251f3"}, + {file = "ruff-0.0.277-py3-none-musllinux_1_2_armv7l.whl", hash = "sha256:323b674c98078be9aaded5b8b51c0d9c424486566fb6ec18439b496ce79e5998"}, + {file = "ruff-0.0.277-py3-none-musllinux_1_2_i686.whl", hash = "sha256:3a43fbe026ca1a2a8c45aa0d600a0116bec4dfa6f8bf0c3b871ecda51ef2b5dd"}, + {file = "ruff-0.0.277-py3-none-musllinux_1_2_x86_64.whl", hash = "sha256:734165ea8feb81b0d53e3bf523adc2413fdb76f1264cde99555161dd5a725522"}, + {file = "ruff-0.0.277-py3-none-win32.whl", hash = "sha256:88d0f2afb2e0c26ac1120e7061ddda2a566196ec4007bd66d558f13b374b9efc"}, + {file = "ruff-0.0.277-py3-none-win_amd64.whl", hash = "sha256:6fe81732f788894a00f6ade1fe69e996cc9e485b7c35b0f53fb00284397284b2"}, + {file = "ruff-0.0.277-py3-none-win_arm64.whl", hash = "sha256:2d4444c60f2e705c14cd802b55cd2b561d25bf4311702c463a002392d3116b22"}, + {file = "ruff-0.0.277.tar.gz", hash = "sha256:2dab13cdedbf3af6d4427c07f47143746b6b95d9e4a254ac369a0edb9280a0d2"}, ] [[package]] @@ -3381,4 +3381,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "8b21561737cfcd5f0c525214f57ba7a91f86455ec55ab1450dfce4a2915658d8" +content-hash = "e3e54754b6884d0bc81f82ed59bcfb52d4ad6669624040137798184f03a15464" diff --git a/pyproject.toml b/pyproject.toml index 741ec308..3e54a5b8 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -35,7 +35,7 @@ pyinstrument = "^4.5.0" pyright = "^1.1.316" watchfiles = "^0.19.0" jishaku = "^2.5.1" -ruff = "^0.0.276" +ruff = "^0.0.277" [tool.poetry.group.docs.dependencies] From 431208a978807a4cc257e342f8ad3b02442a8e34 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Wed, 5 Jul 2023 18:42:07 +0000 Subject: [PATCH 138/184] [Actions](deps): Bump actions/setup-node from 3.6.0 to 3.7.0 (#372) Bumps [actions/setup-node](https://github.com/actions/setup-node) from 3.6.0 to 3.7.0. - [Release notes](https://github.com/actions/setup-node/releases) - [Commits](https://github.com/actions/setup-node/compare/v3.6.0...v3.7.0) --- updated-dependencies: - dependency-name: actions/setup-node dependency-type: direct:production update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- .github/workflows/snyk.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/snyk.yml b/.github/workflows/snyk.yml index 14543e32..beaed98b 100644 --- a/.github/workflows/snyk.yml +++ b/.github/workflows/snyk.yml @@ -18,7 +18,7 @@ jobs: with: python-version: '3.11' - name: Set up Node.js 18 - uses: actions/setup-node@v3.6.0 + uses: actions/setup-node@v3.7.0 with: node-version: '18' - name: Install Snyk CLI From b910ce4950ef36da6fe55f76fb34d5e8e1b76f2f Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Wed, 5 Jul 2023 23:39:32 -0700 Subject: [PATCH 139/184] Implement listeners for the events --- Bot/Cogs/dev-tools.py | 6 +- Bot/Cogs/events-handler.py | 127 +++++++++++++++++-- Bot/Libs/cache/decorators.py | 35 ++--- Bot/Libs/cache/redis_cache.py | 9 +- Bot/Libs/ui/events_log/views.py | 4 +- Bot/Libs/utils/help/kumiko_help_paginated.py | 8 +- Bot/redis_cache.py | 59 +++++++++ 7 files changed, 207 insertions(+), 41 deletions(-) create mode 100644 Bot/redis_cache.py diff --git a/Bot/Cogs/dev-tools.py b/Bot/Cogs/dev-tools.py index 56138d03..d333a0e1 100644 --- a/Bot/Cogs/dev-tools.py +++ b/Bot/Cogs/dev-tools.py @@ -1,6 +1,7 @@ from typing import Literal, Optional import discord +from discord import app_commands from discord.ext import commands from discord.ext.commands import Context, Greedy from kumikocore import KumikoCore @@ -59,13 +60,14 @@ async def sync( @commands.hybrid_command(name="dispatch") @commands.guild_only() @commands.is_owner() - async def dispatch_event(self, ctx: commands.Context) -> None: + @app_commands.describe(event="The event to dispatch") + async def dispatch_event(self, ctx: commands.Context, event: str) -> None: """Dispatches an custom event Args: ctx (commands.Context): _description_ """ - self.bot.dispatch("log", ctx.author) + self.bot.dispatch(event, ctx.author) await ctx.send("Dispatched event") diff --git a/Bot/Cogs/events-handler.py b/Bot/Cogs/events-handler.py index 440ffe6e..d80d69a1 100644 --- a/Bot/Cogs/events-handler.py +++ b/Bot/Cogs/events-handler.py @@ -1,6 +1,13 @@ +from typing import Any, Union + +import asyncpg import discord from discord.ext import commands +from discord.utils import format_dt, utcnow from kumikocore import KumikoCore +from Libs.cache import cacheJson +from Libs.utils import CancelledActionEmbed, Embed, SuccessActionEmbed +from redis.asyncio.connection import ConnectionPool class EventsHandler(commands.Cog): @@ -9,6 +16,30 @@ class EventsHandler(commands.Cog): def __init__(self, bot: KumikoCore) -> None: self.bot = bot self.pool = self.bot.pool + self.redis_pool = self.bot.redis_pool + + @cacheJson(ttl=3600) + async def get_or_fetch_config( + self, id: int, redis_pool: ConnectionPool, pool: asyncpg.Pool + ) -> Union[dict, None]: + query = """ + SELECT guild.id, guild.logs, logging_config.channel_id, logging_config.member_events + FROM guild + INNER JOIN logging_config + ON guild.id = logging_config.guild_id + WHERE guild.id = $1; + """ + async with self.pool.acquire() as conn: + res = await conn.fetchrow(query, id) + return dict(res) + + def ensureEnabled(self, config: Any) -> bool: + if (config is not None) and ( + config["logs"] and config["member_events"] is True + ): + return True + else: + return False @commands.Cog.listener() async def on_guild_join(self, guild: discord.Guild) -> None: @@ -31,20 +62,88 @@ async def on_guild_remove(self, guild: discord.Guild) -> None: await conn.execute("DELETE FROM guild WHERE id = $1", guild.id) self.bot.prefixes[guild.id] = self.bot.default_prefix - # @commands.Cog.listener() - # async def on_member_join(self, member: discord.Member) -> None: - - # @commands.Cog.listener() - # async def on_log(self, member: discord.Member) -> None: - # channel = member.guild.get_channel(1125898205327007774) - # if isinstance(channel, discord.TextChannel): - # embed = JoinEmbed() - # # embed.set_author(name="Member Joined", icon_url=member.display_avatar.url) - # embed.title = "Member Joined" - # embed.set_thumbnail(url=member.display_avatar.url) - # embed.description = f"{member.mention} {member.global_name}" - # await channel.send(embed=embed) - # # await channel.send("hello") + @commands.Cog.listener() + async def on_member_join(self, member: discord.Member) -> None: + guild = member.guild + getConfig = await self.get_or_fetch_config( + id=guild.id, redis_pool=self.redis_pool, pool=self.pool + ) + if self.ensureEnabled(getConfig): + channel = guild.get_channel(getConfig["channel_id"]) # type: ignore + if isinstance(channel, discord.TextChannel): + embed = SuccessActionEmbed() + embed.title = "Member Joined" + embed.set_thumbnail(url=member.display_avatar.url) + embed.description = f"{member.mention} {member.global_name}" + embed.timestamp = utcnow() + embed.add_field( + name="Account Age", value=format_dt(member.created_at, "R") + ) + await channel.send(embed=embed) + + @commands.Cog.listener() + async def on_member_remove(self, member: discord.Member) -> None: + guild = member.guild + getConfig = await self.get_or_fetch_config( + id=guild.id, redis_pool=self.redis_pool, pool=self.pool + ) + if self.ensureEnabled(getConfig): + channel = guild.get_channel(getConfig["channel_id"]) # type: ignore + if isinstance(channel, discord.TextChannel): + embed = CancelledActionEmbed() + embed.title = "Member Left" + embed.set_thumbnail(url=member.display_avatar.url) + embed.description = f"{member.mention} {member.global_name}" + embed.timestamp = utcnow() + embed.add_field( + name="Account Age", value=format_dt(member.created_at, "R") + ) + await channel.send(embed=embed) + + @commands.Cog.listener() + async def on_member_ban(self, guild, user: discord.User) -> None: + getConfig = await self.get_or_fetch_config( + id=guild.id, redis_pool=self.redis_pool, pool=self.pool + ) + if self.ensureEnabled(getConfig): + channel = guild.get_channel(getConfig["channel_id"]) # type: ignore + if isinstance(channel, discord.TextChannel): + embed = CancelledActionEmbed() + embed.title = "Member Banned" + embed.set_thumbnail(url=user.display_avatar.url) + embed.description = f"{user.mention} {user.global_name}" + embed.timestamp = utcnow() + await channel.send(embed=embed) + + @commands.Cog.listener() + async def on_member_unban(self, guild: discord.Guild, user: discord.User) -> None: + getConfig = await self.get_or_fetch_config( + id=guild.id, redis_pool=self.redis_pool, pool=self.pool + ) + if self.ensureEnabled(getConfig): + channel = guild.get_channel(getConfig["channel_id"]) # type: ignore + if isinstance(channel, discord.TextChannel): + embed = Embed(color=discord.Color.from_rgb(255, 143, 143)) + embed.title = "Member Unbanned" + embed.set_thumbnail(url=user.display_avatar.url) + embed.description = f"{user.mention} {user.global_name}" + embed.timestamp = utcnow() + await channel.send(embed=embed) + + @commands.Cog.listener() + async def on_member_kick(self, guild: discord.Guild, user: discord.User) -> None: + getConfig = await self.get_or_fetch_config( + id=guild.id, redis_pool=self.redis_pool, pool=self.pool + ) + if self.ensureEnabled(getConfig): + channel = guild.get_channel(getConfig["channel_id"]) # type: ignore + if isinstance(channel, discord.TextChannel): + embed = CancelledActionEmbed() + embed.title = "Member Kicked" + embed.set_thumbnail(url=user.display_avatar.url) + embed.description = f"{user.mention} {user.global_name}" + embed.timestamp = utcnow() + await channel.send(embed=embed) async def setup(bot: KumikoCore) -> None: diff --git a/Bot/Libs/cache/decorators.py b/Bot/Libs/cache/decorators.py index ba4e1c3e..9a9ba561 100644 --- a/Bot/Libs/cache/decorators.py +++ b/Bot/Libs/cache/decorators.py @@ -42,12 +42,14 @@ async def deco( if isinstance(res, str) is False: return res cache = KumikoCache(connection_pool=redis_pool) - key = CommandKeyBuilder( - prefix="cache", - namespace="kumiko", - id=id or self.key or uuid.uuid4(), # type: ignore - command=func.__name__, - ) + key = self.key + if key is None: + key = CommandKeyBuilder( + prefix="cache", + namespace="kumiko", + id=id or uuid.uuid4(), + command=func.__name__, + ) if await cache.cacheExists(key=key) is False: await cache.setBasicCache(key=key, value=res, ttl=self.ttl) @@ -63,11 +65,10 @@ class cacheJson: Args: connection_pool (ConnectionPool): Redis connection pool to use - ttl (int, optional): TTL (Time-To-Live). - Defaults to 30. + ttl (int, optional): TTL (Time-To-Live). If None, then the TTL will not be set. Defaults to 30. """ - def __init__(self, key: Optional[str] = None, ttl: int = 30): + def __init__(self, key: Optional[str] = None, ttl: Union[int, None] = 30): self.key = key self.ttl = ttl @@ -88,16 +89,18 @@ async def deco( *args, **kwargs ): - res = await func(id, *args, **kwargs) + res = await func(id, redis_pool, *args, **kwargs) if isinstance(res, dict) is False: return res cache = KumikoCache(connection_pool=redis_pool) - key = CommandKeyBuilder( - prefix="cache", - namespace="kumiko", - id=id or self.key or uuid.uuid4(), # type: ignore - command=func.__name__, - ) + key = self.key + if key is None: + key = CommandKeyBuilder( + prefix="cache", + namespace="kumiko", + id=id or uuid.uuid4(), + command=func.__name__, + ) if await cache.cacheExists(key=key) is False: await cache.setJSONCache(key=key, value=res, ttl=self.ttl) diff --git a/Bot/Libs/cache/redis_cache.py b/Bot/Libs/cache/redis_cache.py index d2c9d02e..e46836e9 100644 --- a/Bot/Libs/cache/redis_cache.py +++ b/Bot/Libs/cache/redis_cache.py @@ -41,17 +41,20 @@ async def getBasicCache(self, key: str) -> Union[str, None]: res = await conn.get(key) return res - async def setJSONCache(self, key: str, value: Dict[str, Any], ttl: int = 5) -> None: + async def setJSONCache( + self, key: str, value: Dict[str, Any], ttl: Union[int, None] = 5 + ) -> None: """Sets the JSON cache on Redis Args: key (str): The key to use for Redis value (Dict[str, Any]): The value of the key-pair value - ttl (Optional[int], optional): TTL of the key-value pair. Defaults to 5. + ttl (Union[int, None], optional): TTL of the key-value pair. If None, then the TTL will not be set. Defaults to 5. """ client: redis.Redis = redis.Redis(connection_pool=self.connection_pool) await client.json().set(name=key, path="$", obj=encodeDatetime(value)) - await client.expire(name=key, time=ttl) + if isinstance(ttl, int): + await client.expire(name=key, time=ttl) async def getJSONCache(self, key: str) -> Union[str, None]: """Gets the JSON cache on Redis diff --git a/Bot/Libs/ui/events_log/views.py b/Bot/Libs/ui/events_log/views.py index f4f6517f..e6cbd064 100644 --- a/Bot/Libs/ui/events_log/views.py +++ b/Bot/Libs/ui/events_log/views.py @@ -36,7 +36,7 @@ async def select_channels( except asyncpg.UniqueViolationError: await tr.rollback() await interaction.response.send_message("There are duplicate records") - except: + except Exception: await tr.rollback() await interaction.response.send_message("Could not create records.") else: @@ -93,7 +93,7 @@ async def confirm( await interaction.response.edit_message( embed=uniqueViolationEmbed, view=self ) - except: + except Exception: await tr.rollback() self.clear_items() failedEmbed = ErrorEmbed( diff --git a/Bot/Libs/utils/help/kumiko_help_paginated.py b/Bot/Libs/utils/help/kumiko_help_paginated.py index 169672f2..29665d03 100644 --- a/Bot/Libs/utils/help/kumiko_help_paginated.py +++ b/Bot/Libs/utils/help/kumiko_help_paginated.py @@ -65,7 +65,7 @@ def __init__(self, entries: dict[commands.Cog, list[commands.Command]], bot): max_values=1, row=0, ) - self.commands: dict[commands.Cog, list[commands.Command]] = entries + self.cmds: dict[commands.Cog, list[commands.Command]] = entries self.bot = bot self.__fill_options() @@ -76,8 +76,8 @@ def __fill_options(self) -> None: value="__index", description="The help page showing how to use the bot.", ) - for cog, commands in self.commands.items(): - if not commands: + for cog, cmds in self.cmds.items(): + if not cmds: continue description = cog.description.split("\n", 1)[0] or None emoji = getattr(cog, "display_emoji", None) @@ -101,7 +101,7 @@ async def callback(self, interaction: discord.Interaction): ) return - commands = self.commands[cog] + commands = self.cmds[cog] if not commands: await interaction.response.send_message( "This category has no commands for you", ephemeral=True diff --git a/Bot/redis_cache.py b/Bot/redis_cache.py new file mode 100644 index 00000000..c9d35ae1 --- /dev/null +++ b/Bot/redis_cache.py @@ -0,0 +1,59 @@ +import asyncio +import os +from typing import Union + +import asyncpg +import uvloop +from dotenv import load_dotenv +from Libs.cache import cacheJson +from pyinstrument import Profiler +from redis.asyncio.connection import ConnectionPool + +profiler = Profiler() + +load_dotenv() + +POSTGRES_URI = os.environ["POSTGRES_URI"] + +profiler.start() + + +@cacheJson(ttl=None) +async def get_or_fetch_config( + id: int, redis_pool: ConnectionPool, pool: asyncpg.Pool +) -> Union[dict, None]: + query = """ + SELECT guild.id, guild.logs, logging_config.channel_id, logging_config.member_events + FROM guild + INNER JOIN logging_config + ON guild.id = logging_config.guild_id + WHERE guild.id = $1; + """ + async with pool.acquire() as conn: + res = await conn.fetchrow(query, id) + return dict(res) + + +async def main(): + # r: redis.Redis = redis.Redis(decode_responses=True) + # await r.hset(name="test", mapping={"testMore": int(True), "testSomeMore": int(False)}) + # # res = await r.hgetall(name="test") + # # print(bool(True)) + # # print(res) + # # print(type(res)) + # key = "test" + # print(await r.exists(key)) + async with asyncpg.create_pool(dsn=POSTGRES_URI) as pool: + res = await get_or_fetch_config( + id=970159505390325842, + redis_pool=ConnectionPool(decode_responses=True), + pool=pool, + ) + print(res["id"]) + + +if __name__ == "__main__": + uvloop.install() + asyncio.run(main()) + profiler.stop() + profiler.print() From 7d0130d9d3f9311caddcb7288b596a0d56022304 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Wed, 5 Jul 2023 23:42:32 -0700 Subject: [PATCH 140/184] Remove test file --- Bot/redis_cache.py | 59 ---------------------------------------------- 1 file changed, 59 deletions(-) delete mode 100644 Bot/redis_cache.py diff --git a/Bot/redis_cache.py b/Bot/redis_cache.py deleted file mode 100644 index c9d35ae1..00000000 --- a/Bot/redis_cache.py +++ /dev/null @@ -1,59 +0,0 @@ -import asyncio -import os -from typing import Union - -import asyncpg -import uvloop -from dotenv import load_dotenv -from Libs.cache import cacheJson -from pyinstrument import Profiler -from redis.asyncio.connection import ConnectionPool - -profiler = Profiler() - -load_dotenv() - -POSTGRES_URI = os.environ["POSTGRES_URI"] - -profiler.start() - - -@cacheJson(ttl=None) -async def get_or_fetch_config( - id: int, redis_pool: ConnectionPool, pool: asyncpg.Pool -) -> Union[dict, None]: - query = """ - SELECT guild.id, guild.logs, logging_config.channel_id, logging_config.member_events - FROM guild - INNER JOIN logging_config - ON guild.id = logging_config.guild_id - WHERE guild.id = $1; - """ - async with pool.acquire() as conn: - res = await conn.fetchrow(query, id) - return dict(res) - - -async def main(): - # r: redis.Redis = redis.Redis(decode_responses=True) - # await r.hset(name="test", mapping={"testMore": int(True), "testSomeMore": int(False)}) - # # res = await r.hgetall(name="test") - # # print(bool(True)) - # # print(res) - # # print(type(res)) - # key = "test" - # print(await r.exists(key)) - async with asyncpg.create_pool(dsn=POSTGRES_URI) as pool: - res = await get_or_fetch_config( - id=970159505390325842, - redis_pool=ConnectionPool(decode_responses=True), - pool=pool, - ) - print(res["id"]) - - -if __name__ == "__main__": - uvloop.install() - asyncio.run(main()) - profiler.stop() - profiler.print() From 0385c2b15c103b6621b54880ddcc471f644c26dd Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Wed, 5 Jul 2023 23:51:41 -0700 Subject: [PATCH 141/184] Fix some pyright issues --- Bot/Libs/utils/help/kumiko_help_paginated.py | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/Bot/Libs/utils/help/kumiko_help_paginated.py b/Bot/Libs/utils/help/kumiko_help_paginated.py index 29665d03..2c61a8db 100644 --- a/Bot/Libs/utils/help/kumiko_help_paginated.py +++ b/Bot/Libs/utils/help/kumiko_help_paginated.py @@ -1,5 +1,5 @@ import itertools -from typing import Any, Optional, Union +from typing import Any, Dict, List, Optional, Union import discord from discord.ext import commands, menus @@ -20,7 +20,7 @@ class GroupHelpPageSource(menus.ListPageSource): def __init__( self, group: Union[commands.Group, commands.Cog], - entries: list[commands.Command], + entries: List[commands.Command], *, prefix: str, ): @@ -30,7 +30,7 @@ def __init__( self.title: str = f"{self.group.qualified_name} Commands" self.description: str = self.group.description - async def format_page(self, menu: KumikoPages, commands: list[commands.Command]): + async def format_page(self, menu: KumikoPages, commands: List[commands.Command]): embed = discord.Embed( title=self.title, description=self.description, @@ -58,14 +58,14 @@ async def format_page(self, menu: KumikoPages, commands: list[commands.Command]) class HelpSelectMenu(discord.ui.Select["HelpMenu"]): - def __init__(self, entries: dict[commands.Cog, list[commands.Command]], bot): + def __init__(self, entries: dict[commands.Cog, List[commands.Command]], bot): super().__init__( placeholder="Select a category...", min_values=1, max_values=1, row=0, ) - self.cmds: dict[commands.Cog, list[commands.Command]] = entries + self.cmds: dict[commands.Cog, List[commands.Command]] = entries self.bot = bot self.__fill_options() @@ -119,7 +119,7 @@ def __init__(self, source: menus.PageSource, ctx: commands.Context): super().__init__(source, ctx=ctx, compact=True) def add_categories( - self, commands: dict[commands.Cog, list[commands.Command]] + self, commands: Dict[commands.Cog, List[commands.Command]] ) -> None: self.clear_items() self.add_item(HelpSelectMenu(commands, self.ctx.bot)) @@ -254,7 +254,7 @@ def key(command) -> str: bot.commands, sort=True, key=key ) - all_commands: dict[commands.Cog, list[commands.Command]] = {} + all_commands: dict[commands.Cog, List[commands.Command]] = {} for name, children in itertools.groupby(entries, key=key): if name == "\U0010ffff": continue From b86c850f1b5612d0170fe834b649034a954c667c Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Wed, 5 Jul 2023 23:54:17 -0700 Subject: [PATCH 142/184] I think i fixed it --- Bot/Libs/utils/help/kumiko_help_paginated.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Bot/Libs/utils/help/kumiko_help_paginated.py b/Bot/Libs/utils/help/kumiko_help_paginated.py index 2c61a8db..026f078d 100644 --- a/Bot/Libs/utils/help/kumiko_help_paginated.py +++ b/Bot/Libs/utils/help/kumiko_help_paginated.py @@ -58,7 +58,7 @@ async def format_page(self, menu: KumikoPages, commands: List[commands.Command]) class HelpSelectMenu(discord.ui.Select["HelpMenu"]): - def __init__(self, entries: dict[commands.Cog, List[commands.Command]], bot): + def __init__(self, entries: Dict[commands.Cog, List[commands.Command]], bot): super().__init__( placeholder="Select a category...", min_values=1, From 0cb4ee515f46827c1b223870220c50fda9e76d07 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Thu, 6 Jul 2023 02:33:57 -0700 Subject: [PATCH 143/184] Implement an help page from RDanny Closes #369 --- Bot/Cogs/actions.py | 6 +- Bot/Cogs/dev-tools.py | 6 ++ Bot/Cogs/events-log.py | 8 +- Bot/Cogs/github.py | 7 +- Bot/Cogs/kumiko.py | 4 + Bot/Cogs/moderation.py | 6 +- Bot/Cogs/prefix.py | 9 +- Bot/Cogs/reddit.py | 8 +- Bot/Cogs/search.py | 10 +- Bot/Cogs/waifus.py | 9 +- Bot/Libs/utils/help/kumiko_help_paginated.py | 105 ++++++++++--------- 11 files changed, 118 insertions(+), 60 deletions(-) diff --git a/Bot/Cogs/actions.py b/Bot/Cogs/actions.py index 39c7eafb..3c9bb28f 100644 --- a/Bot/Cogs/actions.py +++ b/Bot/Cogs/actions.py @@ -8,12 +8,16 @@ class Actions(commands.Cog): - """Hug, pet, or kiss someone on Discord!""" + """Hug, pet, or kiss someone on Discord""" def __init__(self, bot: KumikoCore) -> None: self.bot = bot self.session = self.bot.session + @property + def display_emoji(self) -> discord.PartialEmoji: + return discord.PartialEmoji.from_str("<:headpat:1020641548645437491>") + @commands.hybrid_command(name="hug") @app_commands.describe(user="The user to hug") async def hug(self, ctx: commands.Context, user: Greedy[discord.Member]) -> None: diff --git a/Bot/Cogs/dev-tools.py b/Bot/Cogs/dev-tools.py index d333a0e1..4a67e5df 100644 --- a/Bot/Cogs/dev-tools.py +++ b/Bot/Cogs/dev-tools.py @@ -8,9 +8,15 @@ class DevTools(commands.Cog): + """Tools for developing Kumiko""" + def __init__(self, bot: KumikoCore): self.bot = bot + @property + def display_emoji(self) -> discord.PartialEmoji: + return discord.PartialEmoji(name="\U0001f6e0") + @commands.hybrid_command(name="sync") @commands.guild_only() @commands.is_owner() diff --git a/Bot/Cogs/events-log.py b/Bot/Cogs/events-log.py index 20fa32a4..41bcfaea 100644 --- a/Bot/Cogs/events-log.py +++ b/Bot/Cogs/events-log.py @@ -1,3 +1,4 @@ +from discord import PartialEmoji from discord.ext import commands from kumikocore import KumikoCore from Libs.ui.events_log import RegisterView, UnregisterView @@ -5,14 +6,19 @@ class EventsLog(commands.Cog): - """Events logging module - Optional module to log member joins and others""" + """Logging module to track joins, and economy events""" def __init__(self, bot: KumikoCore) -> None: self.bot = bot self.pool = self.bot.pool + @property + def display_emoji(self) -> PartialEmoji: + return PartialEmoji(name="\U0001f4f0") + @commands.hybrid_group(name="logs") async def logs(self, ctx: commands.Context) -> None: + """Logs events and actions on your server""" if ctx.invoked_subcommand is None: await ctx.send_help(ctx.command) diff --git a/Bot/Cogs/github.py b/Bot/Cogs/github.py index 136b4b57..ce7e5dd1 100644 --- a/Bot/Cogs/github.py +++ b/Bot/Cogs/github.py @@ -2,7 +2,7 @@ import ciso8601 import orjson -from discord import app_commands +from discord import PartialEmoji, app_commands from discord.ext import commands from discord.utils import format_dt from dotenv import load_dotenv @@ -23,8 +23,13 @@ def __init__(self, bot: KumikoCore) -> None: self.bot = bot self.session = self.bot.session + @property + def display_emoji(self) -> PartialEmoji: + return PartialEmoji.from_str("<:github:744345792172654643>") + @commands.hybrid_group(name="github") async def github(self, ctx: commands.Context) -> None: + """Github search and utility commands""" if ctx.invoked_subcommand is None: await ctx.send_help(ctx.command) diff --git a/Bot/Cogs/kumiko.py b/Bot/Cogs/kumiko.py index 89300dc6..629eb6fa 100644 --- a/Bot/Cogs/kumiko.py +++ b/Bot/Cogs/kumiko.py @@ -16,6 +16,10 @@ class Kumiko(commands.Cog): def __init__(self, bot: KumikoCore) -> None: self.bot = bot + @property + def display_emoji(self) -> discord.PartialEmoji: + return discord.PartialEmoji.from_str("<:upward_stonks:739614245997641740>") + @commands.Cog.listener() async def on_ready(self): global startTime diff --git a/Bot/Cogs/moderation.py b/Bot/Cogs/moderation.py index ee351814..20eaa85b 100644 --- a/Bot/Cogs/moderation.py +++ b/Bot/Cogs/moderation.py @@ -2,7 +2,7 @@ from typing import Optional import discord -from discord import app_commands +from discord import PartialEmoji, app_commands from discord.ext import commands from kumikocore import KumikoCore from Libs.utils import Embed, parseTimeStr @@ -14,6 +14,10 @@ class Moderation(commands.Cog): def __init__(self, bot: KumikoCore) -> None: self.bot = bot + @property + def display_emoji(self) -> PartialEmoji: + return PartialEmoji.from_str("<:blobban:759935431847968788>") + @commands.hybrid_group(name="mod") async def mod(self, ctx: commands.Context): """A set of fine-tuned moderation commands""" diff --git a/Bot/Cogs/prefix.py b/Bot/Cogs/prefix.py index c6b7e371..2618482d 100644 --- a/Bot/Cogs/prefix.py +++ b/Bot/Cogs/prefix.py @@ -1,4 +1,4 @@ -from discord import app_commands +from discord import PartialEmoji, app_commands from discord.ext import commands from discord.utils import utcnow from kumikocore import KumikoCore @@ -9,14 +9,19 @@ # TODO - Straight up slap an GIN index on the prefixes column class Prefix(commands.Cog): - """Kumiko's custom prefix manager! Set a custom prefix for your server!""" + """Manages custom prefixes for your server""" def __init__(self, bot: KumikoCore) -> None: self.bot = bot self.pool = self.bot.pool + @property + def display_emoji(self) -> PartialEmoji: + return PartialEmoji(name="\U000025b6") + @commands.hybrid_group(name="prefix") async def prefix(self, ctx: commands.Context) -> None: + """Utilities to manage and view your server prefixes""" if ctx.invoked_subcommand is None: await ctx.send_help(ctx.command) diff --git a/Bot/Cogs/reddit.py b/Bot/Cogs/reddit.py index 8ed92bc7..51f72b0d 100644 --- a/Bot/Cogs/reddit.py +++ b/Bot/Cogs/reddit.py @@ -4,7 +4,7 @@ import asyncpraw import orjson -from discord import app_commands +from discord import PartialEmoji, app_commands from discord.ext import commands from discord.utils import format_dt from dotenv import load_dotenv @@ -26,9 +26,13 @@ def __init__(self, bot: KumikoCore) -> None: self.bot = bot self.session = self.bot.session + @property + def display_emoji(self) -> PartialEmoji: + return PartialEmoji.from_str("<:reddit:314349923103670272>") + @commands.hybrid_group(name="reddit") async def reddit(self, ctx: commands.Context) -> None: - """Base command for Reddit""" + """Reddit search and utility commands""" if ctx.invoked_subcommand is None: await ctx.send_help(ctx.command) diff --git a/Bot/Cogs/search.py b/Bot/Cogs/search.py index 98c986a4..c9c67f94 100644 --- a/Bot/Cogs/search.py +++ b/Bot/Cogs/search.py @@ -3,7 +3,7 @@ import ciso8601 import orjson -from discord import app_commands +from discord import PartialEmoji, app_commands from discord.ext import commands from discord.utils import format_dt from dotenv import load_dotenv @@ -19,15 +19,19 @@ class Searches(commands.Cog): - """Search for anime, manga, gifs, memes, and much more!""" + """Search for anime, manga, gifs, memes, and much more""" def __init__(self, bot: KumikoCore) -> None: self.bot = bot self.session = self.bot.session + @property + def display_emoji(self) -> PartialEmoji: + return PartialEmoji.from_str("") + @commands.hybrid_group(name="search") async def search(self, ctx: commands.Context) -> None: - """Base parent command for searches - See the subcommands for more info""" + """Search for anime, manga, gifs, memes, and much more""" if ctx.invoked_subcommand is None: await ctx.send_help(ctx.command) diff --git a/Bot/Cogs/waifus.py b/Bot/Cogs/waifus.py index 5b86bbfd..23066d48 100644 --- a/Bot/Cogs/waifus.py +++ b/Bot/Cogs/waifus.py @@ -1,6 +1,7 @@ import random import orjson +from discord import PartialEmoji from discord.ext import commands from kumikocore import KumikoCore from Libs.utils import Embed @@ -8,15 +9,19 @@ class Waifu(commands.Cog): - """Commands for getting some waifu pics""" + """Gives you random waifu pics""" def __init__(self, bot: KumikoCore) -> None: self.bot = bot self.session = self.bot.session + @property + def display_emoji(self) -> PartialEmoji: + return PartialEmoji.from_str("<:UwU:1013221555003719772>") + @commands.hybrid_group(name="waifu") async def waifu(self, ctx: commands.Context) -> None: - """Base parent command for waifu - See the subcommands for more info""" + """Waifu waifu waifus Mai Sakurajima is the best""" if ctx.invoked_subcommand is None: await ctx.send_help(ctx.command) diff --git a/Bot/Libs/utils/help/kumiko_help_paginated.py b/Bot/Libs/utils/help/kumiko_help_paginated.py index 026f078d..9ee0206f 100644 --- a/Bot/Libs/utils/help/kumiko_help_paginated.py +++ b/Bot/Libs/utils/help/kumiko_help_paginated.py @@ -1,3 +1,4 @@ +import inspect import itertools from typing import Any, Dict, List, Optional, Union @@ -15,6 +16,11 @@ # async def callback(self, interaction: discord.Interaction): +# RGB Colors: +# Pink (255, 161, 231) - Used for the main bot page +# Lavender (197, 184, 255) - Used for cog and group pages +# Light Orange (255, 199, 184) - Used for command pages + class GroupHelpPageSource(menus.ListPageSource): def __init__( @@ -34,7 +40,7 @@ async def format_page(self, menu: KumikoPages, commands: List[commands.Command]) embed = discord.Embed( title=self.title, description=self.description, - colour=discord.Colour(0xA8B9CD), + colour=discord.Colour.from_rgb(197, 184, 255), ) for command in commands: @@ -154,53 +160,58 @@ async def get_page(self, page_number: int) -> Any: return self def format_page(self, menu: HelpMenu, page: Any): - embed = discord.Embed(title="Bot Help", colour=discord.Colour(0xA8B9CD)) - embed.description = "help" - # embed.description = inspect.cleandoc( - # f""" - # Hello! Welcome to the help page. - - # Use "{menu.ctx.clean_prefix}help command" for more info on a command. - # Use "{menu.ctx.clean_prefix}help category" for more info on a category. - # Use the dropdown menu below to select a category. - # """ - # ) - - # embed.add_field( - # name='Support Server', - # value='For more help, consider joining the official server over at https://discord.gg/DWEaqMy', - # inline=False, - # ) + embed = discord.Embed( + title="Bot Help", colour=discord.Colour.from_rgb(255, 161, 231) + ) + # embed.description = "help" + embed.description = inspect.cleandoc( + f""" + Hello! Welcome to the help page. + + Use "{menu.ctx.clean_prefix}help command" for more info on a command. + Use "{menu.ctx.clean_prefix}help category" for more info on a category. + Use the dropdown menu below to select a category. + """ + ) + + embed.add_field( + name="Support Server", + value="For more help, consider joining the official server over at https://discord.gg/sYP7z2sUda", + inline=False, + ) # created_at = time.format_dt(menu.ctx.bot.user.created_at, 'F') - # if self.index == 0: - # embed.add_field( - # name='Who are you?', - # value=( - # "I'm a bot made by Danny#0007. I'm the oldest running Discord bot! I've been running since " - # f'{created_at}. I have features such as moderation, tags, starboard, and more. You can get more ' - # 'information on my commands by using the dropdown below.\n\n' - # "I'm also open source. You can see my code on [GitHub](https://github.com/Rapptz/RoboDanny)!" - # ), - # inline=False, - # ) - # elif self.index == 1: - # entries = ( - # ('', 'This means the argument is __**required**__.'), - # ('[argument]', 'This means the argument is __**optional**__.'), - # ('[A|B]', 'This means that it can be __**either A or B**__.'), - # ( - # '[argument...]', - # 'This means you can have multiple arguments.\n' - # 'Now that you know the basics, it should be noted that...\n' - # '__**You do not type in the brackets!**__', - # ), - # ) - - # embed.add_field(name='How do I use this bot?', value='Reading the bot signature is pretty simple.') - - # for name, value in entries: - # embed.add_field(name=name, value=value, inline=False) + if self.index == 0: + embed.add_field( + name="About Kumiko", + value=( + "Kumiko is an multipurpose bot that takes an unique and alternative approach to " + "what an multipurpose bot is. Kumiko offers features such as moderation, economy, and many more. You can get more " + "information on the commands offered by using the dropdown below.\n\n" + "Kumiko is also open source. You can see the code on [GitHub](https://github.com/No767/Kumiko)" + ), + inline=False, + ) + elif self.index == 1: + entries = ( + ("", "This means the argument is __**required**__."), + ("[argument]", "This means the argument is __**optional**__."), + ("[A|B]", "This means that it can be __**either A or B**__."), + ( + "[argument...]", + "This means you can have multiple arguments.\n" + "Now that you know the basics, it should be noted that...\n" + "__**You do not type in the brackets!**__", + ), + ) + + embed.add_field( + name="How do I use this bot?", + value="Reading the bot signature is pretty simple.", + ) + + for name, value in entries: + embed.add_field(name=name, value=value, inline=False) return embed @@ -284,7 +295,7 @@ def common_command_formatting(self, embed_like, command): async def send_command_help(self, command): # No pagination necessary for a single command. - embed = discord.Embed(colour=discord.Colour(0xA8B9CD)) + embed = discord.Embed(colour=discord.Colour.from_rgb(255, 199, 184)) self.common_command_formatting(embed, command) await self.context.send(embed=embed) From f8fb66d6b91bc2e08ed6ffe8eac92dbdd1cc7295 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Thu, 6 Jul 2023 02:44:57 -0700 Subject: [PATCH 144/184] Move the kumiko cog into the meta cog --- Bot/Cogs/{kumiko.py => meta.py} | 22 ++++++++-------------- 1 file changed, 8 insertions(+), 14 deletions(-) rename Bot/Cogs/{kumiko.py => meta.py} (78%) diff --git a/Bot/Cogs/kumiko.py b/Bot/Cogs/meta.py similarity index 78% rename from Bot/Cogs/kumiko.py rename to Bot/Cogs/meta.py index 629eb6fa..21300b17 100644 --- a/Bot/Cogs/kumiko.py +++ b/Bot/Cogs/meta.py @@ -10,28 +10,22 @@ VERSION = "v0.9.0" -class Kumiko(commands.Cog): - """Commands to get basic info about Kumiko""" +class Meta(commands.Cog): + """Commands to obtain info about Kumiko or others""" def __init__(self, bot: KumikoCore) -> None: self.bot = bot @property def display_emoji(self) -> discord.PartialEmoji: - return discord.PartialEmoji.from_str("<:upward_stonks:739614245997641740>") + return discord.PartialEmoji(name="\U00002754") @commands.Cog.listener() async def on_ready(self): global startTime startTime = time.time() - @commands.hybrid_group(name="kumiko") - async def kumiko(self, ctx: commands.Context) -> None: - """Base parent command for Kumiko - See the subcommands for more info""" - if ctx.invoked_subcommand is None: - await ctx.send_help(ctx.command) - - @kumiko.command(name="uptime") + @commands.hybrid_command(name="uptime") async def botUptime(self, ctx: commands.Context) -> None: """Returns uptime for Kumiko""" uptime = datetime.timedelta(seconds=int(round(time.time() - startTime))) @@ -39,7 +33,7 @@ async def botUptime(self, ctx: commands.Context) -> None: embed.description = f"Kumiko's Uptime: `{uptime.days} Days, {uptime.seconds//3600} Hours, {(uptime.seconds//60)%60} Minutes, {(uptime.seconds%60)} Seconds`" await ctx.send(embed=embed) - @kumiko.command(name="info") + @commands.hybrid_command(name="info") async def kumikoInfo(self, ctx: commands.Context) -> None: """Shows some basic info about Kumiko""" embed = Embed() @@ -56,14 +50,14 @@ async def kumikoInfo(self, ctx: commands.Context) -> None: embed.add_field(name="Kumiko Build Version", value=VERSION, inline=True) await ctx.send(embed=embed) - @kumiko.command(name="version") + @commands.hybrid_command(name="version") async def version(self, ctx: commands.Context) -> None: """Returns the current version of Kumiko""" embed = Embed() embed.description = f"Build Version: {VERSION}" await ctx.send(embed=embed) - @kumiko.command(name="ping") + @commands.hybrid_command(name="ping") async def ping(self, ctx: commands.Context) -> None: """Returns the current latency of Kumiko""" embed = Embed() @@ -72,4 +66,4 @@ async def ping(self, ctx: commands.Context) -> None: async def setup(bot: KumikoCore) -> None: - await bot.add_cog(Kumiko(bot)) + await bot.add_cog(Meta(bot)) From 832b5e0185844eb968db3f5a2b0aae8af2ea9350 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Thu, 6 Jul 2023 02:53:26 -0700 Subject: [PATCH 145/184] [skip ci] Update changelog --- changelog.md | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/changelog.md b/changelog.md index 3f2b011c..988d73b5 100644 --- a/changelog.md +++ b/changelog.md @@ -28,6 +28,7 @@ For the full list of changes, please see them here: [`v0.8.x...v0.9.0`](https:// - Update Dockerfile to use Debian 12 (Bookworm) - Use `Embed.timestamp` for some embeds to show timestamps - Replaced `.gitignore` with a proper one from GitHub +- Replaced `kumiko.py` with `meta.py` to allow for clearer purpose ## ✨ Additions @@ -42,6 +43,8 @@ For the full list of changes, please see them here: [`v0.8.x...v0.9.0`](https:// - EventsLog module - Ping checks to ensure that the connections are open for PostgreSQL and Redis - Docs merged into one repo - this repo +- Added `display_emoji` property to allow for cogs to have emojis when being loaded in the select menus +- The final version of what an help command should be (taken from RDanny directly as usual) ## ➖ Removals - Global KumikoCPM variable in favor of having it stored during runtime instead @@ -113,3 +116,6 @@ For the full list of changes, please see them here: [`v0.8.x...v0.9.0`](https:// - \[pip](deps)\: Bump redis from 4.5.5 to 4.6.0 (#363) (@dependabot) - \[pip](deps-dev)\: Bump pyright from 1.1.315 to 1.1.316 (#362) (@dependabot) - \[pip](deps)\: Bump prisma from 0.9.0 to 0.9.1 (#367) (@dependabot) +- \[pip](deps-dev)\: Bump ruff from 0.0.275 to 0.0.276 (#370) (@dependabot) +- \[pip](deps-dev)\: Bump ruff from 0.0.276 to 0.0.277 (#371) (@dependabot) +- \[Actions](deps)\: Bump actions/setup-node from 3.6.0 to 3.7.0 (#372) (@dependabot) \ No newline at end of file From 14f2b2faadd6cedc76d01fa9d7cdc88aa570c037 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Thu, 6 Jul 2023 23:19:19 -0700 Subject: [PATCH 146/184] Add a *broken* config command --- Bot/Cogs/events-log.py | 50 ++++++++++++++++++++++++++++++++++- Bot/Libs/cache/redis_cache.py | 18 ++++++++++--- 2 files changed, 63 insertions(+), 5 deletions(-) diff --git a/Bot/Cogs/events-log.py b/Bot/Cogs/events-log.py index 41bcfaea..848b656f 100644 --- a/Bot/Cogs/events-log.py +++ b/Bot/Cogs/events-log.py @@ -1,8 +1,13 @@ -from discord import PartialEmoji +from typing import Any, Dict, Union + +import asyncpg +from discord import PartialEmoji, app_commands from discord.ext import commands from kumikocore import KumikoCore +from Libs.cache import KumikoCache, cacheJson from Libs.ui.events_log import RegisterView, UnregisterView from Libs.utils import ConfirmEmbed, Embed +from redis.asyncio.connection import ConnectionPool class EventsLog(commands.Cog): @@ -11,11 +16,27 @@ class EventsLog(commands.Cog): def __init__(self, bot: KumikoCore) -> None: self.bot = bot self.pool = self.bot.pool + self.redis_pool = self.bot.redis_pool @property def display_emoji(self) -> PartialEmoji: return PartialEmoji(name="\U0001f4f0") + @cacheJson(ttl=3600) + async def get_or_fetch_config( + self, id: int, redis_pool: ConnectionPool, pool: asyncpg.Pool + ) -> Union[Dict[str, Any], None]: + query = """ + SELECT guild.id, guild.logs, logging_config.channel_id, logging_config.member_events + FROM guild + INNER JOIN logging_config + ON guild.id = logging_config.guild_id + WHERE guild.id = $1; + """ + async with self.pool.acquire() as conn: + res = await conn.fetchrow(query, id) + return dict(res) + @commands.hybrid_group(name="logs") async def logs(self, ctx: commands.Context) -> None: """Logs events and actions on your server""" @@ -72,6 +93,33 @@ async def logInfo(self, ctx: commands.Context) -> None: ) await ctx.send(embed=embed) + # TODO - Provide an interactive UI to set which one is enabled or not + # Also im well aware that this has a ton of issues that need to be ironed out + # But i will be fixing them before releasing v0.9.0 + # I just want to get this merged and done with + # We need to also update the DB. probably needs a rework + @commands.has_guild_permissions(manage_guild=True) + @commands.guild_only() + @logs.command(name="configure") + @app_commands.describe( + event="The event to enable", status="Whether the event is enabled or disabled" + ) + async def logConfig(self, ctx: commands.Context, event: str, status: bool) -> None: + """Configures which events are enabled""" + guild_id = ctx.guild.id # type: ignore + cache = KumikoCache(connection_pool=self.redis_pool) + config = await self.get_or_fetch_config( + id=guild_id, redis_pool=self.redis_pool, pool=self.pool + ) + if config is None or isinstance(config, str): + await ctx.send("The config was not set up. Please enable the logs module") + return + if event in config and config[event] is True: + key = f"cache:kumiko:{guild_id}:get_or_fetch_config" + await cache.setJSONCache(key=key, value=status, path=f".{event}") + await ctx.send("Config updated. The event has been enabled/disabled") + return + async def setup(bot: KumikoCore) -> None: await bot.add_cog(EventsLog(bot)) diff --git a/Bot/Libs/cache/redis_cache.py b/Bot/Libs/cache/redis_cache.py index e46836e9..e4eafc69 100644 --- a/Bot/Libs/cache/redis_cache.py +++ b/Bot/Libs/cache/redis_cache.py @@ -42,21 +42,31 @@ async def getBasicCache(self, key: str) -> Union[str, None]: return res async def setJSONCache( - self, key: str, value: Dict[str, Any], ttl: Union[int, None] = 5 + self, + key: str, + value: Union[Dict[str, Any], Any], + path: str = "$", + ttl: Union[int, None] = 5, ) -> None: """Sets the JSON cache on Redis Args: key (str): The key to use for Redis - value (Dict[str, Any]): The value of the key-pair value + value (Union[Dict[str, Any], Any]): The value of the key-pair value + path (str): The path to look for or set. Defautls to "$" ttl (Union[int, None], optional): TTL of the key-value pair. If None, then the TTL will not be set. Defaults to 5. """ client: redis.Redis = redis.Redis(connection_pool=self.connection_pool) - await client.json().set(name=key, path="$", obj=encodeDatetime(value)) + await client.json().set( + name=key, + path=path, + obj=encodeDatetime(value) if isinstance(value, dict) else value, + ) if isinstance(ttl, int): await client.expire(name=key, time=ttl) - async def getJSONCache(self, key: str) -> Union[str, None]: + # The output type comes from here: https://github.com/redis/redis-py/blob/9f503578d1ffed20d63e8023bcd8a7dccd15ecc5/redis/commands/json/_util.py#L3C1-L3C73 + async def getJSONCache(self, key: str) -> Union[str, None, Dict[str, Any]]: """Gets the JSON cache on Redis Args: From 69efab79b1200cedbb79f9e1df38815535e115e0 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Thu, 6 Jul 2023 23:32:46 -0700 Subject: [PATCH 147/184] [skip ci] Update Readme and Changelog --- README.md | 7 +++---- changelog.md | 2 ++ 2 files changed, 5 insertions(+), 4 deletions(-) diff --git a/README.md b/README.md index 8e609f9f..18504314 100644 --- a/README.md +++ b/README.md @@ -16,20 +16,19 @@ A multipurpose Discord bot built with freedom and choice in mind ## Kumiko (久美子) -Kumiko is a multipurpose Discord bot built with freedom and choice in mind. Kumiko allows you to decide on whether you wish to use the services provided. Kumiko includes a opt-in economy system, custom quests, and many more features. Kumiko also includes integration with AniList, Reddit, Twitter, and others. +Kumiko is a multipurpose Discord bot built with freedom and choice in mind. Kumiko provides a wide range of features, including an customizable and local economy, logging, and many more features. Integration with AniList, and others are also included. ## Features - Customizable prefix module -- Global or guild economy with jobs and marketplaces -- Custom logging module +- Customizable local economy module with jobs, ranks, and more +- Custom logging module (aka EventsLog) - Basic moderation commands - Search for memes, posts, anime, manga, and others! And some ones that are planned: - Complete Web Dashboard + Custom Embeds (WIP, pinned for v2) -- Event Logging (Pinned for v1) - Annoucement releaser with support from GitHub (Pinned for v2) - Selector Roles (pinned for v2) diff --git a/changelog.md b/changelog.md index 988d73b5..ac243dd5 100644 --- a/changelog.md +++ b/changelog.md @@ -29,6 +29,8 @@ For the full list of changes, please see them here: [`v0.8.x...v0.9.0`](https:// - Use `Embed.timestamp` for some embeds to show timestamps - Replaced `.gitignore` with a proper one from GitHub - Replaced `kumiko.py` with `meta.py` to allow for clearer purpose +- Updated the return types of `KumikoCache().getJSONCache()` +- Allow for custom paths to search for `KumikoCache().setJSONCache()` ## ✨ Additions From e7f1b4e233c9f5b930f015dfee8cbcca18eee10c Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Thu, 6 Jul 2023 23:52:38 -0700 Subject: [PATCH 148/184] Implement any tests to increase coverage --- codecov.yml | 3 ++- tests/redis/test_global_cache.py | 7 +++++++ tests/redis/test_redis_cache.py | 9 +++++++++ 3 files changed, 18 insertions(+), 1 deletion(-) diff --git a/codecov.yml b/codecov.yml index e5a0a241..70048216 100644 --- a/codecov.yml +++ b/codecov.yml @@ -3,4 +3,5 @@ ignore: - "Bot/Libs/utils/help/**" - "Bot/Libs/utils/pages/**" - "Bot/Libs/utils/kumiko_logger.py" - - "Bot/Libs/utils/embeds.py" \ No newline at end of file + - "Bot/Libs/utils/embeds.py" + - "Bots/Libs/utils/prefix.py" # This contains an coroutine that we can't even test to begin with \ No newline at end of file diff --git a/tests/redis/test_global_cache.py b/tests/redis/test_global_cache.py index d837c385..cb03acc6 100644 --- a/tests/redis/test_global_cache.py +++ b/tests/redis/test_global_cache.py @@ -27,3 +27,10 @@ def test_get_cp(): kumikoCP = KumikoCPManager(uri=REDIS_URI) connPool = kumikoCP.getConnPool() assert isinstance(connPool, ConnectionPool) + + +def test_created_cp(): + kumikoCP = KumikoCPManager(uri=REDIS_URI) + kumikoCP.createPool() + newConnPool = kumikoCP.getConnPool() + assert isinstance(newConnPool, ConnectionPool) diff --git a/tests/redis/test_redis_cache.py b/tests/redis/test_redis_cache.py index b965063b..0245fbed 100644 --- a/tests/redis/test_redis_cache.py +++ b/tests/redis/test_redis_cache.py @@ -42,3 +42,12 @@ async def test_key_exists(): await cache.setBasicCache(key=key, value=DATA) res = await cache.cacheExists(key=key) assert res is True # nosec + + +@pytest.mark.asyncio +async def test_get_json_cache_if_none(): + key = CommandKeyBuilder(id=123564343, command="ayo_what_mate") + connPool = ConnectionPool().from_url("redis://localhost:6379/0") + cache = KumikoCache(connection_pool=connPool) + res = await cache.getJSONCache(key=key) + assert res is None From b834b6cf91e4fa5bdb84c985505515fa8e821d71 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Fri, 7 Jul 2023 00:17:20 -0700 Subject: [PATCH 149/184] Update tests --- .../utils/postgresql/ensure_open_conns.py | 9 +++--- Bot/Libs/utils/redis/connections.py | 9 +++--- tests/redis/test_cache_deco.py | 28 +++++++++++++++++++ tests/utils/test_parse_subreddits.py | 4 +++ 4 files changed, 40 insertions(+), 10 deletions(-) diff --git a/Bot/Libs/utils/postgresql/ensure_open_conns.py b/Bot/Libs/utils/postgresql/ensure_open_conns.py index 4000fd94..cb05380b 100644 --- a/Bot/Libs/utils/postgresql/ensure_open_conns.py +++ b/Bot/Libs/utils/postgresql/ensure_open_conns.py @@ -1,22 +1,21 @@ import logging +from typing import Literal import asyncpg -async def ensureOpenPostgresConn(conn_pool: asyncpg.Pool) -> bool: +async def ensureOpenPostgresConn(conn_pool: asyncpg.Pool) -> Literal[True]: """Ensures that the current connection pulled from the pool can be run. Args: conn_pool (asyncpg.Pool): The connection pool to get connections from. Returns: - bool: True if the connection can be ran. + Literal[True]: If successful, the coroutine will return True, otherwise it will raise an exception """ logger = logging.getLogger("discord") async with conn_pool.acquire() as conn: connStatus = conn.is_closed() if connStatus is False: logger.info("PostgreSQL server is up") - return True - logger.error("Failed to connect to PostgreSQL") - return False \ No newline at end of file + return True diff --git a/Bot/Libs/utils/redis/connections.py b/Bot/Libs/utils/redis/connections.py index 74fcff45..1b9767f2 100644 --- a/Bot/Libs/utils/redis/connections.py +++ b/Bot/Libs/utils/redis/connections.py @@ -1,4 +1,5 @@ import logging +from typing import Literal import redis.asyncio as redis from redis.asyncio.connection import ConnectionPool @@ -6,19 +7,17 @@ logger = logging.getLogger("discord") -async def ensureOpenRedisConn(redis_pool: ConnectionPool) -> bool: +async def ensureOpenRedisConn(redis_pool: ConnectionPool) -> Literal[True]: """Pings the Redis server to check if it's open or not Args: connection_pool (Union[ConnectionPool, None]): The supplied connection pool. If none, it will be created automatically Returns: - bool: Whether the server is up or not + Literal[True]: If successful, the coroutine will return True, otherwise it will raise an exception """ r: redis.Redis = redis.Redis(connection_pool=redis_pool) resultPing = await r.ping() if resultPing: logger.info("Sucessfully connected to the Redis server") - return True - logger.error("Failed to connect to the Redis server - Restart Kumiko to reconnect") - return False + return True diff --git a/tests/redis/test_cache_deco.py b/tests/redis/test_cache_deco.py index f9bab76f..cca18f5b 100644 --- a/tests/redis/test_cache_deco.py +++ b/tests/redis/test_cache_deco.py @@ -44,3 +44,31 @@ async def testFuncJSON( ) and isinstance( # nosec res, dict ) + + +# the results of these should be the types returned +# within the decos, there is code that refuses to cache if the return type is not what is needed +@pytest.mark.asyncio +async def test_cache_deco_invalid(): + connPool = ConnectionPool() + + @cache() + async def testFuncInvalid(id=2345973453, redis_pool=ConnectionPool()): + return 23464354 + + res = await testFuncInvalid(2345973453, connPool) + assert await testFuncInvalid(2345973453, connPool) == 23464354 and isinstance( + res, int + ) + + +@pytest.mark.asyncio +async def test_cache_deco_json_invalid(): + connPool = ConnectionPool() + + @cacheJson() + async def testFuncJSONInvalid(id=2345973453, redis_pool=ConnectionPool()): + return [1, 2, 3, 4, 5] + + res = await testFuncJSONInvalid(2345973453, connPool) + assert 1 in res and isinstance(res, list) # type: ignore diff --git a/tests/utils/test_parse_subreddits.py b/tests/utils/test_parse_subreddits.py index 39f8a9ef..e8f3ef5f 100644 --- a/tests/utils/test_parse_subreddits.py +++ b/tests/utils/test_parse_subreddits.py @@ -13,3 +13,7 @@ def test_rslash_egg_irl(): def test_egg_irl(): assert parseSubreddit("egg_irl") == "egg_irl" + + +def test_none_subreddit(): + assert parseSubreddit(subreddit=None) == "all" From dad30145b2b50af2a0597f201672205a001864c6 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Fri, 7 Jul 2023 00:21:02 -0700 Subject: [PATCH 150/184] Fix codecov config --- codecov.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/codecov.yml b/codecov.yml index 70048216..67489276 100644 --- a/codecov.yml +++ b/codecov.yml @@ -4,4 +4,4 @@ ignore: - "Bot/Libs/utils/pages/**" - "Bot/Libs/utils/kumiko_logger.py" - "Bot/Libs/utils/embeds.py" - - "Bots/Libs/utils/prefix.py" # This contains an coroutine that we can't even test to begin with \ No newline at end of file + - "Bot/Libs/utils/prefix.py" # This contains an coroutine that we can't even test to begin with \ No newline at end of file From 51b982afc3205baab1bdb30e53dec488fceb0a22 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Fri, 7 Jul 2023 00:30:46 -0700 Subject: [PATCH 151/184] [skip ci] Cleanup --- playbook.yml => Anible-Playbooks/playbook.yml | 0 postgres.yml => Anible-Playbooks/postgres.yml | 0 docker-compose-example.yml | 34 ------------------- docker-compose.yml | 16 ++++++--- 4 files changed, 11 insertions(+), 39 deletions(-) rename playbook.yml => Anible-Playbooks/playbook.yml (100%) rename postgres.yml => Anible-Playbooks/postgres.yml (100%) delete mode 100644 docker-compose-example.yml diff --git a/playbook.yml b/Anible-Playbooks/playbook.yml similarity index 100% rename from playbook.yml rename to Anible-Playbooks/playbook.yml diff --git a/postgres.yml b/Anible-Playbooks/postgres.yml similarity index 100% rename from postgres.yml rename to Anible-Playbooks/postgres.yml diff --git a/docker-compose-example.yml b/docker-compose-example.yml deleted file mode 100644 index 955265ef..00000000 --- a/docker-compose-example.yml +++ /dev/null @@ -1,34 +0,0 @@ -version: "3.9" -services: - postgres: - container_name: Kumiko-Postgres - image: postgres:15 - env_file: - - .env - volumes: - - postgres_volume:/var/lib/postgresql/data - ports: - - 5432:5432 - - redis: - container_name: Kumiko-Redis-Stack - image: redis/redis-stack:7.0.6-RC6 - ports: - - 6379:6379 - volumes: - - redis_volume:/data - command: redis-stack-server --protected-mode no - - kumiko: - container_name: Kumiko - image: no767/kumiko:edge - command: sh -c '/Kumiko/wait-for postgres:5432 -- echo "[Wait-for] PostgreSQL is fully up. Waiting for Redis" && /Kumiko/wait-for redis:6379 -- echo "[Wait-for] Both PostgreSQL and Redis are fully ready. Starting up Kumiko" && /Kumiko/start.sh' - env_file: - - .env - depends_on: - - postgres - - redis - -volumes: - postgres_volume: - redis_volume: diff --git a/docker-compose.yml b/docker-compose.yml index 21b7ccfd..7af564c3 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -1,9 +1,5 @@ -# This docker compose file is actually not used by Kumiko, since Kumiko relies on the db and other stuff via a seperate server -# This is just for example -# MAKE SURE TO CHANGE THE VALUES FOR KUMIKO - version: "3.9" -name: "kumiko" +name: "kumiko-prod" services: postgres: container_name: Kumiko-Postgres @@ -21,5 +17,15 @@ services: ports: - 6379:6379 + kumiko: + container_name: Kumiko + image: no767/kumiko:latest + command: sh -c '/Kumiko/wait-for postgres:5432 -- echo "[Wait-for] PostgreSQL is fully up. Waiting for Redis" && /Kumiko/wait-for redis:6379 -- echo "[Wait-for] Both PostgreSQL and Redis are fully ready. Starting up Kumiko" && /Kumiko/start.sh' + env_file: + - .env + depends_on: + - postgres + - redis + volumes: postgres_volume: \ No newline at end of file From 3d07ef468005b5f4c4fda72758fb8be0d13d4506 Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Fri, 7 Jul 2023 01:00:54 -0700 Subject: [PATCH 152/184] [skip ci] Update docs --- Kumiko-Docs/source/index.rst | 157 +++++++++++++++++------------------ README.md | 2 +- 2 files changed, 79 insertions(+), 80 deletions(-) diff --git a/Kumiko-Docs/source/index.rst b/Kumiko-Docs/source/index.rst index 22666e16..63e8485d 100644 --- a/Kumiko-Docs/source/index.rst +++ b/Kumiko-Docs/source/index.rst @@ -1,80 +1,79 @@ -.. Kumiko documentation master file, created by - sphinx-quickstart on Sun Apr 16 21:15:08 2023. - You can adapt this file completely to your liking, but it should at least - contain the root `toctree` directive. - - -Kumiko -================================== - -.. toctree:: - :maxdepth: 2 - :hidden: - :caption: Guides - - guides/user/index - guides/dev/index - -.. toctree:: - :maxdepth: 2 - :hidden: - :caption: Terms of Service - - terms-of-service/tos.rst - terms-of-service/privacy-policy.rst - - -.. figure:: /_static/kumiko-resized-round.svg - :align: right - -.. image:: https://img.shields.io/github/v/release/No767/Kumiko?label=Release&logo=github&sort=semver - :alt: GitHub release (latest SemVer) - -.. image:: https://img.shields.io/github/license/No767/Kumiko?label=License&logo=github - :alt: GitHub - -.. image:: https://img.shields.io/badge/Kumiko-Oumae-white - -Kumiko is a multipurpose Discord bot built with freedom and choice in mind. Kumiko takes a unique approach to what a multipurpose bot is defined as. - -Features ----------- - -.. CAUTION:: - Some of these features are not implemented yet. Kumiko is still under heavy development. - -- Customizable prefix module -- Global or guild economy with jobs and marketplaces -- Custom logging module -- Basic moderation commands -- Search for memes, posts, anime, manga, and others! - -And some ones that are planned: - -- Complete Web Dashboard + Custom Embeds (WIP, pinned for v2) -- Event Logging (Pinned for v1) -- Annoucement releaser with support from GitHub (Pinned for v2) -- Selector Roles (pinned for v2) - -Guides ----------------- - -Are you interested in contributing to Kumiko as a developer? Or are you interested in learning how to use Kumiko as the end user? This is the place to get started! - -- :doc:`guides/user/index` -- :doc:`guides/dev/index` - -Resources and Links -------------------- - -- `Docker Hub `_ -- `GHCR `_ -- `GitHub `_ -- Discord Server - -Project Links -^^^^^^^^^^^^^ - -- `Contributing `_ -- `Roadmap `_ +.. Kumiko documentation master file, created by + sphinx-quickstart on Sun Apr 16 21:15:08 2023. + You can adapt this file completely to your liking, but it should at least + contain the root `toctree` directive. + + +Kumiko +================================== + +.. toctree:: + :maxdepth: 2 + :hidden: + :caption: Guides + + guides/user/index + guides/dev/index + +.. toctree:: + :maxdepth: 2 + :hidden: + :caption: Terms of Service + + terms-of-service/tos.rst + terms-of-service/privacy-policy.rst + + +.. figure:: /_static/kumiko-resized-round.svg + :align: right + +.. image:: https://img.shields.io/github/v/release/No767/Kumiko?label=Release&logo=github&sort=semver + :alt: GitHub release (latest SemVer) + +.. image:: https://img.shields.io/github/license/No767/Kumiko?label=License&logo=github + :alt: GitHub + +.. image:: https://img.shields.io/badge/Kumiko-Oumae-white + +Kumiko is a multipurpose Discord bot built with freedom and choice in mind. Kumiko takes a unique approach to what a multipurpose bot is defined as. + +Features +---------- + +.. CAUTION:: + Some of these features are not implemented yet. Kumiko is still under heavy development. + +- Customizable prefix module +- Global or guild economy with jobs and marketplaces +- Custom logging module +- Basic moderation commands +- Search for memes, posts, anime, manga, and others! + +And some ones that are planned: + +- Complete Web Dashboard + Custom Embeds (WIP, pinned for v2) +- Annoucement releaser with support from GitHub (Pinned for v2) + +To see the full list of planned features, please see the roadmap `here `_. +Guides +---------------- + +Are you interested in contributing to Kumiko as a developer? Or are you interested in learning how to use Kumiko as the end user? This is the place to get started! + +- :doc:`guides/user/index` +- :doc:`guides/dev/index` + +Resources and Links +------------------- + +- `Docker Hub `_ +- `GHCR `_ +- `GitHub `_ +- Discord Server + +Project Links +^^^^^^^^^^^^^ + +- `Contributing `_ +- `Roadmap `_ - `Project License `_ \ No newline at end of file diff --git a/README.md b/README.md index 18504314..54f46c86 100644 --- a/README.md +++ b/README.md @@ -30,8 +30,8 @@ And some ones that are planned: - Complete Web Dashboard + Custom Embeds (WIP, pinned for v2) - Annoucement releaser with support from GitHub (Pinned for v2) -- Selector Roles (pinned for v2) +To see the full list of planned features, please see the roadmap [here](https://github.com/No767/Kumiko/discussions/266) (#266) ## Prefix Kumiko uses both a prefixed command and slash commands. The currently supported prefixes are `>` , and `/`. From 2a845f60e6483715497eafbe44231b072238f7c9 Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Fri, 7 Jul 2023 01:06:08 -0700 Subject: [PATCH 153/184] Use netcat-traditional instead of netcat The upgrade from Debian 11 to 12 spilt it into two different packages. One for the traditional verison and one for openbsd. we don't need the openbsd version so we are sticking with the traditional version --- Docker/Dockerfile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Docker/Dockerfile b/Docker/Dockerfile index e09c33da..b5ee1242 100644 --- a/Docker/Dockerfile +++ b/Docker/Dockerfile @@ -36,7 +36,7 @@ RUN apt update \ tini \ ca-certificates \ bash \ - netcat \ + netcat-traditional \ libopus-dev \ libffi-dev \ libnacl-dev \ From e47a98ba772f539c9caae38b6f26ae2a518ad865 Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Fri, 7 Jul 2023 01:11:14 -0700 Subject: [PATCH 154/184] Relock poetry.lock --- poetry.lock | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/poetry.lock b/poetry.lock index 733ea28c..5528c061 100644 --- a/poetry.lock +++ b/poetry.lock @@ -1,4 +1,4 @@ -# This file is automatically @generated by Poetry 1.5.0 and should not be changed by hand. +# This file is automatically @generated by Poetry 1.5.1 and should not be changed by hand. [[package]] name = "aiodns" @@ -3418,4 +3418,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "e3e54754b6884d0bc81f82ed59bcfb52d4ad6669624040137798184f03a15464" +content-hash = "8ae5010ca83ce1267890367afdfdc2e1f18d28ee21c054cfe3e4d5a984adb567" From a127bd6d4f832f88b7ab52de4ba6612ec4b14580 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Fri, 7 Jul 2023 08:15:23 +0000 Subject: [PATCH 155/184] [pip](deps): Bump asyncpg from 0.27.0 to 0.28.0 (#373) Bumps [asyncpg](https://github.com/MagicStack/asyncpg) from 0.27.0 to 0.28.0. - [Release notes](https://github.com/MagicStack/asyncpg/releases) - [Commits](https://github.com/MagicStack/asyncpg/compare/v0.27.0...v0.28.0) --- updated-dependencies: - dependency-name: asyncpg dependency-type: direct:production update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 85 ++++++++++++++++++++++++++------------------------ pyproject.toml | 2 +- 2 files changed, 45 insertions(+), 42 deletions(-) diff --git a/poetry.lock b/poetry.lock index 5528c061..f19fadfd 100644 --- a/poetry.lock +++ b/poetry.lock @@ -264,53 +264,56 @@ test = ["pytest", "pytest-asyncio", "pytest-cov"] [[package]] name = "asyncpg" -version = "0.27.0" +version = "0.28.0" description = "An asyncio PostgreSQL driver" optional = false python-versions = ">=3.7.0" files = [ - {file = "asyncpg-0.27.0-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:fca608d199ffed4903dce1bcd97ad0fe8260f405c1c225bdf0002709132171c2"}, - {file = "asyncpg-0.27.0-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:20b596d8d074f6f695c13ffb8646d0b6bb1ab570ba7b0cfd349b921ff03cfc1e"}, - {file = "asyncpg-0.27.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:7a6206210c869ebd3f4eb9e89bea132aefb56ff3d1b7dd7e26b102b17e27bbb1"}, - {file = "asyncpg-0.27.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:a7a94c03386bb95456b12c66026b3a87d1b965f0f1e5733c36e7229f8f137747"}, - {file = "asyncpg-0.27.0-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:bfc3980b4ba6f97138b04f0d32e8af21d6c9fa1f8e6e140c07d15690a0a99279"}, - {file = "asyncpg-0.27.0-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:9654085f2b22f66952124de13a8071b54453ff972c25c59b5ce1173a4283ffd9"}, - {file = "asyncpg-0.27.0-cp310-cp310-win32.whl", hash = "sha256:879c29a75969eb2722f94443752f4720d560d1e748474de54ae8dd230bc4956b"}, - {file = "asyncpg-0.27.0-cp310-cp310-win_amd64.whl", hash = "sha256:ab0f21c4818d46a60ca789ebc92327d6d874d3b7ccff3963f7af0a21dc6cff52"}, - {file = "asyncpg-0.27.0-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:18f77e8e71e826ba2d0c3ba6764930776719ae2b225ca07e014590545928b576"}, - {file = "asyncpg-0.27.0-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:c2232d4625c558f2aa001942cac1d7952aa9f0dbfc212f63bc754277769e1ef2"}, - {file = "asyncpg-0.27.0-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:9a3a4ff43702d39e3c97a8786314123d314e0f0e4dabc8367db5b665c93914de"}, - {file = "asyncpg-0.27.0-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:ccddb9419ab4e1c48742457d0c0362dbdaeb9b28e6875115abfe319b29ee225d"}, - {file = "asyncpg-0.27.0-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:768e0e7c2898d40b16d4ef7a0b44e8150db3dd8995b4652aa1fe2902e92c7df8"}, - {file = "asyncpg-0.27.0-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:609054a1f47292a905582a1cfcca51a6f3f30ab9d822448693e66fdddde27920"}, - {file = "asyncpg-0.27.0-cp311-cp311-win32.whl", hash = "sha256:8113e17cfe236dc2277ec844ba9b3d5312f61bd2fdae6d3ed1c1cdd75f6cf2d8"}, - {file = "asyncpg-0.27.0-cp311-cp311-win_amd64.whl", hash = "sha256:bb71211414dd1eeb8d31ec529fe77cff04bf53efc783a5f6f0a32d84923f45cf"}, - {file = "asyncpg-0.27.0-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:4750f5cf49ed48a6e49c6e5aed390eee367694636c2dcfaf4a273ca832c5c43c"}, - {file = "asyncpg-0.27.0-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:eca01eb112a39d31cc4abb93a5aef2a81514c23f70956729f42fb83b11b3483f"}, - {file = "asyncpg-0.27.0-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:5710cb0937f696ce303f5eed6d272e3f057339bb4139378ccecafa9ee923a71c"}, - {file = "asyncpg-0.27.0-cp37-cp37m-win_amd64.whl", hash = "sha256:71cca80a056ebe19ec74b7117b09e650990c3ca535ac1c35234a96f65604192f"}, - {file = "asyncpg-0.27.0-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:4bb366ae34af5b5cabc3ac6a5347dfb6013af38c68af8452f27968d49085ecc0"}, - {file = "asyncpg-0.27.0-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:16ba8ec2e85d586b4a12bcd03e8d29e3d99e832764d6a1d0b8c27dbbe4a2569d"}, - {file = "asyncpg-0.27.0-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:d20dea7b83651d93b1eb2f353511fe7fd554752844523f17ad30115d8b9c8cd6"}, - {file = "asyncpg-0.27.0-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:e56ac8a8237ad4adec97c0cd4728596885f908053ab725e22900b5902e7f8e69"}, - {file = "asyncpg-0.27.0-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:bf21ebf023ec67335258e0f3d3ad7b91bb9507985ba2b2206346de488267cad0"}, - {file = "asyncpg-0.27.0-cp38-cp38-win32.whl", hash = "sha256:69aa1b443a182b13a17ff926ed6627af2d98f62f2fe5890583270cc4073f63bf"}, - {file = "asyncpg-0.27.0-cp38-cp38-win_amd64.whl", hash = "sha256:62932f29cf2433988fcd799770ec64b374a3691e7902ecf85da14d5e0854d1ea"}, - {file = "asyncpg-0.27.0-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:fddcacf695581a8d856654bc4c8cfb73d5c9df26d5f55201722d3e6a699e9629"}, - {file = "asyncpg-0.27.0-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:7d8585707ecc6661d07367d444bbaa846b4e095d84451340da8df55a3757e152"}, - {file = "asyncpg-0.27.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:975a320baf7020339a67315284a4d3bf7460e664e484672bd3e71dbd881bc692"}, - {file = "asyncpg-0.27.0-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:2232ebae9796d4600a7819fc383da78ab51b32a092795f4555575fc934c1c89d"}, - {file = "asyncpg-0.27.0-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:88b62164738239f62f4af92567b846a8ef7cf8abf53eddd83650603de4d52163"}, - {file = "asyncpg-0.27.0-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:eb4b2fdf88af4fb1cc569781a8f933d2a73ee82cd720e0cb4edabbaecf2a905b"}, - {file = "asyncpg-0.27.0-cp39-cp39-win32.whl", hash = "sha256:8934577e1ed13f7d2d9cea3cc016cc6f95c19faedea2c2b56a6f94f257cea672"}, - {file = "asyncpg-0.27.0-cp39-cp39-win_amd64.whl", hash = "sha256:1b6499de06fe035cf2fa932ec5617ed3f37d4ebbf663b655922e105a484a6af9"}, - {file = "asyncpg-0.27.0.tar.gz", hash = "sha256:720986d9a4705dd8a40fdf172036f5ae787225036a7eb46e704c45aa8f62c054"}, + {file = "asyncpg-0.28.0-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:0a6d1b954d2b296292ddff4e0060f494bb4270d87fb3655dd23c5c6096d16d83"}, + {file = "asyncpg-0.28.0-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:0740f836985fd2bd73dca42c50c6074d1d61376e134d7ad3ad7566c4f79f8184"}, + {file = "asyncpg-0.28.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:e907cf620a819fab1737f2dd90c0f185e2a796f139ac7de6aa3212a8af96c050"}, + {file = "asyncpg-0.28.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:86b339984d55e8202e0c4b252e9573e26e5afa05617ed02252544f7b3e6de3e9"}, + {file = "asyncpg-0.28.0-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:0c402745185414e4c204a02daca3d22d732b37359db4d2e705172324e2d94e85"}, + {file = "asyncpg-0.28.0-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:c88eef5e096296626e9688f00ab627231f709d0e7e3fb84bb4413dff81d996d7"}, + {file = "asyncpg-0.28.0-cp310-cp310-win32.whl", hash = "sha256:90a7bae882a9e65a9e448fdad3e090c2609bb4637d2a9c90bfdcebbfc334bf89"}, + {file = "asyncpg-0.28.0-cp310-cp310-win_amd64.whl", hash = "sha256:76aacdcd5e2e9999e83c8fbcb748208b60925cc714a578925adcb446d709016c"}, + {file = "asyncpg-0.28.0-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:a0e08fe2c9b3618459caaef35979d45f4e4f8d4f79490c9fa3367251366af207"}, + {file = "asyncpg-0.28.0-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:b24e521f6060ff5d35f761a623b0042c84b9c9b9fb82786aadca95a9cb4a893b"}, + {file = "asyncpg-0.28.0-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:99417210461a41891c4ff301490a8713d1ca99b694fef05dabd7139f9d64bd6c"}, + {file = "asyncpg-0.28.0-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f029c5adf08c47b10bcdc857001bbef551ae51c57b3110964844a9d79ca0f267"}, + {file = "asyncpg-0.28.0-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:ad1d6abf6c2f5152f46fff06b0e74f25800ce8ec6c80967f0bc789974de3c652"}, + {file = "asyncpg-0.28.0-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:d7fa81ada2807bc50fea1dc741b26a4e99258825ba55913b0ddbf199a10d69d8"}, + {file = "asyncpg-0.28.0-cp311-cp311-win32.whl", hash = "sha256:f33c5685e97821533df3ada9384e7784bd1e7865d2b22f153f2e4bd4a083e102"}, + {file = "asyncpg-0.28.0-cp311-cp311-win_amd64.whl", hash = "sha256:5e7337c98fb493079d686a4a6965e8bcb059b8e1b8ec42106322fc6c1c889bb0"}, + {file = "asyncpg-0.28.0-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:1c56092465e718a9fdcc726cc3d9dcf3a692e4834031c9a9f871d92a75d20d48"}, + {file = "asyncpg-0.28.0-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:4acd6830a7da0eb4426249d71353e8895b350daae2380cb26d11e0d4a01c5472"}, + {file = "asyncpg-0.28.0-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:63861bb4a540fa033a56db3bb58b0c128c56fad5d24e6d0a8c37cb29b17c1c7d"}, + {file = "asyncpg-0.28.0-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:a93a94ae777c70772073d0512f21c74ac82a8a49be3a1d982e3f259ab5f27307"}, + {file = "asyncpg-0.28.0-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:d14681110e51a9bc9c065c4e7944e8139076a778e56d6f6a306a26e740ed86d2"}, + {file = "asyncpg-0.28.0-cp37-cp37m-win32.whl", hash = "sha256:8aec08e7310f9ab322925ae5c768532e1d78cfb6440f63c078b8392a38aa636a"}, + {file = "asyncpg-0.28.0-cp37-cp37m-win_amd64.whl", hash = "sha256:319f5fa1ab0432bc91fb39b3960b0d591e6b5c7844dafc92c79e3f1bff96abef"}, + {file = "asyncpg-0.28.0-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:b337ededaabc91c26bf577bfcd19b5508d879c0ad009722be5bb0a9dd30b85a0"}, + {file = "asyncpg-0.28.0-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:4d32b680a9b16d2957a0a3cc6b7fa39068baba8e6b728f2e0a148a67644578f4"}, + {file = "asyncpg-0.28.0-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:f4f62f04cdf38441a70f279505ef3b4eadf64479b17e707c950515846a2df197"}, + {file = "asyncpg-0.28.0-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:4f20cac332c2576c79c2e8e6464791c1f1628416d1115935a34ddd7121bfc6a4"}, + {file = "asyncpg-0.28.0-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:59f9712ce01e146ff71d95d561fb68bd2d588a35a187116ef05028675462d5ed"}, + {file = "asyncpg-0.28.0-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:fc9e9f9ff1aa0eddcc3247a180ac9e9b51a62311e988809ac6152e8fb8097756"}, + {file = "asyncpg-0.28.0-cp38-cp38-win32.whl", hash = "sha256:9e721dccd3838fcff66da98709ed884df1e30a95f6ba19f595a3706b4bc757e3"}, + {file = "asyncpg-0.28.0-cp38-cp38-win_amd64.whl", hash = "sha256:8ba7d06a0bea539e0487234511d4adf81dc8762249858ed2a580534e1720db00"}, + {file = "asyncpg-0.28.0-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:d009b08602b8b18edef3a731f2ce6d3f57d8dac2a0a4140367e194eabd3de457"}, + {file = "asyncpg-0.28.0-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:ec46a58d81446d580fb21b376ec6baecab7288ce5a578943e2fc7ab73bf7eb39"}, + {file = "asyncpg-0.28.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:7b48ceed606cce9e64fd5480a9b0b9a95cea2b798bb95129687abd8599c8b019"}, + {file = "asyncpg-0.28.0-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:8858f713810f4fe67876728680f42e93b7e7d5c7b61cf2118ef9153ec16b9423"}, + {file = "asyncpg-0.28.0-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:5e18438a0730d1c0c1715016eacda6e9a505fc5aa931b37c97d928d44941b4bf"}, + {file = "asyncpg-0.28.0-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:e9c433f6fcdd61c21a715ee9128a3ca48be8ac16fa07be69262f016bb0f4dbd2"}, + {file = "asyncpg-0.28.0-cp39-cp39-win32.whl", hash = "sha256:41e97248d9076bc8e4849da9e33e051be7ba37cd507cbd51dfe4b2d99c70e3dc"}, + {file = "asyncpg-0.28.0-cp39-cp39-win_amd64.whl", hash = "sha256:3ed77f00c6aacfe9d79e9eff9e21729ce92a4b38e80ea99a58ed382f42ebd55b"}, + {file = "asyncpg-0.28.0.tar.gz", hash = "sha256:7252cdc3acb2f52feaa3664280d3bcd78a46bd6c10bfd681acfffefa1120e278"}, ] [package.extras] -dev = ["Cython (>=0.29.24,<0.30.0)", "Sphinx (>=4.1.2,<4.2.0)", "flake8 (>=5.0.4,<5.1.0)", "pytest (>=6.0)", "sphinx-rtd-theme (>=0.5.2,<0.6.0)", "sphinxcontrib-asyncio (>=0.3.0,<0.4.0)", "uvloop (>=0.15.3)"] -docs = ["Sphinx (>=4.1.2,<4.2.0)", "sphinx-rtd-theme (>=0.5.2,<0.6.0)", "sphinxcontrib-asyncio (>=0.3.0,<0.4.0)"] -test = ["flake8 (>=5.0.4,<5.1.0)", "uvloop (>=0.15.3)"] +docs = ["Sphinx (>=5.3.0,<5.4.0)", "sphinx-rtd-theme (>=1.2.2)", "sphinxcontrib-asyncio (>=0.3.0,<0.4.0)"] +test = ["flake8 (>=5.0,<6.0)", "uvloop (>=0.15.3)"] [[package]] name = "asyncpg-trek" @@ -3418,4 +3421,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "8ae5010ca83ce1267890367afdfdc2e1f18d28ee21c054cfe3e4d5a984adb567" +content-hash = "07594587cf41dbc72dbd02e45100e520c6d45dd7b9980b32f5dc59e8fbcf0916" diff --git a/pyproject.toml b/pyproject.toml index ec8536a5..d5dd338e 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -20,7 +20,7 @@ ciso8601 = "^2.3.0" faust-cchardet = "^2.1.18" discord-py = {extras = ["voice"], version = "^2.3.1"} discord-ext-menus = {git = "https://github.com/Rapptz/discord-ext-menus", rev = "8686b5d1bbc1d3c862292eb436ab630d6e9c9b53"} -asyncpg = "^0.27.0" +asyncpg = "^0.28.0" asyncpg-trek = "^0.3.1" lru-dict = "^1.2.0" From 23f7ff1c224d93048cb05c4b393ca879704777f6 Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Fri, 7 Jul 2023 01:19:54 -0700 Subject: [PATCH 156/184] [skip ci] Update docs --- Kumiko-Docs/source/index.rst | 1 + 1 file changed, 1 insertion(+) diff --git a/Kumiko-Docs/source/index.rst b/Kumiko-Docs/source/index.rst index 63e8485d..de242e6d 100644 --- a/Kumiko-Docs/source/index.rst +++ b/Kumiko-Docs/source/index.rst @@ -55,6 +55,7 @@ And some ones that are planned: - Annoucement releaser with support from GitHub (Pinned for v2) To see the full list of planned features, please see the roadmap `here `_. + Guides ---------------- From b4ee8c3dfa78e50f25079a5e231537b0503f9a06 Mon Sep 17 00:00:00 2001 From: No767 <73260931+No767@users.noreply.github.com> Date: Fri, 7 Jul 2023 01:27:12 -0700 Subject: [PATCH 157/184] Fix migrations --- Migrations/20230702_rev2_up_rev3.sql | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/Migrations/20230702_rev2_up_rev3.sql b/Migrations/20230702_rev2_up_rev3.sql index 72b32db1..7dcec1d4 100644 --- a/Migrations/20230702_rev2_up_rev3.sql +++ b/Migrations/20230702_rev2_up_rev3.sql @@ -1,10 +1,10 @@ -ALTER TABLE guild ADD COLUMN local_economy_name VARCHAR(255) DEFAULT 'Server Economy'; - -CREATE TABLE IF NOT EXISTS logging_config ( - id SERIAL PRIMARY KEY, - channel_id BIGINT, - member_events BOOLEAN DEFAULT TRUE, - mod_events BOOLEAN DEFAULT TRUE, - eco_events BOOLEAN DEFAULT FALSE, - guild_id BIGINT UNIQUE (guild_id) REFERENCES guild (id) ON DELETE CASCADE ON UPDATE NO ACTION +ALTER TABLE guild ADD COLUMN local_economy_name VARCHAR(255) DEFAULT 'Server Economy'; + +CREATE TABLE IF NOT EXISTS logging_config ( + id SERIAL PRIMARY KEY, + channel_id BIGINT, + member_events BOOLEAN DEFAULT TRUE, + mod_events BOOLEAN DEFAULT TRUE, + eco_events BOOLEAN DEFAULT FALSE, + guild_id BIGINT UNIQUE REFERENCES guild (id) ON DELETE CASCADE ON UPDATE NO ACTION ); \ No newline at end of file From 63657cac495a715250de7614a67a0c369bafa568 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Fri, 7 Jul 2023 18:23:32 +0000 Subject: [PATCH 158/184] [pip](deps): Bump orjson from 3.9.1 to 3.9.2 (#374) Bumps [orjson](https://github.com/ijl/orjson) from 3.9.1 to 3.9.2. - [Release notes](https://github.com/ijl/orjson/releases) - [Changelog](https://github.com/ijl/orjson/blob/master/CHANGELOG.md) - [Commits](https://github.com/ijl/orjson/compare/3.9.1...3.9.2) --- updated-dependencies: - dependency-name: orjson dependency-type: direct:production update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 96 +++++++++++++++++++++++++------------------------- pyproject.toml | 2 +- 2 files changed, 49 insertions(+), 49 deletions(-) diff --git a/poetry.lock b/poetry.lock index f19fadfd..574c00a4 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2186,57 +2186,57 @@ files = [ [[package]] name = "orjson" -version = "3.9.1" +version = "3.9.2" description = "Fast, correct Python JSON library supporting dataclasses, datetimes, and numpy" optional = false python-versions = ">=3.7" files = [ - {file = "orjson-3.9.1-cp310-cp310-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:c4434b7b786fdc394b95d029fb99949d7c2b05bbd4bf5cb5e3906be96ffeee3b"}, - {file = "orjson-3.9.1-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:09faf14f74ed47e773fa56833be118e04aa534956f661eb491522970b7478e3b"}, - {file = "orjson-3.9.1-cp310-cp310-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:503eb86a8d53a187fe66aa80c69295a3ca35475804da89a9547e4fce5f803822"}, - {file = "orjson-3.9.1-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:20f2804b5a1dbd3609c086041bd243519224d47716efd7429db6c03ed28b7cc3"}, - {file = "orjson-3.9.1-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:0fd828e0656615a711c4cc4da70f3cac142e66a6703ba876c20156a14e28e3fa"}, - {file = "orjson-3.9.1-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:ec53d648176f873203b9c700a0abacab33ca1ab595066e9d616f98cdc56f4434"}, - {file = "orjson-3.9.1-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:e186ae76b0d97c505500664193ddf508c13c1e675d9b25f1f4414a7606100da6"}, - {file = "orjson-3.9.1-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:d4edee78503016f4df30aeede0d999b3cb11fb56f47e9db0e487bce0aaca9285"}, - {file = "orjson-3.9.1-cp310-none-win_amd64.whl", hash = "sha256:a4cc5d21e68af982d9a2528ac61e604f092c60eed27aef3324969c68f182ec7e"}, - {file = "orjson-3.9.1-cp311-cp311-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:761b6efd33c49de20dd73ce64cc59da62c0dab10aa6015f582680e0663cc792c"}, - {file = "orjson-3.9.1-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:31229f9d0b8dc2ef7ee7e4393f2e4433a28e16582d4b25afbfccc9d68dc768f8"}, - {file = "orjson-3.9.1-cp311-cp311-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:0b7ab18d55ecb1de543d452f0a5f8094b52282b916aa4097ac11a4c79f317b86"}, - {file = "orjson-3.9.1-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:db774344c39041f4801c7dfe03483df9203cbd6c84e601a65908e5552228dd25"}, - {file = "orjson-3.9.1-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:ae47ef8c0fe89c4677db7e9e1fb2093ca6e66c3acbee5442d84d74e727edad5e"}, - {file = "orjson-3.9.1-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:103952c21575b9805803c98add2eaecd005580a1e746292ed2ec0d76dd3b9746"}, - {file = "orjson-3.9.1-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:2cb0121e6f2c9da3eddf049b99b95fef0adf8480ea7cb544ce858706cdf916eb"}, - {file = "orjson-3.9.1-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:24d4ddaa2876e657c0fd32902b5c451fd2afc35159d66a58da7837357044b8c2"}, - {file = "orjson-3.9.1-cp311-none-win_amd64.whl", hash = "sha256:0b53b5f72cf536dd8aa4fc4c95e7e09a7adb119f8ff8ee6cc60f735d7740ad6a"}, - {file = "orjson-3.9.1-cp37-cp37m-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:d4b68d01a506242316a07f1d2f29fb0a8b36cee30a7c35076f1ef59dce0890c1"}, - {file = "orjson-3.9.1-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d9dd4abe6c6fd352f00f4246d85228f6a9847d0cc14f4d54ee553718c225388f"}, - {file = "orjson-3.9.1-cp37-cp37m-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:9e20bca5e13041e31ceba7a09bf142e6d63c8a7467f5a9c974f8c13377c75af2"}, - {file = "orjson-3.9.1-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:d8ae0467d01eb1e4bcffef4486d964bfd1c2e608103e75f7074ed34be5df48cc"}, - {file = "orjson-3.9.1-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:06f6ab4697fab090517f295915318763a97a12ee8186054adf21c1e6f6abbd3d"}, - {file = "orjson-3.9.1-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:8515867713301fa065c58ec4c9053ba1a22c35113ab4acad555317b8fd802e50"}, - {file = "orjson-3.9.1-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:393d0697d1dfa18d27d193e980c04fdfb672c87f7765b87952f550521e21b627"}, - {file = "orjson-3.9.1-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:d96747662d3666f79119e5d28c124e7d356c7dc195cd4b09faea4031c9079dc9"}, - {file = "orjson-3.9.1-cp37-none-win_amd64.whl", hash = "sha256:6d173d3921dd58a068c88ec22baea7dbc87a137411501618b1292a9d6252318e"}, - {file = "orjson-3.9.1-cp38-cp38-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:d1c2b0b4246c992ce2529fc610a446b945f1429445ece1c1f826a234c829a918"}, - {file = "orjson-3.9.1-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:19f70ba1f441e1c4bb1a581f0baa092e8b3e3ce5b2aac2e1e090f0ac097966da"}, - {file = "orjson-3.9.1-cp38-cp38-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:375d65f002e686212aac42680aed044872c45ee4bc656cf63d4a215137a6124a"}, - {file = "orjson-3.9.1-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:4751cee4a7b1daeacb90a7f5adf2170ccab893c3ab7c5cea58b45a13f89b30b3"}, - {file = "orjson-3.9.1-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:78d9a2a4b2302d5ebc3695498ebc305c3568e5ad4f3501eb30a6405a32d8af22"}, - {file = "orjson-3.9.1-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:46b4facc32643b2689dfc292c0c463985dac4b6ab504799cf51fc3c6959ed668"}, - {file = "orjson-3.9.1-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:ec7c8a0f1bf35da0d5fd14f8956f3b82a9a6918a3c6963d718dfd414d6d3b604"}, - {file = "orjson-3.9.1-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:d3a40b0fbe06ccd4d6a99e523d20b47985655bcada8d1eba485b1b32a43e4904"}, - {file = "orjson-3.9.1-cp38-none-win_amd64.whl", hash = "sha256:402f9d3edfec4560a98880224ec10eba4c5f7b4791e4bc0d4f4d8df5faf2a006"}, - {file = "orjson-3.9.1-cp39-cp39-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:49c0d78dcd34626e2e934f1192d7c052b94e0ecadc5f386fd2bda6d2e03dadf5"}, - {file = "orjson-3.9.1-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:125f63e56d38393daa0a1a6dc6fedefca16c538614b66ea5997c3bd3af35ef26"}, - {file = "orjson-3.9.1-cp39-cp39-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:08927970365d2e1f3ce4894f9ff928a7b865d53f26768f1bbdd85dd4fee3e966"}, - {file = "orjson-3.9.1-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:f9a744e212d4780ecd67f4b6b128b2e727bee1df03e7059cddb2dfe1083e7dc4"}, - {file = "orjson-3.9.1-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:5d1dbf36db7240c61eec98c8d21545d671bce70be0730deb2c0d772e06b71af3"}, - {file = "orjson-3.9.1-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:80a1e384626f76b66df615f7bb622a79a25c166d08c5d2151ffd41f24c4cc104"}, - {file = "orjson-3.9.1-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:15d28872fb055bf17ffca913826e618af61b2f689d2b170f72ecae1a86f80d52"}, - {file = "orjson-3.9.1-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:1e4d905338f9ef32c67566929dfbfbb23cc80287af8a2c38930fb0eda3d40b76"}, - {file = "orjson-3.9.1-cp39-none-win_amd64.whl", hash = "sha256:48a27da6c7306965846565cc385611d03382bbd84120008653aa2f6741e2105d"}, - {file = "orjson-3.9.1.tar.gz", hash = "sha256:db373a25ec4a4fccf8186f9a72a1b3442837e40807a736a815ab42481e83b7d0"}, + {file = "orjson-3.9.2-cp310-cp310-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:7323e4ca8322b1ecb87562f1ec2491831c086d9faa9a6c6503f489dadbed37d7"}, + {file = "orjson-3.9.2-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:1272688ea1865f711b01ba479dea2d53e037ea00892fd04196b5875f7021d9d3"}, + {file = "orjson-3.9.2-cp310-cp310-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:0b9a26f1d1427a9101a1e8910f2e2df1f44d3d18ad5480ba031b15d5c1cb282e"}, + {file = "orjson-3.9.2-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:6a5ca55b0d8f25f18b471e34abaee4b175924b6cd62f59992945b25963443141"}, + {file = "orjson-3.9.2-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:877872db2c0f41fbe21f852ff642ca842a43bc34895b70f71c9d575df31fffb4"}, + {file = "orjson-3.9.2-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:4a39c2529d75373b7167bf84c814ef9b8f3737a339c225ed6c0df40736df8748"}, + {file = "orjson-3.9.2-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:84ebd6fdf138eb0eb4280045442331ee71c0aab5e16397ba6645f32f911bfb37"}, + {file = "orjson-3.9.2-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:5a60a1cfcfe310547a1946506dd4f1ed0a7d5bd5b02c8697d9d5dcd8d2e9245e"}, + {file = "orjson-3.9.2-cp310-none-win_amd64.whl", hash = "sha256:c290c4f81e8fd0c1683638802c11610b2f722b540f8e5e858b6914b495cf90c8"}, + {file = "orjson-3.9.2-cp311-cp311-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:02ef014f9a605e84b675060785e37ec9c0d2347a04f1307a9d6840ab8ecd6f55"}, + {file = "orjson-3.9.2-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:992af54265ada1c1579500d6594ed73fe333e726de70d64919cf37f93defdd06"}, + {file = "orjson-3.9.2-cp311-cp311-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:a40958f7af7c6d992ee67b2da4098dca8b770fc3b4b3834d540477788bfa76d3"}, + {file = "orjson-3.9.2-cp311-cp311-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:93864dec3e3dd058a2dbe488d11ac0345214a6a12697f53a63e34de7d28d4257"}, + {file = "orjson-3.9.2-cp311-cp311-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:16fdf5a82df80c544c3c91516ab3882cd1ac4f1f84eefeafa642e05cef5f6699"}, + {file = "orjson-3.9.2-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:275b5a18fd9ed60b2720543d3ddac170051c43d680e47d04ff5203d2c6d8ebf1"}, + {file = "orjson-3.9.2-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:b9aea6dcb99fcbc9f6d1dd84fca92322fda261da7fb014514bb4689c7c2097a8"}, + {file = "orjson-3.9.2-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:7d74ae0e101d17c22ef67b741ba356ab896fc0fa64b301c2bf2bb0a4d874b190"}, + {file = "orjson-3.9.2-cp311-none-win_amd64.whl", hash = "sha256:6320b28e7bdb58c3a3a5efffe04b9edad3318d82409e84670a9b24e8035a249d"}, + {file = "orjson-3.9.2-cp37-cp37m-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:368e9cc91ecb7ac21f2aa475e1901204110cf3e714e98649c2502227d248f947"}, + {file = "orjson-3.9.2-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:58e9e70f0dcd6a802c35887f306b555ff7a214840aad7de24901fc8bd9cf5dde"}, + {file = "orjson-3.9.2-cp37-cp37m-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:00c983896c2e01c94c0ef72fd7373b2aa06d0c0eed0342c4884559f812a6835b"}, + {file = "orjson-3.9.2-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:2ee743e8890b16c87a2f89733f983370672272b61ee77429c0a5899b2c98c1a7"}, + {file = "orjson-3.9.2-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:b7b065942d362aad4818ff599d2f104c35a565c2cbcbab8c09ec49edba91da75"}, + {file = "orjson-3.9.2-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:e46e9c5b404bb9e41d5555762fd410d5466b7eb1ec170ad1b1609cbebe71df21"}, + {file = "orjson-3.9.2-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:8170157288714678ffd64f5de33039e1164a73fd8b6be40a8a273f80093f5c4f"}, + {file = "orjson-3.9.2-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:e3e2f087161947dafe8319ea2cfcb9cea4bb9d2172ecc60ac3c9738f72ef2909"}, + {file = "orjson-3.9.2-cp37-none-win_amd64.whl", hash = "sha256:d7de3dbbe74109ae598692113cec327fd30c5a30ebca819b21dfa4052f7b08ef"}, + {file = "orjson-3.9.2-cp38-cp38-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:8cd4385c59bbc1433cad4a80aca65d2d9039646a9c57f8084897549b55913b17"}, + {file = "orjson-3.9.2-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:a74036aab1a80c361039290cdbc51aa7adc7ea13f56e5ef94e9be536abd227bd"}, + {file = "orjson-3.9.2-cp38-cp38-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:1aaa46d7d4ae55335f635eadc9be0bd9bcf742e6757209fc6dc697e390010adc"}, + {file = "orjson-3.9.2-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:2e52c67ed6bb368083aa2078ea3ccbd9721920b93d4b06c43eb4e20c4c860046"}, + {file = "orjson-3.9.2-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:1a6cdfcf9c7dd4026b2b01fdff56986251dc0cc1e980c690c79eec3ae07b36e7"}, + {file = "orjson-3.9.2-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:1882a70bb69595b9ec5aac0040a819e94d2833fe54901e2b32f5e734bc259a8b"}, + {file = "orjson-3.9.2-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:fc05e060d452145ab3c0b5420769e7356050ea311fc03cb9d79c481982917cca"}, + {file = "orjson-3.9.2-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:f8bc2c40d9bb26efefb10949d261a47ca196772c308babc538dd9f4b73e8d386"}, + {file = "orjson-3.9.2-cp38-none-win_amd64.whl", hash = "sha256:3164fc20a585ec30a9aff33ad5de3b20ce85702b2b2a456852c413e3f0d7ab09"}, + {file = "orjson-3.9.2-cp39-cp39-macosx_10_15_x86_64.macosx_11_0_arm64.macosx_10_15_universal2.whl", hash = "sha256:7a6ccadf788531595ed4728aa746bc271955448d2460ff0ef8e21eb3f2a281ba"}, + {file = "orjson-3.9.2-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:3245d230370f571c945f69aab823c279a868dc877352817e22e551de155cb06c"}, + {file = "orjson-3.9.2-cp39-cp39-manylinux_2_17_armv7l.manylinux2014_armv7l.whl", hash = "sha256:205925b179550a4ee39b8418dd4c94ad6b777d165d7d22614771c771d44f57bd"}, + {file = "orjson-3.9.2-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:0325fe2d69512187761f7368c8cda1959bcb75fc56b8e7a884e9569112320e57"}, + {file = "orjson-3.9.2-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:806704cd58708acc66a064a9a58e3be25cf1c3f9f159e8757bd3f515bfabdfa1"}, + {file = "orjson-3.9.2-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:03fb36f187a0c19ff38f6289418863df8b9b7880cdbe279e920bef3a09d8dab1"}, + {file = "orjson-3.9.2-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:20925d07a97c49c6305bff1635318d9fc1804aa4ccacb5fb0deb8a910e57d97a"}, + {file = "orjson-3.9.2-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:eebfed53bec5674e981ebe8ed2cf00b3f7bcda62d634733ff779c264307ea505"}, + {file = "orjson-3.9.2-cp39-none-win_amd64.whl", hash = "sha256:869b961df5fcedf6c79f4096119b35679b63272362e9b745e668f0391a892d39"}, + {file = "orjson-3.9.2.tar.gz", hash = "sha256:24257c8f641979bf25ecd3e27251b5cc194cdd3a6e96004aac8446f5e63d9664"}, ] [[package]] @@ -3421,4 +3421,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "07594587cf41dbc72dbd02e45100e520c6d45dd7b9980b32f5dc59e8fbcf0916" +content-hash = "a3d7ac7bd9d27c8561c3d9d95839d6f84e2aab33d5a469d2fb70e7ae9ceb7f31" diff --git a/pyproject.toml b/pyproject.toml index d5dd338e..0384abd4 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -10,7 +10,7 @@ python = ">=3.8,<4.0" python-dotenv = "^1.0.0" aiodns = "^3.0.0" Brotli = "^1.0.9" -orjson = "^3.9.1" +orjson = "^3.9.2" asyncpraw = "^7.7.0" uvloop = "^0.17.0" gql = { extras = ["aiohttp"], version = "^3.4.1" } From 818580a519ced5f1500543adcdf8c403ddb01dfe Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Sat, 8 Jul 2023 21:42:52 -0700 Subject: [PATCH 159/184] Include custom converters for converting and validating prefix input data --- Bot/Cogs/prefix.py | 7 ++- Bot/Libs/utils/__init__.py | 2 + Bot/Libs/utils/converters.py | 11 +++++ poetry.lock | 25 +++++++++- pyproject.toml | 4 ++ tests/utils/test_converters.py | 83 ++++++++++++++++++++++++++++++++++ 6 files changed, 126 insertions(+), 6 deletions(-) create mode 100644 Bot/Libs/utils/converters.py create mode 100644 tests/utils/test_converters.py diff --git a/Bot/Cogs/prefix.py b/Bot/Cogs/prefix.py index 2618482d..4a2db456 100644 --- a/Bot/Cogs/prefix.py +++ b/Bot/Cogs/prefix.py @@ -4,10 +4,9 @@ from kumikocore import KumikoCore from Libs.errors import ValidationError from Libs.ui.prefix import DeletePrefixView -from Libs.utils import ConfirmEmbed, Embed, get_prefix +from Libs.utils import ConfirmEmbed, Embed, PrefixConverter, get_prefix -# TODO - Straight up slap an GIN index on the prefixes column class Prefix(commands.Cog): """Manages custom prefixes for your server""" @@ -32,7 +31,7 @@ async def prefix(self, ctx: commands.Context) -> None: old_prefix="The old prefix to replace", new_prefix="The new prefix to use" ) async def updatePrefixes( - self, ctx: commands.Context, old_prefix: str, new_prefix: str + self, ctx: commands.Context, old_prefix: str, new_prefix: PrefixConverter ) -> None: """Updates the prefix for your server""" query = """ @@ -60,7 +59,7 @@ async def updatePrefixes( @commands.guild_only() @prefix.command(name="add") @app_commands.describe(prefix="The new prefix to add") - async def addPrefixes(self, ctx: commands.Context, prefix: str) -> None: + async def addPrefixes(self, ctx: commands.Context, prefix: PrefixConverter) -> None: """Adds new prefixes into your server""" prefixes = await get_prefix(self.bot, ctx.message) # validatePrefix(self.bot.prefixes, prefix) is False diff --git a/Bot/Libs/utils/__init__.py b/Bot/Libs/utils/__init__.py index c8bc4cff..574df561 100644 --- a/Bot/Libs/utils/__init__.py +++ b/Bot/Libs/utils/__init__.py @@ -1,3 +1,4 @@ +from .converters import PrefixConverter from .embeds import ( CancelledActionEmbed, ConfirmEmbed, @@ -13,6 +14,7 @@ from .utils import encodeDatetime, parseDatetime, parseSubreddit, parseTimeStr __all__ = [ + "PrefixConverter", "parseDatetime", "encodeDatetime", "Embed", diff --git a/Bot/Libs/utils/converters.py b/Bot/Libs/utils/converters.py new file mode 100644 index 00000000..0867baca --- /dev/null +++ b/Bot/Libs/utils/converters.py @@ -0,0 +1,11 @@ +from discord.ext import commands + + +class PrefixConverter(commands.Converter): + async def convert(self, ctx: commands.Context, argument: str): + user_id = ctx.bot.user.id + if argument.startswith((f"<@{user_id}>", f"<@!{user_id}>")): + raise commands.BadArgument("That is a reserved prefix already in use.") + if len(argument) > 100: + raise commands.BadArgument("That prefix is too long.") + return argument diff --git a/poetry.lock b/poetry.lock index 574c00a4..e38340b5 100644 --- a/poetry.lock +++ b/poetry.lock @@ -1,4 +1,4 @@ -# This file is automatically @generated by Poetry 1.5.1 and should not be changed by hand. +# This file is automatically @generated by Poetry 1.5.0 and should not be changed by hand. [[package]] name = "aiodns" @@ -1036,6 +1036,27 @@ files = [ {file = "docutils-0.20.1.tar.gz", hash = "sha256:f08a4e276c3a1583a86dce3e34aba3fe04d02bba2dd51ed16106244e8a923e3b"}, ] +[[package]] +name = "dpytest" +version = "0.7.0" +description = "A package that assists in writing tests for discord.py" +optional = false +python-versions = ">=3.8" +files = [ + {file = "dpytest-0.7.0-py3-none-any.whl", hash = "sha256:b9febeb860e6bc05bac3d433882becdba1b965ff4db1667e2d629acbc868b0d2"}, + {file = "dpytest-0.7.0.tar.gz", hash = "sha256:9f16d58347591756a8d662a44c2307864698c8a5656408a584d0bb5d69c83bbb"}, +] + +[package.dependencies] +"discord.py" = ">=2.3,<3.0" +pytest = "*" +pytest-asyncio = "*" + +[package.extras] +dev = ["build", "flake8", "invoke"] +doc = ["sphinx"] +test = ["pytest", "pytest-asyncio"] + [[package]] name = "exceptiongroup" version = "1.1.1" @@ -3421,4 +3442,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "a3d7ac7bd9d27c8561c3d9d95839d6f84e2aab33d5a469d2fb70e7ae9ceb7f31" +content-hash = "1e24b921bcd91939305c7a65e6afa2386c32003cb71a41a06e8851ed2b3c59fe" diff --git a/pyproject.toml b/pyproject.toml index 0384abd4..a88200ae 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -47,6 +47,10 @@ sphinx-autobuild = "^2021.3.14" furo = "^2023.5.20" sphinxext-opengraph = "^0.8.2" + +[tool.poetry.group.tests.dependencies] +dpytest = "^0.7.0" + [tool.isort] profile = 'black' diff --git a/tests/utils/test_converters.py b/tests/utils/test_converters.py new file mode 100644 index 00000000..b6df7a2c --- /dev/null +++ b/tests/utils/test_converters.py @@ -0,0 +1,83 @@ +import sys +from pathlib import Path + +path = Path(__file__).parents[2].joinpath("Bot") +sys.path.append(str(path)) +import discord +import discord.ext.test as dpytest +import pytest +import pytest_asyncio +from discord.ext import commands +from Libs.utils import PrefixConverter + + +class PrefixCog(commands.Cog): + def __init__(self, bot): + self.bot = bot + + @commands.command(name="prefix") + async def prefix(self, ctx, prefix: PrefixConverter): + await ctx.send(f"{prefix}") + + +@pytest_asyncio.fixture +async def bot(): + # Setup + intents = discord.Intents.default() + intents.members = True + intents.message_content = True + b = commands.Bot(command_prefix=">", intents=intents) + await b._async_setup_hook() # setup the loop + await b.add_cog(PrefixCog(b)) + + dpytest.configure(b) + + yield b + + # Teardown + await dpytest.empty_queue() + + +@pytest.mark.asyncio +async def test_valid_prefix(bot): + await dpytest.message(">prefix !") + assert dpytest.verify().message().content("!") + + +@pytest.mark.asyncio +async def test_invalid_prefix(bot): + finalStr = "" + for _ in range(103): + finalStr += "a" + with pytest.raises(commands.BadArgument) as e: + await dpytest.message(f">prefix {finalStr}") + # assert dpytest.verify().message().content("!") + assert e.type == commands.BadArgument and "That prefix is too long." in str( + e.value + ) + + +@pytest.mark.asyncio +async def test_invalid_ping_prefix(bot): + user_id = bot.user.id + finalStr = f"<@{user_id}>" + + with pytest.raises(commands.BadArgument) as e: + await dpytest.message(f">prefix {finalStr}") + assert ( + e.type == commands.BadArgument + and "That is a reserved prefix already in use." in str(e.value) + ) + + +@pytest.mark.asyncio +async def test_invalid_mention_prefix(bot): + user_id = bot.user.id + finalStr = f"<@!{user_id}>" + + with pytest.raises(commands.BadArgument) as e: + await dpytest.message(f">prefix {finalStr}") + assert ( + e.type == commands.BadArgument + and "That is a reserved prefix already in use." in str(e.value) + ) From eb8664d79510c722942b79b51b425ad2ea36da42 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Sat, 8 Jul 2023 21:48:43 -0700 Subject: [PATCH 160/184] Move dpytest into the correct group --- poetry.lock | 2 +- pyproject.toml | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/poetry.lock b/poetry.lock index e38340b5..1869eada 100644 --- a/poetry.lock +++ b/poetry.lock @@ -3442,4 +3442,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "1e24b921bcd91939305c7a65e6afa2386c32003cb71a41a06e8851ed2b3c59fe" +content-hash = "313bf950b756ef2c012433fe538f4d5f0bdb47dcd92db0cffb546aab34075ec0" diff --git a/pyproject.toml b/pyproject.toml index a88200ae..b82c6e22 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -30,6 +30,7 @@ pytest-asyncio = "^0.21.0" nox = "^2023.4.22" nox-poetry = "^1.0.2" pytest-cov = "^4.1.0" +dpytest = "^0.7.0" [tool.poetry.group.dev.dependencies] pre-commit = "^3.3.3" @@ -49,7 +50,6 @@ sphinxext-opengraph = "^0.8.2" [tool.poetry.group.tests.dependencies] -dpytest = "^0.7.0" [tool.isort] profile = 'black' From 46b794ff3ab0d89063103d46920f21740cbcf8ef Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Sat, 8 Jul 2023 23:37:21 -0700 Subject: [PATCH 161/184] Add an custom pg dockerfile + fix start.sh --- Docker/pg/Dockerfile | 2 ++ Docker/pg/init-ext.sql | 1 + Docker/start.sh | 2 +- docker-compose.yml | 5 ++++- 4 files changed, 8 insertions(+), 2 deletions(-) create mode 100644 Docker/pg/Dockerfile create mode 100644 Docker/pg/init-ext.sql diff --git a/Docker/pg/Dockerfile b/Docker/pg/Dockerfile new file mode 100644 index 00000000..b5890c1c --- /dev/null +++ b/Docker/pg/Dockerfile @@ -0,0 +1,2 @@ +FROM postgres:15 +COPY /init-ext.sql /docker-entrypoint-initdb.d/ \ No newline at end of file diff --git a/Docker/pg/init-ext.sql b/Docker/pg/init-ext.sql new file mode 100644 index 00000000..59c53695 --- /dev/null +++ b/Docker/pg/init-ext.sql @@ -0,0 +1 @@ +CREATE EXTENSION IF NOT EXISTS pg_trgm; \ No newline at end of file diff --git a/Docker/start.sh b/Docker/start.sh index d3a319b1..9d322468 100644 --- a/Docker/start.sh +++ b/Docker/start.sh @@ -1,4 +1,4 @@ -#!/usr/bin/env bash +#!/bin/bash KUMIKO_FIRST_START_CHECK="KUMIKO_FIRST_START" diff --git a/docker-compose.yml b/docker-compose.yml index 7af564c3..4c354fbd 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -3,7 +3,10 @@ name: "kumiko-prod" services: postgres: container_name: Kumiko-Postgres - image: postgres:15 + image: kumiko-postgres:prod-latest + build: + context: ./Docker/pg + dockerfile: ./Docker/pg/Dockerfile env_file: - .env volumes: From 108ec3f9ec35d74998efad75e84bfbb04f96fdcd Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Sat, 8 Jul 2023 23:53:31 -0700 Subject: [PATCH 162/184] Revert changes to start.sh --- Docker/start.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Docker/start.sh b/Docker/start.sh index 9d322468..d3a319b1 100644 --- a/Docker/start.sh +++ b/Docker/start.sh @@ -1,4 +1,4 @@ -#!/bin/bash +#!/usr/bin/env bash KUMIKO_FIRST_START_CHECK="KUMIKO_FIRST_START" From 72acd526fa51d1727e279abbe5389e2e4aa0b531 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Sun, 9 Jul 2023 00:04:30 -0700 Subject: [PATCH 163/184] Run dos2unix for start.sh Should fix the issues --- Docker/start.sh | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/Docker/start.sh b/Docker/start.sh index d3a319b1..150b6e90 100644 --- a/Docker/start.sh +++ b/Docker/start.sh @@ -1,11 +1,11 @@ -#!/usr/bin/env bash - -KUMIKO_FIRST_START_CHECK="KUMIKO_FIRST_START" - -if [ ! -f $KUMIKO_FIRST_START_CHECK ]; then - touch $KUMIKO_FIRST_START_CHECK - echo 'DO NOT EDIT THIS FILE! THIS IS USED WHEN YOU FIRST RUN KUMIKO USING DOCKER!' >> $KUMIKO_FIRST_START_CHECK - exec python3 /Kumiko/migrations-runner.py -fi - +#!/usr/bin/env bash + +KUMIKO_FIRST_START_CHECK="KUMIKO_FIRST_START" + +if [ ! -f $KUMIKO_FIRST_START_CHECK ]; then + touch $KUMIKO_FIRST_START_CHECK + echo 'DO NOT EDIT THIS FILE! THIS IS USED WHEN YOU FIRST RUN KUMIKO USING DOCKER!' >> $KUMIKO_FIRST_START_CHECK + exec python3 /Kumiko/migrations-runner.py +fi + exec python3 /Kumiko/Bot/kumikobot.py \ No newline at end of file From b510cb6a777fc8a237faf99dc21040937560cfa2 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Sun, 9 Jul 2023 00:11:50 -0700 Subject: [PATCH 164/184] Apparently someone dropped anyio --- poetry.lock | 10 +++++----- pyproject.toml | 1 + 2 files changed, 6 insertions(+), 5 deletions(-) diff --git a/poetry.lock b/poetry.lock index 1869eada..74dbedfe 100644 --- a/poetry.lock +++ b/poetry.lock @@ -174,13 +174,13 @@ files = [ [[package]] name = "anyio" -version = "3.7.0" +version = "3.7.1" description = "High level compatibility layer for multiple asynchronous event loop implementations" optional = false python-versions = ">=3.7" files = [ - {file = "anyio-3.7.0-py3-none-any.whl", hash = "sha256:eddca883c4175f14df8aedce21054bfca3adb70ffe76a9f607aef9d7fa2ea7f0"}, - {file = "anyio-3.7.0.tar.gz", hash = "sha256:275d9973793619a5374e1c89a4f4ad3f4b0a5510a2b5b939444bee8f4c4d37ce"}, + {file = "anyio-3.7.1-py3-none-any.whl", hash = "sha256:91dee416e570e92c64041bd18b900d1d6fa78dff7048769ce5ac5ddad004fbb5"}, + {file = "anyio-3.7.1.tar.gz", hash = "sha256:44a3c9aba0f5defa43261a8b3efb97891f2bd7d804e0e1f56419befa1adfc780"}, ] [package.dependencies] @@ -189,7 +189,7 @@ idna = ">=2.8" sniffio = ">=1.1" [package.extras] -doc = ["Sphinx (>=6.1.0)", "packaging", "sphinx-autodoc-typehints (>=1.2.0)", "sphinx-rtd-theme", "sphinxcontrib-jquery"] +doc = ["Sphinx", "packaging", "sphinx-autodoc-typehints (>=1.2.0)", "sphinx-rtd-theme (>=1.2.2)", "sphinxcontrib-jquery"] test = ["anyio[trio]", "coverage[toml] (>=4.5)", "hypothesis (>=4.0)", "mock (>=4)", "psutil (>=5.9)", "pytest (>=7.0)", "pytest-mock (>=3.6.1)", "trustme", "uvloop (>=0.17)"] trio = ["trio (<0.22)"] @@ -3442,4 +3442,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "313bf950b756ef2c012433fe538f4d5f0bdb47dcd92db0cffb546aab34075ec0" +content-hash = "9cb8e66a19fbf99b1e07ce8254012038d95b1ae183ed20197c964da0643584f7" diff --git a/pyproject.toml b/pyproject.toml index b82c6e22..a6a41c54 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -23,6 +23,7 @@ discord-ext-menus = {git = "https://github.com/Rapptz/discord-ext-menus", rev = asyncpg = "^0.28.0" asyncpg-trek = "^0.3.1" lru-dict = "^1.2.0" +anyio = "^3.7.1" [tool.poetry.group.test.dependencies] pytest = "^7.4.0" From 088bf3c20f4483605d2052b9c1c1688f4e207808 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Sun, 9 Jul 2023 02:01:14 -0700 Subject: [PATCH 165/184] Add sysmetrics cmd, properly handle sigs --- Bot/Cogs/meta.py | 31 +++++++++++++++++++++++++++++++ Bot/kumikobot.py | 7 +++++-- Bot/kumikocore.py | 2 +- Docker/Dockerfile | 5 ++++- poetry.lock | 28 +++++++++++++++++++++++++++- pyproject.toml | 4 +--- 6 files changed, 69 insertions(+), 8 deletions(-) diff --git a/Bot/Cogs/meta.py b/Bot/Cogs/meta.py index 21300b17..03612684 100644 --- a/Bot/Cogs/meta.py +++ b/Bot/Cogs/meta.py @@ -3,9 +3,11 @@ import time import discord +import psutil from discord.ext import commands from kumikocore import KumikoCore from Libs.utils import Embed +from psutil._common import bytes2human VERSION = "v0.9.0" @@ -64,6 +66,35 @@ async def ping(self, ctx: commands.Context) -> None: embed.description = f"Pong! {round(self.bot.latency * 1000)}ms" await ctx.send(embed=embed) + @commands.is_owner() + @commands.hybrid_command(name="sys-metrics", aliases=["sysmetrics"]) + async def sysMetrics(self, ctx: commands.Context) -> None: + """Tells you the current system metrics along with other information""" + await ctx.defer() + currMem = psutil.virtual_memory() + proc = psutil.Process() + with proc.oneshot(): + procMem = bytes2human(proc.memory_info().rss) + diskUsage = psutil.disk_usage("/") + embed = Embed() + embed.title = "System Metrics + Info" + embed.description = ( + f"**CPU:** {psutil.cpu_percent()}% (Proc - {proc.cpu_percent()}%)\n" + f"**Mem:** {procMem} ({procMem}/{bytes2human(currMem.total)})\n" + f"**Disk (System):** {diskUsage.percent}% ({bytes2human(diskUsage.used)}/{bytes2human(diskUsage.total)})\n" + f"**Proc Status:** {proc.status()}\n" + ) + embed.add_field(name="Kernel Version", value=platform.release()) + embed.add_field(name="Python Compiler", value=platform.python_compiler()) + embed.add_field( + name="Python Version", value=platform.python_version(), inline=True + ) + embed.add_field( + name="Discord.py Version", value=discord.__version__, inline=True + ) + embed.add_field(name="Kumiko Build Version", value=VERSION) + await ctx.send(embed=embed) + async def setup(bot: KumikoCore) -> None: await bot.add_cog(Meta(bot)) diff --git a/Bot/kumikobot.py b/Bot/kumikobot.py index fbaaa1df..27def38a 100644 --- a/Bot/kumikobot.py +++ b/Bot/kumikobot.py @@ -1,9 +1,10 @@ +import asyncio import os import asyncpg import discord +import uvloop from aiohttp import ClientSession -from anyio import run from dotenv import load_dotenv from kumikocore import KumikoCore from Libs.cache import KumikoCPManager @@ -37,7 +38,9 @@ async def main() -> None: def launch() -> None: with KumikoLogger(): - run(main, backend_options={"use_uvloop": True}) + asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) + asyncio.run(main()) + # run(main, backend_options={"use_uvloop": True}) if __name__ == "__main__": diff --git a/Bot/kumikocore.py b/Bot/kumikocore.py index 4e52fb06..61f2ef96 100644 --- a/Bot/kumikocore.py +++ b/Bot/kumikocore.py @@ -39,7 +39,7 @@ def __init__( intents=intents, command_prefix=get_prefix, help_command=KumikoHelpPaginated(), - activity=discord.Activity(type=discord.ActivityType.watching, name="/help"), + activity=discord.Activity(type=discord.ActivityType.watching, name=">help"), *args, **kwargs, ) diff --git a/Docker/Dockerfile b/Docker/Dockerfile index b5ee1242..d200095d 100644 --- a/Docker/Dockerfile +++ b/Docker/Dockerfile @@ -72,7 +72,10 @@ ENTRYPOINT ["/usr/bin/tini", "--"] CMD ["/Kumiko/start.sh"] -STOPSIGNAL SIGTERM +# We want to use SIGINT instead since that is the same signal used when hitting ctrl+c +# By default, this is the expected behavior of Kumiko, so we need to keep it that way +# Will result in a clean exit without any dead conns +STOPSIGNAL SIGINT LABEL org.opencontainers.image.title="Kumiko" LABEL org.opencontainers.image.description="A multipurpose Discord bot built with freedom and choice in mind" diff --git a/poetry.lock b/poetry.lock index 74dbedfe..929d4e93 100644 --- a/poetry.lock +++ b/poetry.lock @@ -2398,6 +2398,32 @@ nodeenv = ">=0.11.1" pyyaml = ">=5.1" virtualenv = ">=20.10.0" +[[package]] +name = "psutil" +version = "5.9.5" +description = "Cross-platform lib for process and system monitoring in Python." +optional = false +python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*" +files = [ + {file = "psutil-5.9.5-cp27-cp27m-macosx_10_9_x86_64.whl", hash = "sha256:be8929ce4313f9f8146caad4272f6abb8bf99fc6cf59344a3167ecd74f4f203f"}, + {file = "psutil-5.9.5-cp27-cp27m-manylinux2010_i686.whl", hash = "sha256:ab8ed1a1d77c95453db1ae00a3f9c50227ebd955437bcf2a574ba8adbf6a74d5"}, + {file = "psutil-5.9.5-cp27-cp27m-manylinux2010_x86_64.whl", hash = "sha256:4aef137f3345082a3d3232187aeb4ac4ef959ba3d7c10c33dd73763fbc063da4"}, + {file = "psutil-5.9.5-cp27-cp27mu-manylinux2010_i686.whl", hash = "sha256:ea8518d152174e1249c4f2a1c89e3e6065941df2fa13a1ab45327716a23c2b48"}, + {file = "psutil-5.9.5-cp27-cp27mu-manylinux2010_x86_64.whl", hash = "sha256:acf2aef9391710afded549ff602b5887d7a2349831ae4c26be7c807c0a39fac4"}, + {file = "psutil-5.9.5-cp27-none-win32.whl", hash = "sha256:5b9b8cb93f507e8dbaf22af6a2fd0ccbe8244bf30b1baad6b3954e935157ae3f"}, + {file = "psutil-5.9.5-cp27-none-win_amd64.whl", hash = "sha256:8c5f7c5a052d1d567db4ddd231a9d27a74e8e4a9c3f44b1032762bd7b9fdcd42"}, + {file = "psutil-5.9.5-cp36-abi3-macosx_10_9_x86_64.whl", hash = "sha256:3c6f686f4225553615612f6d9bc21f1c0e305f75d7d8454f9b46e901778e7217"}, + {file = "psutil-5.9.5-cp36-abi3-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:7a7dd9997128a0d928ed4fb2c2d57e5102bb6089027939f3b722f3a210f9a8da"}, + {file = "psutil-5.9.5-cp36-abi3-manylinux_2_12_x86_64.manylinux2010_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:89518112647f1276b03ca97b65cc7f64ca587b1eb0278383017c2a0dcc26cbe4"}, + {file = "psutil-5.9.5-cp36-abi3-win32.whl", hash = "sha256:104a5cc0e31baa2bcf67900be36acde157756b9c44017b86b2c049f11957887d"}, + {file = "psutil-5.9.5-cp36-abi3-win_amd64.whl", hash = "sha256:b258c0c1c9d145a1d5ceffab1134441c4c5113b2417fafff7315a917a026c3c9"}, + {file = "psutil-5.9.5-cp38-abi3-macosx_11_0_arm64.whl", hash = "sha256:c607bb3b57dc779d55e1554846352b4e358c10fff3abf3514a7a6601beebdb30"}, + {file = "psutil-5.9.5.tar.gz", hash = "sha256:5410638e4df39c54d957fc51ce03048acd8e6d60abc0f5107af51e5fb566eb3c"}, +] + +[package.extras] +test = ["enum34", "ipaddress", "mock", "pywin32", "wmi"] + [[package]] name = "pycares" version = "4.3.0" @@ -3442,4 +3468,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "9cb8e66a19fbf99b1e07ce8254012038d95b1ae183ed20197c964da0643584f7" +content-hash = "2ecc86641643805735c120efc4a263253135c32e3cd30860b6b37248b6af3daf" diff --git a/pyproject.toml b/pyproject.toml index a6a41c54..4480c45e 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -23,7 +23,7 @@ discord-ext-menus = {git = "https://github.com/Rapptz/discord-ext-menus", rev = asyncpg = "^0.28.0" asyncpg-trek = "^0.3.1" lru-dict = "^1.2.0" -anyio = "^3.7.1" +psutil = "^5.9.5" [tool.poetry.group.test.dependencies] pytest = "^7.4.0" @@ -50,8 +50,6 @@ furo = "^2023.5.20" sphinxext-opengraph = "^0.8.2" -[tool.poetry.group.tests.dependencies] - [tool.isort] profile = 'black' From 4f5cb0450eacddb30e5a411d3de8afe578343325 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Sun, 9 Jul 2023 02:09:39 -0700 Subject: [PATCH 166/184] Directly run the migration runner every single time --- Docker/start.sh | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/Docker/start.sh b/Docker/start.sh index 150b6e90..c072e1fd 100644 --- a/Docker/start.sh +++ b/Docker/start.sh @@ -1,11 +1,11 @@ #!/usr/bin/env bash -KUMIKO_FIRST_START_CHECK="KUMIKO_FIRST_START" - -if [ ! -f $KUMIKO_FIRST_START_CHECK ]; then - touch $KUMIKO_FIRST_START_CHECK - echo 'DO NOT EDIT THIS FILE! THIS IS USED WHEN YOU FIRST RUN KUMIKO USING DOCKER!' >> $KUMIKO_FIRST_START_CHECK - exec python3 /Kumiko/migrations-runner.py -fi +# KUMIKO_FIRST_START_CHECK="KUMIKO_FIRST_START" +# if [ ! -f $KUMIKO_FIRST_START_CHECK ]; then +# touch $KUMIKO_FIRST_START_CHECK +# echo 'DO NOT EDIT THIS FILE! THIS IS USED WHEN YOU FIRST RUN KUMIKO USING DOCKER!' >> $KUMIKO_FIRST_START_CHECK +# exec python3 /Kumiko/migrations-runner.py +# fi +exec python3 /Kumiko/migrations-runner.py exec python3 /Kumiko/Bot/kumikobot.py \ No newline at end of file From bacc4f65241df7fb1913b7d6e2b4c9272115ec36 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Sun, 9 Jul 2023 02:14:22 -0700 Subject: [PATCH 167/184] Revert changes --- Docker/start.sh | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/Docker/start.sh b/Docker/start.sh index c072e1fd..150b6e90 100644 --- a/Docker/start.sh +++ b/Docker/start.sh @@ -1,11 +1,11 @@ #!/usr/bin/env bash -# KUMIKO_FIRST_START_CHECK="KUMIKO_FIRST_START" +KUMIKO_FIRST_START_CHECK="KUMIKO_FIRST_START" + +if [ ! -f $KUMIKO_FIRST_START_CHECK ]; then + touch $KUMIKO_FIRST_START_CHECK + echo 'DO NOT EDIT THIS FILE! THIS IS USED WHEN YOU FIRST RUN KUMIKO USING DOCKER!' >> $KUMIKO_FIRST_START_CHECK + exec python3 /Kumiko/migrations-runner.py +fi -# if [ ! -f $KUMIKO_FIRST_START_CHECK ]; then -# touch $KUMIKO_FIRST_START_CHECK -# echo 'DO NOT EDIT THIS FILE! THIS IS USED WHEN YOU FIRST RUN KUMIKO USING DOCKER!' >> $KUMIKO_FIRST_START_CHECK -# exec python3 /Kumiko/migrations-runner.py -# fi -exec python3 /Kumiko/migrations-runner.py exec python3 /Kumiko/Bot/kumikobot.py \ No newline at end of file From c4140110b902427a4136d2f577660aae8482cabd Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Mon, 10 Jul 2023 02:53:06 -0700 Subject: [PATCH 168/184] Properly handle cached configs + Fix events handlers --- Bot/Cogs/dev-tools.py | 2 +- Bot/Cogs/events-handler.py | 35 +++------- Bot/Cogs/events-log.py | 70 +++++++------------- Bot/Libs/cache/decorators.py | 17 +++-- Bot/Libs/cache/redis_cache.py | 12 +++- Bot/Libs/cog_utils/events_log/__init__.py | 3 + Bot/Libs/cog_utils/events_log/cache_utils.py | 41 ++++++++++++ Bot/Libs/ui/events_log/views.py | 23 ++++++- changelog.md | 4 ++ tests/cache_utils/test_event_logs_utils.py | 37 +++++++++++ tests/redis/test_redis_cache.py | 11 +++ 11 files changed, 176 insertions(+), 79 deletions(-) create mode 100644 Bot/Libs/cog_utils/events_log/__init__.py create mode 100644 Bot/Libs/cog_utils/events_log/cache_utils.py create mode 100644 tests/cache_utils/test_event_logs_utils.py diff --git a/Bot/Cogs/dev-tools.py b/Bot/Cogs/dev-tools.py index 4a67e5df..d1c051cb 100644 --- a/Bot/Cogs/dev-tools.py +++ b/Bot/Cogs/dev-tools.py @@ -73,7 +73,7 @@ async def dispatch_event(self, ctx: commands.Context, event: str) -> None: Args: ctx (commands.Context): _description_ """ - self.bot.dispatch(event, ctx.author) + self.bot.dispatch(event, ctx.guild, ctx.author) await ctx.send("Dispatched event") diff --git a/Bot/Cogs/events-handler.py b/Bot/Cogs/events-handler.py index d80d69a1..44ca3aa4 100644 --- a/Bot/Cogs/events-handler.py +++ b/Bot/Cogs/events-handler.py @@ -1,13 +1,11 @@ -from typing import Any, Union +from typing import Any -import asyncpg import discord from discord.ext import commands from discord.utils import format_dt, utcnow from kumikocore import KumikoCore -from Libs.cache import cacheJson +from Libs.cog_utils.events_log import get_or_fetch_config from Libs.utils import CancelledActionEmbed, Embed, SuccessActionEmbed -from redis.asyncio.connection import ConnectionPool class EventsHandler(commands.Cog): @@ -18,21 +16,6 @@ def __init__(self, bot: KumikoCore) -> None: self.pool = self.bot.pool self.redis_pool = self.bot.redis_pool - @cacheJson(ttl=3600) - async def get_or_fetch_config( - self, id: int, redis_pool: ConnectionPool, pool: asyncpg.Pool - ) -> Union[dict, None]: - query = """ - SELECT guild.id, guild.logs, logging_config.channel_id, logging_config.member_events - FROM guild - INNER JOIN logging_config - ON guild.id = logging_config.guild_id - WHERE guild.id = $1; - """ - async with self.pool.acquire() as conn: - res = await conn.fetchrow(query, id) - return dict(res) - def ensureEnabled(self, config: Any) -> bool: if (config is not None) and ( config["logs"] and config["member_events"] is True @@ -65,8 +48,8 @@ async def on_guild_remove(self, guild: discord.Guild) -> None: @commands.Cog.listener() async def on_member_join(self, member: discord.Member) -> None: guild = member.guild - getConfig = await self.get_or_fetch_config( - id=guild.id, redis_pool=self.redis_pool, pool=self.pool + getConfig = await get_or_fetch_config( + id=member.guild.id, redis_pool=self.redis_pool, pool=self.pool ) if self.ensureEnabled(getConfig): channel = guild.get_channel(getConfig["channel_id"]) # type: ignore @@ -84,7 +67,7 @@ async def on_member_join(self, member: discord.Member) -> None: @commands.Cog.listener() async def on_member_remove(self, member: discord.Member) -> None: guild = member.guild - getConfig = await self.get_or_fetch_config( + getConfig = await get_or_fetch_config( id=guild.id, redis_pool=self.redis_pool, pool=self.pool ) if self.ensureEnabled(getConfig): @@ -101,8 +84,8 @@ async def on_member_remove(self, member: discord.Member) -> None: await channel.send(embed=embed) @commands.Cog.listener() - async def on_member_ban(self, guild, user: discord.User) -> None: - getConfig = await self.get_or_fetch_config( + async def on_member_ban(self, guild: discord.Guild, user: discord.User) -> None: + getConfig = await get_or_fetch_config( id=guild.id, redis_pool=self.redis_pool, pool=self.pool ) if self.ensureEnabled(getConfig): @@ -117,7 +100,7 @@ async def on_member_ban(self, guild, user: discord.User) -> None: @commands.Cog.listener() async def on_member_unban(self, guild: discord.Guild, user: discord.User) -> None: - getConfig = await self.get_or_fetch_config( + getConfig = await get_or_fetch_config( id=guild.id, redis_pool=self.redis_pool, pool=self.pool ) if self.ensureEnabled(getConfig): @@ -132,7 +115,7 @@ async def on_member_unban(self, guild: discord.Guild, user: discord.User) -> Non @commands.Cog.listener() async def on_member_kick(self, guild: discord.Guild, user: discord.User) -> None: - getConfig = await self.get_or_fetch_config( + getConfig = await get_or_fetch_config( id=guild.id, redis_pool=self.redis_pool, pool=self.pool ) if self.ensureEnabled(getConfig): diff --git a/Bot/Cogs/events-log.py b/Bot/Cogs/events-log.py index 848b656f..ec1d7224 100644 --- a/Bot/Cogs/events-log.py +++ b/Bot/Cogs/events-log.py @@ -1,13 +1,8 @@ -from typing import Any, Dict, Union - -import asyncpg -from discord import PartialEmoji, app_commands +from discord import PartialEmoji from discord.ext import commands from kumikocore import KumikoCore -from Libs.cache import KumikoCache, cacheJson from Libs.ui.events_log import RegisterView, UnregisterView from Libs.utils import ConfirmEmbed, Embed -from redis.asyncio.connection import ConnectionPool class EventsLog(commands.Cog): @@ -22,21 +17,6 @@ def __init__(self, bot: KumikoCore) -> None: def display_emoji(self) -> PartialEmoji: return PartialEmoji(name="\U0001f4f0") - @cacheJson(ttl=3600) - async def get_or_fetch_config( - self, id: int, redis_pool: ConnectionPool, pool: asyncpg.Pool - ) -> Union[Dict[str, Any], None]: - query = """ - SELECT guild.id, guild.logs, logging_config.channel_id, logging_config.member_events - FROM guild - INNER JOIN logging_config - ON guild.id = logging_config.guild_id - WHERE guild.id = $1; - """ - async with self.pool.acquire() as conn: - res = await conn.fetchrow(query, id) - return dict(res) - @commands.hybrid_group(name="logs") async def logs(self, ctx: commands.Context) -> None: """Logs events and actions on your server""" @@ -51,7 +31,7 @@ async def enableLogs(self, ctx: commands.Context) -> None: registerInfo = "In order to get started, **only** select one of the options within the dropdown menu in order to set it.\nOnce you are done, click the finish button." embed = Embed(title="Registration Info") embed.description = registerInfo - view = RegisterView(pool=self.pool) + view = RegisterView(pool=self.pool, redis_pool=self.redis_pool) await ctx.send(embed=embed, view=view) @commands.has_guild_permissions(manage_guild=True) @@ -59,7 +39,7 @@ async def enableLogs(self, ctx: commands.Context) -> None: @logs.command(name="disable") async def disableLogs(self, ctx: commands.Context) -> None: """Disables and unregisters the events logging on the server""" - view = UnregisterView(pool=self.pool) + view = UnregisterView(pool=self.pool, redis_pool=self.redis_pool) embed = ConfirmEmbed() embed.description = "You are about to disable and unregister the events logging feature on Kumiko. Press Confirm to confirm your action." await ctx.send(embed=embed, view=view) @@ -97,28 +77,28 @@ async def logInfo(self, ctx: commands.Context) -> None: # Also im well aware that this has a ton of issues that need to be ironed out # But i will be fixing them before releasing v0.9.0 # I just want to get this merged and done with - # We need to also update the DB. probably needs a rework - @commands.has_guild_permissions(manage_guild=True) - @commands.guild_only() - @logs.command(name="configure") - @app_commands.describe( - event="The event to enable", status="Whether the event is enabled or disabled" - ) - async def logConfig(self, ctx: commands.Context, event: str, status: bool) -> None: - """Configures which events are enabled""" - guild_id = ctx.guild.id # type: ignore - cache = KumikoCache(connection_pool=self.redis_pool) - config = await self.get_or_fetch_config( - id=guild_id, redis_pool=self.redis_pool, pool=self.pool - ) - if config is None or isinstance(config, str): - await ctx.send("The config was not set up. Please enable the logs module") - return - if event in config and config[event] is True: - key = f"cache:kumiko:{guild_id}:get_or_fetch_config" - await cache.setJSONCache(key=key, value=status, path=f".{event}") - await ctx.send("Config updated. The event has been enabled/disabled") - return + # an autocomplete is probably needed but im too lazy to figure out how to get it working + # @commands.has_guild_permissions(manage_guild=True) + # @commands.guild_only() + # @logs.command(name="configure") + # @app_commands.describe( + # event="The event to enable", status="Whether the event is enabled or disabled" + # ) + # async def logConfig(self, ctx: commands.Context, event: str, status: bool) -> None: + # """Configures which events are enabled""" + # guild_id = ctx.guild.id # type: ignore + # cache = KumikoCache(connection_pool=self.redis_pool) + # config = await get_or_fetch_config( + # id=guild_id, redis_pool=self.redis_pool, pool=self.pool + # ) + # if config is None or isinstance(config, str): + # await ctx.send("The config was not set up. Please enable the logs module") + # return + # if event in config and config[event] is True: + # key = f"cache:kumiko:{guild_id}:logging_config" + # await cache.setJSONCache(key=key, value=status, path=f".{event}") + # await ctx.send("Config updated. The event has been enabled/disabled") + # return async def setup(bot: KumikoCore) -> None: diff --git a/Bot/Libs/cache/decorators.py b/Bot/Libs/cache/decorators.py index 9a9ba561..a3ac346d 100644 --- a/Bot/Libs/cache/decorators.py +++ b/Bot/Libs/cache/decorators.py @@ -17,9 +17,12 @@ class cache: ttl (int, optional): TTL (Time-To-Live). Defaults to 30. """ - def __init__(self, key: Optional[str] = None, ttl: int = 30): + def __init__( + self, key: Optional[str] = None, ttl: int = 30, name: Optional[str] = None + ): self.key = key self.ttl = ttl + self.name = name def __call__(self, func: Callable, *args: Any, **kwargs: Any): @wraps(func) @@ -48,7 +51,7 @@ async def deco( prefix="cache", namespace="kumiko", id=id or uuid.uuid4(), - command=func.__name__, + command=self.name or func.__name__, ) if await cache.cacheExists(key=key) is False: @@ -68,9 +71,15 @@ class cacheJson: ttl (int, optional): TTL (Time-To-Live). If None, then the TTL will not be set. Defaults to 30. """ - def __init__(self, key: Optional[str] = None, ttl: Union[int, None] = 30): + def __init__( + self, + key: Optional[str] = None, + ttl: Union[int, None] = 30, + name: Optional[str] = None, + ): self.key = key self.ttl = ttl + self.name = name def __call__(self, func: Callable, *args: Any, **kwargs: Any): @wraps(func) @@ -99,7 +108,7 @@ async def deco( prefix="cache", namespace="kumiko", id=id or uuid.uuid4(), - command=func.__name__, + command=self.name or func.__name__, ) if await cache.cacheExists(key=key) is False: diff --git a/Bot/Libs/cache/redis_cache.py b/Bot/Libs/cache/redis_cache.py index e4eafc69..9a16806c 100644 --- a/Bot/Libs/cache/redis_cache.py +++ b/Bot/Libs/cache/redis_cache.py @@ -66,7 +66,7 @@ async def setJSONCache( await client.expire(name=key, time=ttl) # The output type comes from here: https://github.com/redis/redis-py/blob/9f503578d1ffed20d63e8023bcd8a7dccd15ecc5/redis/commands/json/_util.py#L3C1-L3C73 - async def getJSONCache(self, key: str) -> Union[str, None, Dict[str, Any]]: + async def getJSONCache(self, key: str) -> Union[None, Dict[str, Any]]: """Gets the JSON cache on Redis Args: @@ -81,6 +81,16 @@ async def getJSONCache(self, key: str) -> Union[str, None, Dict[str, Any]]: return None return value + async def deleteJSONCache(self, key: str, path: str = "$") -> None: + """Deletes the JSON cache at key `key` and under `path` + + Args: + key (str): The key to use in Redis + path (str): The path to look for. Defaults to "$" (root) + """ + client: redis.Redis = redis.Redis(connection_pool=self.connection_pool) + await client.json().delete(key=key, path=path) + async def cacheExists(self, key: str) -> bool: """Checks to make sure if the cache exists diff --git a/Bot/Libs/cog_utils/events_log/__init__.py b/Bot/Libs/cog_utils/events_log/__init__.py new file mode 100644 index 00000000..f54449a7 --- /dev/null +++ b/Bot/Libs/cog_utils/events_log/__init__.py @@ -0,0 +1,3 @@ +from .cache_utils import delete_cache, get_or_fetch_config, set_or_update_cache + +__all__ = ["get_or_fetch_config", "set_or_update_cache", "delete_cache"] diff --git a/Bot/Libs/cog_utils/events_log/cache_utils.py b/Bot/Libs/cog_utils/events_log/cache_utils.py new file mode 100644 index 00000000..9b6378b1 --- /dev/null +++ b/Bot/Libs/cog_utils/events_log/cache_utils.py @@ -0,0 +1,41 @@ +from typing import Any, Dict, Union + +import asyncpg +from Libs.cache import KumikoCache, cacheJson +from redis.asyncio.connection import ConnectionPool + + +# idk how to test this one +# Someone remind Noelle to test this once she figures out how to +@cacheJson(ttl=None, name="logging_config") +async def get_or_fetch_config( + id: int, redis_pool: ConnectionPool, pool: asyncpg.Pool +) -> Union[Dict[str, Union[int, bool]], None]: + query = """ + SELECT guild.id, guild.logs, logging_config.channel_id, logging_config.member_events + FROM guild + INNER JOIN logging_config + ON guild.id = logging_config.guild_id + WHERE guild.id = $1; + """ + async with pool.acquire() as conn: + res = await conn.fetchrow(query, id) + return dict(res) + + +async def set_or_update_cache( + key: str, redis_pool: ConnectionPool, data: Dict[str, Any] +) -> None: + cache = KumikoCache(connection_pool=redis_pool) + if not await cache.cacheExists(key=key): + await cache.setJSONCache(key=key, value=data, ttl=None) + else: + await cache.setJSONCache( + key=key, value=data["channel_id"], path="$.channel_id", ttl=None + ) + + +async def delete_cache(key: str, redis_pool: ConnectionPool) -> None: + cache = KumikoCache(connection_pool=redis_pool) + if await cache.cacheExists(key=key): + await cache.deleteJSONCache(key=key) diff --git a/Bot/Libs/ui/events_log/views.py b/Bot/Libs/ui/events_log/views.py index e6cbd064..7d75eb5c 100644 --- a/Bot/Libs/ui/events_log/views.py +++ b/Bot/Libs/ui/events_log/views.py @@ -1,12 +1,15 @@ import asyncpg import discord +from Libs.cog_utils.events_log import delete_cache, set_or_update_cache from Libs.utils import ErrorEmbed, SuccessActionEmbed +from redis.asyncio.connection import ConnectionPool class RegisterView(discord.ui.View): - def __init__(self, pool: asyncpg.Pool) -> None: + def __init__(self, pool: asyncpg.Pool, redis_pool: ConnectionPool) -> None: super().__init__() self.pool = pool + self.redis_pool = redis_pool @discord.ui.select( cls=discord.ui.ChannelSelect, channel_types=[discord.ChannelType.text] @@ -33,6 +36,19 @@ async def select_channels( try: await conn.execute(query, guildId, select.values[0].id, True) + data = { + "id": guildId, + "logs": True, + "channel_id": select.values[0].id, + "member_events": True, + "mod_events": True, + "eco_events": False, + } + await set_or_update_cache( + key=f"cache:kumiko:{guildId}:logging_config", + redis_pool=self.redis_pool, + data=data, + ) except asyncpg.UniqueViolationError: await tr.rollback() await interaction.response.send_message("There are duplicate records") @@ -55,9 +71,10 @@ async def button_quit( class UnregisterView(discord.ui.View): - def __init__(self, pool: asyncpg.Pool) -> None: + def __init__(self, pool: asyncpg.Pool, redis_pool: ConnectionPool) -> None: super().__init__() self.pool = pool + self.redis_pool = redis_pool @discord.ui.button( label="Confirm", @@ -78,12 +95,14 @@ async def confirm( """ async with self.pool.acquire() as conn: guildId = interaction.guild.id # type: ignore + key = f"cache:kumiko:{guildId}:logging_config" tr = conn.transaction() await tr.start() try: await conn.execute(query, guildId, False) + await delete_cache(key=key, redis_pool=self.redis_pool) except asyncpg.UniqueViolationError: await tr.rollback() self.clear_items() diff --git a/changelog.md b/changelog.md index ac243dd5..73f54635 100644 --- a/changelog.md +++ b/changelog.md @@ -3,6 +3,8 @@ More reworks of literally everything... This release migrates from Prisma to pure SQL (asyncpg), and fully stabilities the repo to use discord.py instead of Pycord. Nearly all of the planned features are implemented in this release, except the economy module. For the full list of changes, please see them here: [`v0.8.x...v0.9.0`](https://github.com/No767/Kumiko/compare/v0.8.0...v0.9.0) +**Note**: The commands to configure which events are turned on are disabled as of now, since it would require a full rework of the schema and code. This will be implemented in a future release. + ## :boom: Breaking Changes :boom: - All of the SQL queries have been rewritten to use SQL w/ asyncpg instead of Prisma @@ -31,6 +33,7 @@ For the full list of changes, please see them here: [`v0.8.x...v0.9.0`](https:// - Replaced `kumiko.py` with `meta.py` to allow for clearer purpose - Updated the return types of `KumikoCache().getJSONCache()` - Allow for custom paths to search for `KumikoCache().setJSONCache()` +- Alow for custom keys and names to be used instead in `@cache` and `@cacheJson` decos ## ✨ Additions @@ -47,6 +50,7 @@ For the full list of changes, please see them here: [`v0.8.x...v0.9.0`](https:// - Docs merged into one repo - this repo - Added `display_emoji` property to allow for cogs to have emojis when being loaded in the select menus - The final version of what an help command should be (taken from RDanny directly as usual) +- Increased test coverage ## ➖ Removals - Global KumikoCPM variable in favor of having it stored during runtime instead diff --git a/tests/cache_utils/test_event_logs_utils.py b/tests/cache_utils/test_event_logs_utils.py new file mode 100644 index 00000000..1a79390d --- /dev/null +++ b/tests/cache_utils/test_event_logs_utils.py @@ -0,0 +1,37 @@ +import sys +from pathlib import Path + +import pytest +from redis.asyncio.connection import ConnectionPool + +path = Path(__file__).parents[2].joinpath("Bot") +sys.path.append(str(path)) + +from Libs.cache import KumikoCache +from Libs.cog_utils.events_log import set_or_update_cache + + +@pytest.fixture(scope="session") +def get_data(): + return {"id": 123, "channel_id": 2342634575000} + + +@pytest.mark.asyncio +async def test_set_or_update_cache(get_data): + connPool = ConnectionPool() + key = "cache:kumiko:123:config" + cache = KumikoCache(connPool) + await set_or_update_cache(key=key, redis_pool=connPool, data=get_data) + res = await cache.getJSONCache(key=key) + assert res == get_data + + +@pytest.mark.asyncio +async def test_cached_set_or_update(get_data): + connPool = ConnectionPool() + key = "cache:kumiko:1234:config" + cache = KumikoCache(connPool) + res = await cache.setJSONCache(key=key, value=get_data) + await set_or_update_cache(key=key, redis_pool=connPool, data=get_data) + res = await cache.getJSONCache(key=key) + assert res == get_data and res["channel_id"] == get_data["channel_id"] # type: ignore diff --git a/tests/redis/test_redis_cache.py b/tests/redis/test_redis_cache.py index 0245fbed..0b0bbb0a 100644 --- a/tests/redis/test_redis_cache.py +++ b/tests/redis/test_redis_cache.py @@ -51,3 +51,14 @@ async def test_get_json_cache_if_none(): cache = KumikoCache(connection_pool=connPool) res = await cache.getJSONCache(key=key) assert res is None + + +@pytest.mark.asyncio +async def test_delete_json_cache(): + key = CommandKeyBuilder(id=123564343453453, command="nicer") + connPool = ConnectionPool().from_url("redis://localhost:6379/0") + cache = KumikoCache(connection_pool=connPool) + await cache.setJSONCache(key=key, value=DATA) + await cache.deleteJSONCache(key=key) + res = await cache.cacheExists(key=key) + assert res is False From 70f2fa8382e9597697b777e75c409dac14d78bc0 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Mon, 10 Jul 2023 03:17:59 -0700 Subject: [PATCH 169/184] Replace emoji for github cog --- Bot/Cogs/github.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Bot/Cogs/github.py b/Bot/Cogs/github.py index ce7e5dd1..6b806c6a 100644 --- a/Bot/Cogs/github.py +++ b/Bot/Cogs/github.py @@ -25,7 +25,7 @@ def __init__(self, bot: KumikoCore) -> None: @property def display_emoji(self) -> PartialEmoji: - return PartialEmoji.from_str("<:github:744345792172654643>") + return PartialEmoji.from_str("<:githubmarkwhite:1127906278509912185>") @commands.hybrid_group(name="github") async def github(self, ctx: commands.Context) -> None: From 4ceef1aeee7972ba85c0e13ba13651ac61a5fb52 Mon Sep 17 00:00:00 2001 From: rtk-rnjn Date: Mon, 10 Jul 2023 18:06:42 +0530 Subject: [PATCH 170/184] use WindowsEventLoop for windows --- Bot/kumikobot.py | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/Bot/kumikobot.py b/Bot/kumikobot.py index 27def38a..87c6adc2 100644 --- a/Bot/kumikobot.py +++ b/Bot/kumikobot.py @@ -3,13 +3,22 @@ import asyncpg import discord -import uvloop from aiohttp import ClientSession from dotenv import load_dotenv from kumikocore import KumikoCore from Libs.cache import KumikoCPManager from Libs.utils import KumikoLogger +if os.name == "nt": + asyncio.set_event_loop_policy(asyncio.WindowsSelectorEventLoopPolicy()) +else: + try: + import uvloop + + asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) + except ImportError: + pass + load_dotenv() KUMIKO_TOKEN = os.environ["DEV_BOT_TOKEN"] @@ -38,7 +47,6 @@ async def main() -> None: def launch() -> None: with KumikoLogger(): - asyncio.set_event_loop_policy(uvloop.EventLoopPolicy()) asyncio.run(main()) # run(main, backend_options={"use_uvloop": True}) From fb514ffb49b5e4f00fcf7412111bebda758f6146 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Mon, 10 Jul 2023 18:17:34 +0000 Subject: [PATCH 171/184] [pip](deps-dev): Bump nox-poetry from 1.0.2 to 1.0.3 (#376) Bumps [nox-poetry](https://github.com/cjolowicz/nox-poetry) from 1.0.2 to 1.0.3. - [Release notes](https://github.com/cjolowicz/nox-poetry/releases) - [Commits](https://github.com/cjolowicz/nox-poetry/compare/v1.0.2...v1.0.3) --- updated-dependencies: - dependency-name: nox-poetry dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- poetry.lock | 10 +++++----- pyproject.toml | 2 +- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/poetry.lock b/poetry.lock index 929d4e93..808e589f 100644 --- a/poetry.lock +++ b/poetry.lock @@ -1,4 +1,4 @@ -# This file is automatically @generated by Poetry 1.5.0 and should not be changed by hand. +# This file is automatically @generated by Poetry 1.5.1 and should not be changed by hand. [[package]] name = "aiodns" @@ -2154,13 +2154,13 @@ tox-to-nox = ["jinja2", "tox (<4)"] [[package]] name = "nox-poetry" -version = "1.0.2" +version = "1.0.3" description = "nox-poetry" optional = false python-versions = ">=3.7,<4.0" files = [ - {file = "nox-poetry-1.0.2.tar.gz", hash = "sha256:22bc397979393a0283f5161af708a3a430e1c7e0cc2be274c7b27e9e46de0412"}, - {file = "nox_poetry-1.0.2-py3-none-any.whl", hash = "sha256:a53c36eccbd67f15b5b83dd6562d077dd326c71fd4a942528d8b2299c417dbbe"}, + {file = "nox_poetry-1.0.3-py3-none-any.whl", hash = "sha256:a2fffeb70ae81840479e68287afe1c772bf376f70f1e92f99832a20b3c64d064"}, + {file = "nox_poetry-1.0.3.tar.gz", hash = "sha256:dc7ecbbd812a333a0c0b558f57e5b37f7c12926cddbcecaf2264957fd373824e"}, ] [package.dependencies] @@ -3468,4 +3468,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "2ecc86641643805735c120efc4a263253135c32e3cd30860b6b37248b6af3daf" +content-hash = "22da00d9b9686af21a3460105127c71140dd9b903301633ecacd3f4fe36deb78" diff --git a/pyproject.toml b/pyproject.toml index 4480c45e..7662f56b 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -29,7 +29,7 @@ psutil = "^5.9.5" pytest = "^7.4.0" pytest-asyncio = "^0.21.0" nox = "^2023.4.22" -nox-poetry = "^1.0.2" +nox-poetry = "^1.0.3" pytest-cov = "^4.1.0" dpytest = "^0.7.0" From 2b752e877fcefbe30b582fea846fc1be2e41b638 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Mon, 10 Jul 2023 20:21:47 -0700 Subject: [PATCH 172/184] Use Winloop for Windows event loop --- Bot/kumikobot.py | 6 +++-- poetry.lock | 68 ++++++++++++++++++++++++++++++++++++++++++++++-- pyproject.toml | 3 ++- 3 files changed, 72 insertions(+), 5 deletions(-) diff --git a/Bot/kumikobot.py b/Bot/kumikobot.py index 87c6adc2..005f38b6 100644 --- a/Bot/kumikobot.py +++ b/Bot/kumikobot.py @@ -9,8 +9,11 @@ from Libs.cache import KumikoCPManager from Libs.utils import KumikoLogger +# Only used for Windows development if os.name == "nt": - asyncio.set_event_loop_policy(asyncio.WindowsSelectorEventLoopPolicy()) + import winloop + + asyncio.set_event_loop_policy(winloop.WinLoopPolicy()) else: try: import uvloop @@ -48,7 +51,6 @@ async def main() -> None: def launch() -> None: with KumikoLogger(): asyncio.run(main()) - # run(main, backend_options={"use_uvloop": True}) if __name__ == "__main__": diff --git a/poetry.lock b/poetry.lock index 808e589f..c6c96990 100644 --- a/poetry.lock +++ b/poetry.lock @@ -1,4 +1,4 @@ -# This file is automatically @generated by Poetry 1.5.1 and should not be changed by hand. +# This file is automatically @generated by Poetry 1.5.0 and should not be changed by hand. [[package]] name = "aiodns" @@ -975,6 +975,56 @@ files = [ {file = "cycler-0.11.0.tar.gz", hash = "sha256:9c87405839a19696e837b3b818fed3f5f69f16f1eec1a1ad77e043dcea9c772f"}, ] +[[package]] +name = "cython" +version = "0.29.36" +description = "The Cython compiler for writing C extensions for the Python language." +optional = false +python-versions = ">=2.6, !=3.0.*, !=3.1.*, !=3.2.*" +files = [ + {file = "Cython-0.29.36-cp27-cp27m-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:1ea33c1c57f331f5653baa1313e445fbe80d1da56dd9a42c8611037887897b9d"}, + {file = "Cython-0.29.36-cp27-cp27m-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:2fe34615c13ace29e77bf9d21c26188d23eff7ad8b3e248da70404e5f5436b95"}, + {file = "Cython-0.29.36-cp27-cp27mu-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:ae75eac4f13cbbcb50b2097470dcea570182446a3ebd0f7e95dd425c2017a2d7"}, + {file = "Cython-0.29.36-cp27-cp27mu-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:847d07fc02978c4433d01b4f5ee489b75fd42fd32ccf9cc4b5fd887e8cffe822"}, + {file = "Cython-0.29.36-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.manylinux_2_24_aarch64.whl", hash = "sha256:7cb44aeaf6c5c25bd6a7562ece4eadf50d606fc9b5f624fa95bd0281e8bf0a97"}, + {file = "Cython-0.29.36-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_24_x86_64.whl", hash = "sha256:28fb10aabd56a2e4d399273b48e106abe5a0d271728fd5eed3d36e7171000045"}, + {file = "Cython-0.29.36-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_24_i686.whl", hash = "sha256:86b7a13c6b23ab6471d40a320f573fbc8a4e39833947eebed96661145dc34771"}, + {file = "Cython-0.29.36-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:19ccf7fc527cf556e2e6a3dfeffcadfbcabd24a59a988289117795dfed8a25ad"}, + {file = "Cython-0.29.36-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.manylinux_2_24_aarch64.whl", hash = "sha256:74bddfc7dc8958526b2018d3adc1aa6dc9cf2a24095c972e5ad06758c360b261"}, + {file = "Cython-0.29.36-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_24_x86_64.whl", hash = "sha256:6c4d7e36fe0211e394adffd296382b435ac22762d14f2fe45c506c230f91cf2d"}, + {file = "Cython-0.29.36-cp311-cp311-manylinux_2_5_i686.manylinux1_i686.manylinux_2_24_i686.whl", hash = "sha256:0bca6a7504e8cfc63a4d3c7c9b9a04e5d05501942a6c8cee177363b61a32c2d4"}, + {file = "Cython-0.29.36-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:17c74f80b06e2fa8ffc8acd41925f4f9922da8a219cd25c6901beab2f7c56cc5"}, + {file = "Cython-0.29.36-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:25ff471a459aad82146973b0b8c177175ab896051080713d3035ad4418739f66"}, + {file = "Cython-0.29.36-cp35-cp35m-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:a9738f23d00d99481797b155ad58f8fc1c72096926ea2554b8ccc46e1d356c27"}, + {file = "Cython-0.29.36-cp35-cp35m-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:af2f333f08c4c279f3480532341bf70ec8010bcbc7d8a6daa5ca0bf4513af295"}, + {file = "Cython-0.29.36-cp36-cp36m-manylinux_2_17_aarch64.manylinux2014_aarch64.manylinux_2_24_aarch64.whl", hash = "sha256:cd77cedbcc13cb67aef39b8615fd50a67fc42b0c6defea6fc0a21e19d3a062ec"}, + {file = "Cython-0.29.36-cp36-cp36m-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_24_x86_64.whl", hash = "sha256:50d506d73a46c4a522ef9fdafcbf7a827ba13907b18ff58f61a8fa0887d0bd8d"}, + {file = "Cython-0.29.36-cp36-cp36m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_24_i686.whl", hash = "sha256:6a571d7c7b52ee12d73bc65b4855779c069545da3bac26bec06a1389ad17ade5"}, + {file = "Cython-0.29.36-cp36-cp36m-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:a216b2801c7d9c3babe0a10cc25da3bc92494d7047d1f732d3c47b0cceaf0941"}, + {file = "Cython-0.29.36-cp36-cp36m-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:68abee3be27f21c9642a07a93f8333d491f4c52bc70068e42f51685df9ac1a57"}, + {file = "Cython-0.29.36-cp36-cp36m-musllinux_1_1_x86_64.whl", hash = "sha256:1ef90023da8a9bf84cf16f06186db0906d2ce52a09f751e2cb9d3da9d54eae46"}, + {file = "Cython-0.29.36-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.manylinux_2_24_aarch64.whl", hash = "sha256:9deef0761e8c798043dbb728a1c6df97b26e5edc65b8d6c7608b3c07af3eb722"}, + {file = "Cython-0.29.36-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_24_x86_64.whl", hash = "sha256:69af2365de2343b4e5a61c567e7611ddf2575ae6f6e5c01968f7d4f2747324eb"}, + {file = "Cython-0.29.36-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_24_i686.whl", hash = "sha256:fdf377b0f6e9325b73ad88933136023184afdc795caeeaaf3dca13494cffd15e"}, + {file = "Cython-0.29.36-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:1ff2cc5518558c598028ae8d9a43401e0e734b74b6e598156b005328c9da3472"}, + {file = "Cython-0.29.36-cp37-cp37m-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:7ca921068242cd8b52544870c807fe285c1f248b12df7b6dfae25cc9957b965e"}, + {file = "Cython-0.29.36-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:6058a6d04e04d790cda530e1ff675e9352359eb4b777920df3cac2b62a9a030f"}, + {file = "Cython-0.29.36-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.manylinux_2_24_aarch64.whl", hash = "sha256:de2045ceae1857e56a72f08e0acfa48c994277a353b7bdab1f097db9f8803f19"}, + {file = "Cython-0.29.36-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_24_x86_64.whl", hash = "sha256:9f2a4b4587aaef08815410dc20653613ca04a120a2954a92c39e37c6b5fdf6be"}, + {file = "Cython-0.29.36-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_24_i686.whl", hash = "sha256:2edd9f8edca69178d74cbbbc180bc3e848433c9b7dc80374a11a0bb0076c926d"}, + {file = "Cython-0.29.36-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:c6c0aea8491a70f98b7496b5057c9523740e02cec21cd678eef609d2aa6c1257"}, + {file = "Cython-0.29.36-cp38-cp38-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:768f65b16d23c630d8829ce1f95520ef1531a9c0489fa872d87c8c3813f65aee"}, + {file = "Cython-0.29.36-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:568625e8274ee7288ad87b0f615ec36ab446ca9b35e77481ed010027d99c7020"}, + {file = "Cython-0.29.36-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.manylinux_2_24_aarch64.whl", hash = "sha256:bdc0a4cb99f55e6878d4b67a4bfee23823484915cb6b7e9c9dd01002dd3592ea"}, + {file = "Cython-0.29.36-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_24_x86_64.whl", hash = "sha256:f0df6552be39853b10dfb5a10dbd08f5c49023d6b390d7ce92d4792a8b6e73ee"}, + {file = "Cython-0.29.36-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_24_i686.whl", hash = "sha256:8894db6f5b6479a3c164e0454e13083ebffeaa9a0822668bb2319bdf1b783df1"}, + {file = "Cython-0.29.36-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:53f93a8c342e9445a8f0cb7039775294f2dbbe5241936573daeaf0afe30397e4"}, + {file = "Cython-0.29.36-cp39-cp39-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:ee317f9bcab901a3db39c34ee5a27716f7132e5c0de150125342694d18b30f51"}, + {file = "Cython-0.29.36-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:e4b8269e5a5d127a2191b02b9df3636c0dac73f14f1ff8a831f39cb5197c4f38"}, + {file = "Cython-0.29.36-py2.py3-none-any.whl", hash = "sha256:95bb13d8be507425d03ebe051f90d4b2a9fdccc64e4f30b35645fdb7542742eb"}, + {file = "Cython-0.29.36.tar.gz", hash = "sha256:41c0cfd2d754e383c9eeb95effc9aa4ab847d0c9747077ddd7c0dcb68c3bc01f"}, +] + [[package]] name = "discord-ext-menus" version = "1.0.0a32+g8686b5d" @@ -3363,6 +3413,20 @@ files = [ [package.extras] test = ["pytest (>=6.0.0)"] +[[package]] +name = "winloop" +version = "0.0.6" +description = "An Alternative library for uvloop compatability with windows" +optional = false +python-versions = "*" +files = [ + {file = "winloop-0.0.6-cp39-cp39-win_amd64.whl", hash = "sha256:d5fa5d9ac5e56d428f556691e902bb65e14bacf79433ca18a09e6e0721f1941a"}, + {file = "winloop-0.0.6.tar.gz", hash = "sha256:5708ac397ed5a14db574f96115f693077e049968075a1e7d8ee4db52b468d8c3"}, +] + +[package.dependencies] +cython = "*" + [[package]] name = "yarl" version = "1.9.2" @@ -3468,4 +3532,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "22da00d9b9686af21a3460105127c71140dd9b903301633ecacd3f4fe36deb78" +content-hash = "f034be5584ab4c1ac486bb0a9fe63bd261512b3d11b4bc42aba1694459a156a2" diff --git a/pyproject.toml b/pyproject.toml index 7662f56b..e59209fc 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -12,7 +12,7 @@ aiodns = "^3.0.0" Brotli = "^1.0.9" orjson = "^3.9.2" asyncpraw = "^7.7.0" -uvloop = "^0.17.0" +uvloop = {markers = "sys_platform != \"win32\"", version = "^0.17.0"} gql = { extras = ["aiohttp"], version = "^3.4.1" } better-ipc = "^2.0.3" redis = {extras = ["hiredis"], version = "^4.6.0"} @@ -24,6 +24,7 @@ asyncpg = "^0.28.0" asyncpg-trek = "^0.3.1" lru-dict = "^1.2.0" psutil = "^5.9.5" +winloop = {markers = "sys_platform == \"win32\"", version = "^0.0.6"} [tool.poetry.group.test.dependencies] pytest = "^7.4.0" From 2101148e2e7301287db4dc1bb0cad608ec0c25b8 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Mon, 10 Jul 2023 21:14:07 -0700 Subject: [PATCH 173/184] Run the bot file after migrations --- Docker/start.sh | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/Docker/start.sh b/Docker/start.sh index 150b6e90..536c978c 100644 --- a/Docker/start.sh +++ b/Docker/start.sh @@ -5,7 +5,8 @@ KUMIKO_FIRST_START_CHECK="KUMIKO_FIRST_START" if [ ! -f $KUMIKO_FIRST_START_CHECK ]; then touch $KUMIKO_FIRST_START_CHECK echo 'DO NOT EDIT THIS FILE! THIS IS USED WHEN YOU FIRST RUN KUMIKO USING DOCKER!' >> $KUMIKO_FIRST_START_CHECK - exec python3 /Kumiko/migrations-runner.py + exec python3 /Kumiko/migrations-runner.py \ + exec python3 /Kumiko/Bot/kumikobot.py fi exec python3 /Kumiko/Bot/kumikobot.py \ No newline at end of file From b32c526f8baffdcab6319e5fbd18844e41afb4e8 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Mon, 10 Jul 2023 22:43:36 -0700 Subject: [PATCH 174/184] Add anyio back for finding cogs --- poetry.lock | 2 +- pyproject.toml | 1 + 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/poetry.lock b/poetry.lock index c6c96990..fe1049dd 100644 --- a/poetry.lock +++ b/poetry.lock @@ -3532,4 +3532,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "f034be5584ab4c1ac486bb0a9fe63bd261512b3d11b4bc42aba1694459a156a2" +content-hash = "6508e58f8eb78c5d0f2a6480b7a8003a5a949147e751426a382fe492c340ff6f" diff --git a/pyproject.toml b/pyproject.toml index e59209fc..0006b33b 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -25,6 +25,7 @@ asyncpg-trek = "^0.3.1" lru-dict = "^1.2.0" psutil = "^5.9.5" winloop = {markers = "sys_platform == \"win32\"", version = "^0.0.6"} +anyio = "^3.7.1" [tool.poetry.group.test.dependencies] pytest = "^7.4.0" From 5da42acbbc29e8878373e76eb80820e6df14a9f8 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Mon, 10 Jul 2023 22:59:45 -0700 Subject: [PATCH 175/184] Readjust start.sh again --- Docker/start.sh | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/Docker/start.sh b/Docker/start.sh index 536c978c..25072e4d 100644 --- a/Docker/start.sh +++ b/Docker/start.sh @@ -5,8 +5,7 @@ KUMIKO_FIRST_START_CHECK="KUMIKO_FIRST_START" if [ ! -f $KUMIKO_FIRST_START_CHECK ]; then touch $KUMIKO_FIRST_START_CHECK echo 'DO NOT EDIT THIS FILE! THIS IS USED WHEN YOU FIRST RUN KUMIKO USING DOCKER!' >> $KUMIKO_FIRST_START_CHECK - exec python3 /Kumiko/migrations-runner.py \ - exec python3 /Kumiko/Bot/kumikobot.py + exec python3 /Kumiko/migrations-runner.py && exec python3 /Kumiko/Bot/kumikobot.py fi exec python3 /Kumiko/Bot/kumikobot.py \ No newline at end of file From bc5ed21f3ad6156553f0c8f652bd6473ae9e1c03 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Mon, 10 Jul 2023 23:05:11 -0700 Subject: [PATCH 176/184] Don't exec the python migration runner --- Docker/start.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Docker/start.sh b/Docker/start.sh index 25072e4d..cf4e4a7b 100644 --- a/Docker/start.sh +++ b/Docker/start.sh @@ -5,7 +5,7 @@ KUMIKO_FIRST_START_CHECK="KUMIKO_FIRST_START" if [ ! -f $KUMIKO_FIRST_START_CHECK ]; then touch $KUMIKO_FIRST_START_CHECK echo 'DO NOT EDIT THIS FILE! THIS IS USED WHEN YOU FIRST RUN KUMIKO USING DOCKER!' >> $KUMIKO_FIRST_START_CHECK - exec python3 /Kumiko/migrations-runner.py && exec python3 /Kumiko/Bot/kumikobot.py + python3 /Kumiko/migrations-runner.py fi exec python3 /Kumiko/Bot/kumikobot.py \ No newline at end of file From fa6ee2d14bd4637bc3d585eca9526aad4c27d9ad Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Mon, 10 Jul 2023 23:39:36 -0700 Subject: [PATCH 177/184] [skip ci] Update changelog --- changelog.md | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/changelog.md b/changelog.md index 73f54635..4c167944 100644 --- a/changelog.md +++ b/changelog.md @@ -34,6 +34,11 @@ For the full list of changes, please see them here: [`v0.8.x...v0.9.0`](https:// - Updated the return types of `KumikoCache().getJSONCache()` - Allow for custom paths to search for `KumikoCache().setJSONCache()` - Alow for custom keys and names to be used instead in `@cache` and `@cacheJson` decos +- Use WindowsEventLoop for Windows (#375) (@rtk-rnjn) +- Implement WinLoop event policy for Windows +- Ensure that the migration runner always runs first +- Change stop signal from `SIGTERM` to `SIGINT` for Docker +- Build the Docker image locally for Kumiko's Postgres server ## ✨ Additions @@ -51,6 +56,7 @@ For the full list of changes, please see them here: [`v0.8.x...v0.9.0`](https:// - Added `display_emoji` property to allow for cogs to have emojis when being loaded in the select menus - The final version of what an help command should be (taken from RDanny directly as usual) - Increased test coverage +- `sys-metrics` command to obtain system metrics (for Noelle only) ## ➖ Removals - Global KumikoCPM variable in favor of having it stored during runtime instead @@ -124,4 +130,7 @@ For the full list of changes, please see them here: [`v0.8.x...v0.9.0`](https:// - \[pip](deps)\: Bump prisma from 0.9.0 to 0.9.1 (#367) (@dependabot) - \[pip](deps-dev)\: Bump ruff from 0.0.275 to 0.0.276 (#370) (@dependabot) - \[pip](deps-dev)\: Bump ruff from 0.0.276 to 0.0.277 (#371) (@dependabot) -- \[Actions](deps)\: Bump actions/setup-node from 3.6.0 to 3.7.0 (#372) (@dependabot) \ No newline at end of file +- \[Actions](deps)\: Bump actions/setup-node from 3.6.0 to 3.7.0 (#372) (@dependabot) +- \[pip](deps)\: Bump asyncpg from 0.27.0 to 0.28.0 (#373) (@dependabot) +- \[pip](deps)\: Bump orjson from 3.9.1 to 3.9.2 (#374) (@dependabot) +- \[pip](deps-dev)\: Bump nox-poetry from 1.0.2 to 1.0.3 (#376) (@dependabot) \ No newline at end of file From b44f24572cae11ecc3103d67aed93f7d07a119af Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Mon, 10 Jul 2023 23:49:05 -0700 Subject: [PATCH 178/184] [skip ci] Update changelog again --- changelog.md | 1 + 1 file changed, 1 insertion(+) diff --git a/changelog.md b/changelog.md index 4c167944..0dd709d1 100644 --- a/changelog.md +++ b/changelog.md @@ -9,6 +9,7 @@ For the full list of changes, please see them here: [`v0.8.x...v0.9.0`](https:// - All of the SQL queries have been rewritten to use SQL w/ asyncpg instead of Prisma - A ton of cogs, and commands have been either moved or deleted since v0.8.x. Please consider resyncing your commands with the include dev-tool cog (or by activating jishaku) +- All `*-bullseye` tags are now deprecated. Kumiko is now built using Debian 12 (Bookworm) ## ✨ TD;LR From a2cc2a10a36fedb7319b4b84465e6a6a16c59573 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Mon, 10 Jul 2023 23:54:20 -0700 Subject: [PATCH 179/184] [skip ci] Add a copy button to sphinx --- Kumiko-Docs/requirements.txt | 3 ++- Kumiko-Docs/source/conf.py | 2 +- poetry.lock | 20 +++++++++++++++++++- pyproject.toml | 1 + 4 files changed, 23 insertions(+), 3 deletions(-) diff --git a/Kumiko-Docs/requirements.txt b/Kumiko-Docs/requirements.txt index 3117b777..9538c935 100644 --- a/Kumiko-Docs/requirements.txt +++ b/Kumiko-Docs/requirements.txt @@ -36,6 +36,7 @@ snowballstemmer==2.2.0 ; python_version >= "3.8" and python_version < "4.0" soupsieve==2.4.1 ; python_version >= "3.8" and python_version < "4.0" sphinx-autobuild==2021.3.14 ; python_version >= "3.8" and python_version < "4.0" sphinx-basic-ng==1.0.0b1 ; python_version >= "3.8" and python_version < "4.0" +sphinx-copybutton==0.5.2 ; python_version >= "3.8" and python_version < "4.0" sphinx==7.0.1 ; python_version >= "3.8" and python_version < "4.0" sphinxcontrib-applehelp==1.0.4 ; python_version >= "3.8" and python_version < "4.0" sphinxcontrib-devhelp==1.0.2 ; python_version >= "3.8" and python_version < "4.0" @@ -46,4 +47,4 @@ sphinxcontrib-serializinghtml==1.1.5 ; python_version >= "3.8" and python_versio sphinxext-opengraph==0.8.2 ; python_version >= "3.8" and python_version < "4.0" tornado==6.3.2 ; python_version >= "3.8" and python_version < "4.0" urllib3==2.0.3 ; python_version >= "3.8" and python_version < "4.0" -zipp==3.15.0 ; python_version >= "3.8" and python_version < "3.10" \ No newline at end of file +zipp==3.15.0 ; python_version >= "3.8" and python_version < "3.10" diff --git a/Kumiko-Docs/source/conf.py b/Kumiko-Docs/source/conf.py index a10ddf6b..acffb8f9 100644 --- a/Kumiko-Docs/source/conf.py +++ b/Kumiko-Docs/source/conf.py @@ -13,7 +13,7 @@ # -- General configuration --------------------------------------------------- # https://www.sphinx-doc.org/en/master/usage/configuration.html#general-configuration -extensions = ["sphinx.ext.napoleon", "sphinxext.opengraph"] +extensions = ["sphinx.ext.napoleon", "sphinxext.opengraph", "sphinx_copybutton"] templates_path = ["_templates"] diff --git a/poetry.lock b/poetry.lock index fe1049dd..67bbb2a8 100644 --- a/poetry.lock +++ b/poetry.lock @@ -3029,6 +3029,24 @@ sphinx = ">=4.0" [package.extras] docs = ["furo", "ipython", "myst-parser", "sphinx-copybutton", "sphinx-inline-tabs"] +[[package]] +name = "sphinx-copybutton" +version = "0.5.2" +description = "Add a copy button to each of your code cells." +optional = false +python-versions = ">=3.7" +files = [ + {file = "sphinx-copybutton-0.5.2.tar.gz", hash = "sha256:4cf17c82fb9646d1bc9ca92ac280813a3b605d8c421225fd9913154103ee1fbd"}, + {file = "sphinx_copybutton-0.5.2-py3-none-any.whl", hash = "sha256:fb543fd386d917746c9a2c50360c7905b605726b9355cd26e9974857afeae06e"}, +] + +[package.dependencies] +sphinx = ">=1.8" + +[package.extras] +code-style = ["pre-commit (==2.12.1)"] +rtd = ["ipython", "myst-nb", "sphinx", "sphinx-book-theme", "sphinx-examples"] + [[package]] name = "sphinxcontrib-applehelp" version = "1.0.4" @@ -3532,4 +3550,4 @@ testing = ["big-O", "flake8 (<5)", "jaraco.functools", "jaraco.itertools", "more [metadata] lock-version = "2.0" python-versions = ">=3.8,<4.0" -content-hash = "6508e58f8eb78c5d0f2a6480b7a8003a5a949147e751426a382fe492c340ff6f" +content-hash = "0bbb12b1f58711c36ba44ebfbacbd8935a11dec3d373303eb9f9b9f49e8f60a8" diff --git a/pyproject.toml b/pyproject.toml index 0006b33b..d6403305 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -50,6 +50,7 @@ myst-parser = "^2.0.0" sphinx-autobuild = "^2021.3.14" furo = "^2023.5.20" sphinxext-opengraph = "^0.8.2" +sphinx-copybutton = "^0.5.2" [tool.isort] From 272bdb4ad34e39086ae3e01733aecc566bf81eef Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Tue, 11 Jul 2023 00:05:35 -0700 Subject: [PATCH 180/184] [skip ci] Update docs, move contributing.md into the dev contrib guide --- .../source/guides/dev/requirements.rst | 7 +- contributing.md | 79 +------------------ 2 files changed, 4 insertions(+), 82 deletions(-) diff --git a/Kumiko-Docs/source/guides/dev/requirements.rst b/Kumiko-Docs/source/guides/dev/requirements.rst index 8d75a089..e14d6efb 100644 --- a/Kumiko-Docs/source/guides/dev/requirements.rst +++ b/Kumiko-Docs/source/guides/dev/requirements.rst @@ -9,12 +9,11 @@ Before you get started, please ensure you have the following installed: - `Git `_ - `Python 3 `_ - `Poetry `_ -- `WSL2 `_ (If working on Windows) - `Docker `_ - Discord Account + App -.. NOTE:: - Kumiko is natively developed for Linux. If you are using Windows, please use WSL2. +.. CAUTION:: + Kumiko is natively developed for Linux. Development should work on Windows but it is highly untested. Package Prerequisites ---------------------- @@ -25,7 +24,7 @@ Debian/Ubuntu .. code-block:: bash sudo apt-get install libffi-dev python3-dev libnacl-dev libopus-dev \ - libopusenc-dev build-essentials libssl-dev curl wget git + build-essentials libssl-dev curl wget git Fedora diff --git a/contributing.md b/contributing.md index b9cbd191..1fa507cc 100644 --- a/contributing.md +++ b/contributing.md @@ -1,80 +1,3 @@ # Contributing -We are glad that you're willing to contribute to this project. We are usually very lenient and relaxed with the submissions of PRs, and Issues reports. But there are some stuff that you need to know before contributing. - -## Note to new contributors - -When you contribute to this project, you are subject to the [Code of Conduct](./CODE_OF_CONDUCT.md). Any violations of the Code Of Conduct will be handled as stated. Read the contributing guide. **Support is not given if you didn't bother reading the documentation for setting up any of the requirements, or if you didn't bother to read the contributing guide.** - -## Before Starting - -Make sure to read these guides listed below (read them in order): - -- [Dev Prerequisites](./Docs/dev-prerequisites.md) -- [Getting the Dev Discord Bot](./Docs/getting-dev-discord-bot.md) -- [API Keys](./Docs/api-keys.md) -- [Database Setup](./Docs/database-setup.md) - -## Coding Style -### Variables - -Most of the code written uses camelCasing for variables, `PascalCasing` for classes, and `snake_casing` for args. To sum it up: - -- `camelCasing` for variables -- `PascalCasing` for classes -- `snake_casing` for args -- `ALL_CAPS` for constants -- `kebab-casing` for files - -### Formatting - -Kumiko uses pre-commit hooks to format all of the code. Make sure run `git add --all` before committing to add all of the files. More than likely you'll need to commit twice due to the formatting that pre-commit does afterwards. - -### Docstrings - -Just like how major programs are documented, the libraries that are custom made for Kumiko also have to be documented. The current standard for this project is to use [Google's Docstring format](https://google.github.io/styleguide/pyguide.html#s3.8-comments-and-docstrings). A handy VS Code extension that should be used is the [autoDocstring](https://marketplace.visualstudio.com/items?itemName=njpwerner.autodocstring) extension. By default it will generate the docstring in the Google format. Docstrings should be used on all coroutines and methods (excluding cogs), and on classes as well. - -Google, Numpy, and Sphinx docstrings are also supported for commands. Kumiko is documented w/ Google docstrings, so please make sure to use that format. - -Example Cog: - -```py -import discord -from discord.ext import commands -from discord.ext.commands import Context, Bot - -class MyCog(commands.Cog): - """An example cog for demo purposes""" - def __init__(self, bot: Bot): - self.bot = bot - - @commands.hybrid_command(name="hello") - async def myCommand(self, ctx: Context): - """This is an example of a description for a slash command""" - await ctx.send(f"Hello {ctx.user.name}!") - -async def setup(bot: Bot): - await bot.add_cog(MyCog(bot)) -``` -## GitHub Contributing Guidelines -### Issue and Feature Requests Reports - -If there is an issue or a feature you want to be added, use the built-in GitHub issue tracker. Though a system like Jira could be used, it would be more efficient to just use the issue tracker that GitHub provides. - -- If submitting a issue report, follow the template. Duplicates will not receive support -- If submitting a feature request, follow the template as well. As with issue reports, duplicate requests will not receive support - -### Git Commit Styleguides - -- If updating any other files that aren't project files or not important (stuff like README.md, contributing.md, etc), add the [skip ci] label in the front -- With each new commit, the message should be more or less describing the changes. Please don't write useless commit messages... -- If releasing tags, have it in this style. `Release: v[version number]`, `Update: v[version number]`, and `Fix: v[version number]`. Release is a major release. This means it bumps from 1.0.0 to 2.0.0. Minor means it bumps up the version from 1.4 to 1.5 for example. And fix just applies a patch, which would be 1.4.1 to 1.4.2. - -### Releasing Tags -In order to automate the release system, you have to make sure that in order to use it, the git commit message must be done correctly. Only use this if there is a new update that is ready to be released. Kumiko uses [SemVer](https://semver.org/) as the standard for versioning. Here's a table that should help with explaining this: - -| Type of Release, Update, or Patch | Example | -| :--: | :--: | -| Major Release (For updates that are not backwards compatible) | `Release: v2.0.0` | -| Minor Release (For updates that are backwards compatible) | `Update: v2.5.0`| -| Patch Release (For critical security patches and bug fixes) | `Fix: v2.5.1` | \ No newline at end of file +Please see the [Dev Contributing Guide](https://kumiko.readthedocs.io/en/latest/guides/dev/dev-contributing.html) for more info. \ No newline at end of file From eae8ac8379ef52be645407c5c1a591a0ef9e5fe2 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Tue, 11 Jul 2023 00:50:04 -0700 Subject: [PATCH 181/184] [skip ci] Add pinned prod requirements, and update docs --- .../guides/user/configurations/bot-config.rst | 2 +- Kumiko-Docs/source/guides/user/trying-out.rst | 102 +++++++++++++----- Makefile | 3 + Requirements/prod.txt | 50 +++++++++ 4 files changed, 131 insertions(+), 26 deletions(-) create mode 100644 Requirements/prod.txt diff --git a/Kumiko-Docs/source/guides/user/configurations/bot-config.rst b/Kumiko-Docs/source/guides/user/configurations/bot-config.rst index 41517f93..cc1d72f3 100644 --- a/Kumiko-Docs/source/guides/user/configurations/bot-config.rst +++ b/Kumiko-Docs/source/guides/user/configurations/bot-config.rst @@ -1,4 +1,4 @@ Bot Config ================= -All configs are handled via the ``Bot/.env`` file. Consult the ``.env.example`` file for an example. \ No newline at end of file +All configs are handled via the ``Bot/.env`` file. Consult the ``Env/prod.env`` file for an example. \ No newline at end of file diff --git a/Kumiko-Docs/source/guides/user/trying-out.rst b/Kumiko-Docs/source/guides/user/trying-out.rst index c8881f4f..389f0e38 100644 --- a/Kumiko-Docs/source/guides/user/trying-out.rst +++ b/Kumiko-Docs/source/guides/user/trying-out.rst @@ -10,16 +10,18 @@ Prerequisites 2. Make sure you have these installed: - `Docker `_ - curl or wget + - Git -Standalone Requirements -^^^^^^^^^^^^^^^^^^^^^^^ +Standalone Prerequisites +^^^^^^^^^^^^^^^^^^^^^^^^ If you are running Kumiko on a standalone machine (w/o Docker Compose or using Systemd), you will need to install the following: -- `PostgreSQL `_ +- `PostgreSQL `_ (w/ ``pg_trgm`` extension loaded) - `Redis Stack `_ (or Redis w/ RedisJSON and RedisSearch modules loaded) -Standalone (Docker CLI) + +Docker CLI (Standalone) ----------------------- 1. Pull the image from either GHCR or Docker Hub @@ -36,37 +38,50 @@ Standalone (Docker CLI) docker pull no767/kumiko:latest -2. Download the example docker env file and standalone-setup script. This is the file where you'll put all of your env and credentials in +2. Set up the docker ENV file .. code-block:: bash - curl -o https://raw.githubusercontent.com/no767/kumiko/master/.env-docker-example .env + curl -o https://raw.githubusercontent.com/no767/kumiko/master/Envs/docker.env .env # Or using wget: - wget -O .env https://raw.githubusercontent.com/no767/kumiko/master/.env-docker-example + wget -O .env https://raw.githubusercontent.com/no767/kumiko/master/Envs/docker.env -3. Obtain the API keys, access tokens, discord bot token, and database credentials for Kumiko. Open up the ``.env`` file with an editor like Vim and add the needed values. +3. Edit the ``.env`` file to include any credentials needed for the bot to run + + .. code-block:: bash + + # THIS IS ONLY AN EXAMPLE + POSTGRES_PASSWORD=... + POSTGRES_USER=... + POSTGRES_URI=postgres://user:somepass@localhost:5432/somedb -4. Now it's time to run Kumiko. Just run this command to run the bot: +4. Run the bot - .. code-block:: bash - - sudo docker run -d --env-file .env --name Kumiko no767/kumiko:latest + .. code-block:: bash + + docker run -d --env-file=.env --name Kumiko no767/kumiko:latest -Standalone (Systemd) +Systemd (Standalone) -------------------- **Before you start, ensure that you have PostgreSQL and Redis correctly configured and is running** -1. Clone the repo +1. Ensure that the PostgreSQL extension ``pg_trgm`` and the RedisJSON module are loaded. Refer to the `Redis docs `_ on how to install and load the JSON module. + + .. code-block:: sql + + CREATE EXTENSION IF NOT EXISTS pg_trgm; + +2. Clone the repo .. code-block:: bash git clone https://github.com/No767/Kumiko.git && cd Kumiko - Or if you have the `gh` cli tool installed: + Or if you have the ``gh`` cli tool installed: .. code-block:: bash @@ -76,13 +91,27 @@ Standalone (Systemd) By default, this will clone the dev branch. For stable releases, run ``git checkout master`` to checkout into stable releases (or checkout the latest tag) -2. Set up the prod ENV file. During this step, please also fill your credentials in the ENV file +3. Set up the prod ENV file. During this step, please also fill your credentials in the ENV file .. code-block:: bash cp Envs/prod.env Bot/.env -2. Create an systemd service file. This is an example, and you will need to edit it to point to the correct directory and user. +4. Create an venv so that you can install the dependencies without polluting your system + + .. code-block:: bash + + python3 -m venv ./venv + +5. Activate the venv, install the dependencies, and then deactivate it + + .. code-block:: bash + + source ./venv/bin/activate \ + && pip install -r Requirements/prod.txt \ + && deactivate + +6. Create an systemd service file. This is an example, and you will need to edit it to point to the correct directory and user. .. code-block:: ini @@ -94,7 +123,7 @@ Standalone (Systemd) [Service] Type=simple WorkingDirectory=/your/bots/directory - ExecStart=/usr/bin/python3 /your/bots/directory/Bot/kumikobot.py + ExecStart=/your/bots/directory/venv/bin/python3 /your/bots/directory/Bot/kumikobot.py User=username Restart=on-failure EnvironmentFile=/your/bots/directory/Bot/.env @@ -102,9 +131,9 @@ Standalone (Systemd) [Install] WantedBy=multi-user.target -3. Test whether you have everything set up. If you have ``make`` installed, you can run ``make prod-run`` in order to run the bot. Otherwise, just run ``kumikobot.py`` +7. Test whether you have everything set up. If you have ``make`` installed, you can run ``make prod-run`` in order to run the bot (the ``Makefile`` is found in the root of the repo). Otherwise, just run ``kumikobot.py`` -4. Run and enable the systemd service. +8. Run and enable the systemd service. .. code-block:: bash @@ -113,18 +142,41 @@ Standalone (Systemd) Docker Compose -------------- -1. Download the `.env` file and `docker-compose.yml` file via the `setup.sh` script +1. Clone the repo .. code-block:: bash - curl -s https://raw.githubusercontent.com/No767/Kumiko/master/scripts/setup.sh | sh + git clone https://github.com/No767/Kumiko.git && cd Kumiko + + + Or if you have the ``gh`` cli tool installed: -2. Obtain the API keys, access tokens, discord bot token, and database credentials for Kumiko. Open up the ``.env`` file with an editor like Vim and add the needed values. + .. code-block:: bash -3. Once everything is set, literally just fire up the whole entire Docker Compose stack. All of the database creation, and the seeding of the data will be handled automatically + gh repo clone No767/Kumiko + + .. note:: + + By default, this will clone the dev branch. For stable releases, run ``git checkout master`` to checkout into stable releases (or checkout the latest tag) + +2. Copy the ENV files into the correct places .. code-block:: bash - sudo docker-compose up -d + cp Envs/docker.env .env + +3. Edit the ``.env`` file placed in the root of the repo to include any credentials needed for the bot to run + + .. code-block:: bash + + # THIS IS ONLY AN EXAMPLE + POSTGRES_PASSWORD=... + POSTGRES_USER=... + POSTGRES_URI=postgres://user:somepass@localhost:5432/somedb + +4. Once everything is set, literally just fire up the whole entire Docker Compose stack. All of the database creation, and the migrations will be done automatically. + + .. code-block:: bash + docker-compose up -d diff --git a/Makefile b/Makefile index efaffd9f..d1c3bcd5 100644 --- a/Makefile +++ b/Makefile @@ -9,3 +9,6 @@ dev-setup: run: poetry run python Bot/kumikobot.py + +prod-run: + ./venv/bin/python3 Bot/kumikobot.py \ No newline at end of file diff --git a/Requirements/prod.txt b/Requirements/prod.txt new file mode 100644 index 00000000..010d074c --- /dev/null +++ b/Requirements/prod.txt @@ -0,0 +1,50 @@ +aiodns==3.0.0 ; python_version >= "3.8" and python_version < "4.0" +aiofiles==0.8.0 ; python_version >= "3.8" and python_version < "4.0" +aiohttp==3.8.4 ; python_version >= "3.8" and python_version < "4.0" +aiosignal==1.3.1 ; python_version >= "3.8" and python_version < "4.0" +aiosqlite==0.17.0 ; python_version >= "3.8" and python_version < "4.0" +anyio==3.7.1 ; python_version >= "3.8" and python_version < "4.0" +async-generator==1.10 ; python_version >= "3.8" and python_version < "4.0" +async-timeout==4.0.2 ; python_version >= "3.8" and python_version < "4.0" +asyncio-extras==1.3.2 ; python_version >= "3.8" and python_version < "4.0" +asyncpg-trek==0.3.1 ; python_version >= "3.8" and python_version < "4" +asyncpg==0.28.0 ; python_version >= "3.8" and python_version < "4.0" +asyncpraw==7.7.0 ; python_version >= "3.8" and python_version < "4.0" +asyncprawcore==2.3.0 ; python_version >= "3.8" and python_version < "4.0" +attrs==23.1.0 ; python_version >= "3.8" and python_version < "4.0" +backoff==2.2.1 ; python_version >= "3.8" and python_version < "4.0" +better-ipc==2.0.3 ; python_version >= "3.8" and python_version < "4.0" +brotli==1.0.9 ; python_version >= "3.8" and python_version < "4.0" +certifi==2023.5.7 ; python_version >= "3.8" and python_version < "4.0" +cffi==1.15.1 ; python_version >= "3.8" and python_version < "4.0" +charset-normalizer==3.1.0 ; python_version >= "3.8" and python_version < "4.0" +ciso8601==2.3.0 ; python_version >= "3.8" and python_version < "4.0" +cython==0.29.36 ; python_version >= "3.8" and python_version < "4.0" and sys_platform == "win32" +discord-ext-menus @ git+https://github.com/Rapptz/discord-ext-menus@8686b5d1bbc1d3c862292eb436ab630d6e9c9b53 ; python_version >= "3.8" and python_version < "4.0" +discord-py==2.3.1 ; python_version >= "3.8" and python_version < "4.0" +discord-py[voice]==2.3.1 ; python_version >= "3.8" and python_version < "4.0" +exceptiongroup==1.1.1 ; python_version >= "3.8" and python_version < "3.11" +faust-cchardet==2.1.18 ; python_version >= "3.8" and python_version < "4.0" +frozenlist==1.3.3 ; python_version >= "3.8" and python_version < "4.0" +gql[aiohttp]==3.4.1 ; python_version >= "3.8" and python_version < "4.0" +graphql-core==3.2.3 ; python_version >= "3.8" and python_version < "4" +hiredis==2.2.3 ; python_version >= "3.8" and python_version < "4.0" +idna==3.4 ; python_version >= "3.8" and python_version < "4.0" +lru-dict==1.2.0 ; python_version >= "3.8" and python_version < "4.0" +multidict==6.0.4 ; python_version >= "3.8" and python_version < "4.0" +orjson==3.9.2 ; python_version >= "3.8" and python_version < "4.0" +psutil==5.9.5 ; python_version >= "3.8" and python_version < "4.0" +pycares==4.3.0 ; python_version >= "3.8" and python_version < "4.0" +pycparser==2.21 ; python_version >= "3.8" and python_version < "4.0" +pynacl==1.5.0 ; python_version >= "3.8" and python_version < "4.0" +python-dotenv==1.0.0 ; python_version >= "3.8" and python_version < "4.0" +redis[hiredis]==4.6.0 ; python_version >= "3.8" and python_version < "4.0" +requests==2.31.0 ; python_version >= "3.8" and python_version < "4.0" +sniffio==1.3.0 ; python_version >= "3.8" and python_version < "4.0" +typing-extensions==4.7.0 ; python_version >= "3.8" and python_version < "4.0" +update-checker==0.18.0 ; python_version >= "3.8" and python_version < "4.0" +urllib3==2.0.3 ; python_version >= "3.8" and python_version < "4.0" +uvloop==0.17.0 ; python_version >= "3.8" and python_version < "4.0" and sys_platform != "win32" +websockets==11.0.3 ; python_version >= "3.8" and python_version < "4.0" +winloop==0.0.6 ; python_version >= "3.8" and python_version < "4.0" and sys_platform == "win32" +yarl==1.9.2 ; python_version >= "3.8" and python_version < "4.0" From 4055f97228992cd7801453925e631b046c77a9d1 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Tue, 11 Jul 2023 01:04:38 -0700 Subject: [PATCH 182/184] Purge any old v0.7.x/v0.8.x code and others --- Bot/Libs/economy/__init__.py | 3 -- Bot/Libs/economy/cache_utils.py | 35 ------------ Bot/unloaded_cogs/cogs-ext.py | 36 ------------- Bot/unloaded_cogs/economy.py | 86 ------------------------------ Bot/unloaded_cogs/embeds.py | 42 --------------- Bot/unloaded_cogs/socket-events.py | 22 -------- Docs/api-keys.md | 7 --- Docs/database-setup.md | 15 ------ Docs/dev-prerequisites.md | 59 -------------------- Docs/dev-setup.md | 40 -------------- Docs/getting-dev-discord-bot.md | 37 ------------- changelog.md | 3 ++ docker-compose.yml | 4 +- 13 files changed, 5 insertions(+), 384 deletions(-) delete mode 100644 Bot/Libs/economy/__init__.py delete mode 100644 Bot/Libs/economy/cache_utils.py delete mode 100644 Bot/unloaded_cogs/cogs-ext.py delete mode 100644 Bot/unloaded_cogs/economy.py delete mode 100644 Bot/unloaded_cogs/embeds.py delete mode 100644 Bot/unloaded_cogs/socket-events.py delete mode 100644 Docs/api-keys.md delete mode 100644 Docs/database-setup.md delete mode 100644 Docs/dev-prerequisites.md delete mode 100644 Docs/dev-setup.md delete mode 100644 Docs/getting-dev-discord-bot.md diff --git a/Bot/Libs/economy/__init__.py b/Bot/Libs/economy/__init__.py deleted file mode 100644 index 88b6eedb..00000000 --- a/Bot/Libs/economy/__init__.py +++ /dev/null @@ -1,3 +0,0 @@ -from .cache_utils import getUser - -__all__ = ["getUser"] diff --git a/Bot/Libs/economy/cache_utils.py b/Bot/Libs/economy/cache_utils.py deleted file mode 100644 index 0950e06d..00000000 --- a/Bot/Libs/economy/cache_utils.py +++ /dev/null @@ -1,35 +0,0 @@ -from typing import Dict, Union - -import asyncpg -from redis.asyncio.connection import ConnectionPool - -from ..cache import cacheJson - - -# TODO - Add an join for the items owned -@cacheJson() -async def getUser( - id: int, redis_pool: ConnectionPool, pool: asyncpg.Pool -) -> Union[Dict, None]: - """[Coroutine] Helper coroutine to obtain a user's profile from the database - - For reducing the latency for accessing the data, this helper coroutine is cached on Redis (w/ RedisJSON). - - Args: - id (int): User ID to use to search up the user - redis_pool (ConnectionPool): Redis connection pool to use - pool (asyncpg.Pool): Asyncpg pool - - Returns: - Union[Dict, None]: The user's profile, or None if the user is not found - """ - query = """ - SELECT rank, petals, created_at - FROM eco_user - WHERE id=$1; - """ - async with pool.acquire() as conn: - user = await conn.fetchval(query, id) - if user is None: - return None - return dict(user) diff --git a/Bot/unloaded_cogs/cogs-ext.py b/Bot/unloaded_cogs/cogs-ext.py deleted file mode 100644 index 5780d9e9..00000000 --- a/Bot/unloaded_cogs/cogs-ext.py +++ /dev/null @@ -1,36 +0,0 @@ -from pathlib import Path - -import aiofiles -import discord -from discord import app_commands -from discord.ext import commands -from kumikocore import KumikoCore - - -class CogsExtensions(commands.Cog): - """Utility to add custom cogs for Kumiko""" - - def __init__(self, bot: KumikoCore) -> None: - self.bot = bot - self.session = bot.session - - @commands.hybrid_group(name="cogs-ext", alias=["cext"]) - async def cogsExt(self, ctx: commands.Context) -> None: - if ctx.invoked_subcommand is None: - await ctx.send_help(ctx.command) - - @cogsExt.command(name="add") - @app_commands.describe(cog="The cog to load. Can be from GitHub") - @commands.is_owner() - async def cogsExtAdd(self, ctx: commands.Context, cog: discord.Attachment) -> None: - """Adds and loads the given cog""" - async with self.session.get(cog.url) as r: - writeFile = Path(__file__).parent.joinpath(cog.filename) - async with aiofiles.open(writeFile, "w") as f: - await f.write(await r.text()) - await self.bot.load_extension(f"Cogs.{cog.filename[:-3]}") - await ctx.send("test") - - -async def setup(bot: KumikoCore) -> None: - await bot.add_cog(CogsExtensions(bot)) diff --git a/Bot/unloaded_cogs/economy.py b/Bot/unloaded_cogs/economy.py deleted file mode 100644 index c4a37c88..00000000 --- a/Bot/unloaded_cogs/economy.py +++ /dev/null @@ -1,86 +0,0 @@ -from discord.ext import commands -from discord.utils import format_dt -from kumikocore import KumikoCore -from Libs.economy import getUser -from Libs.ui.economy import RegisterView -from Libs.utils import Embed, parseDatetime -from prisma.models import User # type: ignore - - -class Economy(commands.Cog): - """Earn, sell, and interact with Kumiko's economy!""" - - def __init__(self, bot: KumikoCore) -> None: - self.bot = bot - super().__init__() - - @commands.hybrid_group(name="marketplace") - async def eco(self, ctx: commands.Context) -> None: - if ctx.invoked_subcommand is None: - await ctx.send_help(ctx.command) - - @eco.command(name="buy") - async def marketplaceBuy(self, ctx: commands.Context) -> None: - """Buy an item from the marketplace""" - await ctx.send("Buy") - - @eco.command(name="inventory", aliases=["inv"]) - async def marketplaceInv(self, ctx: commands.Context) -> None: - """View your marketplace inventory""" - currUser = await User.prisma().find_first( - where={"id": ctx.author.id}, include={"user_inv": True} - ) - if currUser is None: - await ctx.send( - embed=Embed( - title="No account!", - description="You don't even have an account yet!", - ) - ) - else: - if len() == 0: # type: ignore - await ctx.send( - embed=Embed( - title="No items!", - description="You don't have any items in your inventory!", - ) - ) - else: - await ctx.send( - embed=Embed(title="Inventory", description="Here are your items!") - ) - - @commands.hybrid_command(name="register") - async def register(self, ctx: commands.Context) -> None: - """Create an account for the economy""" - view = RegisterView() - embed = Embed( - title="Register", - description="Register for the economy! Before you do so, please make sure to follow the TOS. By registering, you are agreeing to use these services.", - ) - await ctx.send(embed=embed, view=view) - - @commands.hybrid_command(name="wallet") - async def wallet(self, ctx: commands.Context) -> None: - """Checks your wallet""" - user = await getUser( - id=ctx.author.id, includes={"user_inv": False, "marketplace": False} - ) # type: ignore - if user is None: - await ctx.send( - embed=Embed( - title="No Wallet", description="You don't have a wallet yet!" - ) - ) - else: - userDesc = f"**Rank**: {user['rank']}\n**Balance**: {user['petals']}\n**Date Joined**: {format_dt(parseDatetime(user['date_joined']))}" # type: ignore - embed = Embed( - title=f"{ctx.author.name}'s Wallet", - description=userDesc, - ) - embed.set_footer(text=f"User ID: {user['id']}") # type: ignore - await ctx.send(embed=embed) - - -async def setup(bot: KumikoCore) -> None: - await bot.add_cog(Economy(bot)) diff --git a/Bot/unloaded_cogs/embeds.py b/Bot/unloaded_cogs/embeds.py deleted file mode 100644 index ccd048cd..00000000 --- a/Bot/unloaded_cogs/embeds.py +++ /dev/null @@ -1,42 +0,0 @@ -import logging - -import discord -from discord.ext import commands -from discord.utils import utcnow -from kumikocore import KumikoCore -from Libs.utils import Embed - - -class EmbedCog(commands.Cog): - """Embed test cog - Please only sync locally""" - - def __init__(self, bot: KumikoCore) -> None: - self.bot = bot - self.logger = logging.getLogger("discord") - - @commands.hybrid_command(name="embed-time") - async def embedTime(self, ctx: commands.Context) -> None: - # await self.bot.change_presence(status=discord.Status.online, activity=discord.Activity(type=discord.ActivityType.watching, name="you")) - await self.bot.change_presence( - status=discord.Status.idle, - activity=discord.Activity(type=discord.ActivityType.watching, name="you"), - ) - # await ctx.send("set status to idle") - embed = Embed() - embed.timestamp = utcnow() - self.logger.info(f"Timestamp: {embed.timestamp}") - embed.set_footer(text=f"{embed.timestamp}") - await ctx.send(embed=embed) - - @commands.hybrid_command(name="embed-user") - async def embedUser(self, ctx: commands.Context) -> None: - - await self.bot.change_presence( - status=discord.Status.idle, - activity=discord.Activity(type=discord.ActivityType.watching, name="you"), - ) - await ctx.send("set status to idle") - - -async def setup(bot: KumikoCore) -> None: - await bot.add_cog(EmbedCog(bot)) diff --git a/Bot/unloaded_cogs/socket-events.py b/Bot/unloaded_cogs/socket-events.py deleted file mode 100644 index 00acbf41..00000000 --- a/Bot/unloaded_cogs/socket-events.py +++ /dev/null @@ -1,22 +0,0 @@ -import discord -from discord.ext import commands -from kumikocore import KumikoCore -from prisma.models import Guild # type: ignore - - -class SocketEvents(commands.Cog): - """Cog for handling socket events from Discord""" - - def __init__(self, bot: KumikoCore) -> None: - self.bot = bot - - @commands.Cog.listener(name="on_guild_join") - async def serverInit(guild: discord.Guild) -> None: # type: ignore - """Initializes the server in the database""" - findGuild = await Guild.prisma().find_unique(where={"id": guild.id}) - if findGuild is None: - await Guild.prisma().create({"id": guild.id}) - - -async def setup(bot: KumikoCore) -> None: - await bot.add_cog(SocketEvents(bot)) diff --git a/Docs/api-keys.md b/Docs/api-keys.md deleted file mode 100644 index c3d0db32..00000000 --- a/Docs/api-keys.md +++ /dev/null @@ -1,7 +0,0 @@ -## API Keys - -Kumiko is built on top of Rin, and Kumiko requires some API keys. Here's a list of current services that require API keys: - -- [GitHub](https://docs.github.com/en/rest/guides/basics-of-authentication) -- [Reddit](https://www.reddit.com/prefs/apps) (Get both the ID and Secret) -- [Tenor](https://developers.google.com/tenor/guides/quickstart#setup) \ No newline at end of file diff --git a/Docs/database-setup.md b/Docs/database-setup.md deleted file mode 100644 index c6259083..00000000 --- a/Docs/database-setup.md +++ /dev/null @@ -1,15 +0,0 @@ -# Database Setup - -Kumiko requires PostgreSQL, and Redis to get started. - -## Setting up the `.env` files - -There are two `.env` files that should be found in your project. One is in the `Bot` directory, and the other is in the root directory of the repo. But they aren't named `.env`. So when you run the `dev-setup` command in make, this will rename the dev env file to `.env`, and is found under `Bot/.env`. The other one should remain in the root directory of the repo. Rename `.env-docker-example` to `.env`. Once you set up the credentials within `Bot/.env`, make sure to copy the values to `.env` in the root directory of the repo. **Do not directly copy and paste the contents of `Bot/.env` into to the one in the root of the repo.** - -## Migration - -There is one last thing that needs to be done. And that is to migrate the data. Run the following command in order to do so: - -```sh -prisma db push -``` diff --git a/Docs/dev-prerequisites.md b/Docs/dev-prerequisites.md deleted file mode 100644 index 2228345f..00000000 --- a/Docs/dev-prerequisites.md +++ /dev/null @@ -1,59 +0,0 @@ -# Dev Prerequisites - -## Software Prerequisites - -Before you get started, please ensure you have the following installed: - -- [Git](https://git-scm.com/) -- [Python 3](https://www.python.org/) (Python 3.11 is what the codebase uses) -- [Poetry](https://python-poetry.org/) -- [Pyenv](https://github.com/pyenv/pyenv) (Optional, Recommended) -- [WSL2](https://docs.microsoft.com/en-us/windows/wsl/) (If working on Windows) -- [Docker](https://www.docker.com/) (Use [Docker Engine](https://docs.docker.com/engine/) on Linux, [Docker Desktop](https://www.docker.com/products/docker-desktop/) on Windows/WSL2, MacOS and Linux (beta)) -- Discord Account + Discord App - -> **Note** -> Kumiko is natively developed for Linux. If you are using Windows, please use WSL2. - -## Package Prerequisites - -### Debian/Ubuntu - -```sh -sudo apt-get install libffi-dev python3-dev libnacl-dev libopus-dev libopus0 libopusenc-dev build-essentials \ -libssl-dev curl wget git -``` - -### RHEL/CentOS/Fedora 22 or below - -```sh -sudo yum install make gcc libffi-devel python-devel \ -openssl-devel opus-devel opus curl wget git -``` - -### Fedora 23+ - -```sh -sudo dnf install make automake gcc gcc-c++ kernel-devel \ -libffi-devel python3-libnacl python3.11-devel openssl11-devel \ -openssl-devel opus opus-devel curl wget git -``` - -### OpenSUSE - -```sh -sudo zypper install gcc make automake openssl-devel openssl-1_1 \ -libffi-devel python311-devel python311-libnacl opus libopus0 wget git curl -``` - -### Arch - -```sh -sudo pacman -S --needed base-devel openssl openssl-1.1 libffi python python-libnacl opus -``` - -### MacOS - -```sh -brew install openssl openssl@1.1 libffi git curl make opus -``` \ No newline at end of file diff --git a/Docs/dev-setup.md b/Docs/dev-setup.md deleted file mode 100644 index 464d0d71..00000000 --- a/Docs/dev-setup.md +++ /dev/null @@ -1,40 +0,0 @@ -# Development Setup - -## Local - -1. Fork and clone the repo - - ```sh - git clone https://github.com/[username]/Kumiko.git && cd Kumiko - ``` - - Or if you have the `gh` cli tool installed: - - ```sh - gh repo clone [username]/Kumiko - ``` - -2. Install all of the dependencies (including dev dependencies) - - ```sh - poetry install --with=dev,test - ``` - -3. Start the Docker Compose stack - - ```sh - sudo docker compose -f docker-compose-dev.yml up -d - ``` - -4. Run the database migrations - - ```sh - poetry run prisma db push - ``` - -## Vagrant - -Kumiko also supports using Vagrant as a development environment. In order to use Vagrant, you will need Oracle VirtualBox or VMWare Workstation installed on your machine. Once installed and properly configured, you can just run `vagrant up` to provision and start it up, and connect to it by SSH or by VSCode. - -## Environment Variables -Kumiko v0.7+ includes an development mode feature, which will set up jishaku and a custom FS watcher. Later on, there may be more development features that will be included. Make sure you first install the dev dependencies first! And in order to enable it, set an environment variable called `DEV_MODE` to `True`. \ No newline at end of file diff --git a/Docs/getting-dev-discord-bot.md b/Docs/getting-dev-discord-bot.md deleted file mode 100644 index e0864b87..00000000 --- a/Docs/getting-dev-discord-bot.md +++ /dev/null @@ -1,37 +0,0 @@ -# Getting the Discord Bot - -First things first, you'll more than likely need a dev bot to run Kumiko. Luckily you'll find the steps below to help you on that - -1. Create the app that will be needed for the bot. Once done, you should see the page as shown above - - ![images](../assets/getting-started-assets/create-app.png) - - -2. Now head done to the bot section, and click on the button that says "Add Bot". - - ![yesyes](../assets/getting-started-assets/create-bot.png) - -3. You'll see a pop-up that asks you if you want to create the bot. - - ![ewom](../assets/getting-started-assets/allow-bot.png) - -4. Make sure to have all 3 of the buttons enabled. Kumiko will need all 3 of them to work. - - ![intents](../assets/getting-started-assets/allow-intents.png) - - -5. You'll see a page just like the one above. We'll need access the the token for the bot, and the only way to do it is to reset the token. - - ![whyyy](../assets/getting-started-assets/reset-token.png) - -6. Allow for the token to be reset. Note that if your account is hooked up with 2FA, it will ask you to enter your 2FA code. Go to your authenticator app and enter the code from the app. - - ![confirm](../assets/getting-started-assets/allow-reset-token.png) - - -7. Now click on the copy button and copy the token - - ![copytoken](../assets/getting-started-assets/copy-token.png) - - -8. Now save this token in `Bot/.env`. Save it in a variable named `DEV_BOT_TOKEN` diff --git a/changelog.md b/changelog.md index 0dd709d1..5f67bf67 100644 --- a/changelog.md +++ b/changelog.md @@ -40,6 +40,7 @@ For the full list of changes, please see them here: [`v0.8.x...v0.9.0`](https:// - Ensure that the migration runner always runs first - Change stop signal from `SIGTERM` to `SIGINT` for Docker - Build the Docker image locally for Kumiko's Postgres server +- Redirect users to the Dev Contributing Guide (located in the docs) within `contributing.md` ## ✨ Additions @@ -64,6 +65,8 @@ For the full list of changes, please see them here: [`v0.8.x...v0.9.0`](https:// - Old economy packages - cog-ext module - Prisma along with other unused libs +- Any old v0.8.x Prisma code +- Old "Docs" # ⬆️ Dependabot Updates - \[pip](deps-dev)\: Bump pre-commit from 3.2.1 to 3.2.2 (#300) (@dependabot) diff --git a/docker-compose.yml b/docker-compose.yml index 4c354fbd..a18b06fc 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -6,7 +6,7 @@ services: image: kumiko-postgres:prod-latest build: context: ./Docker/pg - dockerfile: ./Docker/pg/Dockerfile + dockerfile: Dockerfile env_file: - .env volumes: @@ -22,7 +22,7 @@ services: kumiko: container_name: Kumiko - image: no767/kumiko:latest + image: no767/kumiko:edge command: sh -c '/Kumiko/wait-for postgres:5432 -- echo "[Wait-for] PostgreSQL is fully up. Waiting for Redis" && /Kumiko/wait-for redis:6379 -- echo "[Wait-for] Both PostgreSQL and Redis are fully ready. Starting up Kumiko" && /Kumiko/start.sh' env_file: - .env From 37724dfbfbb34be9c93e74c7d9efb5f74b0a70c9 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Tue, 11 Jul 2023 01:14:11 -0700 Subject: [PATCH 183/184] It's go time --- Bot/Cogs/dev-tools.py | 2 +- Bot/kumikobot.py | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/Bot/Cogs/dev-tools.py b/Bot/Cogs/dev-tools.py index d1c051cb..fc1d1076 100644 --- a/Bot/Cogs/dev-tools.py +++ b/Bot/Cogs/dev-tools.py @@ -7,7 +7,7 @@ from kumikocore import KumikoCore -class DevTools(commands.Cog): +class DevTools(commands.Cog, command_attrs=dict(hidden=True)): """Tools for developing Kumiko""" def __init__(self, bot: KumikoCore): diff --git a/Bot/kumikobot.py b/Bot/kumikobot.py index 005f38b6..aaacd4fd 100644 --- a/Bot/kumikobot.py +++ b/Bot/kumikobot.py @@ -24,7 +24,7 @@ load_dotenv() -KUMIKO_TOKEN = os.environ["DEV_BOT_TOKEN"] +KUMIKO_TOKEN = os.environ["KUMIKO_TOKEN"] DEV_MODE = os.getenv("DEV_MODE") in ("True", "TRUE") POSTGRES_URI = os.environ["POSTGRES_URI"] REDIS_URI = os.environ["REDIS_URI"] From bd5a09492964c0b195025e6aaa9259cb35436c23 Mon Sep 17 00:00:00 2001 From: Noelle <73260931+No767@users.noreply.github.com> Date: Tue, 11 Jul 2023 01:17:18 -0700 Subject: [PATCH 184/184] [skip ci] Bump Black from v23.3.0 to v23.6.0 --- .pre-commit-config.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index a45f5427..b61cebed 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -23,7 +23,7 @@ repos: # description: "Format with AutoPEP8" - repo: https://github.com/psf/black - rev: 22.3.0 + rev: 22.6.0 hooks: - id: black name: Black

    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�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 literal 0 HcmV?d00001 diff --git a/assets/logos/kumiko_possible_rounded.png b/assets/logos/kumiko_possible_rounded.png new file mode 100644 index 0000000000000000000000000000000000000000..04b0c1d3ea96fe07d4c51022be047c33ff4a3a41 GIT binary patch literal 370590 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�U=~Kt> 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�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