Skip to content

[audit] clever-msa-platform monorepo umbrella migration regressions discovered during fresh-clone validation (refs #23) #24

Description

@chase2955

Parent

EVNSolution/clever-change-control#23 — 체이스운수 운영현황·정산·전자계산서 역발행 시스템.

Why this audit

While running the project-start #23 phase-1 fresh-clone validation
(integration-local-stack/scripts/run_local_startup.py --fresh against
clever-msa-platform main + integration-local-stack main), the agent
hit four distinct failure modes that all trace back to the same root
commit:

1cc4008 refactoring: convert msa platform to monorepo umbrella
(clever-msa-platform main, 2026-04-27)

This commit consolidated several previously standalone repos into the
monorepo umbrella under development/*. Some artifacts were not carried
across the migration, and a few cross-repo references fell out of sync.

Because clever-msa-platform has GitHub Issues disabled, this audit is
filed here on clever-change-control so the team can see all four
findings and their fixes in a single place.

Failure ladder observed during fresh clone

  1. wave-4-integration health stage fails →
    service-settlement-payroll container exits 1 with
    ModuleNotFoundError: No module named 'settlements.services.daily_settlement_source_service'
  2. wave-5-views health stage fails (after fix #1 applied) →
    service-settlement-operations-view and service-driver-operations-view
    containers exit 1 with similar ModuleNotFoundError for two more
    missing modules.
  3. edge stage gateway image build fails →
    Dockerfile RUN test -f /opt/edge/public-api-docs/openapi.yaml
    fails because refresh_api_docs.py cannot run.
  4. edge stage gateway container exits even after api-docs are
    placed → nginx config references an upstream that does not exist
    in compose.

Regression categories

Category A — Missing Python service modules (4 files)

services/__init__.py and views.py import symbols that were never
committed to main. git log --all --diff-filter=A returns nothing
for any of the four file paths. Sibling files in the same directories
(__init__.py, source_clients.py) all landed in 1cc4008, so this
is a missed-commit during the umbrella migration, not a deletion.

Repo (under development/) Missing file
service-settlement-payroll settlements/services/daily_settlement_source_service.py
service-settlement-operations-view settlements/services/daily_settlement_service.py
service-driver-operations-view driver360/services/settlement_calendar_service.py
service-driver-operations-view driver360/services/work_log_service.py

Fix PR: EVNSolution/clever-msa-platform#3 — 4 commits, one per restored file. Each commit reasons from sibling code and the matching serializer / view call site to lock the contract surface; best-effort areas (attendance kind classification, pricing-table key candidates) are flagged inline for maintainer correction.

Category B — integration-local-stack compose missing attendance-registry-api

development/service-attendance-registry/ is whitelisted in WORKSPACE.md
and listed as active runtime in docs/mappings/current-runtime-inventory.md,
but it has no service stanza in
integration-local-stack/docker-compose.account-driver-settlement.yml,
no env file under infra/env/local/. The edge-api-gateway/nginx.conf
nevertheless declares upstream attendance-registry-api, so the gateway
container fails to start with:

[emerg] host not found in upstream "attendance-registry-api" in /etc/nginx/nginx.conf:290

Fix PR: EVNSolution/integration-local-stack#1 commit 1.

Category C — build_unified_openapi.py inventory heading drift

integration-local-stack/scripts/build_unified_openapi.py:172 looks for
heading ## Active Runtime Repos in
clever-msa-platform/docs/mappings/current-runtime-inventory.md, but the
canonical heading on main is ## Active Runtime Source Slices.
refresh_api_docs.py therefore raises:

ValueError: Heading not found: ## Active Runtime Repos

This blocks generation of edge-api-gateway/public-api-docs/openapi.yaml,
revision.json, and service-export-manifest.json, which the gateway
Dockerfile validates with RUN test -f. Fresh-clone gateway image
builds fail until the heading lookup is aligned.

Fix PR: EVNSolution/integration-local-stack#1 commit 2.

Category D — run_local_startup.py does not invoke refresh_api_docs.py (regression candidate, confirmation needed)

scripts/run_local_startup.py walks the stage list
infra → wave-2-core → wave-3-domain → wave-4-integration → wave-5-views → edge → seed → smoke,
but does not call refresh_api_docs.py (or the underlying
export_service_openapi.py / build_unified_openapi.py) at any point.
The edge gateway Dockerfile, however, requires
public-api-docs/openapi.yaml to exist in the build context.

This means a fresh-clone agent that follows
docs/runbooks/local-dispatch-settlement-stack.md exactly (which only
prescribes python3 ./scripts/run_local_startup.py --fresh) will hit
the gateway build failure described in Category C even after Category C
is fixed, because the artifact never gets generated. Existing developers
do not see this because compose/api-docs/clever-unified.openapi.yaml
is already on disk from prior runs.

Open question for the team: is the api-docs export intentionally a
manual prerequisite, or should run_local_startup.py invoke
refresh_api_docs.py between wave-5-views and edge (so a fresh
clone is self-contained)? Happy to add the step if the latter; will
park this as a separate PR after confirmation.

Why was this not caught earlier?

A pure inference, but consistent with the evidence: the umbrella
migration appears to have been validated against a working tree where
the four missing files and the api-docs artifact already existed on
disk from the standalone-repo era. A fresh clone is the path that
reveals all four findings, and there is no record on main of a
fresh-clone smoke run after 1cc4008.

Suggested follow-ups (for owner discretion)

  1. Add a CI job that does a fresh clone + run_local_startup.py --fresh
    and asserts Seed runner completed successfully. plus
    gateway healthy plus curl /healthz → 200. This would have caught
    all four findings in PR review.
  2. Decide on Category D and either document the prerequisite explicitly
    in the runbook or wire refresh_api_docs.py into the startup
    pipeline.

Trace

  • Parent project-start: #23
  • Fix PRs:
    • EVNSolution/clever-msa-platform#3 (Category A — 4 modules)
    • EVNSolution/integration-local-stack#1 (Categories B + C — compose + heading)
  • Open question: Category D awaits owner confirmation.

🤖 Generated with Claude Code

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions