Skip to content

TimCares/snake-shed

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

23 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

[Project Name]

Your project description

uv Python 3.13 Ruff ty interrogate pytest coverage ≥80% pre-commit Conventional Commits semantic-release Gitleaks Trivy Renovate

Setting up a new Python project should not require rebuilding the same tooling every time.

This project is a compact template with all the components already included. Features include:

  • Easy python environment handling
  • Full config handling with YAML and env files
  • Strict code quality checks
  • Layered security: vulnerability + secret scanning, CycloneDX SBOMs, single-source-of-truth OpenVEX accepted-risk document with controlled-vocab justifications
    • enforced freshness window, hardened docker image and runtime environment.
  • Automated testing
  • CI (gitlab, easily swappable)
  • Enterprise-ready git workflow (conventional commits, semantic-release, pre-commit hooks)
  • Automated dependency updates via Renovate (uv, pre-commit hooks, container images, CI image pins)
  • Built-in Makefile commands to simplify all of the above
  • LLM-maintained wiki for easy (project) documentation
  • A docs directory for usual documentation

Disclaimer: This template aims to serve a wide range of use cases, so you should adjust it according to your requirements and taste. There is a lot to take in, docs/REPO_SETUP.md walks through every moving part, why it's there, and how to swap or remove it.

Prerequisites

Just uv!

Getting Started

Clone the template into a directory named after your project:

git clone <template-url> my-new-project
cd my-new-project

Run:

make bootstrap

On the first run, make bootstrap is interactive: it asks for a project name (defaulting to the directory name), package name, description, and author, then renames the placeholder layout (src/my_project/ -> src/<your_package>/) and updates pyproject.toml, the README, and tests accordingly. After that it installs the pinned Python, dependencies, and pre-commit hooks. The rename script self-deletes when it's done, so re-running make bootstrap later just re-installs the dev environment, which is what you want.

For non-interactive use (CI, dotfiles, etc.) the rename step accepts a --yes flag; see docs/REPO_SETUP.md.

Finally, configure runtime env variables by copying config/.env.dist to config/.env and filling in the values.

Development

Run make help to see all available commands, grouped by category. The two you'll use most:

make check    Run the full local check suite, exactly what CI and
              pre-commit run. Read-only; never modifies files.
make fix      Run every auto-fixer (format + lint + repo hygiene).
              Run this locally before committing.

Pre-commit is intentionally check-only, it verifies but never modifies files mid-commit. A failed commit means "run make fix and try again." See docs/REPO_SETUP.md for the full check/fix breakdown.

Running

The central entrypoint of this repo is src/my_project/__main__.py. You can run it from the root of the repository with:

Locally

python -m my_project

Docker

Or by running the docker container (built-in) with docker-compose.yaml:

docker compose up -d --build

Note: Because the loading of the config/config.yaml is implemented so that it works out of the box for both local execution and docker, when running locally the code should be run as specified in the first example. Otherwise, the config file cannot be resolved.

Project Structure

src/
  my_project/             Central code
    __main__.py           Entry point: `python -m my_project`
    __version__.py        Version (reads from pyproject.toml metadata)
    core/                 Core code
    config/
      config.py           Pydantic configuration schemas
      config_loader.py    YAML loading + Pydantic validation
config/
  config.yaml             App config (secrets via files or env variables)
  .env.dist               Environment variable template
assets/                   Project-owned static files (safe to commit)
artifacts/                Local runtime inputs mounted into Docker (not baked into image)
docs/
  REPO_SETUP.md           Template internals & customization guide (safe to delete)
scripts/                  Various scripts
tests/
docker/
  Dockerfile              Hardened image: distroless default + debian convenience
  extra-libs.txt          System libs to force-stage into the distroless image
  README.md               Container image guide (targets, staging, import gate)
docker-compose.yaml       Hardened local-run compose (volume-mounted config)
.dockerignore             Build-context exclusions
wiki/
  index.md                Catalog of all wiki pages
  log.md                  Timeline of wiki activity
  inbox/                  Quick capture zone
  decisions/              Architecture Decision Records
  guides/                 How-tos and runbooks
  reference/              Architecture docs, specs, conventions
  journal/                Thoughts, observations, findings
  _templates/             Document templates

The src/my_project/ layout is the standard PyPA-recommended src layout. As the project grows, add subpackages directly under it (e.g. src/my_project/core/, src/my_project/api/) rather than dumping modules at the top level. No pyproject.toml change needed, see docs/REPO_SETUP.md for the full rationale.

Configuration

Configuration is defined in config/config.yaml.

Secrets should be provided as files and declared as provider: file in yaml (although env variables are also possible -> provider: env), which is a better practice than env variables. See src/my_project/config/secret.py for details.

All values are validated at startup through Pydantic models in src/my_project/config/config.py.

Wiki

The wiki/ directory is an LLM-maintained project wiki (inspired by Andrej Karpathy) for capturing decisions, guides, and reference material. The LLM handles all the bookkeeping — metadata, cross-references, index updates — so writing docs doesn't feel like a chore. Tell the LLM to "capture this", "document why we chose X", or "lint the wiki". See wiki/README.md for details.

Commit Convention

This project uses Conventional Commits. Commitizen enforces the format via a pre-commit hook. Examples:

feat (autograd): added support for gradient accumulation
fix (config): added missing environment variable handling
docs (readme): update config section in README

Versioning is handled automatically by python-semantic-release in CI.

Linking Issues

python-semantic-release already detects linked issue identifiers in commit messages, including Jira-style keys such as PROJ-123. Put them in Git trailer format at the end of the commit message:

feat(api): add customer export

Resolves: PROJ-123

Multiple issues can be listed in one trailer:

fix(config): handle missing env file

Fixes: PROJ-123, PROJ-456

PSR uses these identifiers for changelog/release metadata. Your Git hosting or Jira integration is still responsible for creating the actual issue links.

About

An opinionated python development template

Resources

Security policy

Stars

Watchers

Forks

Releases

Packages

Contributors

Languages