From 93097a654ae368c4627480a7cddf63d9444d2247 Mon Sep 17 00:00:00 2001 From: rafsaf Date: Sat, 4 Feb 2023 22:44:02 +0100 Subject: [PATCH 1/3] removed template fastapi users, moved main template to root cookiecutter folder, updated cookiecutter options and readme --- README.md | 68 +- cookiecutter.json | 3 +- hooks/post_gen_project.py | 26 - tests/create_fastapi_users_project.py | 24 - tests/create_minimal_project.py | 1 - .../{template_minimal => }/Dockerfile | 0 .../{template_minimal => }/alembic.ini | 0 .../alembic/README | 0 .../{template_minimal => }/alembic/env.py | 0 .../alembic/script.py.mako | 0 ...2022050745_init_user_model_d1252175c146.py | 0 .../app/__init__.py | 0 .../app/api/__init__.py | 0 .../{template_minimal => }/app/api/api.py | 0 .../{template_minimal => }/app/api/deps.py | 0 .../app/api/endpoints/__init__.py | 0 .../app/api/endpoints/auth.py | 0 .../app/api/endpoints/users.py | 0 .../app/conftest.py | 0 .../app/core/__init__.py | 0 .../{template_minimal => }/app/core/config.py | 0 .../app/core/security.py | 0 .../app/core/session.py | 0 .../app/initial_data.py | 0 .../{template_minimal => }/app/main.py | 0 .../{template_minimal => }/app/models.py | 0 .../app/tests => app/schemas}/__init__.py | 0 .../app/schemas/requests.py | 0 .../app/schemas/responses.py | 0 .../app => app/tests}/__init__.py | 0 .../app/tests/conftest.py | 0 .../app/tests/test_auth.py | 0 .../app/tests/test_users.py | 0 .../docker-compose.dev.yml | 0 .../{template_minimal => }/docker-compose.yml | 0 .../{template_fastapi_users => }/init.sh | 0 .../nginx-unit-config.json | 0 .../{template_minimal => }/poetry.lock | 0 .../{template_fastapi_users => }/pre-push.sh | 0 .../{template_minimal => }/pyproject.toml | 0 .../requirements-dev.txt | 0 .../{template_minimal => }/requirements.txt | 0 .../template_fastapi_users/.env.example | 19 - .../template_fastapi_users/.env.template | 19 - .../template_fastapi_users/.flake8 | 11 - .../template_fastapi_users/.gitignore | 136 -- .../template_fastapi_users/Dockerfile | 29 - .../template_fastapi_users/alembic.ini | 100 -- .../template_fastapi_users/alembic/env.py | 96 -- ...itial_fastapi_users_model__57b460a916d4.py | 39 - .../template_fastapi_users/app/api/api.py | 31 - .../template_fastapi_users/app/api/deps.py | 42 - .../template_fastapi_users/app/core/config.py | 98 -- .../app/core/security.py | 64 - .../app/initial_data.py | 50 - .../template_fastapi_users/app/main.py | 29 - .../template_fastapi_users/app/models.py | 16 - .../app/schemas/__init__.py | 1 - .../app/schemas/user.py | 42 - .../template_fastapi_users/app/session.py | 12 - .../app/tests/conftest.py | 63 - .../app/tests/test_auth.py | 36 - .../template_fastapi_users/app/tests/utils.py | 36 - .../template_fastapi_users/docker-compose.yml | 36 - .../nginx-unit-config.json | 17 - .../template_fastapi_users/poetry.lock | 1305 ----------------- .../template_fastapi_users/pyproject.toml | 41 - .../requirements-dev.txt | 61 - .../template_fastapi_users/requirements.txt | 26 - .../template_minimal/.env.example | 21 - .../template_minimal/.env.template | 21 - .../template_minimal/.flake8 | 11 - .../template_minimal/.gitignore | 136 -- .../template_minimal/alembic/README | 1 - .../template_minimal/alembic/script.py.mako | 24 - .../template_minimal/app/api/__init__.py | 0 .../app/api/endpoints/__init__.py | 0 .../template_minimal/app/conftest.py | 11 - .../template_minimal/app/core/__init__.py | 0 .../template_minimal/app/schemas/__init__.py | 0 .../template_minimal/app/tests/__init__.py | 0 .../template_minimal/init.sh | 7 - .../template_minimal/pre-push.sh | 16 - 83 files changed, 36 insertions(+), 2789 deletions(-) delete mode 100644 tests/create_fastapi_users_project.py rename {{cookiecutter.project_name}}/{template_minimal => }/Dockerfile (100%) rename {{cookiecutter.project_name}}/{template_minimal => }/alembic.ini (100%) rename {{cookiecutter.project_name}}/{template_fastapi_users => }/alembic/README (100%) rename {{cookiecutter.project_name}}/{template_minimal => }/alembic/env.py (100%) rename {{cookiecutter.project_name}}/{template_fastapi_users => }/alembic/script.py.mako (100%) rename {{cookiecutter.project_name}}/{template_minimal => }/alembic/versions/2022050745_init_user_model_d1252175c146.py (100%) rename {{cookiecutter.project_name}}/{template_fastapi_users => }/app/__init__.py (100%) rename {{cookiecutter.project_name}}/{template_fastapi_users => }/app/api/__init__.py (100%) rename {{cookiecutter.project_name}}/{template_minimal => }/app/api/api.py (100%) rename {{cookiecutter.project_name}}/{template_minimal => }/app/api/deps.py (100%) rename {{cookiecutter.project_name}}/{template_fastapi_users => }/app/api/endpoints/__init__.py (100%) rename {{cookiecutter.project_name}}/{template_minimal => }/app/api/endpoints/auth.py (100%) rename {{cookiecutter.project_name}}/{template_minimal => }/app/api/endpoints/users.py (100%) rename {{cookiecutter.project_name}}/{template_fastapi_users => }/app/conftest.py (100%) rename {{cookiecutter.project_name}}/{template_fastapi_users => }/app/core/__init__.py (100%) rename {{cookiecutter.project_name}}/{template_minimal => }/app/core/config.py (100%) rename {{cookiecutter.project_name}}/{template_minimal => }/app/core/security.py (100%) rename {{cookiecutter.project_name}}/{template_minimal => }/app/core/session.py (100%) rename {{cookiecutter.project_name}}/{template_minimal => }/app/initial_data.py (100%) rename {{cookiecutter.project_name}}/{template_minimal => }/app/main.py (100%) rename {{cookiecutter.project_name}}/{template_minimal => }/app/models.py (100%) rename {{cookiecutter.project_name}}/{template_fastapi_users/app/tests => app/schemas}/__init__.py (100%) rename {{cookiecutter.project_name}}/{template_minimal => }/app/schemas/requests.py (100%) rename {{cookiecutter.project_name}}/{template_minimal => }/app/schemas/responses.py (100%) rename {{cookiecutter.project_name}}/{template_minimal/app => app/tests}/__init__.py (100%) rename {{cookiecutter.project_name}}/{template_minimal => }/app/tests/conftest.py (100%) rename {{cookiecutter.project_name}}/{template_minimal => }/app/tests/test_auth.py (100%) rename {{cookiecutter.project_name}}/{template_minimal => }/app/tests/test_users.py (100%) rename {{cookiecutter.project_name}}/{template_minimal => }/docker-compose.dev.yml (100%) rename {{cookiecutter.project_name}}/{template_minimal => }/docker-compose.yml (100%) rename {{cookiecutter.project_name}}/{template_fastapi_users => }/init.sh (100%) rename {{cookiecutter.project_name}}/{template_minimal => }/nginx-unit-config.json (100%) rename {{cookiecutter.project_name}}/{template_minimal => }/poetry.lock (100%) rename {{cookiecutter.project_name}}/{template_fastapi_users => }/pre-push.sh (100%) rename {{cookiecutter.project_name}}/{template_minimal => }/pyproject.toml (100%) rename {{cookiecutter.project_name}}/{template_minimal => }/requirements-dev.txt (100%) rename {{cookiecutter.project_name}}/{template_minimal => }/requirements.txt (100%) delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/.env.example delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/.env.template delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/.flake8 delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/.gitignore delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/Dockerfile delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/alembic.ini delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/alembic/env.py delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/alembic/versions/2022_01_09_1952_initial_fastapi_users_model__57b460a916d4.py delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/app/api/api.py delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/app/api/deps.py delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/app/core/config.py delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/app/core/security.py delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/app/initial_data.py delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/app/main.py delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/app/models.py delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/app/schemas/__init__.py delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/app/schemas/user.py delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/app/session.py delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/app/tests/conftest.py delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/app/tests/test_auth.py delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/app/tests/utils.py delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/docker-compose.yml delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/nginx-unit-config.json delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/poetry.lock delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/pyproject.toml delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/requirements-dev.txt delete mode 100644 {{cookiecutter.project_name}}/template_fastapi_users/requirements.txt delete mode 100644 {{cookiecutter.project_name}}/template_minimal/.env.example delete mode 100644 {{cookiecutter.project_name}}/template_minimal/.env.template delete mode 100644 {{cookiecutter.project_name}}/template_minimal/.flake8 delete mode 100644 {{cookiecutter.project_name}}/template_minimal/.gitignore delete mode 100644 {{cookiecutter.project_name}}/template_minimal/alembic/README delete mode 100644 {{cookiecutter.project_name}}/template_minimal/alembic/script.py.mako delete mode 100644 {{cookiecutter.project_name}}/template_minimal/app/api/__init__.py delete mode 100644 {{cookiecutter.project_name}}/template_minimal/app/api/endpoints/__init__.py delete mode 100644 {{cookiecutter.project_name}}/template_minimal/app/conftest.py delete mode 100644 {{cookiecutter.project_name}}/template_minimal/app/core/__init__.py delete mode 100644 {{cookiecutter.project_name}}/template_minimal/app/schemas/__init__.py delete mode 100644 {{cookiecutter.project_name}}/template_minimal/app/tests/__init__.py delete mode 100644 {{cookiecutter.project_name}}/template_minimal/init.sh delete mode 100644 {{cookiecutter.project_name}}/template_minimal/pre-push.sh diff --git a/README.md b/README.md index 1e5cf14..142fee5 100644 --- a/README.md +++ b/README.md @@ -54,20 +54,18 @@ _Check out also online example: https://minimal-fastapi-postgres-template.rafsaf ## Quickstart - ### 1. Install cookiecutter globally and cookiecutter this project + ```bash pip install cookiecutter # And cookiecutter this project :) cookiecutter https://github.com/rafsaf/minimal-fastapi-postgres-template -# if you want experimental fastapi-users template -# check "experimental_fastapi_users_template" -# to True in cookiecutter option ``` ### 2. Install dependecies with poetry or without it + ```bash cd project_name ### Poetry install (python3.10) @@ -78,9 +76,11 @@ python3.10 -m venv venv source venv/bin/activate pip install -r requirements-dev.txt ``` + Note, be sure to use `python3.10` with this template with either poetry or standard venv & pip, if you need to stick to some earlier python version, you should adapt it yourself (remove python3.10+ specific syntax for example `str | int`) ### 3. Setup databases + ```bash ### Setup two databases docker-compose up -d @@ -88,14 +88,16 @@ docker-compose up -d ### Alembic migrations upgrade and initial_data.py script bash init.sh ``` + ### 4. Now you can run app + ```bash ### And this is it: uvicorn app.main:app --reload ``` -You should then use `git init` to initialize git repository and access OpenAPI spec at http://localhost:8000/ by default. To customize docs url, cors and allowed hosts settings, read section about it. +You should then use `git init` to initialize git repository and access OpenAPI spec at http://localhost:8000/ by default. To customize docs url, cors and allowed hosts settings, read section about it. ### Running tests @@ -388,36 +390,36 @@ There are some **opinionated** default settings in `/app/main.py` for documentat 1. Docs - ```python - app = FastAPI( - title=config.settings.PROJECT_NAME, - version=config.settings.VERSION, - description=config.settings.DESCRIPTION, - openapi_url="/openapi.json", - docs_url="/", - ) - ``` - Docs page is simpy `/` (by default in FastAPI it is `/docs`). Title, version and description are taken directly from `config` and then directly from `pyproject.toml` file. You can change it completely for the project, remove or use environment variables `PROJECT_NAME`, `VERSION`, `DESCRIPTION`. - -2. CORS - - ```python - app.add_middleware( - CORSMiddleware, - allow_origins=[str(origin) for origin in config.settings.BACKEND_CORS_ORIGINS], - allow_credentials=True, - allow_methods=["*"], - allow_headers=["*"], - ) - ``` + ```python + app = FastAPI( + title=config.settings.PROJECT_NAME, + version=config.settings.VERSION, + description=config.settings.DESCRIPTION, + openapi_url="/openapi.json", + docs_url="/", + ) + ``` - If you are not sure what are CORS for, follow https://developer.mozilla.org/en-US/docs/Web/HTTP/CORS. React and most frontend frameworks nowadays operate on `localhost:3000` thats why it's included in `BACKEND_CORS_ORIGINS` in .env file, before going production be sure to include and frontend domain here, like `my-fontend-app.example.com` + Docs page is simpy `/` (by default in FastAPI it is `/docs`). Title, version and description are taken directly from `config` and then directly from `pyproject.toml` file. You can change it completely for the project, remove or use environment variables `PROJECT_NAME`, `VERSION`, `DESCRIPTION`. -3. Allowed Hosts +2. CORS - ```python - app.add_middleware(TrustedHostMiddleware, allowed_hosts=config.settings.ALLOWED_HOSTS) - ``` + ```python + app.add_middleware( + CORSMiddleware, + allow_origins=[str(origin) for origin in config.settings.BACKEND_CORS_ORIGINS], + allow_credentials=True, + allow_methods=["*"], + allow_headers=["*"], + ) + ``` + + If you are not sure what are CORS for, follow https://developer.mozilla.org/en-US/docs/Web/HTTP/CORS. React and most frontend frameworks nowadays operate on `localhost:3000` thats why it's included in `BACKEND_CORS_ORIGINS` in .env file, before going production be sure to include and frontend domain here, like `my-fontend-app.example.com` + +3. Allowed Hosts - Prevents HTTP Host Headers attack, you shoud put here you server IP or (preferably) full domain under it's accessible like `example.com`. By default in .env there are two most popular records: `ALLOWED_HOSTS=["localhost", "127.0.0.1"]` + ```python + app.add_middleware(TrustedHostMiddleware, allowed_hosts=config.settings.ALLOWED_HOSTS) + ``` + Prevents HTTP Host Headers attack, you shoud put here you server IP or (preferably) full domain under it's accessible like `example.com`. By default in .env there are two most popular records: `ALLOWED_HOSTS=["localhost", "127.0.0.1"]` diff --git a/cookiecutter.json b/cookiecutter.json index 5782100..866dd9b 100644 --- a/cookiecutter.json +++ b/cookiecutter.json @@ -1,4 +1,3 @@ { - "project_name": "my_project_name", - "experimental_fastapi_users_template": false + "project_name": "my_project_name" } diff --git a/hooks/post_gen_project.py b/hooks/post_gen_project.py index d49ef24..268613a 100644 --- a/hooks/post_gen_project.py +++ b/hooks/post_gen_project.py @@ -1,26 +1,10 @@ """ -Copy template choosen from TEMPLATES to main folder. - Copy content from env template (autogenerated passwords etc) to .env which is gitignored, then remove template env file as it is redundant. """ from pathlib import Path -from shutil import copytree, rmtree PROJECT_NAME = "{{ cookiecutter.project_name }}" -USE_FASTAPI_USERS = "{{ cookiecutter.experimental_fastapi_users_template }}" -TEMPLATES = ["template_fastapi_users", "template_minimal"] - - -def copy_choosen_template_to_main_dir(used_template: str): - if used_template not in TEMPLATES: - raise ValueError(f"{used_template} not in {TEMPLATES}") - - copytree(used_template, "./", dirs_exist_ok=True) - - for template in TEMPLATES: - rmtree(Path(template)) - def create_env_file_and_remove_env_template(): env_template_file = Path(".env.template") @@ -31,14 +15,4 @@ def create_env_file_and_remove_env_template(): if __name__ == "__main__": - truthy = ["T", "t", "true", "True", 1] - falsy = ["F", "f", "false", "False", 0] - if USE_FASTAPI_USERS in truthy: - used_template = "template_fastapi_users" - elif USE_FASTAPI_USERS in falsy: - used_template = "template_minimal" - else: - raise ValueError(f"'experimental_fastapi_users_template' param must be in {truthy + falsy}") - - copy_choosen_template_to_main_dir(used_template=used_template) create_env_file_and_remove_env_template() diff --git a/tests/create_fastapi_users_project.py b/tests/create_fastapi_users_project.py deleted file mode 100644 index b7640ec..0000000 --- a/tests/create_fastapi_users_project.py +++ /dev/null @@ -1,24 +0,0 @@ -""" -Creates fastapi_users template project in root folder with default values -""" - -from pathlib import Path - -from cookiecutter.main import cookiecutter - -ROOT_FOLDER = Path(__file__).parent.parent - - -def main(): - cookiecutter( - template=str(ROOT_FOLDER), - no_input=True, - extra_context={ - "project_name": "fastapi_users_project", - "experimental_fastapi_users_template": True, - }, - ) - - -if __name__ == "__main__": - main() diff --git a/tests/create_minimal_project.py b/tests/create_minimal_project.py index 52b8e29..b3697e8 100644 --- a/tests/create_minimal_project.py +++ b/tests/create_minimal_project.py @@ -15,7 +15,6 @@ def main(): no_input=True, extra_context={ "project_name": "minimal_project", - "experimental_fastapi_users_template": False, }, ) diff --git a/{{cookiecutter.project_name}}/template_minimal/Dockerfile b/{{cookiecutter.project_name}}/Dockerfile similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/Dockerfile rename to {{cookiecutter.project_name}}/Dockerfile diff --git a/{{cookiecutter.project_name}}/template_minimal/alembic.ini b/{{cookiecutter.project_name}}/alembic.ini similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/alembic.ini rename to {{cookiecutter.project_name}}/alembic.ini diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/alembic/README b/{{cookiecutter.project_name}}/alembic/README similarity index 100% rename from {{cookiecutter.project_name}}/template_fastapi_users/alembic/README rename to {{cookiecutter.project_name}}/alembic/README diff --git a/{{cookiecutter.project_name}}/template_minimal/alembic/env.py b/{{cookiecutter.project_name}}/alembic/env.py similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/alembic/env.py rename to {{cookiecutter.project_name}}/alembic/env.py diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/alembic/script.py.mako b/{{cookiecutter.project_name}}/alembic/script.py.mako similarity index 100% rename from {{cookiecutter.project_name}}/template_fastapi_users/alembic/script.py.mako rename to {{cookiecutter.project_name}}/alembic/script.py.mako diff --git a/{{cookiecutter.project_name}}/template_minimal/alembic/versions/2022050745_init_user_model_d1252175c146.py b/{{cookiecutter.project_name}}/alembic/versions/2022050745_init_user_model_d1252175c146.py similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/alembic/versions/2022050745_init_user_model_d1252175c146.py rename to {{cookiecutter.project_name}}/alembic/versions/2022050745_init_user_model_d1252175c146.py diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/app/__init__.py b/{{cookiecutter.project_name}}/app/__init__.py similarity index 100% rename from {{cookiecutter.project_name}}/template_fastapi_users/app/__init__.py rename to {{cookiecutter.project_name}}/app/__init__.py diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/app/api/__init__.py b/{{cookiecutter.project_name}}/app/api/__init__.py similarity index 100% rename from {{cookiecutter.project_name}}/template_fastapi_users/app/api/__init__.py rename to {{cookiecutter.project_name}}/app/api/__init__.py diff --git a/{{cookiecutter.project_name}}/template_minimal/app/api/api.py b/{{cookiecutter.project_name}}/app/api/api.py similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/app/api/api.py rename to {{cookiecutter.project_name}}/app/api/api.py diff --git a/{{cookiecutter.project_name}}/template_minimal/app/api/deps.py b/{{cookiecutter.project_name}}/app/api/deps.py similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/app/api/deps.py rename to {{cookiecutter.project_name}}/app/api/deps.py diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/app/api/endpoints/__init__.py b/{{cookiecutter.project_name}}/app/api/endpoints/__init__.py similarity index 100% rename from {{cookiecutter.project_name}}/template_fastapi_users/app/api/endpoints/__init__.py rename to {{cookiecutter.project_name}}/app/api/endpoints/__init__.py diff --git a/{{cookiecutter.project_name}}/template_minimal/app/api/endpoints/auth.py b/{{cookiecutter.project_name}}/app/api/endpoints/auth.py similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/app/api/endpoints/auth.py rename to {{cookiecutter.project_name}}/app/api/endpoints/auth.py diff --git a/{{cookiecutter.project_name}}/template_minimal/app/api/endpoints/users.py b/{{cookiecutter.project_name}}/app/api/endpoints/users.py similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/app/api/endpoints/users.py rename to {{cookiecutter.project_name}}/app/api/endpoints/users.py diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/app/conftest.py b/{{cookiecutter.project_name}}/app/conftest.py similarity index 100% rename from {{cookiecutter.project_name}}/template_fastapi_users/app/conftest.py rename to {{cookiecutter.project_name}}/app/conftest.py diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/app/core/__init__.py b/{{cookiecutter.project_name}}/app/core/__init__.py similarity index 100% rename from {{cookiecutter.project_name}}/template_fastapi_users/app/core/__init__.py rename to {{cookiecutter.project_name}}/app/core/__init__.py diff --git a/{{cookiecutter.project_name}}/template_minimal/app/core/config.py b/{{cookiecutter.project_name}}/app/core/config.py similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/app/core/config.py rename to {{cookiecutter.project_name}}/app/core/config.py diff --git a/{{cookiecutter.project_name}}/template_minimal/app/core/security.py b/{{cookiecutter.project_name}}/app/core/security.py similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/app/core/security.py rename to {{cookiecutter.project_name}}/app/core/security.py diff --git a/{{cookiecutter.project_name}}/template_minimal/app/core/session.py b/{{cookiecutter.project_name}}/app/core/session.py similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/app/core/session.py rename to {{cookiecutter.project_name}}/app/core/session.py diff --git a/{{cookiecutter.project_name}}/template_minimal/app/initial_data.py b/{{cookiecutter.project_name}}/app/initial_data.py similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/app/initial_data.py rename to {{cookiecutter.project_name}}/app/initial_data.py diff --git a/{{cookiecutter.project_name}}/template_minimal/app/main.py b/{{cookiecutter.project_name}}/app/main.py similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/app/main.py rename to {{cookiecutter.project_name}}/app/main.py diff --git a/{{cookiecutter.project_name}}/template_minimal/app/models.py b/{{cookiecutter.project_name}}/app/models.py similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/app/models.py rename to {{cookiecutter.project_name}}/app/models.py diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/app/tests/__init__.py b/{{cookiecutter.project_name}}/app/schemas/__init__.py similarity index 100% rename from {{cookiecutter.project_name}}/template_fastapi_users/app/tests/__init__.py rename to {{cookiecutter.project_name}}/app/schemas/__init__.py diff --git a/{{cookiecutter.project_name}}/template_minimal/app/schemas/requests.py b/{{cookiecutter.project_name}}/app/schemas/requests.py similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/app/schemas/requests.py rename to {{cookiecutter.project_name}}/app/schemas/requests.py diff --git a/{{cookiecutter.project_name}}/template_minimal/app/schemas/responses.py b/{{cookiecutter.project_name}}/app/schemas/responses.py similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/app/schemas/responses.py rename to {{cookiecutter.project_name}}/app/schemas/responses.py diff --git a/{{cookiecutter.project_name}}/template_minimal/app/__init__.py b/{{cookiecutter.project_name}}/app/tests/__init__.py similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/app/__init__.py rename to {{cookiecutter.project_name}}/app/tests/__init__.py diff --git a/{{cookiecutter.project_name}}/template_minimal/app/tests/conftest.py b/{{cookiecutter.project_name}}/app/tests/conftest.py similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/app/tests/conftest.py rename to {{cookiecutter.project_name}}/app/tests/conftest.py diff --git a/{{cookiecutter.project_name}}/template_minimal/app/tests/test_auth.py b/{{cookiecutter.project_name}}/app/tests/test_auth.py similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/app/tests/test_auth.py rename to {{cookiecutter.project_name}}/app/tests/test_auth.py diff --git a/{{cookiecutter.project_name}}/template_minimal/app/tests/test_users.py b/{{cookiecutter.project_name}}/app/tests/test_users.py similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/app/tests/test_users.py rename to {{cookiecutter.project_name}}/app/tests/test_users.py diff --git a/{{cookiecutter.project_name}}/template_minimal/docker-compose.dev.yml b/{{cookiecutter.project_name}}/docker-compose.dev.yml similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/docker-compose.dev.yml rename to {{cookiecutter.project_name}}/docker-compose.dev.yml diff --git a/{{cookiecutter.project_name}}/template_minimal/docker-compose.yml b/{{cookiecutter.project_name}}/docker-compose.yml similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/docker-compose.yml rename to {{cookiecutter.project_name}}/docker-compose.yml diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/init.sh b/{{cookiecutter.project_name}}/init.sh similarity index 100% rename from {{cookiecutter.project_name}}/template_fastapi_users/init.sh rename to {{cookiecutter.project_name}}/init.sh diff --git a/{{cookiecutter.project_name}}/template_minimal/nginx-unit-config.json b/{{cookiecutter.project_name}}/nginx-unit-config.json similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/nginx-unit-config.json rename to {{cookiecutter.project_name}}/nginx-unit-config.json diff --git a/{{cookiecutter.project_name}}/template_minimal/poetry.lock b/{{cookiecutter.project_name}}/poetry.lock similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/poetry.lock rename to {{cookiecutter.project_name}}/poetry.lock diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/pre-push.sh b/{{cookiecutter.project_name}}/pre-push.sh similarity index 100% rename from {{cookiecutter.project_name}}/template_fastapi_users/pre-push.sh rename to {{cookiecutter.project_name}}/pre-push.sh diff --git a/{{cookiecutter.project_name}}/template_minimal/pyproject.toml b/{{cookiecutter.project_name}}/pyproject.toml similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/pyproject.toml rename to {{cookiecutter.project_name}}/pyproject.toml diff --git a/{{cookiecutter.project_name}}/template_minimal/requirements-dev.txt b/{{cookiecutter.project_name}}/requirements-dev.txt similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/requirements-dev.txt rename to {{cookiecutter.project_name}}/requirements-dev.txt diff --git a/{{cookiecutter.project_name}}/template_minimal/requirements.txt b/{{cookiecutter.project_name}}/requirements.txt similarity index 100% rename from {{cookiecutter.project_name}}/template_minimal/requirements.txt rename to {{cookiecutter.project_name}}/requirements.txt diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/.env.example b/{{cookiecutter.project_name}}/template_fastapi_users/.env.example deleted file mode 100644 index 5578451..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/.env.example +++ /dev/null @@ -1,19 +0,0 @@ -SECRET_KEY=DVnFmhwvjEhJZpuhndxjhlezxQPJmBIIkMDEmFREWQADPcUnrG -ENVIRONMENT=DEV -ACCESS_TOKEN_EXPIRE_MINUTES=11520 -BACKEND_CORS_ORIGINS=http://localhost:3000,http://localhost:8001 - -DEFAULT_DATABASE_HOSTNAME=localhost -DEFAULT_DATABASE_USER=rDGJeEDqAz -DEFAULT_DATABASE_PASSWORD=XsPQhCoEfOQZueDjsILetLDUvbvSxAMnrVtgVZpmdcSssUgbvs -DEFAULT_DATABASE_PORT=5387 -DEFAULT_DATABASE_DB=default_db - -TEST_DATABASE_HOSTNAME=localhost -TEST_DATABASE_USER=test -TEST_DATABASE_PASSWORD=ywRCUjJijmQoBmWxIfLldOoITPzajPSNvTvHyugQoSqGwNcvQE -TEST_DATABASE_PORT=37270 -TEST_DATABASE_DB=test_db - -FIRST_SUPERUSER_EMAIL=example@example.com -FIRST_SUPERUSER_PASSWORD=OdLknKQJMUwuhpAVHvRC \ No newline at end of file diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/.env.template b/{{cookiecutter.project_name}}/template_fastapi_users/.env.template deleted file mode 100644 index 77de33b..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/.env.template +++ /dev/null @@ -1,19 +0,0 @@ -SECRET_KEY={{ random_ascii_string(50) }} -ENVIRONMENT=DEV -ACCESS_TOKEN_EXPIRE_MINUTES=11520 -BACKEND_CORS_ORIGINS=http://localhost:3000,http://localhost:8001 - -DEFAULT_DATABASE_HOSTNAME=localhost -DEFAULT_DATABASE_USER={{ random_ascii_string(10) }} -DEFAULT_DATABASE_PASSWORD={{ random_ascii_string(50) }} -DEFAULT_DATABASE_PORT={{ range(4000, 7000) | random }} -DEFAULT_DATABASE_DB=default_db - -TEST_DATABASE_HOSTNAME=localhost -TEST_DATABASE_USER=test -TEST_DATABASE_PASSWORD={{ random_ascii_string(50) }} -TEST_DATABASE_PORT={{ range(30000, 40000) | random }} -TEST_DATABASE_DB=test_db - -FIRST_SUPERUSER_EMAIL=example@example.com -FIRST_SUPERUSER_PASSWORD={{ random_ascii_string(20) }} \ No newline at end of file diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/.flake8 b/{{cookiecutter.project_name}}/template_fastapi_users/.flake8 deleted file mode 100644 index 6b8856f..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/.flake8 +++ /dev/null @@ -1,11 +0,0 @@ -[flake8] -max-line-length = 88 -select = C,E,F,W,B,B9 -ignore = E203, E501, W503 -exclude = - __init__.py, - .venv, - venv, - __pycache__, - .github, - .vscode, diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/.gitignore b/{{cookiecutter.project_name}}/template_fastapi_users/.gitignore deleted file mode 100644 index 32562ce..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/.gitignore +++ /dev/null @@ -1,136 +0,0 @@ - -# postgresql -data -default_database_data -test_database_data - -# Byte-compiled / optimized / DLL files -__pycache__/ -*.py[cod] -*$py.class -.env - -# C extensions -*.so - -# Distribution / packaging -.Python -build/ -develop-eggs/ -dist/ -downloads/ -eggs/ -.eggs/ -lib/ -lib64/ -parts/ -sdist/ -var/ -wheels/ -pip-wheel-metadata/ -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/ - -# 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 -target/ - -# Jupyter Notebook -.ipynb_checkpoints - -# IPython -profile_default/ -ipython_config.py - -# pyenv -.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 - -# PEP 582; used by e.g. github.com/David-OConnor/pyflow -__pypackages__/ - -# Celery stuff -celerybeat-schedule -celerybeat.pid - -# SageMath parsed files -*.sage.py - -# Environments - -.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/ \ No newline at end of file diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/Dockerfile b/{{cookiecutter.project_name}}/template_fastapi_users/Dockerfile deleted file mode 100644 index 1461692..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/Dockerfile +++ /dev/null @@ -1,29 +0,0 @@ -# See https://unit.nginx.org/installation/#docker-images - -FROM nginx/unit:1.26.1-python3.9 - -ENV PYTHONUNBUFFERED 1 - -RUN apt update && apt install -y python3-pip - -# Build folder for our app, only stuff that matters copied. -RUN mkdir build -WORKDIR /build - -# Update, install requirements and then cleanup. -COPY ./requirements.txt . - -RUN pip3 install -r requirements.txt \ - && apt remove -y python3-pip \ - && apt autoremove --purge -y \ - && rm -rf /var/lib/apt/lists/* /etc/apt/sources.list.d/*.list - -# Copy the rest of app -COPY ./app ./app -COPY ./alembic ./alembic -COPY ./alembic.ini . - -# Nginx unit config and init.sh will be consumed at container startup. -COPY ./app/init.sh /docker-entrypoint.d/init.sh -COPY ./nginx-unit-config.json /docker-entrypoint.d/config.json -RUN chmod a+x /docker-entrypoint.d/init.sh \ No newline at end of file diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/alembic.ini b/{{cookiecutter.project_name}}/template_fastapi_users/alembic.ini deleted file mode 100644 index 61630d3..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/alembic.ini +++ /dev/null @@ -1,100 +0,0 @@ -# A generic, single database configuration. - -[alembic] -# path to migration scripts -script_location = alembic - -# template used to generate migration files -file_template = %%(year)d_%%(month).2d_%%(day).2d_%%(hour).2d%%(minute).2d_%%(slug)s__%%(rev)s - -# sys.path path, will be prepended to sys.path if present. -# defaults to the current working directory. -prepend_sys_path = . - -# timezone to use when rendering the date within the migration file -# as well as the filename. -# If specified, requires the python-dateutil library that can be -# installed by adding `alembic[tz]` to the pip requirements -# string value is passed to dateutil.tz.gettz() -# leave blank for localtime -# timezone = - -# max length of characters to apply to the -# "slug" field -# truncate_slug_length = 40 - -# set to 'true' to run the environment during -# the 'revision' command, regardless of autogenerate -# revision_environment = false - -# set to 'true' to allow .pyc and .pyo files without -# a source .py file to be detected as revisions in the -# versions/ directory -# sourceless = false - -# version location specification; This defaults -# to alembic/versions. When using multiple version -# directories, initial revisions must be specified with --version-path. -# The path separator used here should be the separator specified by "version_path_separator" -# version_locations = %(here)s/bar:%(here)s/bat:alembic/versions - -# version path separator; As mentioned above, this is the character used to split -# version_locations. Valid values are: -# -# version_path_separator = : -# version_path_separator = ; -# version_path_separator = space -version_path_separator = os # default: use os.pathsep - -# the output encoding used when revision files -# are written from script.py.mako -# output_encoding = utf-8 - -sqlalchemy.url = driver://user:pass@localhost/dbname - - -[post_write_hooks] -# post_write_hooks defines scripts or Python functions that are run -# on newly generated revision scripts. See the documentation for further -# detail and examples - -# format using "black" - use the console_scripts runner, against the "black" entrypoint -# hooks = black -# black.type = console_scripts -# black.entrypoint = black -# black.options = -l 79 REVISION_SCRIPT_FILENAME - -# Logging configuration -[loggers] -keys = root,sqlalchemy,alembic - -[handlers] -keys = console - -[formatters] -keys = generic - -[logger_root] -level = WARN -handlers = console -qualname = - -[logger_sqlalchemy] -level = WARN -handlers = -qualname = sqlalchemy.engine - -[logger_alembic] -level = INFO -handlers = -qualname = alembic - -[handler_console] -class = StreamHandler -args = (sys.stderr,) -level = NOTSET -formatter = generic - -[formatter_generic] -format = %(levelname)-5.5s [%(name)s] %(message)s -datefmt = %H:%M:%S diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/alembic/env.py b/{{cookiecutter.project_name}}/template_fastapi_users/alembic/env.py deleted file mode 100644 index 6e02264..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/alembic/env.py +++ /dev/null @@ -1,96 +0,0 @@ -from logging.config import fileConfig - -from sqlalchemy import engine_from_config -from sqlalchemy import pool -from sqlalchemy.ext.asyncio import AsyncEngine -from asyncio import get_event_loop - -from app.core import config as app_config -from alembic import context - -# this is the Alembic Config object, which provides -# access to the values within the .ini file in use. -config = context.config - -# Interpret the config file for Python logging. -# This line sets up loggers basically. -fileConfig(config.config_file_name) # type: ignore - -# add your model's MetaData object here -# for 'autogenerate' support -# from myapp import mymodel -# target_metadata = mymodel.Base.metadata -from app.models import Base - -target_metadata = Base.metadata - -# other values from the config, defined by the needs of env.py, -# can be acquired: -# my_important_option = config.get_main_option("my_important_option") -# ... etc. - - -def get_database_uri(): - return app_config.settings.DEFAULT_SQLALCHEMY_DATABASE_URI - - -def run_migrations_offline(): - """Run migrations in 'offline' mode. - - This configures the context with just a URL - and not an Engine, though an Engine is acceptable - here as well. By skipping the Engine creation - we don't even need a DBAPI to be available. - - Calls to context.execute() here emit the given string to the - script output. - - """ - url = get_database_uri() - context.configure( - url=url, - target_metadata=target_metadata, - literal_binds=True, - dialect_opts={"paramstyle": "named"}, - compare_type=True, - ) - - with context.begin_transaction(): - context.run_migrations() - - -def do_run_migrations(connection): - context.configure( - connection=connection, target_metadata=target_metadata, compare_type=True - ) - - with context.begin_transaction(): - context.run_migrations() - - -async def run_migrations_online(): - """Run migrations in 'online' mode. - - In this scenario we need to create an Engine - and associate a connection with the context. - - """ - configuration = config.get_section(config.config_ini_section) - assert configuration - configuration["sqlalchemy.url"] = get_database_uri() - connectable = AsyncEngine( - engine_from_config( - configuration, - prefix="sqlalchemy.", - poolclass=pool.NullPool, - future=True, - ) # type: ignore - ) - async with connectable.connect() as connection: - await connection.run_sync(do_run_migrations) - - -if context.is_offline_mode(): - run_migrations_offline() -else: - get_event_loop().run_until_complete(run_migrations_online()) diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/alembic/versions/2022_01_09_1952_initial_fastapi_users_model__57b460a916d4.py b/{{cookiecutter.project_name}}/template_fastapi_users/alembic/versions/2022_01_09_1952_initial_fastapi_users_model__57b460a916d4.py deleted file mode 100644 index aa186f6..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/alembic/versions/2022_01_09_1952_initial_fastapi_users_model__57b460a916d4.py +++ /dev/null @@ -1,39 +0,0 @@ -"""initial_fastapi_users_model - -Revision ID: 57b460a916d4 -Revises: -Create Date: 2022-01-09 19:52:37.810574 - -""" -from alembic import op -import sqlalchemy as sa -from fastapi_users_db_sqlalchemy import guid - -# revision identifiers, used by Alembic. -revision = "57b460a916d4" -down_revision = None -branch_labels = None -depends_on = None - - -def upgrade(): - # ### commands auto generated by Alembic - please adjust! ### - op.create_table( - "user", - sa.Column("id", guid.GUID(), nullable=False), - sa.Column("email", sa.String(length=320), nullable=False), - sa.Column("hashed_password", sa.String(length=72), nullable=False), - sa.Column("is_active", sa.Boolean(), nullable=False), - sa.Column("is_superuser", sa.Boolean(), nullable=False), - sa.Column("is_verified", sa.Boolean(), nullable=False), - sa.PrimaryKeyConstraint("id"), - ) - op.create_index(op.f("ix_user_email"), "user", ["email"], unique=True) - # ### end Alembic commands ### - - -def downgrade(): - # ### commands auto generated by Alembic - please adjust! ### - op.drop_index(op.f("ix_user_email"), table_name="user") - op.drop_table("user") - # ### end Alembic commands ### diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/app/api/api.py b/{{cookiecutter.project_name}}/template_fastapi_users/app/api/api.py deleted file mode 100644 index 2d91f3c..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/app/api/api.py +++ /dev/null @@ -1,31 +0,0 @@ -""" -Users and auth routers 'for free' from FastAPI Users. -https://fastapi-users.github.io/fastapi-users/configuration/routers/ - -You can include more of them + oauth login endpoints. - -fastapi_users in defined in deps, because it also -includes useful dependencies. -""" - -from fastapi import APIRouter - -from app.api.deps import fastapi_users -from app.core import security - -api_router = APIRouter() -api_router.include_router( - fastapi_users.get_auth_router(security.AUTH_BACKEND), - prefix="/auth/jwt", - tags=["auth"], -) -api_router.include_router( - fastapi_users.get_register_router(), - prefix="/auth", - tags=["auth"], -) -api_router.include_router( - fastapi_users.get_users_router(), - prefix="/users", - tags=["users"], -) diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/app/api/deps.py b/{{cookiecutter.project_name}}/template_fastapi_users/app/api/deps.py deleted file mode 100644 index 7dc3e17..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/app/api/deps.py +++ /dev/null @@ -1,42 +0,0 @@ -from typing import AsyncGenerator - -from fastapi import Depends -from fastapi.security import OAuth2PasswordBearer -from fastapi_users.fastapi_users import FastAPIUsers -from fastapi_users_db_sqlalchemy import SQLAlchemyUserDatabase -from sqlalchemy.ext.asyncio import AsyncSession - -from app import schemas -from app.core import security -from app.models import UserTable -from app.session import async_session - -reusable_oauth2 = OAuth2PasswordBearer(tokenUrl="auth/access-token") - - -async def get_session() -> AsyncGenerator[AsyncSession, None]: - async with async_session() as session: - yield session - - -async def get_user_db(session: AsyncSession = Depends(get_session)): - yield SQLAlchemyUserDatabase(schemas.UserDB, session, UserTable) - - -async def get_user_manager(user_db: SQLAlchemyUserDatabase = Depends(get_user_db)): - yield security.UserManager(user_db) - - -fastapi_users = FastAPIUsers( - get_user_manager, # type: ignore - [security.AUTH_BACKEND], - schemas.User, - schemas.UserCreate, - schemas.UserUpdate, - schemas.UserDB, -) - - -get_current_user = fastapi_users.current_user() -get_current_active_user = fastapi_users.current_user(active=True) -get_current_superuser = fastapi_users.current_user(active=True, superuser=True) diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/app/core/config.py b/{{cookiecutter.project_name}}/template_fastapi_users/app/core/config.py deleted file mode 100644 index a86a202..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/app/core/config.py +++ /dev/null @@ -1,98 +0,0 @@ -""" -File with environment variables and general configuration logic. -`SECRET_KEY`, `ENVIRONMENT` etc. map to env variables with the same names. - -Pydantic priority ordering: - -1. (Most important, will overwrite everything) - environment variables -2. `.env` file in root folder of project -3. Default values - -For project name, version, description we use pyproject.toml -For the rest, we use file `.env` (gitignored), see `.env.example` - -`DEFAULT_SQLALCHEMY_DATABASE_URI` and `TEST_SQLALCHEMY_DATABASE_URI`: -Both are ment to be validated at the runtime, do not change unless you know -what are you doing. All the two validators do is to build full URI (TCP protocol) -to databases to avoid typo bugs. - -See https://pydantic-docs.helpmanual.io/usage/settings/ -""" - -from pathlib import Path -from typing import Literal, Union - -import toml -from pydantic import AnyHttpUrl, AnyUrl, BaseSettings, EmailStr, validator - -PROJECT_DIR = Path(__file__).parent.parent.parent -PYPROJECT_CONTENT = toml.load(f"{PROJECT_DIR}/pyproject.toml")["tool"]["poetry"] - - -class Settings(BaseSettings): - # CORE SETTINGS - SECRET_KEY: str - ENVIRONMENT: Literal["DEV", "PYTEST", "STAGE", "PRODUCTION"] - ACCESS_TOKEN_EXPIRE_MINUTES: int - BACKEND_CORS_ORIGINS: Union[str, list[AnyHttpUrl]] - - # PROJECT NAME, VERSION AND DESCRIPTION - PROJECT_NAME: str = PYPROJECT_CONTENT["name"] - VERSION: str = PYPROJECT_CONTENT["version"] - DESCRIPTION: str = PYPROJECT_CONTENT["description"] - - # POSTGRESQL DEFAULT DATABASE - DEFAULT_DATABASE_HOSTNAME: str - DEFAULT_DATABASE_USER: str - DEFAULT_DATABASE_PASSWORD: str - DEFAULT_DATABASE_PORT: str - DEFAULT_DATABASE_DB: str - DEFAULT_SQLALCHEMY_DATABASE_URI: str = "" - - # POSTGRESQL TEST DATABASE - TEST_DATABASE_HOSTNAME: str - TEST_DATABASE_USER: str - TEST_DATABASE_PASSWORD: str - TEST_DATABASE_PORT: str - TEST_DATABASE_DB: str - TEST_SQLALCHEMY_DATABASE_URI: str = "" - - # FIRST SUPERUSER - FIRST_SUPERUSER_EMAIL: EmailStr - FIRST_SUPERUSER_PASSWORD: str - - # VALIDATORS - @validator("BACKEND_CORS_ORIGINS") - def _assemble_cors_origins(cls, cors_origins: Union[str, list[AnyHttpUrl]]): - if isinstance(cors_origins, str): - return [item.strip() for item in cors_origins.split(",")] - return cors_origins - - @validator("DEFAULT_SQLALCHEMY_DATABASE_URI") - def _assemble_default_db_connection(cls, v: str, values: dict[str, str]) -> str: - return AnyUrl.build( - scheme="postgresql+asyncpg", - user=values["DEFAULT_DATABASE_USER"], - password=values["DEFAULT_DATABASE_PASSWORD"], - host=values["DEFAULT_DATABASE_HOSTNAME"], - port=values["DEFAULT_DATABASE_PORT"], - path=f"/{values['DEFAULT_DATABASE_DB']}", - ) - - @validator("TEST_SQLALCHEMY_DATABASE_URI") - def _assemble_test_db_connection(cls, v: str, values: dict[str, str]) -> str: - return AnyUrl.build( - scheme="postgresql+asyncpg", - user=values["TEST_DATABASE_USER"], - password=values["TEST_DATABASE_PASSWORD"], - host=values["TEST_DATABASE_HOSTNAME"], - port=values["TEST_DATABASE_PORT"], - path=f"/{values['TEST_DATABASE_DB']}", - ) - - class Config: - env_file = f"{PROJECT_DIR}/.env" - case_sensitive = True - - -settings: Settings = Settings() # type: ignore diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/app/core/security.py b/{{cookiecutter.project_name}}/template_fastapi_users/app/core/security.py deleted file mode 100644 index 4ceb025..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/app/core/security.py +++ /dev/null @@ -1,64 +0,0 @@ -""" -You can have several authentication methods, e.g. a cookie -authentication for browser-based queries and a JWT token authentication for pure API queries. - -In this template, token will be sent through Bearer header -{"Authorization": "Bearer xyz"} -using JWT tokens. - -There are more option to consider, refer to -https://fastapi-users.github.io/fastapi-users/configuration/authentication/ - -UserManager class is core fastapi users class with customizable attrs and methods -https://fastapi-users.github.io/fastapi-users/configuration/user-manager/ -""" - - -from typing import Optional - -from fastapi import Request -from fastapi_users.authentication import ( - AuthenticationBackend, - BearerTransport, - JWTStrategy, -) -from fastapi_users.manager import BaseUserManager - -from app import schemas -from app.core import config - - -def get_jwt_strategy() -> JWTStrategy: - return JWTStrategy( - secret=config.settings.SECRET_KEY, - lifetime_seconds=config.settings.ACCESS_TOKEN_EXPIRE_MINUTES * 60, - ) - - -BEARER_TRANSPORT = BearerTransport(tokenUrl="auth/jwt/login") -AUTH_BACKEND = AuthenticationBackend( - name="jwt", - transport=BEARER_TRANSPORT, - get_strategy=get_jwt_strategy, -) - - -class UserManager(BaseUserManager[schemas.UserCreate, schemas.UserDB]): - user_db_model = schemas.UserDB - reset_password_token_secret = config.settings.SECRET_KEY - verification_token_secret = config.settings.SECRET_KEY - - async def on_after_register( - self, user: schemas.UserDB, request: Optional[Request] = None - ): - print(f"User {user.id} has registered.") - - async def on_after_forgot_password( - self, user: schemas.UserDB, token: str, request: Optional[Request] = None - ): - print(f"User {user.id} has forgot their password. Reset token: {token}") - - async def on_after_request_verify( - self, user: schemas.UserDB, token: str, request: Optional[Request] = None - ): - print(f"Verification requested for user {user.id}. Verification token: {token}") diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/app/initial_data.py b/{{cookiecutter.project_name}}/template_fastapi_users/app/initial_data.py deleted file mode 100644 index 4577040..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/app/initial_data.py +++ /dev/null @@ -1,50 +0,0 @@ -""" -Put here any Python code that must be runned before application startup. -It is included in `init.sh` script. - -By defualt `main` create a superuser if it does not exist. -""" - -import asyncio -from typing import Optional - -from fastapi_users.password import get_password_hash -from fastapi_users_db_sqlalchemy import SQLAlchemyUserDatabase -from sqlalchemy import select - -from app import schemas -from app.core import config -from app.models import UserTable -from app.session import async_session - - -async def main() -> None: - print("Start initial data") - async with async_session() as session: - result = await session.execute( - select(UserTable).where( - UserTable.email == config.settings.FIRST_SUPERUSER_EMAIL - ) - ) - user: Optional[UserTable] = result.scalars().first() - - if user is None: - await SQLAlchemyUserDatabase(schemas.UserDB, session, UserTable).create( - schemas.UserDB( - email=config.settings.FIRST_SUPERUSER_EMAIL, - is_superuser=True, - is_verified=True, - hashed_password=get_password_hash( - config.settings.FIRST_SUPERUSER_PASSWORD - ), - ) - ) - print("Superuser was created") - else: - print("Superuser already exists in database") - - print("Initial data created") - - -if __name__ == "__main__": - asyncio.run(main()) diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/app/main.py b/{{cookiecutter.project_name}}/template_fastapi_users/app/main.py deleted file mode 100644 index 0892233..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/app/main.py +++ /dev/null @@ -1,29 +0,0 @@ -""" -Main FastAPI app instance declaration -""" - -from fastapi import FastAPI -from fastapi.middleware.cors import CORSMiddleware - -from app.api.api import api_router -from app.core import config - -app = FastAPI( - title=config.settings.PROJECT_NAME, - version=config.settings.VERSION, - description=config.settings.DESCRIPTION, - openapi_url="/openapi.json", - docs_url="/", -) - -# Set all CORS enabled origins -if config.settings.BACKEND_CORS_ORIGINS: - app.add_middleware( - CORSMiddleware, - allow_origins=[str(origin) for origin in config.settings.BACKEND_CORS_ORIGINS], - allow_credentials=True, - allow_methods=["*"], - allow_headers=["*"], - ) - -app.include_router(api_router) diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/app/models.py b/{{cookiecutter.project_name}}/template_fastapi_users/app/models.py deleted file mode 100644 index 7316b29..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/app/models.py +++ /dev/null @@ -1,16 +0,0 @@ -""" -SQL Alchemy models declaration. - -Note, imported by alembic migrations logic, see `alembic/env.py` -""" - -from typing import Any, cast - -from fastapi_users_db_sqlalchemy import SQLAlchemyBaseUserTable -from sqlalchemy.orm.decl_api import declarative_base - -Base = cast(Any, declarative_base()) - - -class UserTable(Base, SQLAlchemyBaseUserTable): - pass diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/app/schemas/__init__.py b/{{cookiecutter.project_name}}/template_fastapi_users/app/schemas/__init__.py deleted file mode 100644 index 6037db2..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/app/schemas/__init__.py +++ /dev/null @@ -1 +0,0 @@ -from .user import User, UserCreate, UserDB, UserUpdate diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/app/schemas/user.py b/{{cookiecutter.project_name}}/template_fastapi_users/app/schemas/user.py deleted file mode 100644 index ff08ab2..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/app/schemas/user.py +++ /dev/null @@ -1,42 +0,0 @@ -""" -All fields in schemas are defaults from FastAPI Users, repeated below for easier view -""" - -import uuid -from typing import Optional - -from fastapi_users import models -from pydantic import UUID4, EmailStr, Field - - -class User(models.BaseUser): - id: UUID4 = Field(default_factory=uuid.uuid4) - email: EmailStr - is_active: bool = True - is_superuser: bool = False - is_verified: bool = False - - -class UserCreate(models.BaseUserCreate): - email: EmailStr - password: str - is_active: Optional[bool] = True - is_superuser: Optional[bool] = False - is_verified: Optional[bool] = False - - -class UserUpdate(models.BaseUserUpdate): - password: Optional[str] - email: Optional[EmailStr] - is_active: Optional[bool] - is_superuser: Optional[bool] - is_verified: Optional[bool] - - -class UserDB(User, models.BaseUserDB): - id: UUID4 = Field(default_factory=uuid.uuid4) - email: EmailStr - is_active: bool = True - is_superuser: bool = False - is_verified: bool = False - hashed_password: str diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/app/session.py b/{{cookiecutter.project_name}}/template_fastapi_users/app/session.py deleted file mode 100644 index 5b27e40..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/app/session.py +++ /dev/null @@ -1,12 +0,0 @@ -from sqlalchemy.ext.asyncio import AsyncSession, create_async_engine -from sqlalchemy.orm.session import sessionmaker - -from app.core import config - -if config.settings.ENVIRONMENT == "PYTEST": - sqlalchemy_database_uri = config.settings.TEST_SQLALCHEMY_DATABASE_URI -else: - sqlalchemy_database_uri = config.settings.DEFAULT_SQLALCHEMY_DATABASE_URI - -async_engine = create_async_engine(sqlalchemy_database_uri, pool_pre_ping=True) -async_session = sessionmaker(async_engine, expire_on_commit=False, class_=AsyncSession) diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/app/tests/conftest.py b/{{cookiecutter.project_name}}/template_fastapi_users/app/tests/conftest.py deleted file mode 100644 index 4c11514..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/app/tests/conftest.py +++ /dev/null @@ -1,63 +0,0 @@ -import asyncio -from typing import AsyncGenerator - -import pytest -from fastapi_users.password import get_password_hash -from httpx import AsyncClient -from sqlalchemy.ext.asyncio import AsyncSession - -from app.core import config -from app.main import app -from app.models import Base -from app.session import async_engine, async_session -from app.tests import utils - -default_user_email = "geralt@wiedzmin.pl" -default_user_hash = get_password_hash("geralt") -superuser_user_email = "yennefer@wiedzmin.pl" -superuser_user_hash = get_password_hash("yennefer") - - -@pytest.fixture(scope="session") -def event_loop(): - loop = asyncio.get_event_loop() - yield loop - loop.close() - - -@pytest.fixture(scope="session") -async def client(): - async with AsyncClient(app=app, base_url="http://doesnt.matter") as client: - yield client - - -@pytest.fixture(scope="session") -async def test_db_setup_sessionmaker(): - # assert if we use TEST_DB URL for 100% - assert config.settings.ENVIRONMENT == "PYTEST" - assert str(async_engine.url) == config.settings.TEST_SQLALCHEMY_DATABASE_URI - - # always drop and create test db tables between tests session - async with async_engine.begin() as conn: - - await conn.run_sync(Base.metadata.drop_all) - await conn.run_sync(Base.metadata.create_all) - return async_session - - -@pytest.fixture -async def session(test_db_setup_sessionmaker) -> AsyncGenerator[AsyncSession, None]: - async with test_db_setup_sessionmaker() as session: - yield session - - -@pytest.fixture -async def default_user(session: AsyncSession): - return await utils.create_db_user(default_user_email, default_user_hash, session) - - -@pytest.fixture -async def superuser_user(session: AsyncSession): - return await utils.create_db_user( - superuser_user_email, superuser_user_hash, session, is_superuser=True - ) diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/app/tests/test_auth.py b/{{cookiecutter.project_name}}/template_fastapi_users/app/tests/test_auth.py deleted file mode 100644 index 25b6a15..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/app/tests/test_auth.py +++ /dev/null @@ -1,36 +0,0 @@ -""" -Testing FastAPI Users makes no sense, its just an example to remove. -""" - -import pytest -from httpx import AsyncClient - -from app.schemas import UserDB - -# All test coroutines in file will be treated as marked (async allowed). -pytestmark = pytest.mark.asyncio - - -async def test_login_endpoints(client: AsyncClient, default_user: UserDB): - - # access-token endpoint - access_token_res = await client.post( - "/auth/jwt/login", - data={ - "username": "geralt@wiedzmin.pl", - "password": "geralt", - }, - headers={"Content-Type": "application/x-www-form-urlencoded"}, - ) - assert access_token_res.status_code == 200 - token = access_token_res.json() - - access_token = token["access_token"] - - # test-token endpoint - test_token = await client.get( - "/users/me", headers={"Authorization": f"Bearer {access_token}"} - ) - assert test_token.status_code == 200 - response_user = test_token.json() - assert response_user["email"] == default_user.email diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/app/tests/utils.py b/{{cookiecutter.project_name}}/template_fastapi_users/app/tests/utils.py deleted file mode 100644 index aacc1c5..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/app/tests/utils.py +++ /dev/null @@ -1,36 +0,0 @@ -import random -import string - -from fastapi_users_db_sqlalchemy import SQLAlchemyUserDatabase -from pydantic.networks import EmailStr -from sqlalchemy.ext.asyncio import AsyncSession - -from app import schemas -from app.models import UserTable - - -def random_lower_string(length: int = 32) -> str: - return "".join(random.choices(string.ascii_lowercase, k=length)) - - -def random_email(length: int = 10) -> str: - return f"{random_lower_string(length)}@{random_lower_string(length)}.com" - - -async def create_db_user( - email: str, - hashed_password: str, - session: AsyncSession, - is_superuser: bool = False, - is_verified: bool = True, -) -> schemas.UserDB: - - new_user = await SQLAlchemyUserDatabase(schemas.UserDB, session, UserTable).create( - schemas.UserDB( - email=EmailStr(email), - is_superuser=is_superuser, - is_verified=is_verified, - hashed_password=hashed_password, - ) - ) - return new_user diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/docker-compose.yml b/{{cookiecutter.project_name}}/template_fastapi_users/docker-compose.yml deleted file mode 100644 index 4f33f36..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/docker-compose.yml +++ /dev/null @@ -1,36 +0,0 @@ -version: "3.3" - -# For local development, only database is running -# -# docker-compose up -d -# uvicorn app.main:app --reload -# - -services: - default_database: - restart: unless-stopped - image: postgres:latest - volumes: - - ./default_database_data/db:/var/lib/postgresql/data - environment: - - POSTGRES_DB=${DEFAULT_DATABASE_DB} - - POSTGRES_USER=${DEFAULT_DATABASE_USER} - - POSTGRES_PASSWORD=${DEFAULT_DATABASE_PASSWORD} - env_file: - - .env - ports: - - "${DEFAULT_DATABASE_PORT}:5432" - - test_database: - restart: unless-stopped - image: postgres:latest - volumes: - - ./test_database_data/db:/var/lib/postgresql/data - environment: - - POSTGRES_DB=${TEST_DATABASE_DB} - - POSTGRES_USER=${TEST_DATABASE_USER} - - POSTGRES_PASSWORD=${TEST_DATABASE_PASSWORD} - env_file: - - .env - ports: - - "${TEST_DATABASE_PORT}:5432" diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/nginx-unit-config.json b/{{cookiecutter.project_name}}/template_fastapi_users/nginx-unit-config.json deleted file mode 100644 index dda3653..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/nginx-unit-config.json +++ /dev/null @@ -1,17 +0,0 @@ -{ - "listeners": { - "*:80": { - "pass": "applications/fastapi" - } - }, - "applications": { - "fastapi": { - "type": "python 3.9", - "processes": 1, - "threads": 1, - "path": "/build/", - "module": "app.main", - "callable": "app" - } - } -} diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/poetry.lock b/{{cookiecutter.project_name}}/template_fastapi_users/poetry.lock deleted file mode 100644 index cb9bf80..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/poetry.lock +++ /dev/null @@ -1,1305 +0,0 @@ -[[package]] -name = "alembic" -version = "1.7.5" -description = "A database migration tool for SQLAlchemy." -category = "main" -optional = false -python-versions = ">=3.6" - -[package.dependencies] -Mako = "*" -SQLAlchemy = ">=1.3.0" - -[package.extras] -tz = ["python-dateutil"] - -[[package]] -name = "anyio" -version = "3.4.0" -description = "High level compatibility layer for multiple asynchronous event loop implementations" -category = "main" -optional = false -python-versions = ">=3.6.2" - -[package.dependencies] -idna = ">=2.8" -sniffio = ">=1.1" - -[package.extras] -doc = ["sphinx-rtd-theme", "sphinx-autodoc-typehints (>=1.2.0)"] -test = ["coverage[toml] (>=4.5)", "hypothesis (>=4.0)", "pytest (>=6.0)", "pytest-mock (>=3.6.1)", "trustme", "contextlib2", "uvloop (<0.15)", "mock (>=4)", "uvloop (>=0.15)"] -trio = ["trio (>=0.16)"] - -[[package]] -name = "asgiref" -version = "3.4.1" -description = "ASGI specs, helper code, and adapters" -category = "dev" -optional = false -python-versions = ">=3.6" - -[package.extras] -tests = ["pytest", "pytest-asyncio", "mypy (>=0.800)"] - -[[package]] -name = "asyncpg" -version = "0.25.0" -description = "An asyncio PostgreSQL driver" -category = "main" -optional = false -python-versions = ">=3.6.0" - -[package.extras] -dev = ["Cython (>=0.29.24,<0.30.0)", "pytest (>=6.0)", "Sphinx (>=4.1.2,<4.2.0)", "sphinxcontrib-asyncio (>=0.3.0,<0.4.0)", "sphinx-rtd-theme (>=0.5.2,<0.6.0)", "pycodestyle (>=2.7.0,<2.8.0)", "flake8 (>=3.9.2,<3.10.0)", "uvloop (>=0.15.3)"] -docs = ["Sphinx (>=4.1.2,<4.2.0)", "sphinxcontrib-asyncio (>=0.3.0,<0.4.0)", "sphinx-rtd-theme (>=0.5.2,<0.6.0)"] -test = ["pycodestyle (>=2.7.0,<2.8.0)", "flake8 (>=3.9.2,<3.10.0)", "uvloop (>=0.15.3)"] - -[[package]] -name = "atomicwrites" -version = "1.4.0" -description = "Atomic file writes." -category = "dev" -optional = false -python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*" - -[[package]] -name = "attrs" -version = "21.4.0" -description = "Classes Without Boilerplate" -category = "dev" -optional = false -python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, !=3.4.*" - -[package.extras] -dev = ["coverage[toml] (>=5.0.2)", "hypothesis", "pympler", "pytest (>=4.3.0)", "six", "mypy", "pytest-mypy-plugins", "zope.interface", "furo", "sphinx", "sphinx-notfound-page", "pre-commit", "cloudpickle"] -docs = ["furo", "sphinx", "zope.interface", "sphinx-notfound-page"] -tests = ["coverage[toml] (>=5.0.2)", "hypothesis", "pympler", "pytest (>=4.3.0)", "six", "mypy", "pytest-mypy-plugins", "zope.interface", "cloudpickle"] -tests_no_zope = ["coverage[toml] (>=5.0.2)", "hypothesis", "pympler", "pytest (>=4.3.0)", "six", "mypy", "pytest-mypy-plugins", "cloudpickle"] - -[[package]] -name = "autoflake" -version = "1.4" -description = "Removes unused imports and unused variables" -category = "dev" -optional = false -python-versions = "*" - -[package.dependencies] -pyflakes = ">=1.1.0" - -[[package]] -name = "bcrypt" -version = "3.2.0" -description = "Modern password hashing for your software and your servers" -category = "main" -optional = false -python-versions = ">=3.6" - -[package.dependencies] -cffi = ">=1.1" -six = ">=1.4.1" - -[package.extras] -tests = ["pytest (>=3.2.1,!=3.3.0)"] -typecheck = ["mypy"] - -[[package]] -name = "black" -version = "21.12b0" -description = "The uncompromising code formatter." -category = "dev" -optional = false -python-versions = ">=3.6.2" - -[package.dependencies] -click = ">=7.1.2" -mypy-extensions = ">=0.4.3" -pathspec = ">=0.9.0,<1" -platformdirs = ">=2" -tomli = ">=0.2.6,<2.0.0" -typing-extensions = [ - {version = ">=3.10.0.0", markers = "python_version < \"3.10\""}, - {version = "!=3.10.0.1", markers = "python_version >= \"3.10\""}, -] - -[package.extras] -colorama = ["colorama (>=0.4.3)"] -d = ["aiohttp (>=3.7.4)"] -jupyter = ["ipython (>=7.8.0)", "tokenize-rt (>=3.2.0)"] -python2 = ["typed-ast (>=1.4.3)"] -uvloop = ["uvloop (>=0.15.2)"] - -[[package]] -name = "certifi" -version = "2021.10.8" -description = "Python package for providing Mozilla's CA Bundle." -category = "dev" -optional = false -python-versions = "*" - -[[package]] -name = "cffi" -version = "1.15.0" -description = "Foreign Function Interface for Python calling C code." -category = "main" -optional = false -python-versions = "*" - -[package.dependencies] -pycparser = "*" - -[[package]] -name = "charset-normalizer" -version = "2.0.10" -description = "The Real First Universal Charset Detector. Open, modern and actively maintained alternative to Chardet." -category = "dev" -optional = false -python-versions = ">=3.5.0" - -[package.extras] -unicode_backport = ["unicodedata2"] - -[[package]] -name = "click" -version = "8.0.3" -description = "Composable command line interface toolkit" -category = "dev" -optional = false -python-versions = ">=3.6" - -[package.dependencies] -colorama = {version = "*", markers = "platform_system == \"Windows\""} - -[[package]] -name = "colorama" -version = "0.4.4" -description = "Cross-platform colored terminal text." -category = "dev" -optional = false -python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, !=3.4.*" - -[[package]] -name = "coverage" -version = "6.2" -description = "Code coverage measurement for Python" -category = "dev" -optional = false -python-versions = ">=3.6" - -[package.extras] -toml = ["tomli"] - -[[package]] -name = "dnspython" -version = "2.1.0" -description = "DNS toolkit" -category = "main" -optional = false -python-versions = ">=3.6" - -[package.extras] -dnssec = ["cryptography (>=2.6)"] -doh = ["requests", "requests-toolbelt"] -idna = ["idna (>=2.1)"] -curio = ["curio (>=1.2)", "sniffio (>=1.1)"] -trio = ["trio (>=0.14.0)", "sniffio (>=1.1)"] - -[[package]] -name = "email-validator" -version = "1.1.3" -description = "A robust email syntax and deliverability validation library for Python 2.x/3.x." -category = "main" -optional = false -python-versions = "!=3.0.*,!=3.1.*,!=3.2.*,!=3.3.*,!=3.4.*,>=2.7" - -[package.dependencies] -dnspython = ">=1.15.0" -idna = ">=2.0.0" - -[[package]] -name = "fastapi" -version = "0.70.1" -description = "FastAPI framework, high performance, easy to learn, fast to code, ready for production" -category = "main" -optional = false -python-versions = ">=3.6.1" - -[package.dependencies] -pydantic = ">=1.6.2,<1.7 || >1.7,<1.7.1 || >1.7.1,<1.7.2 || >1.7.2,<1.7.3 || >1.7.3,<1.8 || >1.8,<1.8.1 || >1.8.1,<2.0.0" -starlette = "0.16.0" - -[package.extras] -all = ["requests (>=2.24.0,<3.0.0)", "jinja2 (>=2.11.2,<4.0.0)", "python-multipart (>=0.0.5,<0.0.6)", "itsdangerous (>=1.1.0,<3.0.0)", "pyyaml (>=5.3.1,<6.0.0)", "ujson (>=4.0.1,<5.0.0)", "orjson (>=3.2.1,<4.0.0)", "email_validator (>=1.1.1,<2.0.0)", "uvicorn[standard] (>=0.12.0,<0.16.0)"] -dev = ["python-jose[cryptography] (>=3.3.0,<4.0.0)", "passlib[bcrypt] (>=1.7.2,<2.0.0)", "autoflake (>=1.4.0,<2.0.0)", "flake8 (>=3.8.3,<4.0.0)", "uvicorn[standard] (>=0.12.0,<0.16.0)"] -doc = ["mkdocs (>=1.1.2,<2.0.0)", "mkdocs-material (>=7.1.9,<8.0.0)", "mdx-include (>=1.4.1,<2.0.0)", "mkdocs-markdownextradata-plugin (>=0.1.7,<0.3.0)", "typer-cli (>=0.0.12,<0.0.13)", "pyyaml (>=5.3.1,<6.0.0)"] -test = ["pytest (>=6.2.4,<7.0.0)", "pytest-cov (>=2.12.0,<4.0.0)", "mypy (==0.910)", "flake8 (>=3.8.3,<4.0.0)", "black (==21.9b0)", "isort (>=5.0.6,<6.0.0)", "requests (>=2.24.0,<3.0.0)", "httpx (>=0.14.0,<0.19.0)", "email_validator (>=1.1.1,<2.0.0)", "sqlalchemy (>=1.3.18,<1.5.0)", "peewee (>=3.13.3,<4.0.0)", "databases[sqlite] (>=0.3.2,<0.6.0)", "orjson (>=3.2.1,<4.0.0)", "ujson (>=4.0.1,<5.0.0)", "python-multipart (>=0.0.5,<0.0.6)", "flask (>=1.1.2,<3.0.0)", "anyio[trio] (>=3.2.1,<4.0.0)", "types-ujson (==0.1.1)", "types-orjson (==3.6.0)", "types-dataclasses (==0.1.7)"] - -[[package]] -name = "fastapi-users" -version = "9.2.0" -description = "Ready-to-use and customizable users management for FastAPI." -category = "main" -optional = false -python-versions = ">=3.7" - -[package.dependencies] -email-validator = ">=1.1.0,<1.2" -fastapi = ">=0.65.2,<0.71.0" -fastapi-users-db-sqlalchemy = {version = ">=2.0.0", optional = true, markers = "extra == \"sqlalchemy2\""} -makefun = ">=1.9.2,<1.13" -passlib = {version = "1.7.4", extras = ["bcrypt"]} -pyjwt = "2.3.0" -python-multipart = "0.0.5" - -[package.extras] -mongodb = ["fastapi-users-db-mongodb (>=1.1.0)"] -oauth = ["httpx-oauth (>=0.4,<0.5)"] -ormar = ["fastapi-users-db-ormar (>=1.0.0)"] -redis = ["aioredis (>=2.0.1,<2.1.0)", "hiredis (>=2.0.0,<2.1.0)"] -sqlalchemy = ["fastapi-users-db-sqlalchemy (>=1.1.0,<2.0.0)"] -sqlalchemy2 = ["fastapi-users-db-sqlalchemy (>=2.0.0)"] -tortoise-orm = ["fastapi-users-db-tortoise (>=1.1.0)"] - -[[package]] -name = "fastapi-users-db-sqlalchemy" -version = "2.0.4" -description = "FastAPI Users database adapter for SQLAlchemy." -category = "main" -optional = false -python-versions = ">=3.7" - -[package.dependencies] -fastapi-users = ">=9.1.0" -sqlalchemy = ">=1.4" - -[[package]] -name = "flake8" -version = "4.0.1" -description = "the modular source code checker: pep8 pyflakes and co" -category = "dev" -optional = false -python-versions = ">=3.6" - -[package.dependencies] -mccabe = ">=0.6.0,<0.7.0" -pycodestyle = ">=2.8.0,<2.9.0" -pyflakes = ">=2.4.0,<2.5.0" - -[[package]] -name = "greenlet" -version = "1.1.2" -description = "Lightweight in-process concurrent programming" -category = "main" -optional = false -python-versions = ">=2.7,!=3.0.*,!=3.1.*,!=3.2.*,!=3.3.*,!=3.4.*" - -[package.extras] -docs = ["sphinx"] - -[[package]] -name = "h11" -version = "0.12.0" -description = "A pure-Python, bring-your-own-I/O implementation of HTTP/1.1" -category = "dev" -optional = false -python-versions = ">=3.6" - -[[package]] -name = "httpcore" -version = "0.14.4" -description = "A minimal low-level HTTP client." -category = "dev" -optional = false -python-versions = ">=3.6" - -[package.dependencies] -anyio = ">=3.0.0,<4.0.0" -certifi = "*" -h11 = ">=0.11,<0.13" -sniffio = ">=1.0.0,<2.0.0" - -[package.extras] -http2 = ["h2 (>=3,<5)"] - -[[package]] -name = "httpx" -version = "0.21.3" -description = "The next generation HTTP client." -category = "dev" -optional = false -python-versions = ">=3.6" - -[package.dependencies] -certifi = "*" -charset-normalizer = "*" -httpcore = ">=0.14.0,<0.15.0" -rfc3986 = {version = ">=1.3,<2", extras = ["idna2008"]} -sniffio = "*" - -[package.extras] -brotli = ["brotlicffi", "brotli"] -cli = ["click (>=8.0.0,<9.0.0)", "rich (>=10.0.0,<11.0.0)", "pygments (>=2.0.0,<3.0.0)"] -http2 = ["h2 (>=3,<5)"] - -[[package]] -name = "idna" -version = "3.3" -description = "Internationalized Domain Names in Applications (IDNA)" -category = "main" -optional = false -python-versions = ">=3.5" - -[[package]] -name = "iniconfig" -version = "1.1.1" -description = "iniconfig: brain-dead simple config-ini parsing" -category = "dev" -optional = false -python-versions = "*" - -[[package]] -name = "isort" -version = "5.10.1" -description = "A Python utility / library to sort Python imports." -category = "dev" -optional = false -python-versions = ">=3.6.1,<4.0" - -[package.extras] -pipfile_deprecated_finder = ["pipreqs", "requirementslib"] -requirements_deprecated_finder = ["pipreqs", "pip-api"] -colors = ["colorama (>=0.4.3,<0.5.0)"] -plugins = ["setuptools"] - -[[package]] -name = "makefun" -version = "1.12.1" -description = "Small library to dynamically create python functions." -category = "main" -optional = false -python-versions = "*" - -[[package]] -name = "mako" -version = "1.1.6" -description = "A super-fast templating language that borrows the best ideas from the existing templating languages." -category = "main" -optional = false -python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*" - -[package.dependencies] -MarkupSafe = ">=0.9.2" - -[package.extras] -babel = ["babel"] -lingua = ["lingua"] - -[[package]] -name = "markupsafe" -version = "2.0.1" -description = "Safely add untrusted strings to HTML/XML markup." -category = "main" -optional = false -python-versions = ">=3.6" - -[[package]] -name = "mccabe" -version = "0.6.1" -description = "McCabe checker, plugin for flake8" -category = "dev" -optional = false -python-versions = "*" - -[[package]] -name = "mypy-extensions" -version = "0.4.3" -description = "Experimental type system extensions for programs checked with the mypy typechecker." -category = "dev" -optional = false -python-versions = "*" - -[[package]] -name = "packaging" -version = "21.3" -description = "Core utilities for Python packages" -category = "dev" -optional = false -python-versions = ">=3.6" - -[package.dependencies] -pyparsing = ">=2.0.2,<3.0.5 || >3.0.5" - -[[package]] -name = "passlib" -version = "1.7.4" -description = "comprehensive password hashing framework supporting over 30 schemes" -category = "main" -optional = false -python-versions = "*" - -[package.dependencies] -bcrypt = {version = ">=3.1.0", optional = true, markers = "extra == \"bcrypt\""} - -[package.extras] -argon2 = ["argon2-cffi (>=18.2.0)"] -bcrypt = ["bcrypt (>=3.1.0)"] -build_docs = ["sphinx (>=1.6)", "sphinxcontrib-fulltoc (>=1.2.0)", "cloud-sptheme (>=1.10.1)"] -totp = ["cryptography"] - -[[package]] -name = "pathspec" -version = "0.9.0" -description = "Utility library for gitignore style pattern matching of file paths." -category = "dev" -optional = false -python-versions = "!=3.0.*,!=3.1.*,!=3.2.*,!=3.3.*,!=3.4.*,>=2.7" - -[[package]] -name = "platformdirs" -version = "2.4.1" -description = "A small Python module for determining appropriate platform-specific dirs, e.g. a \"user data dir\"." -category = "dev" -optional = false -python-versions = ">=3.7" - -[package.extras] -docs = ["Sphinx (>=4)", "furo (>=2021.7.5b38)", "proselint (>=0.10.2)", "sphinx-autodoc-typehints (>=1.12)"] -test = ["appdirs (==1.4.4)", "pytest (>=6)", "pytest-cov (>=2.7)", "pytest-mock (>=3.6)"] - -[[package]] -name = "pluggy" -version = "1.0.0" -description = "plugin and hook calling mechanisms for python" -category = "dev" -optional = false -python-versions = ">=3.6" - -[package.extras] -dev = ["pre-commit", "tox"] -testing = ["pytest", "pytest-benchmark"] - -[[package]] -name = "py" -version = "1.11.0" -description = "library with cross-python path, ini-parsing, io, code, log facilities" -category = "dev" -optional = false -python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, !=3.4.*" - -[[package]] -name = "pycodestyle" -version = "2.8.0" -description = "Python style guide checker" -category = "dev" -optional = false -python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, !=3.4.*" - -[[package]] -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.*" - -[[package]] -name = "pydantic" -version = "1.9.0" -description = "Data validation and settings management using python 3.6 type hinting" -category = "main" -optional = false -python-versions = ">=3.6.1" - -[package.dependencies] -email-validator = {version = ">=1.0.3", optional = true, markers = "extra == \"email\""} -typing-extensions = ">=3.7.4.3" - -[package.extras] -dotenv = ["python-dotenv (>=0.10.4)"] -email = ["email-validator (>=1.0.3)"] - -[[package]] -name = "pyflakes" -version = "2.4.0" -description = "passive checker of Python programs" -category = "dev" -optional = false -python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*" - -[[package]] -name = "pyjwt" -version = "2.3.0" -description = "JSON Web Token implementation in Python" -category = "main" -optional = false -python-versions = ">=3.6" - -[package.extras] -crypto = ["cryptography (>=3.3.1)"] -dev = ["sphinx", "sphinx-rtd-theme", "zope.interface", "cryptography (>=3.3.1)", "pytest (>=6.0.0,<7.0.0)", "coverage[toml] (==5.0.4)", "mypy", "pre-commit"] -docs = ["sphinx", "sphinx-rtd-theme", "zope.interface"] -tests = ["pytest (>=6.0.0,<7.0.0)", "coverage[toml] (==5.0.4)"] - -[[package]] -name = "pyparsing" -version = "3.0.6" -description = "Python parsing module" -category = "dev" -optional = false -python-versions = ">=3.6" - -[package.extras] -diagrams = ["jinja2", "railroad-diagrams"] - -[[package]] -name = "pytest" -version = "6.2.5" -description = "pytest: simple powerful testing with Python" -category = "dev" -optional = false -python-versions = ">=3.6" - -[package.dependencies] -atomicwrites = {version = ">=1.0", markers = "sys_platform == \"win32\""} -attrs = ">=19.2.0" -colorama = {version = "*", markers = "sys_platform == \"win32\""} -iniconfig = "*" -packaging = "*" -pluggy = ">=0.12,<2.0" -py = ">=1.8.2" -toml = "*" - -[package.extras] -testing = ["argcomplete", "hypothesis (>=3.56)", "mock", "nose", "requests", "xmlschema"] - -[[package]] -name = "pytest-asyncio" -version = "0.16.0" -description = "Pytest support for asyncio." -category = "dev" -optional = false -python-versions = ">= 3.6" - -[package.dependencies] -pytest = ">=5.4.0" - -[package.extras] -testing = ["coverage", "hypothesis (>=5.7.1)"] - -[[package]] -name = "python-dotenv" -version = "0.19.2" -description = "Read key-value pairs from a .env file and set them as environment variables" -category = "main" -optional = false -python-versions = ">=3.5" - -[package.extras] -cli = ["click (>=5.0)"] - -[[package]] -name = "python-multipart" -version = "0.0.5" -description = "A streaming multipart parser for Python" -category = "main" -optional = false -python-versions = "*" - -[package.dependencies] -six = ">=1.4.0" - -[[package]] -name = "requests" -version = "2.27.1" -description = "Python HTTP for Humans." -category = "dev" -optional = false -python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, !=3.4.*, !=3.5.*" - -[package.dependencies] -certifi = ">=2017.4.17" -charset-normalizer = {version = ">=2.0.0,<2.1.0", markers = "python_version >= \"3\""} -idna = {version = ">=2.5,<4", markers = "python_version >= \"3\""} -urllib3 = ">=1.21.1,<1.27" - -[package.extras] -socks = ["PySocks (>=1.5.6,!=1.5.7)", "win-inet-pton"] -use_chardet_on_py3 = ["chardet (>=3.0.2,<5)"] - -[[package]] -name = "rfc3986" -version = "1.5.0" -description = "Validating URI References per RFC 3986" -category = "dev" -optional = false -python-versions = "*" - -[package.dependencies] -idna = {version = "*", optional = true, markers = "extra == \"idna2008\""} - -[package.extras] -idna2008 = ["idna"] - -[[package]] -name = "six" -version = "1.16.0" -description = "Python 2 and 3 compatibility utilities" -category = "main" -optional = false -python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*" - -[[package]] -name = "sniffio" -version = "1.2.0" -description = "Sniff out which async library your code is running under" -category = "main" -optional = false -python-versions = ">=3.5" - -[[package]] -name = "sqlalchemy" -version = "1.4.29" -description = "Database Abstraction Library" -category = "main" -optional = false -python-versions = "!=3.0.*,!=3.1.*,!=3.2.*,!=3.3.*,!=3.4.*,!=3.5.*,>=2.7" - -[package.dependencies] -greenlet = {version = "!=0.4.17", markers = "python_version >= \"3\" and (platform_machine == \"aarch64\" or platform_machine == \"ppc64le\" or platform_machine == \"x86_64\" or platform_machine == \"amd64\" or platform_machine == \"AMD64\" or platform_machine == \"win32\" or platform_machine == \"WIN32\")"} - -[package.extras] -aiomysql = ["greenlet (!=0.4.17)", "aiomysql"] -aiosqlite = ["typing_extensions (!=3.10.0.1)", "greenlet (!=0.4.17)", "aiosqlite"] -asyncio = ["greenlet (!=0.4.17)"] -asyncmy = ["greenlet (!=0.4.17)", "asyncmy (>=0.2.3)"] -mariadb_connector = ["mariadb (>=1.0.1)"] -mssql = ["pyodbc"] -mssql_pymssql = ["pymssql"] -mssql_pyodbc = ["pyodbc"] -mypy = ["sqlalchemy2-stubs", "mypy (>=0.910)"] -mysql = ["mysqlclient (>=1.4.0,<2)", "mysqlclient (>=1.4.0)"] -mysql_connector = ["mysql-connector-python"] -oracle = ["cx_oracle (>=7,<8)", "cx_oracle (>=7)"] -postgresql = ["psycopg2 (>=2.7)"] -postgresql_asyncpg = ["greenlet (!=0.4.17)", "asyncpg"] -postgresql_pg8000 = ["pg8000 (>=1.16.6)"] -postgresql_psycopg2binary = ["psycopg2-binary"] -postgresql_psycopg2cffi = ["psycopg2cffi"] -pymysql = ["pymysql (<1)", "pymysql"] -sqlcipher = ["sqlcipher3-binary"] - -[[package]] -name = "sqlalchemy2-stubs" -version = "0.0.2a19" -description = "Typing Stubs for SQLAlchemy 1.4" -category = "dev" -optional = false -python-versions = ">=3.6" - -[package.dependencies] -typing-extensions = ">=3.7.4" - -[[package]] -name = "starlette" -version = "0.16.0" -description = "The little ASGI library that shines." -category = "main" -optional = false -python-versions = ">=3.6" - -[package.dependencies] -anyio = ">=3.0.0,<4" - -[package.extras] -full = ["itsdangerous", "jinja2", "python-multipart", "pyyaml", "requests", "graphene"] - -[[package]] -name = "toml" -version = "0.10.2" -description = "Python Library for Tom's Obvious, Minimal Language" -category = "dev" -optional = false -python-versions = ">=2.6, !=3.0.*, !=3.1.*, !=3.2.*" - -[[package]] -name = "tomli" -version = "1.2.3" -description = "A lil' TOML parser" -category = "dev" -optional = false -python-versions = ">=3.6" - -[[package]] -name = "typing-extensions" -version = "4.0.1" -description = "Backported and Experimental Type Hints for Python 3.6+" -category = "main" -optional = false -python-versions = ">=3.6" - -[[package]] -name = "urllib3" -version = "1.26.8" -description = "HTTP library with thread-safe connection pooling, file post, and more." -category = "dev" -optional = false -python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, !=3.4.*, <4" - -[package.extras] -brotli = ["brotlipy (>=0.6.0)"] -secure = ["pyOpenSSL (>=0.14)", "cryptography (>=1.3.4)", "idna (>=2.0.0)", "certifi", "ipaddress"] -socks = ["PySocks (>=1.5.6,!=1.5.7,<2.0)"] - -[[package]] -name = "uvicorn" -version = "0.16.0" -description = "The lightning-fast ASGI server." -category = "dev" -optional = false -python-versions = "*" - -[package.dependencies] -asgiref = ">=3.4.0" -click = ">=7.0" -h11 = ">=0.8" - -[package.extras] -standard = ["httptools (>=0.2.0,<0.4.0)", "watchgod (>=0.6)", "python-dotenv (>=0.13)", "PyYAML (>=5.1)", "websockets (>=9.1)", "websockets (>=10.0)", "uvloop (>=0.14.0,!=0.15.0,!=0.15.1)", "colorama (>=0.4)"] - -[metadata] -lock-version = "1.1" -python-versions = "^3.9" -content-hash = "0f47109307eb4b11a2898d492ccca09b9d5562dff15bfb9f7b71ef0366da122f" - -[metadata.files] -alembic = [ - {file = "alembic-1.7.5-py3-none-any.whl", hash = "sha256:a9dde941534e3d7573d9644e8ea62a2953541e27bc1793e166f60b777ae098b4"}, - {file = "alembic-1.7.5.tar.gz", hash = "sha256:7c328694a2e68f03ee971e63c3bd885846470373a5b532cf2c9f1601c413b153"}, -] -anyio = [ - {file = "anyio-3.4.0-py3-none-any.whl", hash = "sha256:2855a9423524abcdd652d942f8932fda1735210f77a6b392eafd9ff34d3fe020"}, - {file = "anyio-3.4.0.tar.gz", hash = "sha256:24adc69309fb5779bc1e06158e143e0b6d2c56b302a3ac3de3083c705a6ed39d"}, -] -asgiref = [ - {file = "asgiref-3.4.1-py3-none-any.whl", hash = "sha256:ffc141aa908e6f175673e7b1b3b7af4fdb0ecb738fc5c8b88f69f055c2415214"}, - {file = "asgiref-3.4.1.tar.gz", hash = "sha256:4ef1ab46b484e3c706329cedeff284a5d40824200638503f5768edb6de7d58e9"}, -] -asyncpg = [ - {file = "asyncpg-0.25.0-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:bf5e3408a14a17d480f36ebaf0401a12ff6ae5457fdf45e4e2775c51cc9517d3"}, - {file = "asyncpg-0.25.0-cp310-cp310-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:2bc197fc4aca2fd24f60241057998124012469d2e414aed3f992579db0c88e3a"}, - {file = "asyncpg-0.25.0-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:1a70783f6ffa34cc7dd2de20a873181414a34fd35a4a208a1f1a7f9f695e4ec4"}, - {file = "asyncpg-0.25.0-cp310-cp310-win32.whl", hash = "sha256:43cde84e996a3afe75f325a68300093425c2f47d340c0fc8912765cf24a1c095"}, - {file = "asyncpg-0.25.0-cp310-cp310-win_amd64.whl", hash = "sha256:56d88d7ef4341412cd9c68efba323a4519c916979ba91b95d4c08799d2ff0c09"}, - {file = "asyncpg-0.25.0-cp36-cp36m-macosx_10_9_x86_64.whl", hash = "sha256:a84d30e6f850bac0876990bcd207362778e2208df0bee8be8da9f1558255e634"}, - {file = "asyncpg-0.25.0-cp36-cp36m-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:beaecc52ad39614f6ca2e48c3ca15d56e24a2c15cbfdcb764a4320cc45f02fd5"}, - {file = "asyncpg-0.25.0-cp36-cp36m-musllinux_1_1_x86_64.whl", hash = "sha256:6f8f5fc975246eda83da8031a14004b9197f510c41511018e7b1bedde6968e92"}, - {file = "asyncpg-0.25.0-cp36-cp36m-win32.whl", hash = "sha256:ddb4c3263a8d63dcde3d2c4ac1c25206bfeb31fa83bd70fd539e10f87739dee4"}, - {file = "asyncpg-0.25.0-cp36-cp36m-win_amd64.whl", hash = "sha256:bf6dc9b55b9113f39eaa2057337ce3f9ef7de99a053b8a16360395ce588925cd"}, - {file = "asyncpg-0.25.0-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:acb311722352152936e58a8ee3c5b8e791b24e84cd7d777c414ff05b3530ca68"}, - {file = "asyncpg-0.25.0-cp37-cp37m-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:0a61fb196ce4dae2f2fa26eb20a778db21bbee484d2e798cb3cc988de13bdd1b"}, - {file = "asyncpg-0.25.0-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:2633331cbc8429030b4f20f712f8d0fbba57fa8555ee9b2f45f981b81328b256"}, - {file = "asyncpg-0.25.0-cp37-cp37m-win32.whl", hash = "sha256:863d36eba4a7caa853fd7d83fad5fd5306f050cc2fe6e54fbe10cdb30420e5e9"}, - {file = "asyncpg-0.25.0-cp37-cp37m-win_amd64.whl", hash = "sha256:fe471ccd915b739ca65e2e4dbd92a11b44a5b37f2e38f70827a1c147dafe0fa8"}, - {file = "asyncpg-0.25.0-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:72a1e12ea0cf7c1e02794b697e3ca967b2360eaa2ce5d4bfdd8604ec2d6b774b"}, - {file = "asyncpg-0.25.0-cp38-cp38-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:4327f691b1bdb222df27841938b3e04c14068166b3a97491bec2cb982f49f03e"}, - {file = "asyncpg-0.25.0-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:739bbd7f89a2b2f6bc44cb8bf967dab12c5bc714fcbe96e68d512be45ecdf962"}, - {file = "asyncpg-0.25.0-cp38-cp38-win32.whl", hash = "sha256:18d49e2d93a7139a2fdbd113e320cc47075049997268a61bfbe0dde680c55471"}, - {file = "asyncpg-0.25.0-cp38-cp38-win_amd64.whl", hash = "sha256:191fe6341385b7fdea7dbdcf47fd6db3fd198827dcc1f2b228476d13c05a03c6"}, - {file = "asyncpg-0.25.0-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:52fab7f1b2c29e187dd8781fce896249500cf055b63471ad66332e537e9b5f7e"}, - {file = "asyncpg-0.25.0-cp39-cp39-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:a738f1b2876f30d710d3dc1e7858160a0afe1603ba16bf5f391f5316eb0ed855"}, - {file = "asyncpg-0.25.0-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:5e4105f57ad1e8fbc8b1e535d8fcefa6ce6c71081228f08680c6dea24384ff0e"}, - {file = "asyncpg-0.25.0-cp39-cp39-win32.whl", hash = "sha256:f55918ded7b85723a5eaeb34e86e7b9280d4474be67df853ab5a7fa0cc7c6bf2"}, - {file = "asyncpg-0.25.0-cp39-cp39-win_amd64.whl", hash = "sha256:649e2966d98cc48d0646d9a4e29abecd8b59d38d55c256d5c857f6b27b7407ac"}, - {file = "asyncpg-0.25.0.tar.gz", hash = "sha256:63f8e6a69733b285497c2855464a34de657f2cccd25aeaeeb5071872e9382540"}, -] -atomicwrites = [ - {file = "atomicwrites-1.4.0-py2.py3-none-any.whl", hash = "sha256:6d1784dea7c0c8d4a5172b6c620f40b6e4cbfdf96d783691f2e1302a7b88e197"}, - {file = "atomicwrites-1.4.0.tar.gz", hash = "sha256:ae70396ad1a434f9c7046fd2dd196fc04b12f9e91ffb859164193be8b6168a7a"}, -] -attrs = [ - {file = "attrs-21.4.0-py2.py3-none-any.whl", hash = "sha256:2d27e3784d7a565d36ab851fe94887c5eccd6a463168875832a1be79c82828b4"}, - {file = "attrs-21.4.0.tar.gz", hash = "sha256:626ba8234211db98e869df76230a137c4c40a12d72445c45d5f5b716f076e2fd"}, -] -autoflake = [ - {file = "autoflake-1.4.tar.gz", hash = "sha256:61a353012cff6ab94ca062823d1fb2f692c4acda51c76ff83a8d77915fba51ea"}, -] -bcrypt = [ - {file = "bcrypt-3.2.0-cp36-abi3-macosx_10_9_x86_64.whl", hash = "sha256:c95d4cbebffafcdd28bd28bb4e25b31c50f6da605c81ffd9ad8a3d1b2ab7b1b6"}, - {file = "bcrypt-3.2.0-cp36-abi3-manylinux1_x86_64.whl", hash = "sha256:63d4e3ff96188e5898779b6057878fecf3f11cfe6ec3b313ea09955d587ec7a7"}, - {file = "bcrypt-3.2.0-cp36-abi3-manylinux2010_x86_64.whl", hash = "sha256:cd1ea2ff3038509ea95f687256c46b79f5fc382ad0aa3664d200047546d511d1"}, - {file = "bcrypt-3.2.0-cp36-abi3-manylinux2014_aarch64.whl", hash = "sha256:cdcdcb3972027f83fe24a48b1e90ea4b584d35f1cc279d76de6fc4b13376239d"}, - {file = "bcrypt-3.2.0-cp36-abi3-win32.whl", hash = "sha256:a67fb841b35c28a59cebed05fbd3e80eea26e6d75851f0574a9273c80f3e9b55"}, - {file = "bcrypt-3.2.0-cp36-abi3-win_amd64.whl", hash = "sha256:81fec756feff5b6818ea7ab031205e1d323d8943d237303baca2c5f9c7846f34"}, - {file = "bcrypt-3.2.0.tar.gz", hash = "sha256:5b93c1726e50a93a033c36e5ca7fdcd29a5c7395af50a6892f5d9e7c6cfbfb29"}, -] -black = [ - {file = "black-21.12b0-py3-none-any.whl", hash = "sha256:a615e69ae185e08fdd73e4715e260e2479c861b5740057fde6e8b4e3b7dd589f"}, - {file = "black-21.12b0.tar.gz", hash = "sha256:77b80f693a569e2e527958459634f18df9b0ba2625ba4e0c2d5da5be42e6f2b3"}, -] -certifi = [ - {file = "certifi-2021.10.8-py2.py3-none-any.whl", hash = "sha256:d62a0163eb4c2344ac042ab2bdf75399a71a2d8c7d47eac2e2ee91b9d6339569"}, - {file = "certifi-2021.10.8.tar.gz", hash = "sha256:78884e7c1d4b00ce3cea67b44566851c4343c120abd683433ce934a68ea58872"}, -] -cffi = [ - {file = "cffi-1.15.0-cp27-cp27m-macosx_10_9_x86_64.whl", hash = "sha256:c2502a1a03b6312837279c8c1bd3ebedf6c12c4228ddbad40912d671ccc8a962"}, - {file = "cffi-1.15.0-cp27-cp27m-manylinux1_i686.whl", hash = "sha256:23cfe892bd5dd8941608f93348c0737e369e51c100d03718f108bf1add7bd6d0"}, - {file = "cffi-1.15.0-cp27-cp27m-manylinux1_x86_64.whl", hash = "sha256:41d45de54cd277a7878919867c0f08b0cf817605e4eb94093e7516505d3c8d14"}, - {file = "cffi-1.15.0-cp27-cp27m-win32.whl", hash = "sha256:4a306fa632e8f0928956a41fa8e1d6243c71e7eb59ffbd165fc0b41e316b2474"}, - {file = "cffi-1.15.0-cp27-cp27m-win_amd64.whl", hash = "sha256:e7022a66d9b55e93e1a845d8c9eba2a1bebd4966cd8bfc25d9cd07d515b33fa6"}, - {file = "cffi-1.15.0-cp27-cp27mu-manylinux1_i686.whl", hash = "sha256:14cd121ea63ecdae71efa69c15c5543a4b5fbcd0bbe2aad864baca0063cecf27"}, - {file = "cffi-1.15.0-cp27-cp27mu-manylinux1_x86_64.whl", hash = "sha256:d4d692a89c5cf08a8557fdeb329b82e7bf609aadfaed6c0d79f5a449a3c7c023"}, - {file = "cffi-1.15.0-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:0104fb5ae2391d46a4cb082abdd5c69ea4eab79d8d44eaaf79f1b1fd806ee4c2"}, - {file = "cffi-1.15.0-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:91ec59c33514b7c7559a6acda53bbfe1b283949c34fe7440bcf917f96ac0723e"}, - {file = "cffi-1.15.0-cp310-cp310-manylinux_2_12_i686.manylinux2010_i686.whl", hash = "sha256:f5c7150ad32ba43a07c4479f40241756145a1f03b43480e058cfd862bf5041c7"}, - {file = "cffi-1.15.0-cp310-cp310-manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:00c878c90cb53ccfaae6b8bc18ad05d2036553e6d9d1d9dbcf323bbe83854ca3"}, - {file = "cffi-1.15.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:abb9a20a72ac4e0fdb50dae135ba5e77880518e742077ced47eb1499e29a443c"}, - {file = "cffi-1.15.0-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:a5263e363c27b653a90078143adb3d076c1a748ec9ecc78ea2fb916f9b861962"}, - {file = "cffi-1.15.0-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:f54a64f8b0c8ff0b64d18aa76675262e1700f3995182267998c31ae974fbc382"}, - {file = "cffi-1.15.0-cp310-cp310-win32.whl", hash = "sha256:c21c9e3896c23007803a875460fb786118f0cdd4434359577ea25eb556e34c55"}, - {file = "cffi-1.15.0-cp310-cp310-win_amd64.whl", hash = "sha256:5e069f72d497312b24fcc02073d70cb989045d1c91cbd53979366077959933e0"}, - {file = "cffi-1.15.0-cp36-cp36m-macosx_10_9_x86_64.whl", hash = "sha256:64d4ec9f448dfe041705426000cc13e34e6e5bb13736e9fd62e34a0b0c41566e"}, - {file = "cffi-1.15.0-cp36-cp36m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:2756c88cbb94231c7a147402476be2c4df2f6078099a6f4a480d239a8817ae39"}, - {file = "cffi-1.15.0-cp36-cp36m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:3b96a311ac60a3f6be21d2572e46ce67f09abcf4d09344c49274eb9e0bf345fc"}, - {file = "cffi-1.15.0-cp36-cp36m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:75e4024375654472cc27e91cbe9eaa08567f7fbdf822638be2814ce059f58032"}, - {file = "cffi-1.15.0-cp36-cp36m-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:59888172256cac5629e60e72e86598027aca6bf01fa2465bdb676d37636573e8"}, - {file = "cffi-1.15.0-cp36-cp36m-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:27c219baf94952ae9d50ec19651a687b826792055353d07648a5695413e0c605"}, - {file = "cffi-1.15.0-cp36-cp36m-win32.whl", hash = "sha256:4958391dbd6249d7ad855b9ca88fae690783a6be9e86df65865058ed81fc860e"}, - {file = "cffi-1.15.0-cp36-cp36m-win_amd64.whl", hash = "sha256:f6f824dc3bce0edab5f427efcfb1d63ee75b6fcb7282900ccaf925be84efb0fc"}, - {file = "cffi-1.15.0-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:06c48159c1abed75c2e721b1715c379fa3200c7784271b3c46df01383b593636"}, - {file = "cffi-1.15.0-cp37-cp37m-manylinux_2_12_i686.manylinux2010_i686.whl", hash = "sha256:c2051981a968d7de9dd2d7b87bcb9c939c74a34626a6e2f8181455dd49ed69e4"}, - {file = "cffi-1.15.0-cp37-cp37m-manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:fd8a250edc26254fe5b33be00402e6d287f562b6a5b2152dec302fa15bb3e997"}, - {file = "cffi-1.15.0-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:91d77d2a782be4274da750752bb1650a97bfd8f291022b379bb8e01c66b4e96b"}, - {file = "cffi-1.15.0-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:45db3a33139e9c8f7c09234b5784a5e33d31fd6907800b316decad50af323ff2"}, - {file = "cffi-1.15.0-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:263cc3d821c4ab2213cbe8cd8b355a7f72a8324577dc865ef98487c1aeee2bc7"}, - {file = "cffi-1.15.0-cp37-cp37m-win32.whl", hash = "sha256:17771976e82e9f94976180f76468546834d22a7cc404b17c22df2a2c81db0c66"}, - {file = "cffi-1.15.0-cp37-cp37m-win_amd64.whl", hash = "sha256:3415c89f9204ee60cd09b235810be700e993e343a408693e80ce7f6a40108029"}, - {file = "cffi-1.15.0-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:4238e6dab5d6a8ba812de994bbb0a79bddbdf80994e4ce802b6f6f3142fcc880"}, - {file = "cffi-1.15.0-cp38-cp38-manylinux_2_12_i686.manylinux2010_i686.whl", hash = "sha256:0808014eb713677ec1292301ea4c81ad277b6cdf2fdd90fd540af98c0b101d20"}, - {file = "cffi-1.15.0-cp38-cp38-manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:57e9ac9ccc3101fac9d6014fba037473e4358ef4e89f8e181f8951a2c0162024"}, - {file = "cffi-1.15.0-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:8b6c2ea03845c9f501ed1313e78de148cd3f6cad741a75d43a29b43da27f2e1e"}, - {file = "cffi-1.15.0-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:10dffb601ccfb65262a27233ac273d552ddc4d8ae1bf93b21c94b8511bffe728"}, - {file = "cffi-1.15.0-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:786902fb9ba7433aae840e0ed609f45c7bcd4e225ebb9c753aa39725bb3e6ad6"}, - {file = "cffi-1.15.0-cp38-cp38-win32.whl", hash = "sha256:da5db4e883f1ce37f55c667e5c0de439df76ac4cb55964655906306918e7363c"}, - {file = "cffi-1.15.0-cp38-cp38-win_amd64.whl", hash = "sha256:181dee03b1170ff1969489acf1c26533710231c58f95534e3edac87fff06c443"}, - {file = "cffi-1.15.0-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:45e8636704eacc432a206ac7345a5d3d2c62d95a507ec70d62f23cd91770482a"}, - {file = "cffi-1.15.0-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:31fb708d9d7c3f49a60f04cf5b119aeefe5644daba1cd2a0fe389b674fd1de37"}, - {file = "cffi-1.15.0-cp39-cp39-manylinux_2_12_i686.manylinux2010_i686.whl", hash = "sha256:6dc2737a3674b3e344847c8686cf29e500584ccad76204efea14f451d4cc669a"}, - {file = "cffi-1.15.0-cp39-cp39-manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:74fdfdbfdc48d3f47148976f49fab3251e550a8720bebc99bf1483f5bfb5db3e"}, - {file = "cffi-1.15.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ffaa5c925128e29efbde7301d8ecaf35c8c60ffbcd6a1ffd3a552177c8e5e796"}, - {file = "cffi-1.15.0-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:3f7d084648d77af029acb79a0ff49a0ad7e9d09057a9bf46596dac9514dc07df"}, - {file = "cffi-1.15.0-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:ef1f279350da2c586a69d32fc8733092fd32cc8ac95139a00377841f59a3f8d8"}, - {file = "cffi-1.15.0-cp39-cp39-win32.whl", hash = "sha256:2a23af14f408d53d5e6cd4e3d9a24ff9e05906ad574822a10563efcef137979a"}, - {file = "cffi-1.15.0-cp39-cp39-win_amd64.whl", hash = "sha256:3773c4d81e6e818df2efbc7dd77325ca0dcb688116050fb2b3011218eda36139"}, - {file = "cffi-1.15.0.tar.gz", hash = "sha256:920f0d66a896c2d99f0adbb391f990a84091179542c205fa53ce5787aff87954"}, -] -charset-normalizer = [ - {file = "charset-normalizer-2.0.10.tar.gz", hash = "sha256:876d180e9d7432c5d1dfd4c5d26b72f099d503e8fcc0feb7532c9289be60fcbd"}, - {file = "charset_normalizer-2.0.10-py3-none-any.whl", hash = "sha256:cb957888737fc0bbcd78e3df769addb41fd1ff8cf950dc9e7ad7793f1bf44455"}, -] -click = [ - {file = "click-8.0.3-py3-none-any.whl", hash = "sha256:353f466495adaeb40b6b5f592f9f91cb22372351c84caeb068132442a4518ef3"}, - {file = "click-8.0.3.tar.gz", hash = "sha256:410e932b050f5eed773c4cda94de75971c89cdb3155a72a0831139a79e5ecb5b"}, -] -colorama = [ - {file = "colorama-0.4.4-py2.py3-none-any.whl", hash = "sha256:9f47eda37229f68eee03b24b9748937c7dc3868f906e8ba69fbcbdd3bc5dc3e2"}, - {file = "colorama-0.4.4.tar.gz", hash = "sha256:5941b2b48a20143d2267e95b1c2a7603ce057ee39fd88e7329b0c292aa16869b"}, -] -coverage = [ - {file = "coverage-6.2-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:6dbc1536e105adda7a6312c778f15aaabe583b0e9a0b0a324990334fd458c94b"}, - {file = "coverage-6.2-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:174cf9b4bef0db2e8244f82059a5a72bd47e1d40e71c68ab055425172b16b7d0"}, - {file = "coverage-6.2-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_12_i686.manylinux2010_i686.whl", hash = "sha256:92b8c845527eae547a2a6617d336adc56394050c3ed8a6918683646328fbb6da"}, - {file = "coverage-6.2-cp310-cp310-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:c7912d1526299cb04c88288e148c6c87c0df600eca76efd99d84396cfe00ef1d"}, - {file = "coverage-6.2-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:d5d2033d5db1d58ae2d62f095e1aefb6988af65b4b12cb8987af409587cc0739"}, - {file = "coverage-6.2-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:3feac4084291642165c3a0d9eaebedf19ffa505016c4d3db15bfe235718d4971"}, - {file = "coverage-6.2-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:276651978c94a8c5672ea60a2656e95a3cce2a3f31e9fb2d5ebd4c215d095840"}, - {file = "coverage-6.2-cp310-cp310-win32.whl", hash = "sha256:f506af4f27def639ba45789fa6fde45f9a217da0be05f8910458e4557eed020c"}, - {file = "coverage-6.2-cp310-cp310-win_amd64.whl", hash = "sha256:3f7c17209eef285c86f819ff04a6d4cbee9b33ef05cbcaae4c0b4e8e06b3ec8f"}, - {file = "coverage-6.2-cp311-cp311-macosx_10_14_x86_64.whl", hash = "sha256:13362889b2d46e8d9f97c421539c97c963e34031ab0cb89e8ca83a10cc71ac76"}, - {file = "coverage-6.2-cp311-cp311-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:22e60a3ca5acba37d1d4a2ee66e051f5b0e1b9ac950b5b0cf4aa5366eda41d47"}, - {file = "coverage-6.2-cp311-cp311-win_amd64.whl", hash = "sha256:b637c57fdb8be84e91fac60d9325a66a5981f8086c954ea2772efe28425eaf64"}, - {file = "coverage-6.2-cp36-cp36m-macosx_10_9_x86_64.whl", hash = "sha256:f467bbb837691ab5a8ca359199d3429a11a01e6dfb3d9dcc676dc035ca93c0a9"}, - {file = "coverage-6.2-cp36-cp36m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:2641f803ee9f95b1f387f3e8f3bf28d83d9b69a39e9911e5bfee832bea75240d"}, - {file = "coverage-6.2-cp36-cp36m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_12_i686.manylinux2010_i686.whl", hash = "sha256:1219d760ccfafc03c0822ae2e06e3b1248a8e6d1a70928966bafc6838d3c9e48"}, - {file = "coverage-6.2-cp36-cp36m-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:9a2b5b52be0a8626fcbffd7e689781bf8c2ac01613e77feda93d96184949a98e"}, - {file = "coverage-6.2-cp36-cp36m-musllinux_1_1_aarch64.whl", hash = "sha256:8e2c35a4c1f269704e90888e56f794e2d9c0262fb0c1b1c8c4ee44d9b9e77b5d"}, - {file = "coverage-6.2-cp36-cp36m-musllinux_1_1_i686.whl", hash = "sha256:5d6b09c972ce9200264c35a1d53d43ca55ef61836d9ec60f0d44273a31aa9f17"}, - {file = "coverage-6.2-cp36-cp36m-musllinux_1_1_x86_64.whl", hash = "sha256:e3db840a4dee542e37e09f30859f1612da90e1c5239a6a2498c473183a50e781"}, - {file = "coverage-6.2-cp36-cp36m-win32.whl", hash = "sha256:4e547122ca2d244f7c090fe3f4b5a5861255ff66b7ab6d98f44a0222aaf8671a"}, - {file = "coverage-6.2-cp36-cp36m-win_amd64.whl", hash = "sha256:01774a2c2c729619760320270e42cd9e797427ecfddd32c2a7b639cdc481f3c0"}, - {file = "coverage-6.2-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:fb8b8ee99b3fffe4fd86f4c81b35a6bf7e4462cba019997af2fe679365db0c49"}, - {file = "coverage-6.2-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:619346d57c7126ae49ac95b11b0dc8e36c1dd49d148477461bb66c8cf13bb521"}, - {file = "coverage-6.2-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_12_i686.manylinux2010_i686.whl", hash = "sha256:0a7726f74ff63f41e95ed3a89fef002916c828bb5fcae83b505b49d81a066884"}, - {file = "coverage-6.2-cp37-cp37m-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:cfd9386c1d6f13b37e05a91a8583e802f8059bebfccde61a418c5808dea6bbfa"}, - {file = "coverage-6.2-cp37-cp37m-musllinux_1_1_aarch64.whl", hash = "sha256:17e6c11038d4ed6e8af1407d9e89a2904d573be29d51515f14262d7f10ef0a64"}, - {file = "coverage-6.2-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:c254b03032d5a06de049ce8bca8338a5185f07fb76600afff3c161e053d88617"}, - {file = "coverage-6.2-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:dca38a21e4423f3edb821292e97cec7ad38086f84313462098568baedf4331f8"}, - {file = "coverage-6.2-cp37-cp37m-win32.whl", hash = "sha256:600617008aa82032ddeace2535626d1bc212dfff32b43989539deda63b3f36e4"}, - {file = "coverage-6.2-cp37-cp37m-win_amd64.whl", hash = "sha256:bf154ba7ee2fd613eb541c2bc03d3d9ac667080a737449d1a3fb342740eb1a74"}, - {file = "coverage-6.2-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:f9afb5b746781fc2abce26193d1c817b7eb0e11459510fba65d2bd77fe161d9e"}, - {file = "coverage-6.2-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:edcada2e24ed68f019175c2b2af2a8b481d3d084798b8c20d15d34f5c733fa58"}, - {file = "coverage-6.2-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_12_i686.manylinux2010_i686.whl", hash = "sha256:a9c8c4283e17690ff1a7427123ffb428ad6a52ed720d550e299e8291e33184dc"}, - {file = "coverage-6.2-cp38-cp38-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:f614fc9956d76d8a88a88bb41ddc12709caa755666f580af3a688899721efecd"}, - {file = "coverage-6.2-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:9365ed5cce5d0cf2c10afc6add145c5037d3148585b8ae0e77cc1efdd6aa2953"}, - {file = "coverage-6.2-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:8bdfe9ff3a4ea37d17f172ac0dff1e1c383aec17a636b9b35906babc9f0f5475"}, - {file = "coverage-6.2-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:63c424e6f5b4ab1cf1e23a43b12f542b0ec2e54f99ec9f11b75382152981df57"}, - {file = "coverage-6.2-cp38-cp38-win32.whl", hash = "sha256:49dbff64961bc9bdd2289a2bda6a3a5a331964ba5497f694e2cbd540d656dc1c"}, - {file = "coverage-6.2-cp38-cp38-win_amd64.whl", hash = "sha256:9a29311bd6429be317c1f3fe4bc06c4c5ee45e2fa61b2a19d4d1d6111cb94af2"}, - {file = "coverage-6.2-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:03b20e52b7d31be571c9c06b74746746d4eb82fc260e594dc662ed48145e9efd"}, - {file = "coverage-6.2-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:215f8afcc02a24c2d9a10d3790b21054b58d71f4b3c6f055d4bb1b15cecce685"}, - {file = "coverage-6.2-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_12_i686.manylinux2010_i686.whl", hash = "sha256:a4bdeb0a52d1d04123b41d90a4390b096f3ef38eee35e11f0b22c2d031222c6c"}, - {file = "coverage-6.2-cp39-cp39-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:c332d8f8d448ded473b97fefe4a0983265af21917d8b0cdcb8bb06b2afe632c3"}, - {file = "coverage-6.2-cp39-cp39-win32.whl", hash = "sha256:6e1394d24d5938e561fbeaa0cd3d356207579c28bd1792f25a068743f2d5b282"}, - {file = "coverage-6.2-cp39-cp39-win_amd64.whl", hash = "sha256:86f2e78b1eff847609b1ca8050c9e1fa3bd44ce755b2ec30e70f2d3ba3844644"}, - {file = "coverage-6.2-pp36.pp37.pp38-none-any.whl", hash = "sha256:5829192582c0ec8ca4a2532407bc14c2f338d9878a10442f5d03804a95fac9de"}, - {file = "coverage-6.2.tar.gz", hash = "sha256:e2cad8093172b7d1595b4ad66f24270808658e11acf43a8f95b41276162eb5b8"}, -] -dnspython = [ - {file = "dnspython-2.1.0-py3-none-any.whl", hash = "sha256:95d12f6ef0317118d2a1a6fc49aac65ffec7eb8087474158f42f26a639135216"}, - {file = "dnspython-2.1.0.zip", hash = "sha256:e4a87f0b573201a0f3727fa18a516b055fd1107e0e5477cded4a2de497df1dd4"}, -] -email-validator = [ - {file = "email_validator-1.1.3-py2.py3-none-any.whl", hash = "sha256:5675c8ceb7106a37e40e2698a57c056756bf3f272cfa8682a4f87ebd95d8440b"}, - {file = "email_validator-1.1.3.tar.gz", hash = "sha256:aa237a65f6f4da067119b7df3f13e89c25c051327b2b5b66dc075f33d62480d7"}, -] -fastapi = [ - {file = "fastapi-0.70.1-py3-none-any.whl", hash = "sha256:5367226c7bcd7bfb2e17edaf225fd9a983095b1372281e9a3eb661336fb93748"}, - {file = "fastapi-0.70.1.tar.gz", hash = "sha256:21d03979b5336375c66fa5d1f3126c6beca650d5d2166fbb78345a30d33c8d06"}, -] -fastapi-users = [ - {file = "fastapi-users-9.2.0.tar.gz", hash = "sha256:49d452ce785134aea64428be3747785d1cae1cfd1fd546eefc248088d806ff06"}, - {file = "fastapi_users-9.2.0-py3-none-any.whl", hash = "sha256:67d0c7fdcf5bbaf46849b79c12fd3188627746753389f732b4c459b279944253"}, -] -fastapi-users-db-sqlalchemy = [ - {file = "fastapi-users-db-sqlalchemy-2.0.4.tar.gz", hash = "sha256:93bd5ba48f7a7e9fe43b62a48ad7c5ec5993c8230c6dafb61c341ceee811ebf1"}, - {file = "fastapi_users_db_sqlalchemy-2.0.4-py3-none-any.whl", hash = "sha256:4d246157c18335353111bfdf47dca081a6663a337e2f7e9670eb9606730399bb"}, -] -flake8 = [ - {file = "flake8-4.0.1-py2.py3-none-any.whl", hash = "sha256:479b1304f72536a55948cb40a32dce8bb0ffe3501e26eaf292c7e60eb5e0428d"}, - {file = "flake8-4.0.1.tar.gz", hash = "sha256:806e034dda44114815e23c16ef92f95c91e4c71100ff52813adf7132a6ad870d"}, -] -greenlet = [ - {file = "greenlet-1.1.2-cp27-cp27m-macosx_10_14_x86_64.whl", hash = "sha256:58df5c2a0e293bf665a51f8a100d3e9956febfbf1d9aaf8c0677cf70218910c6"}, - {file = "greenlet-1.1.2-cp27-cp27m-manylinux1_x86_64.whl", hash = "sha256:aec52725173bd3a7b56fe91bc56eccb26fbdff1386ef123abb63c84c5b43b63a"}, - {file = "greenlet-1.1.2-cp27-cp27m-manylinux2010_x86_64.whl", hash = "sha256:833e1551925ed51e6b44c800e71e77dacd7e49181fdc9ac9a0bf3714d515785d"}, - {file = "greenlet-1.1.2-cp27-cp27m-win32.whl", hash = "sha256:aa5b467f15e78b82257319aebc78dd2915e4c1436c3c0d1ad6f53e47ba6e2713"}, - {file = "greenlet-1.1.2-cp27-cp27m-win_amd64.whl", hash = "sha256:40b951f601af999a8bf2ce8c71e8aaa4e8c6f78ff8afae7b808aae2dc50d4c40"}, - {file = "greenlet-1.1.2-cp27-cp27mu-manylinux1_x86_64.whl", hash = "sha256:95e69877983ea39b7303570fa6760f81a3eec23d0e3ab2021b7144b94d06202d"}, - {file = "greenlet-1.1.2-cp27-cp27mu-manylinux2010_x86_64.whl", hash = "sha256:356b3576ad078c89a6107caa9c50cc14e98e3a6c4874a37c3e0273e4baf33de8"}, - {file = "greenlet-1.1.2-cp310-cp310-macosx_10_14_x86_64.whl", hash = "sha256:8639cadfda96737427330a094476d4c7a56ac03de7265622fcf4cfe57c8ae18d"}, - {file = "greenlet-1.1.2-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:97e5306482182170ade15c4b0d8386ded995a07d7cc2ca8f27958d34d6736497"}, - {file = "greenlet-1.1.2-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:e6a36bb9474218c7a5b27ae476035497a6990e21d04c279884eb10d9b290f1b1"}, - {file = "greenlet-1.1.2-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:abb7a75ed8b968f3061327c433a0fbd17b729947b400747c334a9c29a9af6c58"}, - {file = "greenlet-1.1.2-cp310-cp310-win_amd64.whl", hash = "sha256:14d4f3cd4e8b524ae9b8aa567858beed70c392fdec26dbdb0a8a418392e71708"}, - {file = "greenlet-1.1.2-cp35-cp35m-macosx_10_14_x86_64.whl", hash = "sha256:17ff94e7a83aa8671a25bf5b59326ec26da379ace2ebc4411d690d80a7fbcf23"}, - {file = "greenlet-1.1.2-cp35-cp35m-manylinux1_x86_64.whl", hash = "sha256:9f3cba480d3deb69f6ee2c1825060177a22c7826431458c697df88e6aeb3caee"}, - {file = "greenlet-1.1.2-cp35-cp35m-manylinux2010_x86_64.whl", hash = "sha256:fa877ca7f6b48054f847b61d6fa7bed5cebb663ebc55e018fda12db09dcc664c"}, - {file = "greenlet-1.1.2-cp35-cp35m-win32.whl", hash = "sha256:7cbd7574ce8e138bda9df4efc6bf2ab8572c9aff640d8ecfece1b006b68da963"}, - {file = "greenlet-1.1.2-cp35-cp35m-win_amd64.whl", hash = "sha256:903bbd302a2378f984aef528f76d4c9b1748f318fe1294961c072bdc7f2ffa3e"}, - {file = "greenlet-1.1.2-cp36-cp36m-macosx_10_14_x86_64.whl", hash = "sha256:049fe7579230e44daef03a259faa24511d10ebfa44f69411d99e6a184fe68073"}, - {file = "greenlet-1.1.2-cp36-cp36m-manylinux1_x86_64.whl", hash = "sha256:dd0b1e9e891f69e7675ba5c92e28b90eaa045f6ab134ffe70b52e948aa175b3c"}, - {file = "greenlet-1.1.2-cp36-cp36m-manylinux2010_x86_64.whl", hash = "sha256:7418b6bfc7fe3331541b84bb2141c9baf1ec7132a7ecd9f375912eca810e714e"}, - {file = "greenlet-1.1.2-cp36-cp36m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:f9d29ca8a77117315101425ec7ec2a47a22ccf59f5593378fc4077ac5b754fce"}, - {file = "greenlet-1.1.2-cp36-cp36m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:21915eb821a6b3d9d8eefdaf57d6c345b970ad722f856cd71739493ce003ad08"}, - {file = "greenlet-1.1.2-cp36-cp36m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:eff9d20417ff9dcb0d25e2defc2574d10b491bf2e693b4e491914738b7908168"}, - {file = "greenlet-1.1.2-cp36-cp36m-win32.whl", hash = "sha256:32ca72bbc673adbcfecb935bb3fb1b74e663d10a4b241aaa2f5a75fe1d1f90aa"}, - {file = "greenlet-1.1.2-cp36-cp36m-win_amd64.whl", hash = "sha256:f0214eb2a23b85528310dad848ad2ac58e735612929c8072f6093f3585fd342d"}, - {file = "greenlet-1.1.2-cp37-cp37m-macosx_10_14_x86_64.whl", hash = "sha256:b92e29e58bef6d9cfd340c72b04d74c4b4e9f70c9fa7c78b674d1fec18896dc4"}, - {file = "greenlet-1.1.2-cp37-cp37m-manylinux1_x86_64.whl", hash = "sha256:fdcec0b8399108577ec290f55551d926d9a1fa6cad45882093a7a07ac5ec147b"}, - {file = "greenlet-1.1.2-cp37-cp37m-manylinux2010_x86_64.whl", hash = "sha256:93f81b134a165cc17123626ab8da2e30c0455441d4ab5576eed73a64c025b25c"}, - {file = "greenlet-1.1.2-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:1e12bdc622676ce47ae9abbf455c189e442afdde8818d9da983085df6312e7a1"}, - {file = "greenlet-1.1.2-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:8c790abda465726cfb8bb08bd4ca9a5d0a7bd77c7ac1ca1b839ad823b948ea28"}, - {file = "greenlet-1.1.2-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f276df9830dba7a333544bd41070e8175762a7ac20350786b322b714b0e654f5"}, - {file = "greenlet-1.1.2-cp37-cp37m-win32.whl", hash = "sha256:64e6175c2e53195278d7388c454e0b30997573f3f4bd63697f88d855f7a6a1fc"}, - {file = "greenlet-1.1.2-cp37-cp37m-win_amd64.whl", hash = "sha256:b11548073a2213d950c3f671aa88e6f83cda6e2fb97a8b6317b1b5b33d850e06"}, - {file = "greenlet-1.1.2-cp38-cp38-macosx_10_14_x86_64.whl", hash = "sha256:9633b3034d3d901f0a46b7939f8c4d64427dfba6bbc5a36b1a67364cf148a1b0"}, - {file = "greenlet-1.1.2-cp38-cp38-manylinux1_x86_64.whl", hash = "sha256:eb6ea6da4c787111adf40f697b4e58732ee0942b5d3bd8f435277643329ba627"}, - {file = "greenlet-1.1.2-cp38-cp38-manylinux2010_x86_64.whl", hash = "sha256:f3acda1924472472ddd60c29e5b9db0cec629fbe3c5c5accb74d6d6d14773478"}, - {file = "greenlet-1.1.2-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:e859fcb4cbe93504ea18008d1df98dee4f7766db66c435e4882ab35cf70cac43"}, - {file = "greenlet-1.1.2-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:00e44c8afdbe5467e4f7b5851be223be68adb4272f44696ee71fe46b7036a711"}, - {file = "greenlet-1.1.2-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:ec8c433b3ab0419100bd45b47c9c8551248a5aee30ca5e9d399a0b57ac04651b"}, - {file = "greenlet-1.1.2-cp38-cp38-win32.whl", hash = "sha256:288c6a76705dc54fba69fbcb59904ae4ad768b4c768839b8ca5fdadec6dd8cfd"}, - {file = "greenlet-1.1.2-cp38-cp38-win_amd64.whl", hash = "sha256:8d2f1fb53a421b410751887eb4ff21386d119ef9cde3797bf5e7ed49fb51a3b3"}, - {file = "greenlet-1.1.2-cp39-cp39-macosx_10_14_x86_64.whl", hash = "sha256:166eac03e48784a6a6e0e5f041cfebb1ab400b394db188c48b3a84737f505b67"}, - {file = "greenlet-1.1.2-cp39-cp39-manylinux1_x86_64.whl", hash = "sha256:572e1787d1460da79590bf44304abbc0a2da944ea64ec549188fa84d89bba7ab"}, - {file = "greenlet-1.1.2-cp39-cp39-manylinux2010_x86_64.whl", hash = "sha256:be5f425ff1f5f4b3c1e33ad64ab994eed12fc284a6ea71c5243fd564502ecbe5"}, - {file = "greenlet-1.1.2-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:b1692f7d6bc45e3200844be0dba153612103db241691088626a33ff1f24a0d88"}, - {file = "greenlet-1.1.2-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:7227b47e73dedaa513cdebb98469705ef0d66eb5a1250144468e9c3097d6b59b"}, - {file = "greenlet-1.1.2-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:7ff61ff178250f9bb3cd89752df0f1dd0e27316a8bd1465351652b1b4a4cdfd3"}, - {file = "greenlet-1.1.2-cp39-cp39-win32.whl", hash = "sha256:f70a9e237bb792c7cc7e44c531fd48f5897961701cdaa06cf22fc14965c496cf"}, - {file = "greenlet-1.1.2-cp39-cp39-win_amd64.whl", hash = "sha256:013d61294b6cd8fe3242932c1c5e36e5d1db2c8afb58606c5a67efce62c1f5fd"}, - {file = "greenlet-1.1.2.tar.gz", hash = "sha256:e30f5ea4ae2346e62cedde8794a56858a67b878dd79f7df76a0767e356b1744a"}, -] -h11 = [ - {file = "h11-0.12.0-py3-none-any.whl", hash = "sha256:36a3cb8c0a032f56e2da7084577878a035d3b61d104230d4bd49c0c6b555a9c6"}, - {file = "h11-0.12.0.tar.gz", hash = "sha256:47222cb6067e4a307d535814917cd98fd0a57b6788ce715755fa2b6c28b56042"}, -] -httpcore = [ - {file = "httpcore-0.14.4-py3-none-any.whl", hash = "sha256:9410fe352bea732311f2b2bee0555c8cc5e62b9a73b9d3272fe125a2aa6eb28e"}, - {file = "httpcore-0.14.4.tar.gz", hash = "sha256:d4305811f604d3c2e22869147392f134796976ff946c96a8cfba87f4e0171d83"}, -] -httpx = [ - {file = "httpx-0.21.3-py3-none-any.whl", hash = "sha256:df9a0fd43fa79dbab411d83eb1ea6f7a525c96ad92e60c2d7f40388971b25777"}, - {file = "httpx-0.21.3.tar.gz", hash = "sha256:7a3eb67ef0b8abbd6d9402248ef2f84a76080fa1c839f8662e6eb385640e445a"}, -] -idna = [ - {file = "idna-3.3-py3-none-any.whl", hash = "sha256:84d9dd047ffa80596e0f246e2eab0b391788b0503584e8945f2368256d2735ff"}, - {file = "idna-3.3.tar.gz", hash = "sha256:9d643ff0a55b762d5cdb124b8eaa99c66322e2157b69160bc32796e824360e6d"}, -] -iniconfig = [ - {file = "iniconfig-1.1.1-py2.py3-none-any.whl", hash = "sha256:011e24c64b7f47f6ebd835bb12a743f2fbe9a26d4cecaa7f53bc4f35ee9da8b3"}, - {file = "iniconfig-1.1.1.tar.gz", hash = "sha256:bc3af051d7d14b2ee5ef9969666def0cd1a000e121eaea580d4a313df4b37f32"}, -] -isort = [ - {file = "isort-5.10.1-py3-none-any.whl", hash = "sha256:6f62d78e2f89b4500b080fe3a81690850cd254227f27f75c3a0c491a1f351ba7"}, - {file = "isort-5.10.1.tar.gz", hash = "sha256:e8443a5e7a020e9d7f97f1d7d9cd17c88bcb3bc7e218bf9cf5095fe550be2951"}, -] -makefun = [ - {file = "makefun-1.12.1-py2.py3-none-any.whl", hash = "sha256:639ac01a68ddd76ab156ca435bcd89dab25c717fb09af23f1563dc26362b4dcc"}, - {file = "makefun-1.12.1.tar.gz", hash = "sha256:4d0e90ca3fdbdeb6a4a0891e2da7d4b8e80386e19e6db91ce29b8aa5c876ecfe"}, -] -mako = [ - {file = "Mako-1.1.6-py2.py3-none-any.whl", hash = "sha256:afaf8e515d075b22fad7d7b8b30e4a1c90624ff2f3733a06ec125f5a5f043a57"}, - {file = "Mako-1.1.6.tar.gz", hash = "sha256:4e9e345a41924a954251b95b4b28e14a301145b544901332e658907a7464b6b2"}, -] -markupsafe = [ - {file = "MarkupSafe-2.0.1-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:d8446c54dc28c01e5a2dbac5a25f071f6653e6e40f3a8818e8b45d790fe6ef53"}, - {file = "MarkupSafe-2.0.1-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:36bc903cbb393720fad60fc28c10de6acf10dc6cc883f3e24ee4012371399a38"}, - {file = "MarkupSafe-2.0.1-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:2d7d807855b419fc2ed3e631034685db6079889a1f01d5d9dac950f764da3dad"}, - {file = "MarkupSafe-2.0.1-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_12_i686.manylinux2010_i686.whl", hash = "sha256:add36cb2dbb8b736611303cd3bfcee00afd96471b09cda130da3581cbdc56a6d"}, - {file = "MarkupSafe-2.0.1-cp310-cp310-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:168cd0a3642de83558a5153c8bd34f175a9a6e7f6dc6384b9655d2697312a646"}, - {file = "MarkupSafe-2.0.1-cp310-cp310-win32.whl", hash = "sha256:99df47edb6bda1249d3e80fdabb1dab8c08ef3975f69aed437cb69d0a5de1e28"}, - {file = "MarkupSafe-2.0.1-cp310-cp310-win_amd64.whl", hash = "sha256:e0f138900af21926a02425cf736db95be9f4af72ba1bb21453432a07f6082134"}, - {file = "MarkupSafe-2.0.1-cp36-cp36m-macosx_10_9_x86_64.whl", hash = "sha256:f9081981fe268bd86831e5c75f7de206ef275defcb82bc70740ae6dc507aee51"}, - {file = "MarkupSafe-2.0.1-cp36-cp36m-manylinux1_i686.whl", hash = "sha256:0955295dd5eec6cb6cc2fe1698f4c6d84af2e92de33fbcac4111913cd100a6ff"}, - {file = "MarkupSafe-2.0.1-cp36-cp36m-manylinux1_x86_64.whl", hash = "sha256:0446679737af14f45767963a1a9ef7620189912317d095f2d9ffa183a4d25d2b"}, - {file = "MarkupSafe-2.0.1-cp36-cp36m-manylinux2010_i686.whl", hash = "sha256:f826e31d18b516f653fe296d967d700fddad5901ae07c622bb3705955e1faa94"}, - {file = "MarkupSafe-2.0.1-cp36-cp36m-manylinux2010_x86_64.whl", hash = "sha256:fa130dd50c57d53368c9d59395cb5526eda596d3ffe36666cd81a44d56e48872"}, - {file = "MarkupSafe-2.0.1-cp36-cp36m-manylinux2014_aarch64.whl", hash = "sha256:905fec760bd2fa1388bb5b489ee8ee5f7291d692638ea5f67982d968366bef9f"}, - {file = "MarkupSafe-2.0.1-cp36-cp36m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:bf5d821ffabf0ef3533c39c518f3357b171a1651c1ff6827325e4489b0e46c3c"}, - {file = "MarkupSafe-2.0.1-cp36-cp36m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_12_i686.manylinux2010_i686.whl", hash = "sha256:0d4b31cc67ab36e3392bbf3862cfbadac3db12bdd8b02a2731f509ed5b829724"}, - {file = "MarkupSafe-2.0.1-cp36-cp36m-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:baa1a4e8f868845af802979fcdbf0bb11f94f1cb7ced4c4b8a351bb60d108145"}, - {file = "MarkupSafe-2.0.1-cp36-cp36m-win32.whl", hash = "sha256:6c4ca60fa24e85fe25b912b01e62cb969d69a23a5d5867682dd3e80b5b02581d"}, - {file = "MarkupSafe-2.0.1-cp36-cp36m-win_amd64.whl", hash = "sha256:b2f4bf27480f5e5e8ce285a8c8fd176c0b03e93dcc6646477d4630e83440c6a9"}, - {file = "MarkupSafe-2.0.1-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:0717a7390a68be14b8c793ba258e075c6f4ca819f15edfc2a3a027c823718567"}, - {file = "MarkupSafe-2.0.1-cp37-cp37m-manylinux1_i686.whl", hash = "sha256:6557b31b5e2c9ddf0de32a691f2312a32f77cd7681d8af66c2692efdbef84c18"}, - {file = "MarkupSafe-2.0.1-cp37-cp37m-manylinux1_x86_64.whl", hash = "sha256:49e3ceeabbfb9d66c3aef5af3a60cc43b85c33df25ce03d0031a608b0a8b2e3f"}, - {file = "MarkupSafe-2.0.1-cp37-cp37m-manylinux2010_i686.whl", hash = "sha256:d7f9850398e85aba693bb640262d3611788b1f29a79f0c93c565694658f4071f"}, - {file = "MarkupSafe-2.0.1-cp37-cp37m-manylinux2010_x86_64.whl", hash = "sha256:6a7fae0dd14cf60ad5ff42baa2e95727c3d81ded453457771d02b7d2b3f9c0c2"}, - {file = "MarkupSafe-2.0.1-cp37-cp37m-manylinux2014_aarch64.whl", hash = "sha256:b7f2d075102dc8c794cbde1947378051c4e5180d52d276987b8d28a3bd58c17d"}, - {file = "MarkupSafe-2.0.1-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:e9936f0b261d4df76ad22f8fee3ae83b60d7c3e871292cd42f40b81b70afae85"}, - {file = "MarkupSafe-2.0.1-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_12_i686.manylinux2010_i686.whl", hash = "sha256:2a7d351cbd8cfeb19ca00de495e224dea7e7d919659c2841bbb7f420ad03e2d6"}, - {file = "MarkupSafe-2.0.1-cp37-cp37m-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:60bf42e36abfaf9aff1f50f52644b336d4f0a3fd6d8a60ca0d054ac9f713a864"}, - {file = "MarkupSafe-2.0.1-cp37-cp37m-win32.whl", hash = "sha256:a30e67a65b53ea0a5e62fe23682cfe22712e01f453b95233b25502f7c61cb415"}, - {file = "MarkupSafe-2.0.1-cp37-cp37m-win_amd64.whl", hash = "sha256:611d1ad9a4288cf3e3c16014564df047fe08410e628f89805e475368bd304914"}, - {file = "MarkupSafe-2.0.1-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:5bb28c636d87e840583ee3adeb78172efc47c8b26127267f54a9c0ec251d41a9"}, - {file = "MarkupSafe-2.0.1-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:be98f628055368795d818ebf93da628541e10b75b41c559fdf36d104c5787066"}, - {file = "MarkupSafe-2.0.1-cp38-cp38-manylinux1_i686.whl", hash = "sha256:1d609f577dc6e1aa17d746f8bd3c31aa4d258f4070d61b2aa5c4166c1539de35"}, - {file = "MarkupSafe-2.0.1-cp38-cp38-manylinux1_x86_64.whl", hash = "sha256:7d91275b0245b1da4d4cfa07e0faedd5b0812efc15b702576d103293e252af1b"}, - {file = "MarkupSafe-2.0.1-cp38-cp38-manylinux2010_i686.whl", hash = "sha256:01a9b8ea66f1658938f65b93a85ebe8bc016e6769611be228d797c9d998dd298"}, - {file = "MarkupSafe-2.0.1-cp38-cp38-manylinux2010_x86_64.whl", hash = "sha256:47ab1e7b91c098ab893b828deafa1203de86d0bc6ab587b160f78fe6c4011f75"}, - {file = "MarkupSafe-2.0.1-cp38-cp38-manylinux2014_aarch64.whl", hash = "sha256:97383d78eb34da7e1fa37dd273c20ad4320929af65d156e35a5e2d89566d9dfb"}, - {file = "MarkupSafe-2.0.1-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:6fcf051089389abe060c9cd7caa212c707e58153afa2c649f00346ce6d260f1b"}, - {file = "MarkupSafe-2.0.1-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_12_i686.manylinux2010_i686.whl", hash = "sha256:5855f8438a7d1d458206a2466bf82b0f104a3724bf96a1c781ab731e4201731a"}, - {file = "MarkupSafe-2.0.1-cp38-cp38-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:3dd007d54ee88b46be476e293f48c85048603f5f516008bee124ddd891398ed6"}, - {file = "MarkupSafe-2.0.1-cp38-cp38-win32.whl", hash = "sha256:023cb26ec21ece8dc3907c0e8320058b2e0cb3c55cf9564da612bc325bed5e64"}, - {file = "MarkupSafe-2.0.1-cp38-cp38-win_amd64.whl", hash = "sha256:984d76483eb32f1bcb536dc27e4ad56bba4baa70be32fa87152832cdd9db0833"}, - {file = "MarkupSafe-2.0.1-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:2ef54abee730b502252bcdf31b10dacb0a416229b72c18b19e24a4509f273d26"}, - {file = "MarkupSafe-2.0.1-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:3c112550557578c26af18a1ccc9e090bfe03832ae994343cfdacd287db6a6ae7"}, - {file = "MarkupSafe-2.0.1-cp39-cp39-manylinux1_i686.whl", hash = "sha256:53edb4da6925ad13c07b6d26c2a852bd81e364f95301c66e930ab2aef5b5ddd8"}, - {file = "MarkupSafe-2.0.1-cp39-cp39-manylinux1_x86_64.whl", hash = "sha256:f5653a225f31e113b152e56f154ccbe59eeb1c7487b39b9d9f9cdb58e6c79dc5"}, - {file = "MarkupSafe-2.0.1-cp39-cp39-manylinux2010_i686.whl", hash = "sha256:4efca8f86c54b22348a5467704e3fec767b2db12fc39c6d963168ab1d3fc9135"}, - {file = "MarkupSafe-2.0.1-cp39-cp39-manylinux2010_x86_64.whl", hash = "sha256:ab3ef638ace319fa26553db0624c4699e31a28bb2a835c5faca8f8acf6a5a902"}, - {file = "MarkupSafe-2.0.1-cp39-cp39-manylinux2014_aarch64.whl", hash = "sha256:f8ba0e8349a38d3001fae7eadded3f6606f0da5d748ee53cc1dab1d6527b9509"}, - {file = "MarkupSafe-2.0.1-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:c47adbc92fc1bb2b3274c4b3a43ae0e4573d9fbff4f54cd484555edbf030baf1"}, - {file = "MarkupSafe-2.0.1-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_12_i686.manylinux2010_i686.whl", hash = "sha256:37205cac2a79194e3750b0af2a5720d95f786a55ce7df90c3af697bfa100eaac"}, - {file = "MarkupSafe-2.0.1-cp39-cp39-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:1f2ade76b9903f39aa442b4aadd2177decb66525062db244b35d71d0ee8599b6"}, - {file = "MarkupSafe-2.0.1-cp39-cp39-win32.whl", hash = "sha256:10f82115e21dc0dfec9ab5c0223652f7197feb168c940f3ef61563fc2d6beb74"}, - {file = "MarkupSafe-2.0.1-cp39-cp39-win_amd64.whl", hash = "sha256:693ce3f9e70a6cf7d2fb9e6c9d8b204b6b39897a2c4a1aa65728d5ac97dcc1d8"}, - {file = "MarkupSafe-2.0.1.tar.gz", hash = "sha256:594c67807fb16238b30c44bdf74f36c02cdf22d1c8cda91ef8a0ed8dabf5620a"}, -] -mccabe = [ - {file = "mccabe-0.6.1-py2.py3-none-any.whl", hash = "sha256:ab8a6258860da4b6677da4bd2fe5dc2c659cff31b3ee4f7f5d64e79735b80d42"}, - {file = "mccabe-0.6.1.tar.gz", hash = "sha256:dd8d182285a0fe56bace7f45b5e7d1a6ebcbf524e8f3bd87eb0f125271b8831f"}, -] -mypy-extensions = [ - {file = "mypy_extensions-0.4.3-py2.py3-none-any.whl", hash = "sha256:090fedd75945a69ae91ce1303b5824f428daf5a028d2f6ab8a299250a846f15d"}, - {file = "mypy_extensions-0.4.3.tar.gz", hash = "sha256:2d82818f5bb3e369420cb3c4060a7970edba416647068eb4c5343488a6c604a8"}, -] -packaging = [ - {file = "packaging-21.3-py3-none-any.whl", hash = "sha256:ef103e05f519cdc783ae24ea4e2e0f508a9c99b2d4969652eed6a2e1ea5bd522"}, - {file = "packaging-21.3.tar.gz", hash = "sha256:dd47c42927d89ab911e606518907cc2d3a1f38bbd026385970643f9c5b8ecfeb"}, -] -passlib = [ - {file = "passlib-1.7.4-py2.py3-none-any.whl", hash = "sha256:aa6bca462b8d8bda89c70b382f0c298a20b5560af6cbfa2dce410c0a2fb669f1"}, - {file = "passlib-1.7.4.tar.gz", hash = "sha256:defd50f72b65c5402ab2c573830a6978e5f202ad0d984793c8dde2c4152ebe04"}, -] -pathspec = [ - {file = "pathspec-0.9.0-py2.py3-none-any.whl", hash = "sha256:7d15c4ddb0b5c802d161efc417ec1a2558ea2653c2e8ad9c19098201dc1c993a"}, - {file = "pathspec-0.9.0.tar.gz", hash = "sha256:e564499435a2673d586f6b2130bb5b95f04a3ba06f81b8f895b651a3c76aabb1"}, -] -platformdirs = [ - {file = "platformdirs-2.4.1-py3-none-any.whl", hash = "sha256:1d7385c7db91728b83efd0ca99a5afb296cab9d0ed8313a45ed8ba17967ecfca"}, - {file = "platformdirs-2.4.1.tar.gz", hash = "sha256:440633ddfebcc36264232365d7840a970e75e1018d15b4327d11f91909045fda"}, -] -pluggy = [ - {file = "pluggy-1.0.0-py2.py3-none-any.whl", hash = "sha256:74134bbf457f031a36d68416e1509f34bd5ccc019f0bcc952c7b909d06b37bd3"}, - {file = "pluggy-1.0.0.tar.gz", hash = "sha256:4224373bacce55f955a878bf9cfa763c1e360858e330072059e10bad68531159"}, -] -py = [ - {file = "py-1.11.0-py2.py3-none-any.whl", hash = "sha256:607c53218732647dff4acdfcd50cb62615cedf612e72d1724fb1a0cc6405b378"}, - {file = "py-1.11.0.tar.gz", hash = "sha256:51c75c4126074b472f746a24399ad32f6053d1b34b68d2fa41e558e6f4a98719"}, -] -pycodestyle = [ - {file = "pycodestyle-2.8.0-py2.py3-none-any.whl", hash = "sha256:720f8b39dde8b293825e7ff02c475f3077124006db4f440dcbc9a20b76548a20"}, - {file = "pycodestyle-2.8.0.tar.gz", hash = "sha256:eddd5847ef438ea1c7870ca7eb78a9d47ce0cdb4851a5523949f2601d0cbbe7f"}, -] -pycparser = [ - {file = "pycparser-2.21-py2.py3-none-any.whl", hash = "sha256:8ee45429555515e1f6b185e78100aea234072576aa43ab53aefcae078162fca9"}, - {file = "pycparser-2.21.tar.gz", hash = "sha256:e644fdec12f7872f86c58ff790da456218b10f863970249516d60a5eaca77206"}, -] -pydantic = [ - {file = "pydantic-1.9.0-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:cb23bcc093697cdea2708baae4f9ba0e972960a835af22560f6ae4e7e47d33f5"}, - {file = "pydantic-1.9.0-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:1d5278bd9f0eee04a44c712982343103bba63507480bfd2fc2790fa70cd64cf4"}, - {file = "pydantic-1.9.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:ab624700dc145aa809e6f3ec93fb8e7d0f99d9023b713f6a953637429b437d37"}, - {file = "pydantic-1.9.0-cp310-cp310-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:c8d7da6f1c1049eefb718d43d99ad73100c958a5367d30b9321b092771e96c25"}, - {file = "pydantic-1.9.0-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:3c3b035103bd4e2e4a28da9da7ef2fa47b00ee4a9cf4f1a735214c1bcd05e0f6"}, - {file = "pydantic-1.9.0-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:3011b975c973819883842c5ab925a4e4298dffccf7782c55ec3580ed17dc464c"}, - {file = "pydantic-1.9.0-cp310-cp310-win_amd64.whl", hash = "sha256:086254884d10d3ba16da0588604ffdc5aab3f7f09557b998373e885c690dd398"}, - {file = "pydantic-1.9.0-cp36-cp36m-macosx_10_9_x86_64.whl", hash = "sha256:0fe476769acaa7fcddd17cadd172b156b53546ec3614a4d880e5d29ea5fbce65"}, - {file = "pydantic-1.9.0-cp36-cp36m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:c8e9dcf1ac499679aceedac7e7ca6d8641f0193c591a2d090282aaf8e9445a46"}, - {file = "pydantic-1.9.0-cp36-cp36m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:d1e4c28f30e767fd07f2ddc6f74f41f034d1dd6bc526cd59e63a82fe8bb9ef4c"}, - {file = "pydantic-1.9.0-cp36-cp36m-musllinux_1_1_i686.whl", hash = "sha256:c86229333cabaaa8c51cf971496f10318c4734cf7b641f08af0a6fbf17ca3054"}, - {file = "pydantic-1.9.0-cp36-cp36m-musllinux_1_1_x86_64.whl", hash = "sha256:c0727bda6e38144d464daec31dff936a82917f431d9c39c39c60a26567eae3ed"}, - {file = "pydantic-1.9.0-cp36-cp36m-win_amd64.whl", hash = "sha256:dee5ef83a76ac31ab0c78c10bd7d5437bfdb6358c95b91f1ba7ff7b76f9996a1"}, - {file = "pydantic-1.9.0-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:d9c9bdb3af48e242838f9f6e6127de9be7063aad17b32215ccc36a09c5cf1070"}, - {file = "pydantic-1.9.0-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:2ee7e3209db1e468341ef41fe263eb655f67f5c5a76c924044314e139a1103a2"}, - {file = "pydantic-1.9.0-cp37-cp37m-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:0b6037175234850ffd094ca77bf60fb54b08b5b22bc85865331dd3bda7a02fa1"}, - {file = "pydantic-1.9.0-cp37-cp37m-musllinux_1_1_i686.whl", hash = "sha256:b2571db88c636d862b35090ccf92bf24004393f85c8870a37f42d9f23d13e032"}, - {file = "pydantic-1.9.0-cp37-cp37m-musllinux_1_1_x86_64.whl", hash = "sha256:8b5ac0f1c83d31b324e57a273da59197c83d1bb18171e512908fe5dc7278a1d6"}, - {file = "pydantic-1.9.0-cp37-cp37m-win_amd64.whl", hash = "sha256:bbbc94d0c94dd80b3340fc4f04fd4d701f4b038ebad72c39693c794fd3bc2d9d"}, - {file = "pydantic-1.9.0-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:e0896200b6a40197405af18828da49f067c2fa1f821491bc8f5bde241ef3f7d7"}, - {file = "pydantic-1.9.0-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:7bdfdadb5994b44bd5579cfa7c9b0e1b0e540c952d56f627eb227851cda9db77"}, - {file = "pydantic-1.9.0-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:574936363cd4b9eed8acdd6b80d0143162f2eb654d96cb3a8ee91d3e64bf4cf9"}, - {file = "pydantic-1.9.0-cp38-cp38-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:c556695b699f648c58373b542534308922c46a1cda06ea47bc9ca45ef5b39ae6"}, - {file = "pydantic-1.9.0-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:f947352c3434e8b937e3aa8f96f47bdfe6d92779e44bb3f41e4c213ba6a32145"}, - {file = "pydantic-1.9.0-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:5e48ef4a8b8c066c4a31409d91d7ca372a774d0212da2787c0d32f8045b1e034"}, - {file = "pydantic-1.9.0-cp38-cp38-win_amd64.whl", hash = "sha256:96f240bce182ca7fe045c76bcebfa0b0534a1bf402ed05914a6f1dadff91877f"}, - {file = "pydantic-1.9.0-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:815ddebb2792efd4bba5488bc8fde09c29e8ca3227d27cf1c6990fc830fd292b"}, - {file = "pydantic-1.9.0-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:6c5b77947b9e85a54848343928b597b4f74fc364b70926b3c4441ff52620640c"}, - {file = "pydantic-1.9.0-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:4c68c3bc88dbda2a6805e9a142ce84782d3930f8fdd9655430d8576315ad97ce"}, - {file = "pydantic-1.9.0-cp39-cp39-manylinux_2_5_i686.manylinux1_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:5a79330f8571faf71bf93667d3ee054609816f10a259a109a0738dac983b23c3"}, - {file = "pydantic-1.9.0-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:f5a64b64ddf4c99fe201ac2724daada8595ada0d102ab96d019c1555c2d6441d"}, - {file = "pydantic-1.9.0-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:a733965f1a2b4090a5238d40d983dcd78f3ecea221c7af1497b845a9709c1721"}, - {file = "pydantic-1.9.0-cp39-cp39-win_amd64.whl", hash = "sha256:2cc6a4cb8a118ffec2ca5fcb47afbacb4f16d0ab8b7350ddea5e8ef7bcc53a16"}, - {file = "pydantic-1.9.0-py3-none-any.whl", hash = "sha256:085ca1de245782e9b46cefcf99deecc67d418737a1fd3f6a4f511344b613a5b3"}, - {file = "pydantic-1.9.0.tar.gz", hash = "sha256:742645059757a56ecd886faf4ed2441b9c0cd406079c2b4bee51bcc3fbcd510a"}, -] -pyflakes = [ - {file = "pyflakes-2.4.0-py2.py3-none-any.whl", hash = "sha256:3bb3a3f256f4b7968c9c788781e4ff07dce46bdf12339dcda61053375426ee2e"}, - {file = "pyflakes-2.4.0.tar.gz", hash = "sha256:05a85c2872edf37a4ed30b0cce2f6093e1d0581f8c19d7393122da7e25b2b24c"}, -] -pyjwt = [ - {file = "PyJWT-2.3.0-py3-none-any.whl", hash = "sha256:e0c4bb8d9f0af0c7f5b1ec4c5036309617d03d56932877f2f7a0beeb5318322f"}, - {file = "PyJWT-2.3.0.tar.gz", hash = "sha256:b888b4d56f06f6dcd777210c334e69c737be74755d3e5e9ee3fe67dc18a0ee41"}, -] -pyparsing = [ - {file = "pyparsing-3.0.6-py3-none-any.whl", hash = "sha256:04ff808a5b90911829c55c4e26f75fa5ca8a2f5f36aa3a51f68e27033341d3e4"}, - {file = "pyparsing-3.0.6.tar.gz", hash = "sha256:d9bdec0013ef1eb5a84ab39a3b3868911598afa494f5faa038647101504e2b81"}, -] -pytest = [ - {file = "pytest-6.2.5-py3-none-any.whl", hash = "sha256:7310f8d27bc79ced999e760ca304d69f6ba6c6649c0b60fb0e04a4a77cacc134"}, - {file = "pytest-6.2.5.tar.gz", hash = "sha256:131b36680866a76e6781d13f101efb86cf674ebb9762eb70d3082b6f29889e89"}, -] -pytest-asyncio = [ - {file = "pytest-asyncio-0.16.0.tar.gz", hash = "sha256:7496c5977ce88c34379df64a66459fe395cd05543f0a2f837016e7144391fcfb"}, - {file = "pytest_asyncio-0.16.0-py3-none-any.whl", hash = "sha256:5f2a21273c47b331ae6aa5b36087047b4899e40f03f18397c0e65fa5cca54e9b"}, -] -python-dotenv = [ - {file = "python-dotenv-0.19.2.tar.gz", hash = "sha256:a5de49a31e953b45ff2d2fd434bbc2670e8db5273606c1e737cc6b93eff3655f"}, - {file = "python_dotenv-0.19.2-py2.py3-none-any.whl", hash = "sha256:32b2bdc1873fd3a3c346da1c6db83d0053c3c62f28f1f38516070c4c8971b1d3"}, -] -python-multipart = [ - {file = "python-multipart-0.0.5.tar.gz", hash = "sha256:f7bb5f611fc600d15fa47b3974c8aa16e93724513b49b5f95c81e6624c83fa43"}, -] -requests = [ - {file = "requests-2.27.1-py2.py3-none-any.whl", hash = "sha256:f22fa1e554c9ddfd16e6e41ac79759e17be9e492b3587efa038054674760e72d"}, - {file = "requests-2.27.1.tar.gz", hash = "sha256:68d7c56fd5a8999887728ef304a6d12edc7be74f1cfa47714fc8b414525c9a61"}, -] -rfc3986 = [ - {file = "rfc3986-1.5.0-py2.py3-none-any.whl", hash = "sha256:a86d6e1f5b1dc238b218b012df0aa79409667bb209e58da56d0b94704e712a97"}, - {file = "rfc3986-1.5.0.tar.gz", hash = "sha256:270aaf10d87d0d4e095063c65bf3ddbc6ee3d0b226328ce21e036f946e421835"}, -] -six = [ - {file = "six-1.16.0-py2.py3-none-any.whl", hash = "sha256:8abb2f1d86890a2dfb989f9a77cfcfd3e47c2a354b01111771326f8aa26e0254"}, - {file = "six-1.16.0.tar.gz", hash = "sha256:1e61c37477a1626458e36f7b1d82aa5c9b094fa4802892072e49de9c60c4c926"}, -] -sniffio = [ - {file = "sniffio-1.2.0-py3-none-any.whl", hash = "sha256:471b71698eac1c2112a40ce2752bb2f4a4814c22a54a3eed3676bc0f5ca9f663"}, - {file = "sniffio-1.2.0.tar.gz", hash = "sha256:c4666eecec1d3f50960c6bdf61ab7bc350648da6c126e3cf6898d8cd4ddcd3de"}, -] -sqlalchemy = [ - {file = "SQLAlchemy-1.4.29-cp27-cp27m-macosx_10_14_x86_64.whl", hash = "sha256:da64423c05256f4ab8c0058b90202053b201cbe3a081f3a43eb590cd554395ab"}, - {file = "SQLAlchemy-1.4.29-cp27-cp27m-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:0fc4eec2f46b40bdd42112b3be3fbbf88e194bcf02950fbb88bcdc1b32f07dc7"}, - {file = "SQLAlchemy-1.4.29-cp27-cp27m-win32.whl", hash = "sha256:101d2e100ba9182c9039699588e0b2d833c54b3bad46c67c192159876c9f27ea"}, - {file = "SQLAlchemy-1.4.29-cp27-cp27m-win_amd64.whl", hash = "sha256:ceac84dd9abbbe115e8be0c817bed85d9fa639b4d294e7817f9e61162d5f766c"}, - {file = "SQLAlchemy-1.4.29-cp27-cp27mu-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:15b65887b6c324cad638c7671cb95985817b733242a7eb69edd7cdf6953be1e0"}, - {file = "SQLAlchemy-1.4.29-cp310-cp310-macosx_10_14_x86_64.whl", hash = "sha256:78abc507d17753ed434b6cc0c0693126279723d5656d9775bfcac966a99a899b"}, - {file = "SQLAlchemy-1.4.29-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:eb8c993706e86178ce15a6b86a335a2064f52254b640e7f53365e716423d33f4"}, - {file = "SQLAlchemy-1.4.29-cp310-cp310-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:804e22d5b6165a4f3f019dd9c94bec5687de985a9c54286b93ded9f7846b8c82"}, - {file = "SQLAlchemy-1.4.29-cp310-cp310-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:56d9d62021946263d4478c9ca012fbd1805f10994cb615c88e7bfd1ae14604d8"}, - {file = "SQLAlchemy-1.4.29-cp310-cp310-win32.whl", hash = "sha256:027f356c727db24f3c75828c7feb426f87ce1241242d08958e454bd025810660"}, - {file = "SQLAlchemy-1.4.29-cp310-cp310-win_amd64.whl", hash = "sha256:debaf09a823061f88a8dee04949814cf7e82fb394c5bca22c780cb03172ca23b"}, - {file = "SQLAlchemy-1.4.29-cp36-cp36m-macosx_10_14_x86_64.whl", hash = "sha256:dc27dcc6c72eb38be7f144e9c2c4372d35a3684d3a6dd43bd98c1238358ee17c"}, - {file = "SQLAlchemy-1.4.29-cp36-cp36m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:e4ddd4f2e247128c58bb3dd4489922874afce157d2cff0b2295d67fcd0f22494"}, - {file = "SQLAlchemy-1.4.29-cp36-cp36m-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:9ce960a1dc60524136cf6f75621588e2508a117e04a6e3eedb0968bd13b8c824"}, - {file = "SQLAlchemy-1.4.29-cp36-cp36m-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5919e647e1d4805867ea556ed4967c68b4d8b266059fa35020dbaed8ffdd60f3"}, - {file = "SQLAlchemy-1.4.29-cp36-cp36m-win32.whl", hash = "sha256:886359f734b95ad1ef443b13bb4518bcade4db4f9553c9ce33d6d04ebda8d44e"}, - {file = "SQLAlchemy-1.4.29-cp36-cp36m-win_amd64.whl", hash = "sha256:e9cc6d844e24c307c3272677982a9b33816aeb45e4977791c3bdd47637a8d810"}, - {file = "SQLAlchemy-1.4.29-cp37-cp37m-macosx_10_14_x86_64.whl", hash = "sha256:5e9cd33459afa69c88fa648e803d1f1245e3caa60bfe8b80a9595e5edd3bda9c"}, - {file = "SQLAlchemy-1.4.29-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:eeaebceb24b46e884c4ad3c04f37feb178b81f6ce720af19bfa2592ca32fdef7"}, - {file = "SQLAlchemy-1.4.29-cp37-cp37m-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:e89347d3bd2ef873832b47e85f4bbd810a5e626c5e749d90a07638da100eb1c8"}, - {file = "SQLAlchemy-1.4.29-cp37-cp37m-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5a717c2e70fd1bb477161c4cc85258e41d978584fbe5522613618195f7e87d9b"}, - {file = "SQLAlchemy-1.4.29-cp37-cp37m-win32.whl", hash = "sha256:f74d6c05d2d163464adbdfbc1ab85048cc15462ff7d134b8aed22bd521e1faa5"}, - {file = "SQLAlchemy-1.4.29-cp37-cp37m-win_amd64.whl", hash = "sha256:621854dbb4d2413c759a5571564170de45ef37299df52e78e62b42e2880192e1"}, - {file = "SQLAlchemy-1.4.29-cp38-cp38-macosx_10_14_x86_64.whl", hash = "sha256:f3909194751bb6cb7c5511dd18bcf77e6e3f0b31604ed4004dffa9461f71e737"}, - {file = "SQLAlchemy-1.4.29-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:dd49d21d1f03c81fbec9080ecdc4486d5ddda67e7fbb75ebf48294465c022cdc"}, - {file = "SQLAlchemy-1.4.29-cp38-cp38-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:e5f6959466a42b6569774c257e55f9cd85200d5b0ba09f0f5d8b5845349c5822"}, - {file = "SQLAlchemy-1.4.29-cp38-cp38-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:0072f9887aabe66db23f818bbe950cfa1b6127c5cb769b00bcc07935b3adb0ad"}, - {file = "SQLAlchemy-1.4.29-cp38-cp38-win32.whl", hash = "sha256:ad618d687d26d4cbfa9c6fa6141d59e05bcdfc60cb6e1f1d3baa18d8c62fef5f"}, - {file = "SQLAlchemy-1.4.29-cp38-cp38-win_amd64.whl", hash = "sha256:878daecb6405e786b07f97e1c77a9cfbbbec17432e8a90c487967e32cfdecb33"}, - {file = "SQLAlchemy-1.4.29-cp39-cp39-macosx_10_14_x86_64.whl", hash = "sha256:e027bdf0a4cf6bd0a3ad3b998643ea374d7991bd117b90bf9982e41ceb742941"}, - {file = "SQLAlchemy-1.4.29-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:c5de7adfb91d351f44062b8dedf29f49d4af7cb765be65816e79223a4e31062b"}, - {file = "SQLAlchemy-1.4.29-cp39-cp39-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:fbc6e63e481fa323036f305ada96a3362e1d60dd2bfa026cac10c3553e6880e9"}, - {file = "SQLAlchemy-1.4.29-cp39-cp39-manylinux_2_5_x86_64.manylinux1_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:7dd0502cb091660ad0d89c5e95a29825f37cde2a5249957838e975871fbffaad"}, - {file = "SQLAlchemy-1.4.29-cp39-cp39-win32.whl", hash = "sha256:37b46bfc4af3dc226acb6fa28ecd2e1fd223433dc5e15a2bad62bf0a0cbb4e8b"}, - {file = "SQLAlchemy-1.4.29-cp39-cp39-win_amd64.whl", hash = "sha256:08cfd35eecaba79be930c9bfd2e1f0c67a7e1314355d83a378f9a512b1cf7587"}, - {file = "SQLAlchemy-1.4.29.tar.gz", hash = "sha256:fa2bad14e1474ba649cfc969c1d2ec915dd3e79677f346bbfe08e93ef9020b39"}, -] -sqlalchemy2-stubs = [ - {file = "sqlalchemy2-stubs-0.0.2a19.tar.gz", hash = "sha256:2117c48ce5acfe33bf9c9bfce2a981632d931949e68fa313aa5c2a3bc980ca7a"}, - {file = "sqlalchemy2_stubs-0.0.2a19-py3-none-any.whl", hash = "sha256:aac7dca77a2c49e5f0934976421d5e25ae4dc5e27db48c01e055f81caa1e3ead"}, -] -starlette = [ - {file = "starlette-0.16.0-py3-none-any.whl", hash = "sha256:38eb24bf705a2c317e15868e384c1b8a12ca396e5a3c3a003db7e667c43f939f"}, - {file = "starlette-0.16.0.tar.gz", hash = "sha256:e1904b5d0007aee24bdd3c43994be9b3b729f4f58e740200de1d623f8c3a8870"}, -] -toml = [ - {file = "toml-0.10.2-py2.py3-none-any.whl", hash = "sha256:806143ae5bfb6a3c6e736a764057db0e6a0e05e338b5630894a5f779cabb4f9b"}, - {file = "toml-0.10.2.tar.gz", hash = "sha256:b3bda1d108d5dd99f4a20d24d9c348e91c4db7ab1b749200bded2f839ccbe68f"}, -] -tomli = [ - {file = "tomli-1.2.3-py3-none-any.whl", hash = "sha256:e3069e4be3ead9668e21cb9b074cd948f7b3113fd9c8bba083f48247aab8b11c"}, - {file = "tomli-1.2.3.tar.gz", hash = "sha256:05b6166bff487dc068d322585c7ea4ef78deed501cc124060e0f238e89a9231f"}, -] -typing-extensions = [ - {file = "typing_extensions-4.0.1-py3-none-any.whl", hash = "sha256:7f001e5ac290a0c0401508864c7ec868be4e701886d5b573a9528ed3973d9d3b"}, - {file = "typing_extensions-4.0.1.tar.gz", hash = "sha256:4ca091dea149f945ec56afb48dae714f21e8692ef22a395223bcd328961b6a0e"}, -] -urllib3 = [ - {file = "urllib3-1.26.8-py2.py3-none-any.whl", hash = "sha256:000ca7f471a233c2251c6c7023ee85305721bfdf18621ebff4fd17a8653427ed"}, - {file = "urllib3-1.26.8.tar.gz", hash = "sha256:0e7c33d9a63e7ddfcb86780aac87befc2fbddf46c58dbb487e0855f7ceec283c"}, -] -uvicorn = [ - {file = "uvicorn-0.16.0-py3-none-any.whl", hash = "sha256:d8c839231f270adaa6d338d525e2652a0b4a5f4c2430b5c4ef6ae4d11776b0d2"}, - {file = "uvicorn-0.16.0.tar.gz", hash = "sha256:eacb66afa65e0648fcbce5e746b135d09722231ffffc61883d4fac2b62fbea8d"}, -] diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/pyproject.toml b/{{cookiecutter.project_name}}/template_fastapi_users/pyproject.toml deleted file mode 100644 index e8cd804..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/pyproject.toml +++ /dev/null @@ -1,41 +0,0 @@ -[tool.poetry] -name = "{{cookiecutter.project_name}}" -version = "0.1.0-alpha" -description = "FastAPI project generated using minimal-fastapi-postgres-template." -authors = ["admin "] - -[tool.poetry.dependencies] -python = "^3.9" -SQLAlchemy = {extras = ["asyncio"], version = "^1.4.29"} -python-dotenv = "^0.19.2" -pydantic = {extras = ["email"], version = "^1.9.0"} -alembic = "^1.7.5" -asyncpg = "^0.25.0" -fastapi-users = {extras = ["sqlalchemy2"], version = "^9.2.0"} - -[tool.poetry.dev-dependencies] -black = {version = "^21.12b0", allow-prereleases = true} -autoflake = "^1.4" -uvicorn = "^0.16.0" -flake8 = "^4.0.1" -isort = "^5.10.1" -requests = "^2.27.1" -coverage = "^6.2" -pytest = "^6.2.5" -pytest-asyncio = "^0.16.0" -httpx = "^0.21.3" -sqlalchemy2-stubs = "^0.0.2-alpha.19" - -[build-system] -requires = ["poetry-core>=1.0.0"] -build-backend = "poetry.core.masonry.api" - -[tool.pytest.ini_options] -minversion = "6.0" -addopts = "-v" -testpaths = [ - "app/tests", -] - -[tool.isort] -profile = "black" \ No newline at end of file diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/requirements-dev.txt b/{{cookiecutter.project_name}}/template_fastapi_users/requirements-dev.txt deleted file mode 100644 index 7a33726..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/requirements-dev.txt +++ /dev/null @@ -1,61 +0,0 @@ -alembic==1.7.5; python_version >= "3.6" -anyio==3.4.0; python_full_version >= "3.6.2" and python_version >= "3.7" -asgiref==3.4.1; python_version >= "3.6" -asyncpg==0.25.0; python_full_version >= "3.6.0" -atomicwrites==1.4.0; python_version >= "3.6" and python_full_version < "3.0.0" and sys_platform == "win32" or sys_platform == "win32" and python_version >= "3.6" and python_full_version >= "3.4.0" -attrs==21.4.0; python_version >= "3.6" and python_full_version < "3.0.0" or python_full_version >= "3.5.0" and python_version >= "3.6" -autoflake==1.4 -bcrypt==3.2.0; python_version >= "3.7" -black==21.12b0; python_full_version >= "3.6.2" -certifi==2021.10.8; python_version >= "3.6" and python_full_version < "3.0.0" or python_full_version >= "3.6.0" and python_version >= "3.6" -cffi==1.15.0; python_version >= "3.7" -charset-normalizer==2.0.10; python_full_version >= "3.6.0" and python_version >= "3.6" -click==8.0.3; python_version >= "3.6" and python_full_version >= "3.6.2" -colorama==0.4.4; sys_platform == "win32" and python_version >= "3.6" and python_full_version >= "3.6.2" and platform_system == "Windows" and (python_version >= "3.6" and python_full_version < "3.0.0" and sys_platform == "win32" or sys_platform == "win32" and python_version >= "3.6" and python_full_version >= "3.5.0") -coverage==6.2; python_version >= "3.6" -dnspython==2.1.0; python_full_version >= "3.6.1" and python_version >= "3.6" -email-validator==1.1.3; python_full_version >= "3.6.1" and (python_version >= "3.7" and python_full_version < "3.0.0" or python_full_version >= "3.5.0" and python_version >= "3.7") and python_version >= "3.7" -fastapi-users-db-sqlalchemy==2.0.4; python_version >= "3.7" -fastapi-users==9.2.0; python_version >= "3.7" -fastapi==0.70.1; python_full_version >= "3.6.1" and python_version >= "3.7" -flake8==4.0.1; python_version >= "3.6" -greenlet==1.1.2; python_version >= "3" and python_full_version < "3.0.0" and (platform_machine == "aarch64" or platform_machine == "ppc64le" or platform_machine == "x86_64" or platform_machine == "amd64" or platform_machine == "AMD64" or platform_machine == "win32" or platform_machine == "WIN32") and (python_version >= "2.7" and python_full_version < "3.0.0" or python_full_version >= "3.6.0") and (python_version >= "3.6" and python_full_version < "3.0.0" or python_full_version >= "3.6.0" and python_version >= "3.6") or python_version >= "3" and (platform_machine == "aarch64" or platform_machine == "ppc64le" or platform_machine == "x86_64" or platform_machine == "amd64" or platform_machine == "AMD64" or platform_machine == "win32" or platform_machine == "WIN32") and (python_version >= "2.7" and python_full_version < "3.0.0" or python_full_version >= "3.6.0") and python_full_version >= "3.5.0" and (python_version >= "3.6" and python_full_version < "3.0.0" or python_full_version >= "3.6.0" and python_version >= "3.6") -h11==0.12.0; python_version >= "3.6" -httpcore==0.14.4; python_version >= "3.6" -httpx==0.21.3; python_version >= "3.6" -idna==3.3 -iniconfig==1.1.1; python_version >= "3.6" -isort==5.10.1; python_full_version >= "3.6.1" and python_version < "4.0" -makefun==1.12.1; python_version >= "3.7" -mako==1.1.6; python_version >= "3.6" and python_full_version < "3.0.0" or python_full_version >= "3.4.0" and python_version >= "3.6" -markupsafe==2.0.1; python_version >= "3.6" and python_full_version < "3.0.0" or python_full_version >= "3.4.0" and python_version >= "3.6" -mccabe==0.6.1; python_version >= "3.6" -mypy-extensions==0.4.3; python_full_version >= "3.6.2" -packaging==21.3; python_version >= "3.6" -passlib==1.7.4; python_version >= "3.7" -pathspec==0.9.0; python_full_version >= "3.6.2" -platformdirs==2.4.1; python_version >= "3.7" and python_full_version >= "3.6.2" -pluggy==1.0.0; python_version >= "3.6" -py==1.11.0; python_version >= "3.6" and python_full_version < "3.0.0" or python_full_version >= "3.5.0" and python_version >= "3.6" -pycodestyle==2.8.0; python_version >= "3.6" and python_full_version < "3.0.0" or python_full_version >= "3.5.0" and python_version >= "3.6" -pycparser==2.21; python_version >= "3.7" and python_full_version < "3.0.0" or python_version >= "3.7" and python_full_version >= "3.4.0" -pydantic==1.9.0; python_full_version >= "3.6.1" -pyflakes==2.4.0; python_version >= "3.6" and python_full_version < "3.0.0" or python_full_version >= "3.4.0" and python_version >= "3.6" -pyjwt==2.3.0; python_version >= "3.7" -pyparsing==3.0.6; python_version >= "3.6" -pytest-asyncio==0.16.0; python_version >= "3.6" -pytest==6.2.5; python_version >= "3.6" -python-dotenv==0.19.2; python_version >= "3.5" -python-multipart==0.0.5; python_version >= "3.7" -requests==2.27.1; (python_version >= "2.7" and python_full_version < "3.0.0") or (python_full_version >= "3.6.0") -rfc3986==1.5.0; python_version >= "3.6" -six==1.16.0; python_version >= "3.7" and python_full_version < "3.0.0" or python_full_version >= "3.3.0" and python_version >= "3.7" -sniffio==1.2.0; python_full_version >= "3.6.2" and python_version >= "3.6" -sqlalchemy2-stubs==0.0.2a19; python_version >= "3.6" -sqlalchemy==1.4.29; (python_version >= "2.7" and python_full_version < "3.0.0") or (python_full_version >= "3.6.0") -starlette==0.16.0; python_full_version >= "3.6.1" and python_version >= "3.7" -toml==0.10.2; python_version >= "3.6" and python_full_version < "3.0.0" or python_full_version >= "3.3.0" and python_version >= "3.6" -tomli==1.2.3; python_version >= "3.6" and python_full_version >= "3.6.2" -typing-extensions==4.0.1 -urllib3==1.26.8; python_version >= "2.7" and python_full_version < "3.0.0" or python_full_version >= "3.6.0" and python_version < "4" -uvicorn==0.16.0 diff --git a/{{cookiecutter.project_name}}/template_fastapi_users/requirements.txt b/{{cookiecutter.project_name}}/template_fastapi_users/requirements.txt deleted file mode 100644 index e1fc98b..0000000 --- a/{{cookiecutter.project_name}}/template_fastapi_users/requirements.txt +++ /dev/null @@ -1,26 +0,0 @@ -alembic==1.7.5; python_version >= "3.6" -anyio==3.4.0; python_full_version >= "3.6.2" and python_version >= "3.7" -asyncpg==0.25.0; python_full_version >= "3.6.0" -bcrypt==3.2.0; python_version >= "3.7" -cffi==1.15.0; python_version >= "3.7" -dnspython==2.1.0; python_full_version >= "3.6.1" and python_version >= "3.6" -email-validator==1.1.3; python_full_version >= "3.6.1" and (python_version >= "3.7" and python_full_version < "3.0.0" or python_full_version >= "3.5.0" and python_version >= "3.7") and python_version >= "3.7" -fastapi-users-db-sqlalchemy==2.0.4; python_version >= "3.7" -fastapi-users==9.2.0; python_version >= "3.7" -fastapi==0.70.1; python_full_version >= "3.6.1" and python_version >= "3.7" -greenlet==1.1.2; python_version >= "3" and python_full_version < "3.0.0" and (platform_machine == "aarch64" or platform_machine == "ppc64le" or platform_machine == "x86_64" or platform_machine == "amd64" or platform_machine == "AMD64" or platform_machine == "win32" or platform_machine == "WIN32") and (python_version >= "2.7" and python_full_version < "3.0.0" or python_full_version >= "3.6.0") and (python_version >= "3.6" and python_full_version < "3.0.0" or python_full_version >= "3.6.0" and python_version >= "3.6") or python_version >= "3" and (platform_machine == "aarch64" or platform_machine == "ppc64le" or platform_machine == "x86_64" or platform_machine == "amd64" or platform_machine == "AMD64" or platform_machine == "win32" or platform_machine == "WIN32") and (python_version >= "2.7" and python_full_version < "3.0.0" or python_full_version >= "3.6.0") and python_full_version >= "3.5.0" and (python_version >= "3.6" and python_full_version < "3.0.0" or python_full_version >= "3.6.0" and python_version >= "3.6") -idna==3.3; python_full_version >= "3.6.2" and python_version >= "3.7" -makefun==1.12.1; python_version >= "3.7" -mako==1.1.6; python_version >= "3.6" and python_full_version < "3.0.0" or python_full_version >= "3.4.0" and python_version >= "3.6" -markupsafe==2.0.1; python_version >= "3.6" and python_full_version < "3.0.0" or python_full_version >= "3.4.0" and python_version >= "3.6" -passlib==1.7.4; python_version >= "3.7" -pycparser==2.21; python_version >= "3.7" and python_full_version < "3.0.0" or python_version >= "3.7" and python_full_version >= "3.4.0" -pydantic==1.9.0; python_full_version >= "3.6.1" -pyjwt==2.3.0; python_version >= "3.7" -python-dotenv==0.19.2; python_version >= "3.5" -python-multipart==0.0.5; python_version >= "3.7" -six==1.16.0; python_version >= "3.7" and python_full_version < "3.0.0" or python_full_version >= "3.3.0" and python_version >= "3.7" -sniffio==1.2.0; python_full_version >= "3.6.2" and python_version >= "3.7" -sqlalchemy==1.4.29; (python_version >= "2.7" and python_full_version < "3.0.0") or (python_full_version >= "3.6.0") -starlette==0.16.0; python_full_version >= "3.6.1" and python_version >= "3.7" -typing-extensions==4.0.1; python_version >= "3.7" and python_full_version >= "3.6.1" diff --git a/{{cookiecutter.project_name}}/template_minimal/.env.example b/{{cookiecutter.project_name}}/template_minimal/.env.example deleted file mode 100644 index 8803f10..0000000 --- a/{{cookiecutter.project_name}}/template_minimal/.env.example +++ /dev/null @@ -1,21 +0,0 @@ -SECRET_KEY=DVnFmhwvjEhJZpuhndxjhlezxQPJmBIIkMDEmFREWQADPcUnrG -ENVIRONMENT=DEV -ACCESS_TOKEN_EXPIRE_MINUTES=11520 -REFRESH_TOKEN_EXPIRE_MINUTES=40320 -BACKEND_CORS_ORIGINS=["http://localhost:3000","http://localhost:8001"] -ALLOWED_HOSTS=["localhost", "127.0.0.1"] - -DEFAULT_DATABASE_HOSTNAME=localhost -DEFAULT_DATABASE_USER=rDGJeEDqAz -DEFAULT_DATABASE_PASSWORD=XsPQhCoEfOQZueDjsILetLDUvbvSxAMnrVtgVZpmdcSssUgbvs -DEFAULT_DATABASE_PORT=5387 -DEFAULT_DATABASE_DB=default_db - -TEST_DATABASE_HOSTNAME=localhost -TEST_DATABASE_USER=test -TEST_DATABASE_PASSWORD=ywRCUjJijmQoBmWxIfLldOoITPzajPSNvTvHyugQoSqGwNcvQE -TEST_DATABASE_PORT=37270 -TEST_DATABASE_DB=test_db - -FIRST_SUPERUSER_EMAIL=example@example.com -FIRST_SUPERUSER_PASSWORD=OdLknKQJMUwuhpAVHvRC \ No newline at end of file diff --git a/{{cookiecutter.project_name}}/template_minimal/.env.template b/{{cookiecutter.project_name}}/template_minimal/.env.template deleted file mode 100644 index 629a4fa..0000000 --- a/{{cookiecutter.project_name}}/template_minimal/.env.template +++ /dev/null @@ -1,21 +0,0 @@ -SECRET_KEY={{ random_ascii_string(50) }} -ENVIRONMENT=DEV -ACCESS_TOKEN_EXPIRE_MINUTES=11520 -REFRESH_TOKEN_EXPIRE_MINUTES=40320 -BACKEND_CORS_ORIGINS=["http://localhost:3000","http://localhost:8001"] -ALLOWED_HOSTS=["localhost", "127.0.0.1"] - -DEFAULT_DATABASE_HOSTNAME=localhost -DEFAULT_DATABASE_USER=postgres -DEFAULT_DATABASE_PASSWORD={{ random_ascii_string(50) }} -DEFAULT_DATABASE_PORT={{ range(4000, 7000) | random }} -DEFAULT_DATABASE_DB=postgres - -TEST_DATABASE_HOSTNAME=localhost -TEST_DATABASE_USER=postgres -TEST_DATABASE_PASSWORD={{ random_ascii_string(50) }} -TEST_DATABASE_PORT={{ range(30000, 40000) | random }} -TEST_DATABASE_DB=postgres - -FIRST_SUPERUSER_EMAIL=example@example.com -FIRST_SUPERUSER_PASSWORD={{ random_ascii_string(20) }} \ No newline at end of file diff --git a/{{cookiecutter.project_name}}/template_minimal/.flake8 b/{{cookiecutter.project_name}}/template_minimal/.flake8 deleted file mode 100644 index 6b8856f..0000000 --- a/{{cookiecutter.project_name}}/template_minimal/.flake8 +++ /dev/null @@ -1,11 +0,0 @@ -[flake8] -max-line-length = 88 -select = C,E,F,W,B,B9 -ignore = E203, E501, W503 -exclude = - __init__.py, - .venv, - venv, - __pycache__, - .github, - .vscode, diff --git a/{{cookiecutter.project_name}}/template_minimal/.gitignore b/{{cookiecutter.project_name}}/template_minimal/.gitignore deleted file mode 100644 index 32562ce..0000000 --- a/{{cookiecutter.project_name}}/template_minimal/.gitignore +++ /dev/null @@ -1,136 +0,0 @@ - -# postgresql -data -default_database_data -test_database_data - -# Byte-compiled / optimized / DLL files -__pycache__/ -*.py[cod] -*$py.class -.env - -# C extensions -*.so - -# Distribution / packaging -.Python -build/ -develop-eggs/ -dist/ -downloads/ -eggs/ -.eggs/ -lib/ -lib64/ -parts/ -sdist/ -var/ -wheels/ -pip-wheel-metadata/ -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/ - -# 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 -target/ - -# Jupyter Notebook -.ipynb_checkpoints - -# IPython -profile_default/ -ipython_config.py - -# pyenv -.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 - -# PEP 582; used by e.g. github.com/David-OConnor/pyflow -__pypackages__/ - -# Celery stuff -celerybeat-schedule -celerybeat.pid - -# SageMath parsed files -*.sage.py - -# Environments - -.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/ \ No newline at end of file diff --git a/{{cookiecutter.project_name}}/template_minimal/alembic/README b/{{cookiecutter.project_name}}/template_minimal/alembic/README deleted file mode 100644 index 98e4f9c..0000000 --- a/{{cookiecutter.project_name}}/template_minimal/alembic/README +++ /dev/null @@ -1 +0,0 @@ -Generic single-database configuration. \ No newline at end of file diff --git a/{{cookiecutter.project_name}}/template_minimal/alembic/script.py.mako b/{{cookiecutter.project_name}}/template_minimal/alembic/script.py.mako deleted file mode 100644 index 2c01563..0000000 --- a/{{cookiecutter.project_name}}/template_minimal/alembic/script.py.mako +++ /dev/null @@ -1,24 +0,0 @@ -"""${message} - -Revision ID: ${up_revision} -Revises: ${down_revision | comma,n} -Create Date: ${create_date} - -""" -from alembic import op -import sqlalchemy as sa -${imports if imports else ""} - -# revision identifiers, used by Alembic. -revision = ${repr(up_revision)} -down_revision = ${repr(down_revision)} -branch_labels = ${repr(branch_labels)} -depends_on = ${repr(depends_on)} - - -def upgrade(): - ${upgrades if upgrades else "pass"} - - -def downgrade(): - ${downgrades if downgrades else "pass"} diff --git a/{{cookiecutter.project_name}}/template_minimal/app/api/__init__.py b/{{cookiecutter.project_name}}/template_minimal/app/api/__init__.py deleted file mode 100644 index e69de29..0000000 diff --git a/{{cookiecutter.project_name}}/template_minimal/app/api/endpoints/__init__.py b/{{cookiecutter.project_name}}/template_minimal/app/api/endpoints/__init__.py deleted file mode 100644 index e69de29..0000000 diff --git a/{{cookiecutter.project_name}}/template_minimal/app/conftest.py b/{{cookiecutter.project_name}}/template_minimal/app/conftest.py deleted file mode 100644 index 9d48255..0000000 --- a/{{cookiecutter.project_name}}/template_minimal/app/conftest.py +++ /dev/null @@ -1,11 +0,0 @@ -""" -Used to execute code before running tests, in this case we want to use test database. -We don't want to mess up dev database. - -Put here any Pytest related code (it will be executed before `app/tests/...`) -""" - -import os - -# This will ensure using test database -os.environ["ENVIRONMENT"] = "PYTEST" diff --git a/{{cookiecutter.project_name}}/template_minimal/app/core/__init__.py b/{{cookiecutter.project_name}}/template_minimal/app/core/__init__.py deleted file mode 100644 index e69de29..0000000 diff --git a/{{cookiecutter.project_name}}/template_minimal/app/schemas/__init__.py b/{{cookiecutter.project_name}}/template_minimal/app/schemas/__init__.py deleted file mode 100644 index e69de29..0000000 diff --git a/{{cookiecutter.project_name}}/template_minimal/app/tests/__init__.py b/{{cookiecutter.project_name}}/template_minimal/app/tests/__init__.py deleted file mode 100644 index e69de29..0000000 diff --git a/{{cookiecutter.project_name}}/template_minimal/init.sh b/{{cookiecutter.project_name}}/template_minimal/init.sh deleted file mode 100644 index 5811845..0000000 --- a/{{cookiecutter.project_name}}/template_minimal/init.sh +++ /dev/null @@ -1,7 +0,0 @@ -#!/bin/bash - -echo "Run migrations" -alembic upgrade head - -echo "Create initial data in DB" -python -m app.initial_data diff --git a/{{cookiecutter.project_name}}/template_minimal/pre-push.sh b/{{cookiecutter.project_name}}/template_minimal/pre-push.sh deleted file mode 100644 index 8631794..0000000 --- a/{{cookiecutter.project_name}}/template_minimal/pre-push.sh +++ /dev/null @@ -1,16 +0,0 @@ -echo "export requirements.txt" -poetry export -o requirements.txt --without-hashes -poetry export -o requirements-dev.txt --dev --without-hashes -echo "autoflake" -autoflake --recursive --in-place \ - --remove-unused-variables \ - --remove-all-unused-imports \ - --ignore-init-module-imports \ - app -echo "black" -black app -echo "isort" -isort app -echo "flake8" -flake8 app --count --statistics -echo "OK" \ No newline at end of file From a3968136e2a44b3871c39905f11442d898d870a3 Mon Sep 17 00:00:00 2001 From: rafsaf Date: Sat, 4 Feb 2023 22:51:53 +0100 Subject: [PATCH 2/3] add back hiiden files removed by accident --- {{cookiecutter.project_name}}/.env.example | 21 +++ {{cookiecutter.project_name}}/.env.template | 21 +++ {{cookiecutter.project_name}}/.flake8 | 11 ++ {{cookiecutter.project_name}}/.gitignore | 136 ++++++++++++++++++++ 4 files changed, 189 insertions(+) create mode 100644 {{cookiecutter.project_name}}/.env.example create mode 100644 {{cookiecutter.project_name}}/.env.template create mode 100644 {{cookiecutter.project_name}}/.flake8 create mode 100644 {{cookiecutter.project_name}}/.gitignore diff --git a/{{cookiecutter.project_name}}/.env.example b/{{cookiecutter.project_name}}/.env.example new file mode 100644 index 0000000..8803f10 --- /dev/null +++ b/{{cookiecutter.project_name}}/.env.example @@ -0,0 +1,21 @@ +SECRET_KEY=DVnFmhwvjEhJZpuhndxjhlezxQPJmBIIkMDEmFREWQADPcUnrG +ENVIRONMENT=DEV +ACCESS_TOKEN_EXPIRE_MINUTES=11520 +REFRESH_TOKEN_EXPIRE_MINUTES=40320 +BACKEND_CORS_ORIGINS=["http://localhost:3000","http://localhost:8001"] +ALLOWED_HOSTS=["localhost", "127.0.0.1"] + +DEFAULT_DATABASE_HOSTNAME=localhost +DEFAULT_DATABASE_USER=rDGJeEDqAz +DEFAULT_DATABASE_PASSWORD=XsPQhCoEfOQZueDjsILetLDUvbvSxAMnrVtgVZpmdcSssUgbvs +DEFAULT_DATABASE_PORT=5387 +DEFAULT_DATABASE_DB=default_db + +TEST_DATABASE_HOSTNAME=localhost +TEST_DATABASE_USER=test +TEST_DATABASE_PASSWORD=ywRCUjJijmQoBmWxIfLldOoITPzajPSNvTvHyugQoSqGwNcvQE +TEST_DATABASE_PORT=37270 +TEST_DATABASE_DB=test_db + +FIRST_SUPERUSER_EMAIL=example@example.com +FIRST_SUPERUSER_PASSWORD=OdLknKQJMUwuhpAVHvRC \ No newline at end of file diff --git a/{{cookiecutter.project_name}}/.env.template b/{{cookiecutter.project_name}}/.env.template new file mode 100644 index 0000000..629a4fa --- /dev/null +++ b/{{cookiecutter.project_name}}/.env.template @@ -0,0 +1,21 @@ +SECRET_KEY={{ random_ascii_string(50) }} +ENVIRONMENT=DEV +ACCESS_TOKEN_EXPIRE_MINUTES=11520 +REFRESH_TOKEN_EXPIRE_MINUTES=40320 +BACKEND_CORS_ORIGINS=["http://localhost:3000","http://localhost:8001"] +ALLOWED_HOSTS=["localhost", "127.0.0.1"] + +DEFAULT_DATABASE_HOSTNAME=localhost +DEFAULT_DATABASE_USER=postgres +DEFAULT_DATABASE_PASSWORD={{ random_ascii_string(50) }} +DEFAULT_DATABASE_PORT={{ range(4000, 7000) | random }} +DEFAULT_DATABASE_DB=postgres + +TEST_DATABASE_HOSTNAME=localhost +TEST_DATABASE_USER=postgres +TEST_DATABASE_PASSWORD={{ random_ascii_string(50) }} +TEST_DATABASE_PORT={{ range(30000, 40000) | random }} +TEST_DATABASE_DB=postgres + +FIRST_SUPERUSER_EMAIL=example@example.com +FIRST_SUPERUSER_PASSWORD={{ random_ascii_string(20) }} \ No newline at end of file diff --git a/{{cookiecutter.project_name}}/.flake8 b/{{cookiecutter.project_name}}/.flake8 new file mode 100644 index 0000000..6b8856f --- /dev/null +++ b/{{cookiecutter.project_name}}/.flake8 @@ -0,0 +1,11 @@ +[flake8] +max-line-length = 88 +select = C,E,F,W,B,B9 +ignore = E203, E501, W503 +exclude = + __init__.py, + .venv, + venv, + __pycache__, + .github, + .vscode, diff --git a/{{cookiecutter.project_name}}/.gitignore b/{{cookiecutter.project_name}}/.gitignore new file mode 100644 index 0000000..32562ce --- /dev/null +++ b/{{cookiecutter.project_name}}/.gitignore @@ -0,0 +1,136 @@ + +# postgresql +data +default_database_data +test_database_data + +# Byte-compiled / optimized / DLL files +__pycache__/ +*.py[cod] +*$py.class +.env + +# C extensions +*.so + +# Distribution / packaging +.Python +build/ +develop-eggs/ +dist/ +downloads/ +eggs/ +.eggs/ +lib/ +lib64/ +parts/ +sdist/ +var/ +wheels/ +pip-wheel-metadata/ +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/ + +# 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 +target/ + +# Jupyter Notebook +.ipynb_checkpoints + +# IPython +profile_default/ +ipython_config.py + +# pyenv +.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 + +# PEP 582; used by e.g. github.com/David-OConnor/pyflow +__pypackages__/ + +# Celery stuff +celerybeat-schedule +celerybeat.pid + +# SageMath parsed files +*.sage.py + +# Environments + +.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/ \ No newline at end of file From fe43ba19fe99327560276b3cd894af49161a9465 Mon Sep 17 00:00:00 2001 From: rafsaf Date: Sat, 4 Feb 2023 22:58:38 +0100 Subject: [PATCH 3/3] fix tests after removing template fastapi users --- .github/workflows/tests.yml | 42 ++++++------------------------------- 1 file changed, 6 insertions(+), 36 deletions(-) diff --git a/.github/workflows/tests.yml b/.github/workflows/tests.yml index e1186fb..38f9bb1 100644 --- a/.github/workflows/tests.yml +++ b/.github/workflows/tests.yml @@ -26,13 +26,11 @@ jobs: with: python-version: "3.10" - - name: Generate projects from templates using cookiecutter - # fastapi_users_project folder - # minimal_project folder + # Below will create fresh template in path: minimal_project + - name: Generate project from template using cookiecutter run: | pip install cookiecutter python tests/create_minimal_project.py - python tests/create_fastapi_users_project.py - name: Install Poetry uses: snok/install-poetry@v1 @@ -40,17 +38,16 @@ jobs: virtualenvs-create: true virtualenvs-in-project: true - ### template minimal ### - - - name: Load cached venv-1 - id: cached-poetry-dependencies-template-1 + # run tests from folder minimal_project + - name: Load cached venv + id: cached-poetry-dependencies-template uses: actions/cache@v2 with: path: minimal_project/.venv key: venv-${{ runner.os }}-${{ hashFiles('minimal_project/poetry.lock') }} - name: Install template minimal dependencies - if: steps.cached-poetry-dependencies-template-1.outputs.cache-hit != 'true' + if: steps.cached-poetry-dependencies-template.outputs.cache-hit != 'true' run: | cd minimal_project poetry install --no-interaction --no-root @@ -66,30 +63,3 @@ jobs: cd minimal_project poetry run flake8 app --count --exit-zero --statistics poetry run coverage run -m pytest - - ### template fastapi users ### - - - name: Load cached venv-2 - id: cached-poetry-dependencies-template-2 - uses: actions/cache@v2 - with: - path: fastapi_users_project/.venv - key: venv-${{ runner.os }}-${{ hashFiles('fastapi_users_project/poetry.lock') }} - - - name: Install template fastapi users dependencies - if: steps.cached-poetry-dependencies-template-1.outputs.cache-hit != 'true' - run: | - cd fastapi_users_project - poetry install --no-interaction --no-root - - - name: Run template fastapi users flake8 and then tests - env: - TEST_DATABASE_HOSTNAME: localhost - TEST_DATABASE_PASSWORD: postgres - TEST_DATABASE_PORT: 5432 - TEST_DATABASE_USER: postgres - TEST_DATABASE_DB: postgres - run: | - cd fastapi_users_project - poetry run flake8 app --count --exit-zero --statistics - poetry run coverage run -m pytest