commit a0b76f1d51f36f4d24187549867c1a43027698a4 Author: leo <3181538941@qq.com> Date: Mon Jan 20 14:57:31 2025 +0800 init diff --git a/cookiecutter.json b/cookiecutter.json new file mode 100644 index 0000000..41e8d10 --- /dev/null +++ b/cookiecutter.json @@ -0,0 +1,9 @@ +{ + "project_name": "Python Boilerplate", + "project_slug": "{{ cookiecutter.project_name.lower().replace(' ', '_').replace('-', '_') }}", + "project_short_description": "Python Boilerplate contains all the boilerplate you need to create a Python package.", + "email": "leolswq@163.com", + "github_username": "leo03wzz", + "secret_key": "super_secret", + "version": "0.1.0" +} diff --git a/{{cookiecutter.project_slug}}/.gitignore b/{{cookiecutter.project_slug}}/.gitignore new file mode 100644 index 0000000..44bbb13 --- /dev/null +++ b/{{cookiecutter.project_slug}}/.gitignore @@ -0,0 +1,161 @@ +# Byte-compiled / optimized / DLL files +__pycache__/ +*.py[cod] +*$py.class + +# C extensions +*.so + +# Distribution / packaging +.Python +build/ +develop-eggs/ +dist/ +downloads/ +eggs/ +.eggs/ +lib/ +lib64/ +parts/ +sdist/ +var/ +wheels/ +share/python-wheels/ +*.egg-info/ +.installed.cfg +*.egg +MANIFEST + +# PyInstaller +# Usually these files are written by a python script from a template +# before PyInstaller builds the exe, so as to inject date/other infos into it. +*.manifest +*.spec + +# Installer logs +pip-log.txt +pip-delete-this-directory.txt + +# Unit test / coverage reports +htmlcov/ +.tox/ +.nox/ +.coverage +.coverage.* +.cache +nosetests.xml +coverage.xml +*.cover +*.py,cover +.hypothesis/ +.pytest_cache/ +cover/ + +# Translations +*.mo +*.pot + +# Django stuff: +*.log +local_settings.py +db.sqlite3 +db.sqlite3-journal + +# Flask stuff: +instance/ +.webassets-cache + +# Scrapy stuff: +.scrapy + +# Sphinx documentation +docs/_build/ + +# PyBuilder +.pybuilder/ +target/ + +# Jupyter Notebook +.ipynb_checkpoints + +# IPython +profile_default/ +ipython_config.py + +# pyenv +# For a library or package, you might want to ignore these files since the code is +# intended to run in multiple environments; otherwise, check them in: +# .python-version + +# pipenv +# According to pypa/pipenv#598, it is recommended to include Pipfile.lock in version control. +# However, in case of collaboration, if having platform-specific dependencies or dependencies +# having no cross-platform support, pipenv may install dependencies that don't work, or not +# install all needed dependencies. +#Pipfile.lock + +# poetry +# Similar to Pipfile.lock, it is generally recommended to include poetry.lock in version control. +# This is especially recommended for binary packages to ensure reproducibility, and is more +# commonly ignored for libraries. +# https://python-poetry.org/docs/basic-usage/#commit-your-poetrylock-file-to-version-control +#poetry.lock + +# pdm +# Similar to Pipfile.lock, it is generally recommended to include pdm.lock in version control. +#pdm.lock +# pdm stores project-wide configurations in .pdm.toml, but it is recommended to not include it +# in version control. +# https://pdm.fming.dev/#use-with-ide +.pdm.toml + +# PEP 582; used by e.g. github.com/David-OConnor/pyflow and github.com/pdm-project/pdm +__pypackages__/ + +# Celery stuff +celerybeat-schedule +celerybeat.pid + +# SageMath parsed files +*.sage.py + +# Environments +.env +.venv +env/ +venv/ +ENV/ +env.bak/ +venv.bak/ + +# Spyder project settings +.spyderproject +.spyproject + +# Rope project settings +.ropeproject + +# mkdocs documentation +/site + +# mypy +.mypy_cache/ +.dmypy.json +dmypy.json + +# Pyre type checker +.pyre/ + +# pytype static type analyzer +.pytype/ + +# Cython debug symbols +cython_debug/ + +# PyCharm +# JetBrains specific template is maintained in a separate JetBrains.gitignore that can +# be found at https://github.com/github/gitignore/blob/main/Global/JetBrains.gitignore +# and can be added to the global gitignore or merged into this file. For a more nuclear +# option (not recommended) you can uncomment the following to ignore the entire idea folder. +.idea/ +.vscode/ diff --git a/{{cookiecutter.project_slug}}/.prettierignore b/{{cookiecutter.project_slug}}/.prettierignore new file mode 100644 index 0000000..412c257 --- /dev/null +++ b/{{cookiecutter.project_slug}}/.prettierignore @@ -0,0 +1 @@ +docker-compose.yml \ No newline at end of file diff --git a/{{cookiecutter.project_slug}}/Dockerfile b/{{cookiecutter.project_slug}}/Dockerfile new file mode 100644 index 0000000..77d7d2a --- /dev/null +++ b/{{cookiecutter.project_slug}}/Dockerfile @@ -0,0 +1,6 @@ +FROM python:3.10 + +COPY requirements.txt /tmp/requirements.txt +RUN pip install --no-cache-dir -r /tmp/requirements.txt + +COPY . . \ No newline at end of file diff --git a/{{cookiecutter.project_slug}}/LICENSE b/{{cookiecutter.project_slug}}/LICENSE new file mode 100644 index 0000000..ad76fb3 --- /dev/null +++ b/{{cookiecutter.project_slug}}/LICENSE @@ -0,0 +1,21 @@ +MIT License + +Copyright (c) 2020 Gabriel Abud + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. diff --git a/{{cookiecutter.project_slug}}/README.md b/{{cookiecutter.project_slug}}/README.md new file mode 100644 index 0000000..1b79f88 --- /dev/null +++ b/{{cookiecutter.project_slug}}/README.md @@ -0,0 +1,80 @@ +# {{cookiecutter.project_name}} + +{{cookiecutter.project_short_description}} + +## Development + +The only dependencies for this project should be docker and docker-compose. + +### Quick Start + +Starting the project with hot-reloading enabled +(the first time it will take a while): + +```bash +docker-compose up -d +``` + +To run the alembic migrations (for the users table): + +```bash +docker-compose run --rm backend alembic upgrade head +``` + +### Rebuilding containers: + +``` +docker-compose build +``` + +### Restarting containers: + +``` +docker-compose restart +``` + +### Bringing containers down: + +``` +docker-compose down +``` + +## Logging + +``` +docker-compose logs +``` + +Or for a specific service: + +``` +docker-compose logs -f name_of_service # frontend|backend|db +``` + +## Project Layout + +``` +backend +└── app + ├── alembic + │ └── versions # where migrations are located + ├── api + │ └── api_v1 + │ └── endpoints + ├── core # config + ├── db # db models + ├── tests # pytest + └── main.py # entrypoint to backend + +frontend +└── public +└── src + ├── components + │ └── Home.tsx + ├── config + │ └── index.tsx # constants + ├── __tests__ + │ └── test_home.tsx + ├── index.tsx # entrypoint + └── App.tsx # handles routing +``` diff --git a/{{cookiecutter.project_slug}}/core/__init__.py b/{{cookiecutter.project_slug}}/core/__init__.py new file mode 100644 index 0000000..27c9ec6 --- /dev/null +++ b/{{cookiecutter.project_slug}}/core/__init__.py @@ -0,0 +1 @@ +from .config import * diff --git a/{{cookiecutter.project_slug}}/core/config.py b/{{cookiecutter.project_slug}}/core/config.py new file mode 100644 index 0000000..8a1df45 --- /dev/null +++ b/{{cookiecutter.project_slug}}/core/config.py @@ -0,0 +1,5 @@ +import os + +PROJECT_NAME = "{{cookiecutter.project_name}}" + +BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__))) diff --git a/{{cookiecutter.project_slug}}/docker-compose.yml b/{{cookiecutter.project_slug}}/docker-compose.yml new file mode 100644 index 0000000..d0d76d2 --- /dev/null +++ b/{{cookiecutter.project_slug}}/docker-compose.yml @@ -0,0 +1,7 @@ +version: '3.7' +services: + {{ cookiecutter.project_slug }}: + build: + context: . + dockerfile: Dockerfile + command: python main.py diff --git a/{{cookiecutter.project_slug}}/main.py b/{{cookiecutter.project_slug}}/main.py new file mode 100644 index 0000000..7761001 --- /dev/null +++ b/{{cookiecutter.project_slug}}/main.py @@ -0,0 +1,4 @@ +from core import BASE_DIR + +if __name__ == "__main__": + print(BASE_DIR) diff --git a/{{cookiecutter.project_slug}}/requirements.txt b/{{cookiecutter.project_slug}}/requirements.txt new file mode 100644 index 0000000..f1d0b55 --- /dev/null +++ b/{{cookiecutter.project_slug}}/requirements.txt @@ -0,0 +1,2 @@ +loguru +rich \ No newline at end of file diff --git a/{{cookiecutter.project_slug}}/scripts/build.sh b/{{cookiecutter.project_slug}}/scripts/build.sh new file mode 100644 index 0000000..56e5836 --- /dev/null +++ b/{{cookiecutter.project_slug}}/scripts/build.sh @@ -0,0 +1,13 @@ +#!/bin/bash + +# Exit in case of error +set -e + +# Build and run containers +docker-compose up -d + +# Hack to wait for postgres container to be up before running alembic migrations +sleep 5; + +# build +docker-compose build diff --git a/{{cookiecutter.project_slug}}/scripts/test.sh b/{{cookiecutter.project_slug}}/scripts/test.sh new file mode 100644 index 0000000..aaabb1c --- /dev/null +++ b/{{cookiecutter.project_slug}}/scripts/test.sh @@ -0,0 +1,6 @@ +#! /usr/bin/env bash + +# Exit in case of error +set -e + +docker-compose run {{ cookiecutter.project_slug }} pytest \ No newline at end of file diff --git a/{{cookiecutter.project_slug}}/utils/__init__.py b/{{cookiecutter.project_slug}}/utils/__init__.py new file mode 100644 index 0000000..c53f601 --- /dev/null +++ b/{{cookiecutter.project_slug}}/utils/__init__.py @@ -0,0 +1,2 @@ +#!/usr/bin/env python3 +# -*- coding:utf-8 -*-