fix(docker): drop COPY of gitignored data/ so staging image builds from a worktree
All checks were successful
CI / test (push) Successful in 17s
CI / test (pull_request) Successful in 16s

The staging-image rebuild (check_staging_image_fresh, ORCH-058) uses the task
git worktree as the docker build context. `data/` is gitignored (runtime SQLite
DB + backups) so it is absent in every worktree -> `COPY data/ ./data/` failed
the build (rc=1) -> deploy-staging rolled back to development (the loop ORCH-061
targets, surfaced one step later once the C9a/C9b waiver let the pipeline reach
the rebuild). The DB always arrives via the compose bind mount, so baking it in
was pointless (and leaked a stale host DB into the image).

Replace `COPY data/ ./data/` with `RUN mkdir -p /app/data` and add a static
regression guard asserting the Dockerfile never COPYs a gitignored path.

Refs: ORCH-061

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
This commit is contained in:
2026-06-07 13:39:02 +00:00
parent e18947d2d9
commit 01684a89df
5 changed files with 110 additions and 1 deletions

View File

@@ -118,6 +118,14 @@ helper `validated_revision` питает и штамп A, и `EXPECTED_REVISION`
образа, без миграций). Подробнее: [adr-0008](adr/adr-0008-staging-image-provenance.md),
детально — `docs/work-items/ORCH-058/06-adr/ADR-001-staging-image-provenance.md`.
**Инвариант build-context (ORCH-061):** staging-rebuild собирает образ из **git-воркти**
задачи, а воркти содержит только git-tracked файлы. Поэтому `Dockerfile` НЕ должен
`COPY` ни одного gitignore-пути — иначе `docker build` падает (rc=1) и `deploy-staging`
зацикливается на откате в `development`. В частности `data/` (рантайм-БД + бэкапы)
gitignore'нут и приходит исключительно через compose bind-mount (`./data:/app/data`),
поэтому образ лишь создаёт каталог монтирования (`RUN mkdir -p /app/data`), а не копирует
его. Гард — `tests/test_dockerfile_worktree_buildable.py`.
### Reconciler: реконсиляция потерянных webhook (ORCH-053 — реализовано)
Конвейер продвигается только входящими webhook; потерянное событие (502 на ребилде,
нет ретраев у Plane/Gitea, неразрезолвленный `sha→branch`) → задача застревает молча