feat(slice-1): backend skeleton, deps, and import-linter layer contract
Four-layer package (main > domains > platform) per SD-0001 §6.2; GraphQL api layer deferred. main.py is a stub so the top layer exists from the start (fleshed out in the /healthz task). lint-imports green on the skeleton. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -6,3 +6,6 @@ node_modules/
|
|||||||
dist/
|
dist/
|
||||||
.env
|
.env
|
||||||
*.local
|
*.local
|
||||||
|
.pytest_cache/
|
||||||
|
frontend/dist/
|
||||||
|
backend/var/
|
||||||
|
|||||||
@@ -0,0 +1,14 @@
|
|||||||
|
# Enforces SD-0001 §6.2: the four-layer contract main > domains > platform, with
|
||||||
|
# imports flowing only downward. The GraphQL `api` layer is deferred (§2), so the
|
||||||
|
# MVP contract has three layers; `app.api` is added back between main and domains
|
||||||
|
# when GraphQL arrives. Run from backend/: .venv/bin/lint-imports
|
||||||
|
[importlinter]
|
||||||
|
root_package = app
|
||||||
|
|
||||||
|
[importlinter:contract:layers]
|
||||||
|
name = App layering (main > domains > platform)
|
||||||
|
type = layers
|
||||||
|
layers =
|
||||||
|
app.main
|
||||||
|
app.domains
|
||||||
|
app.platform
|
||||||
@@ -0,0 +1,6 @@
|
|||||||
|
"""domains layer — bounded contexts (accounts, storefronts).
|
||||||
|
|
||||||
|
Empty in SLICE-1; the accounts domain lands in SLICE-2 and storefronts in SLICE-3.
|
||||||
|
The package exists now so the layer contract (.importlinter) has a target and later
|
||||||
|
slices add to a stable seam. Domains import only from app.platform, never upward.
|
||||||
|
"""
|
||||||
@@ -0,0 +1,5 @@
|
|||||||
|
"""ecomm backend — FastAPI app factory + the REST BFF.
|
||||||
|
|
||||||
|
Stub in SLICE-1 Task 1 so the top layer of the import-linter contract exists from the
|
||||||
|
start; the FastAPI factory and /healthz are added in Task 5.
|
||||||
|
"""
|
||||||
@@ -0,0 +1,5 @@
|
|||||||
|
"""platform layer — cross-cutting primitives (config, db, deps).
|
||||||
|
|
||||||
|
The bottom layer: imports nothing from app.domains or app.main. Owns the schema
|
||||||
|
lifecycle and request wiring, never business rules (SD-0001 §6.2).
|
||||||
|
"""
|
||||||
@@ -0,0 +1,7 @@
|
|||||||
|
[pytest]
|
||||||
|
testpaths = tests
|
||||||
|
python_files = test_*.py
|
||||||
|
addopts = -q
|
||||||
|
# Put backend/ (this rootdir) on sys.path so tests import the `app` package under
|
||||||
|
# pytest's default prepend import mode (tests/ has no __init__.py).
|
||||||
|
pythonpath = .
|
||||||
@@ -0,0 +1,7 @@
|
|||||||
|
fastapi>=0.110
|
||||||
|
uvicorn[standard]>=0.29
|
||||||
|
httpx>=0.27
|
||||||
|
psycopg[binary]>=3.1
|
||||||
|
psycopg-pool>=3.2
|
||||||
|
pytest>=8.0
|
||||||
|
import-linter>=2.0
|
||||||
Reference in New Issue
Block a user