* test(#3696): failing-first coverage for the last_activity invariant and --strict exit status * fix(#3696): report the last_activity invariant and make the verdict gateable with --strict * fix(#3696): agree with the real reader on last_activity, and stop reporting structure as truncation * chore(#3696): backfill changeset PR number --------- Co-authored-by: sim <sim@local>
This commit is contained in:
@@ -2023,6 +2023,24 @@ Detect drift between STATE.md and the actual filesystem.
|
||||
node gsd-tools.cjs state validate
|
||||
```
|
||||
|
||||
| Flag | Description |
|
||||
|------|-------------|
|
||||
| `--strict` | Exit non-zero when the report is not `valid: true`. Off by default. |
|
||||
|
||||
Without `--strict` the command always exits `0`, including when it reports
|
||||
`valid: false` — so a CI step or git hook has to parse the JSON to decide whether
|
||||
state is correct. `--strict` makes the verdict gateable directly:
|
||||
|
||||
```bash
|
||||
node gsd-tools.cjs state validate --strict || echo "STATE.md needs attention"
|
||||
```
|
||||
|
||||
The default is deliberately unchanged: the exit status is observable behavior that
|
||||
reaches downstream consumers who cannot be enumerated, so opting in is a choice the
|
||||
caller makes rather than one imposed on every existing script.
|
||||
|
||||
A missing or unreadable STATE.md exits non-zero under `--strict` too — those report
|
||||
`error` or `valid: false` and are as gateable as any drift warning.
|
||||
The report also carries a `scope` field reporting whether the drift derivation could actually run:
|
||||
|
||||
| `scope` | Meaning |
|
||||
@@ -2045,6 +2063,8 @@ Each `warnings` entry is a coded diagnostic object (`{code, severity, message, r
|
||||
| `S005` | warning | STATE.md's plan count disagrees with the plan count on disk |
|
||||
| `S006` | warning | STATE.md still says "executing" but a `*-VERIFICATION.md` in the phase shows verification passed |
|
||||
| `S007` | warning | Every plan in the phase has a summary, but STATE.md still says "executing" |
|
||||
| `S008` | warning | STATE.md's `Last activity` value does not begin with a real calendar date, so no reader can date the project's activity |
|
||||
| `S009` | warning | The `Last activity` description wrapped onto a second line, and every reader silently drops the remainder |
|
||||
|
||||
---
|
||||
|
||||
|
||||
@@ -1796,7 +1796,7 @@ Test suite that scans all agent, workflow, and command files for embedded inject
|
||||
|
||||
### 69. STATE.md Consistency Gates
|
||||
|
||||
**Commands:** `state validate`, `state sync [--verify]`, `state planned-phase --phase N --plans N`
|
||||
**Commands:** `state validate [--strict]`, `state sync [--verify]`, `state planned-phase --phase N --plans N`
|
||||
|
||||
**Purpose:** Detect and repair drift between STATE.md and the actual filesystem, preventing cascading errors from stale state.
|
||||
|
||||
@@ -1805,6 +1805,8 @@ Test suite that scans all agent, workflow, and command files for embedded inject
|
||||
- REQ-STATE-02: `state sync` MUST reconstruct STATE.md from actual project state on disk
|
||||
- REQ-STATE-03: `state sync --verify` MUST perform a dry-run showing proposed changes without writing
|
||||
- REQ-STATE-04: `state planned-phase` MUST record the state transition after plan-phase completes (Planned/Ready to execute)
|
||||
- REQ-STATE-05: `state validate` MUST report a `Last activity` value that no reader can parse, rather than validating clean
|
||||
- REQ-STATE-06: `state validate --strict` MUST reflect `valid` in the process exit status, leaving the default exit status unchanged
|
||||
|
||||
**Produces:**
|
||||
| Artifact | Description |
|
||||
|
||||
@@ -49,6 +49,25 @@ A freshly-initialized project is the clearest example of a **legitimate** non-`c
|
||||
|
||||
---
|
||||
|
||||
## Gate on the result from a script
|
||||
|
||||
By default `state validate` exits `0` whatever it finds, so a shell gate needs the
|
||||
JSON. Pass `--strict` and the exit status carries the verdict instead:
|
||||
|
||||
```bash
|
||||
node gsd-tools.cjs state validate --strict
|
||||
```
|
||||
|
||||
Exit `0` means `valid: true`; any other exit means the report was not clean (drift
|
||||
warnings, an unreadable STATE.md, or no STATE.md at all).
|
||||
|
||||
`--strict` reads `valid`, **not** `scope` — so it stays silent about a scan that could
|
||||
not run. A degraded scope still reports `valid: true` and still exits `0`. Read `scope`
|
||||
yourself, exactly as the table above says, before treating a green `--strict` run as a
|
||||
guarantee the check actually looked.
|
||||
|
||||
---
|
||||
|
||||
## Related
|
||||
|
||||
- [`state validate`](../COMMANDS.md#state-validate) — command reference, flags, and the full output shape
|
||||
|
||||
Reference in New Issue
Block a user