Release 0.2.3: /api/health framework dependency for flotilla
Adds an unauthenticated GET /api/health endpoint returning JSON
{version, status} for ops tooling. version is the running framework
version (read from VERSION at process start, cached as a module-level
constant in backend/app/health.py); status is "ok" with HTTP 200 in
v1, with the "degraded" / 503 path reserved in the response shape for
future degradation conditions.
The structural value is the version-match check: a deploy control
panel (flotilla, in particular) polls the endpoint after
`systemctl restart` reports active and verifies the returned version
equals the tag just deployed, catching the failure mode where a
restart did not pick up the new code.
Patch-shaped per SPEC.md §20.2 — no operator action required, no env
vars, no schema changes. The CHANGELOG carries one MAY-language step
naming the optional monitoring affordance.
SPEC.md §17 now lists the endpoint; the §19.2 candidate-topic entry
records the topic's settlement (version source = VERSION file at
import time; degraded = reserved v1 scaffold; CHANGELOG = patch shape
with MAY-language).
Tests: backend/tests/test_health.py (3 tests — 200/payload shape,
unauthenticated, version-matches-VERSION). Full suite 128/128 green.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -28,6 +28,7 @@ from . import (
|
||||
entry as entry_mod,
|
||||
cache,
|
||||
funder,
|
||||
health,
|
||||
philosophy,
|
||||
providers as providers_mod,
|
||||
)
|
||||
@@ -81,6 +82,16 @@ def make_router(
|
||||
# (role, write-mute, audit-log, graduation-readiness queue).
|
||||
router.include_router(api_admin.make_router(config))
|
||||
|
||||
# ---------------------------------------------------------------
|
||||
# §17: /api/health — unauthenticated post-flight probe.
|
||||
# Used by ops tooling (flotilla) to verify a deploy landed via
|
||||
# version-match. v1 always reports ok; see backend/app/health.py.
|
||||
# ---------------------------------------------------------------
|
||||
|
||||
@router.get("/api/health")
|
||||
async def get_health() -> dict[str, Any]:
|
||||
return {"version": health.VERSION, "status": "ok"}
|
||||
|
||||
# ---------------------------------------------------------------
|
||||
# §14.2: /api/philosophy — PHILOSOPHY.md served verbatim.
|
||||
# No auth gate; anonymous visitors reach `/philosophy` per §14.1.
|
||||
|
||||
Reference in New Issue
Block a user