Setting Up Python Backends
Prerequisites
This is a Python-specific extension to myai's setting-up-backends.
Load setting-up-backends first for the backend architecture philosophy,
directory layout patterns, wiring rules, defer-by-default guidance, and
migrations/operations strategy. This skill provides only Python-specific
framework choices, library selections, and code patterns.
Also requires engineering-principles and architecting-changes (via myai bootstrap).
This skill is a backend-specialized extension of setting-up-python-projects.
Start here for backend repos, then pull generic Python bootstrap pieces from
setting-up-python-projects as needed.
Python Framework Choice
- FastAPI is the default boring choice for most service APIs.
- Django is justified when auth, admin, sessions, and CRUD-heavy backend surface are obviously large from the start.
- Starlette is for deliberate thin-edge builds, not as a default.
Python Default Stack
FastAPI + uvicorn
pydantic models at the FastAPI HTTP edge; msgspec.Struct for config and non-framework external payload decoding
dataclass(frozen=True, slots=True) + Result[T, E] in the core
SQLAlchemy 2 + Alembic when the service owns relational persistence
httpx for outbound HTTP
- existing repo logging setup via
shared/logging
pytest, pytest-asyncio, and integration tests through real app wiring
uv, poethepoet, basedpyright, and ruff
Keep pydantic request/response DTOs at the HTTP boundary and convert immediately into framework-free typed structures.
Python Backend Layout
See setting-up-backends for the philosophy behind this layout.
src/appname/
api/
app.py
routes/
schemas/
errors.py
domain/
models.py
services.py
errors.py
infrastructure/
config.py
logging.py
db/
models.py
session.py
queries.py
clients/
workers/
__main__.py
bootstrap.py
tests/
integration/
unit/
fixtures/
migrations/
Omit what you do not need. No DB, no db/ or migrations/. No workers, no workers/.
First Files
api/app.py with create_app()
api/routes/health.py with /healthz
bootstrap.py with create_services() and app wiring
domain/models.py and one small service/use-case module
infrastructure/config.py to parse env into typed settings
- DB files and migrations only if persistence exists
- one smoke API test and one domain test
Wiring Rules
create_app() assembles only the HTTP layer.
bootstrap.py wires settings, DB/session factories, external clients, and services.
- No DI framework by default. Use constructor injection and one composition root.
- Keep
__main__.py or ASGI entrypoints thin.
Boundary Rules
- Request/response schemas are not domain models.
- No
Request, Response, Depends, ORM session, or framework auth objects in domain services.
- Convert request data and auth/session state at the edge.
- Workers are another adapter, not a separate business-logic stack.
- CLI/admin scripts should call the same core services when they touch the same workflows.
Python Migrations and Operations
- If the service owns a relational DB, initialize
Alembic early.
- Add health and readiness endpoints early.
- Keep dev run, lint, test, and migrate commands in Poe tasks.
- Containerize when needed, but keep v1 Linux-first and boring.
Defer by Default
See setting-up-backends for the full defer-by-default philosophy. The list below is the Python ecosystem application:
- queues and background-job stacks
- caching layers
- metrics/tracing vendors
- event buses or CQRS
- multitenancy
- API versioning strategy beyond basic room for growth
- generated SDKs and OpenAPI customization
- Kubernetes-specific guidance
Add those only when the project actually needs them.
Handoff
- Use
building-backends (myai) for day-2 backend architecture and service/API/worker shaping.
- Use
building-multi-ui-apps if API, CLI, and automation share one core.
- Use
writing-python-code for implementation rules.
Related Skills
setting-up-backends (myai) — Parent skill. Load first for backend architecture philosophy.
engineering-principles (myai) — Foundation.
architecting-changes (myai) — Architecture decisions.
api-design (myai) — Stable API and protocol design.
security-and-hardening (myai) — Auth, secrets, boundary hardening.
setting-up-python-projects — Generic Python bootstrap pieces (templates, shared code).
building-backends (myai) — Day-2 backend architecture.
testing-python — Python API/service test setup.
1---2name: setting-up-python-backends3description: Python-specific extension to myai's `setting-up-backends`. ALWAYS LOAD `setting-up-backends` FIRST, AND THAN THIS skill for Python backend tooling. Backend/API bootstrap for Python: FastAPI/Django choice, backend repo layout, app factory, SQLAlchemy+Alembic, pydantic at edge, migrations, and service-first conventions.4---56# Setting Up Python Backends78## Prerequisites910This is a Python-specific extension to myai's `setting-up-backends`.11**Load `setting-up-backends` first** for the backend architecture philosophy,12directory layout patterns, wiring rules, defer-by-default guidance, and13migrations/operations strategy. This skill provides only Python-specific14framework choices, library selections, and code patterns.1516Also requires `engineering-principles` and `architecting-changes` (via myai bootstrap).1718This skill is a backend-specialized extension of `setting-up-python-projects`.19Start here for backend repos, then pull generic Python bootstrap pieces from20`setting-up-python-projects` as needed.2122## Python Framework Choice2324- **FastAPI** is the default boring choice for most service APIs.25- **Django** is justified when auth, admin, sessions, and CRUD-heavy backend surface are obviously large from the start.26- **Starlette** is for deliberate thin-edge builds, not as a default.2728## Python Default Stack2930- `FastAPI` + `uvicorn`31- `pydantic` models at the FastAPI HTTP edge; `msgspec.Struct` for config and non-framework external payload decoding32- `dataclass(frozen=True, slots=True)` + `Result[T, E]` in the core33- `SQLAlchemy 2` + `Alembic` when the service owns relational persistence34- `httpx` for outbound HTTP35- existing repo logging setup via `shared/logging`36- `pytest`, `pytest-asyncio`, and integration tests through real app wiring37- `uv`, `poethepoet`, `basedpyright`, and `ruff`3839Keep `pydantic` request/response DTOs at the HTTP boundary and convert immediately into framework-free typed structures.4041## Python Backend Layout4243See `setting-up-backends` for the philosophy behind this layout.4445```text46src/appname/47 api/48 app.py49 routes/50 schemas/51 errors.py52 domain/53 models.py54 services.py55 errors.py56 infrastructure/57 config.py58 logging.py59 db/60 models.py61 session.py62 queries.py63 clients/64 workers/65 __main__.py66 bootstrap.py67tests/68 integration/69 unit/70 fixtures/71migrations/72```7374Omit what you do not need. No DB, no `db/` or `migrations/`. No workers, no `workers/`.7576## First Files7778- `api/app.py` with `create_app()`79- `api/routes/health.py` with `/healthz`80- `bootstrap.py` with `create_services()` and app wiring81- `domain/models.py` and one small service/use-case module82- `infrastructure/config.py` to parse env into typed settings83- DB files and migrations only if persistence exists84- one smoke API test and one domain test8586## Wiring Rules8788- `create_app()` assembles only the HTTP layer.89- `bootstrap.py` wires settings, DB/session factories, external clients, and services.90- No DI framework by default. Use constructor injection and one composition root.91- Keep `__main__.py` or ASGI entrypoints thin.9293---9495## Boundary Rules9697- Request/response schemas are not domain models.98- No `Request`, `Response`, `Depends`, ORM session, or framework auth objects in domain services.99- Convert request data and auth/session state at the edge.100- Workers are another adapter, not a separate business-logic stack.101- CLI/admin scripts should call the same core services when they touch the same workflows.102## Python Migrations and Operations103104- If the service owns a relational DB, initialize `Alembic` early.105- Add health and readiness endpoints early.106- Keep dev run, lint, test, and migrate commands in Poe tasks.107- Containerize when needed, but keep v1 Linux-first and boring.108109## Defer by Default110111See `setting-up-backends` for the full defer-by-default philosophy. The list below is the Python ecosystem application:112113- queues and background-job stacks114- caching layers115- metrics/tracing vendors116- event buses or CQRS117- multitenancy118- API versioning strategy beyond basic room for growth119- generated SDKs and OpenAPI customization120- Kubernetes-specific guidance121122Add those only when the project actually needs them.123124## Handoff125126- Use `building-backends` (myai) for day-2 backend architecture and service/API/worker shaping.127- Use `building-multi-ui-apps` if API, CLI, and automation share one core.128- Use `writing-python-code` for implementation rules.129130## Related Skills131132- **`setting-up-backends`** (myai) — Parent skill. Load first for backend architecture philosophy.133- **`engineering-principles`** (myai) — Foundation.134- **`architecting-changes`** (myai) — Architecture decisions.135- **`api-design`** (myai) — Stable API and protocol design.136- **`security-and-hardening`** (myai) — Auth, secrets, boundary hardening.137- **`setting-up-python-projects`** — Generic Python bootstrap pieces (templates, shared code).138- **`building-backends`** (myai) — Day-2 backend architecture.139- **`testing-python`** — Python API/service test setup.