Files
cc-ci/machine-docs/STATUS-samever.md
autonomic-bot 398f559168
All checks were successful
continuous-integration/drone/push Build is passing
status(samever): M1 PASS recorded; M2 in progress (custom-html two-run on cc-ci)
2026-06-17 04:32:51 +00:00

84 lines
5.2 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# STATUS — phase `samever` (step-back to older base when canonical == head version)
SSOT: `/srv/cc-ci/cc-ci-plan/plan-phase-samever-older-base-fallback.md`.
State files: this + BACKLOG-samever.md, REVIEW-samever.md (Adversary), JOURNAL-samever.md. DECISIONS.md shared.
## Phase
Started 2026-06-17. Gates: **M1** (implemented + unit-tested), **M2** (proven in real CI).
## Current status
**M1: PASS** (REVIEW-samever.md @2026-06-17T04:27Z — cold-verified, teeth hold, no regression).
**M2: IN PROGRESS** — real-CI demonstration on cc-ci. Plan: custom-html cold-on-latest twice (run A
promotes canonical→latest 1.13.0+1.31.1; run B = nightly steady state → step-back to 1.11.0+1.29.0,
base<latest); PR form (head==canonical step-back); version-bump UNAFFECTED (canonical olderhead);
discourse #4 unaffected; spot-check.
## M1 — WHAT is claimed
`resolve_upgrade_base` now reads the head's published version and steps back to a genuinely older
published base when the last-green warm-canonical version equals the head version never a
same-version no-op, never a needless skip when an older base exists.
Resolution chain (override / EXPECTED_NA / upgradestages short-circuits unchanged):
1. explicit `UPGRADE_BASE_VERSION` override unchanged.
2. last-green canonical **IF its version ≠ head version** `kind="version"` (canonical), unchanged from prevb.
3. last-green canonical **== head version** **step back**: `newest published version strictly older
than head` → `kind="version"` (the older tag). Reason starts `"step-back: …"`.
4. canonical == head **and no older published tag** → `kind="skip"`, reason
`"base == head (<v>) and no older published predecessor"`.
5. no canonical → main-tip ref / skip paths unchanged.
`head_version is None` (compose unreadable) → comparison is False → canonical stays primary (prevb behavior).
## M1 — WHERE (commit + paths)
- Implementation commit: **b29bb3f** (feat(samever): …), on `main`.
- `runner/run_recipe_ci.py` — `resolve_upgrade_base(..., head_version=None)` new chain (canonical
block ~lines 147180); call site `main()` reads `head_version = abra.head_compose_version(recipe)`
(~line 1023) and passes it.
- `runner/harness/abra.py` — `head_compose_version(recipe)` (regex `coop-cloud\.[^.\s]*\.version=([^\s"']+)`
over the head checkout's `compose.yml`; matches quoted + unquoted labels; does NOT match `.chaos-version`).
- `runner/warm_reconcile.py` — `version_key(tag)` (lifted from sort_versions; single ordering source)
+ `newest_older_version(tags, version)` (newest tag with `version_key < target`; None if none / version None).
- `tests/unit/test_upgrade_base.py` — 5 new tests (13 total).
## M1 — HOW to verify (cold, from a clean clone)
1. Unit suite (the gate):
```
nix shell nixpkgs#python311Packages.pytest -c pytest tests/unit/test_upgrade_base.py -v
```
**EXPECTED: 13 passed.** New tests:
- `test_canonical_equals_head_steps_back_to_newest_older` — canonical==head==`10.8.0+26.6.3`,
tags `[10.6.0+26.5.0, 10.8.0+26.6.3, 10.7.1+26.6.2, 10.7.0+26.6.0, not-a-version]` →
`plan.version == "10.7.1+26.6.2"` (strictly older; asserts `version_key(plan.version) < version_key(head)`),
`kind=="version"`, reason contains `"step-back"`. main never consulted.
- `test_canonical_differs_from_head_uses_canonical_unchanged` — canonical `10.7.1+26.6.2` ≠ head
`10.8.0+26.6.3` → `version==10.7.1+26.6.2`, reason `"last-green"`; recipe_tags NOT consulted.
- `test_canonical_equals_head_no_older_published_skips` — canonical==head==`1.0.0+3.5.3`, tags
`[1.0.0+3.5.3]` only → `kind=="skip"`, reason contains `"no older published predecessor"`.
- `test_no_head_version_preserves_canonical_primary` — head_version omitted → canonical primary, no step-back.
- `test_newest_older_version_ordering` — ordering helper picks correct strictly-older tag, excludes equal, None-safe.
The 8 prior tests (override / EXPECTED_NA / main-tip / head==main-tip skip / no-predecessor skip /
other-rung) are UNCHANGED and still pass — proving override/ref/skip paths untouched.
2. Teeth (canonical==head MUST NOT yield a same-version base): in
`test_canonical_equals_head_steps_back_to_newest_older`, `plan.version != head_version` and the
`version_key(plan.version) < version_key(head)` assertion fails loudly if the resolver ever returns
the same version or a newer one.
3. Compose-label parse (the head-version reader): the regex extracts `10.8.0+26.6.3` from a quoted
label and `3.5.3+1.24.2-rootless` from an unquoted one, and returns no match for a `.chaos-version`
label (verified — see JOURNAL). Real labels confirmed on cc-ci: keycloak `10.8.0+26.6.3`,
gitea `3.5.3+1.24.2-rootless`, discourse `1.0.0+3.5.3`.
4. F1d-2: the step-back returns `kind="version"`, so it flows through the SAME pinned-tag deploy path
as a normal canonical base (`abra.recipe_checkout` pins the tag on disk) — no new deploy code.
Note (pre-existing, NOT introduced by this gate): `tests/unit/test_meta.py::test_generated_doc_table_in_sync`
and `tests/unit/test_warm_reconcile.py::test_traefik_spec_is_stateless_with_setup` fail on clean
`279d84d` too (verified by stashing my changes). Out of scope for samever.
## Blocked
(none)