Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
51 commits
Select commit Hold shift + click to select a range
bce49cb
Queue in the inbox: ContentParams expressions fail CE1613 on mxcli v0.24
claude Sep 26, 2026
e2ecb98
fix(coverage-preflight): LEVEL 1 measures per-BRD ledger directories
claude Sep 26, 2026
d053550
fix(design-audit): defined-class corpus reads rules nested in at-rules
claude Sep 26, 2026
9fe925e
fix(design-audit): nav parser reads items carrying an icon clause
claude Sep 26, 2026
f38f808
fix(report-normalize): read inputs and write docs/report.json in the …
claude Sep 26, 2026
8ca908f
fix(otel): rung 2 waits for the claimed microflow spans, not the firs…
claude Sep 26, 2026
1fdc58e
Fix three verify-module instruments that could not go green or misrea…
claude Sep 26, 2026
c85cfb4
Inbox: three field notes from the card-disbursement build's MockServi…
claude Sep 26, 2026
fe1651c
journey-runner control: exact-expect outcome and numeric mustPointAt …
claude Sep 26, 2026
3dfc236
journey-runner: a click on a covered widget fails and names the cover
claude Sep 26, 2026
5e265d9
fix(helpers.js): logout() ends the session on Mendix 11
claude Sep 26, 2026
07e9111
BUG-141: workflow condition outcomes carry no PersistentId
claude Sep 26, 2026
b2201ca
fix(model-stamp): pre-model projects commit; worktree/--git-dir commi…
claude Sep 27, 2026
4dd6ed4
fix(closeout): rows the entry mode does not owe are N/A, not "still m…
claude Sep 27, 2026
7c2fae2
fix(check-root-clean): allow intake.md, triage.md and mxcli's FINDING…
claude Sep 27, 2026
144b0af
learn(extractor-quality-loop): non-code sources declare their own dim…
claude Sep 27, 2026
faf79c6
learn(conversion-runbook): say which bin/ a bare bin/<script> means
claude Sep 27, 2026
204ce47
fix(images-to-md): --out runs print the --out paths, not the default …
claude Sep 27, 2026
86b0d66
learn(brd-validation): a use case with no source is `proposed`, owed …
claude Sep 27, 2026
1cc0a76
fix(gate-check): name the dashboard after the resolved directory, not…
claude Sep 27, 2026
3b37e6f
learn(architecture-blueprint): number Step 5 register rows OI-n, neve…
claude Sep 27, 2026
1d99512
learn(demo users): the password is mandatory on mxcli v0.24.0
claude Sep 27, 2026
700317a
fix(lint-gate): probe app/*.mpr so the ratchet runs on two-tree projects
claude Sep 27, 2026
c6d385c
fix(helpers.js): navTo() finds menu items in a top-bar navbar too
claude Sep 27, 2026
1fb44d7
fix(verify-module): export the derived MXTK_ROOT so the coverage rung…
claude Sep 27, 2026
c21724e
fix(conformance-check): a probe mxcli rejects is UNRUNNABLE, not ABSENT
claude Sep 27, 2026
724035f
fix(check-design-reaches-app): compare token values, probe app/ on tw…
claude Sep 27, 2026
4164fd6
learn(bug-logs): BUG-141 fix proven — patch, regression test, restart…
claude Sep 27, 2026
ed57492
fix(project.config): derive id from the .mpr name when ROOT is app/
claude Sep 27, 2026
24b7738
fix(render-improvement-register): corrections are not findings
claude Sep 27, 2026
9ad87bd
fix(report-normalize): --selftest pins its own walkthrough declarations
claude Sep 27, 2026
634b5e0
learn(rest-integration): custom on-error blocks on rest call pass now
claude Sep 27, 2026
affb6f8
learn(testing-shape): a test --attach run leaves the catalog stale
claude Sep 27, 2026
50686f4
fix(check-page-shell): skip quoted strings and block comments in the …
claude Sep 27, 2026
8c9c62b
fix(review-report): sum multi-ledger coverage instead of faulting on it
claude Sep 27, 2026
39ea999
fix(constants-audit): a sentinel default is SENTINEL, not MODEL-SECRET
claude Sep 27, 2026
38658d1
fix(otel): capture() pages back to t0 instead of the newest 400 traces
claude Sep 27, 2026
5fe3aaf
learn(workflow): re-probe five workflow rules on mxcli v0.24.0
claude Sep 27, 2026
7e471d3
learn(detection-gaps): four new gap rows and one closed gap on v0.24.0
claude Sep 27, 2026
75e9fe9
learn(ui, testing): five UI and test-harness notes from one build
claude Sep 27, 2026
8d2e2fc
learn(bug-logs): BUG-142..154 and five v0.24.0 retests
claude Sep 27, 2026
9948a88
learn(skills): the skills side of BUG-142..154; triage three inbox notes
claude Sep 27, 2026
b9ca1fd
process(contrib/inbox): delete seven triaged 2026-09-26 notes
claude Sep 27, 2026
29a419d
process(CHANGELOG): end 19 Unreleased entries with their credit segment
claude Sep 27, 2026
dfd176e
Merge origin/master into the field-harvest branch
claude Sep 27, 2026
17442d5
Merge origin/master into the field-harvest branch
claude Sep 27, 2026
f8ed1b4
fix(tests): five new wave2 fixtures parse on bash 3.2
claude Sep 27, 2026
3c26c7f
Merge master into the field-harvest branch
claude Sep 28, 2026
14d5e05
Merge master into the field-harvest branch
claude Sep 28, 2026
dd0f788
Merge master (#164) into the field-harvest branch
claude Sep 28, 2026
ed258b1
Merge remote-tracking branch 'origin/master' into prep-162
f3vy Sep 29, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
44 changes: 44 additions & 0 deletions CHANGELOG.md

Large diffs are not rendered by default.

4 changes: 3 additions & 1 deletion bin/gate-check.sh
Original file line number Diff line number Diff line change
Expand Up @@ -2690,7 +2690,9 @@ fi
# the board shows the Sync/Drift FAIL rows, so it does not lie). Nothing overrides 2. A flag
# must not be able to destroy a file this script did not write.
INDEX="$PROJECT_DIR/index.html"
PROJECT_NAME="$(basename "$PROJECT_DIR")"
# Name the board after the resolved directory: `gate-check.sh . 2` from inside the project
# titled it ". — Conversion Dashboard" (card-disbursement requirements-driven build, 2026-09-25).
PROJECT_NAME="$(basename "$(cd "$PROJECT_DIR" 2>/dev/null && pwd -P || printf '%s' "$PROJECT_DIR")")"
GC_SENTINEL="<!-- generated-by: mxcli-project-toolkit/bin/gate-check.sh -->"

WRITE_HTML=1
Expand Down
22 changes: 20 additions & 2 deletions bin/lib/closeout.sh
Original file line number Diff line number Diff line change
Expand Up @@ -201,6 +201,16 @@ _co_plain_gate_needs() {
*) echo "" ;;
esac
}
# _co_owed <manifest modes> <entry mode> — does this project's entry mode owe the row? The same
# test as artifact-check.sh's second pass, and the same rule: an unknown mode (young register, no
# `Entry mode:` line yet) owes every row — louder, never quieter.
#
# WHY (2026-09-25, card-disbursement requirements-driven build). The three manifest loops below
# ignored the modes column, so a requirements-driven Stage 0 PASS still said "still missing for
# this stage: app-report" — a row only existing-app-change owes, which artifact-check.sh itself
# reported as N/A on the same run.
_co_owed() { [ -z "$2" ] && return 0; case ",$1," in *",$2,"*) return 0 ;; esac; return 1; }

# mxtk_plain_verdict <stage> <verdict text> <project-dir> [register]
# The "In plain words" paragraph under a gate line: status first, then every reason the
# technical text carries that has a known plain translation, then what is still missing on
Expand Down Expand Up @@ -244,11 +254,13 @@ mxtk_plain_verdict() {
case "$low" in *"unanswered"*|*"no blanks"*|*"blank"*)
_co_say "a kickoff question is still blank" ;; esac
# Missing mandatory artifacts for this stage, in plain names.
local id stage paths producer consumers modes absence miss=""
local id stage paths producer consumers modes absence miss="" mode
mode="$(_art_entry_mode "$reg" 2>/dev/null || true)"
if [ -f "$ARTIFACT_TSV" ]; then
while IFS=$'\t' read -r id stage paths producer consumers modes absence; do
case "$id" in ''|'#'*|artifact) continue ;; esac
[ "$stage" = "$st" ] && [ "$absence" != "optin" ] || continue
_co_owed "$modes" "$mode" || continue
_art_waiver "$reg" "$id" "$stage" >/dev/null 2>&1 && continue
_art_find "$root" "$paths"
[ -z "$ART_HIT" ] && miss="$miss${miss:+; }$(_co_plain_artifact "$id")"
Expand All @@ -274,11 +286,16 @@ mxtk_closeout_report() {

# ── Artifacts produced ──────────────────────────────────────────────────
printf '**Artifacts produced** (rows of `bin/lib/artifact-manifest.tsv` for stage %s; presence only, never quality)\n' "$st"
local id stage paths producer consumers modes absence reason n_art=0 optin
local id stage paths producer consumers modes absence reason n_art=0 optin mode
mode="$(_art_entry_mode "$reg" 2>/dev/null || true)"
if [ -f "$ARTIFACT_TSV" ]; then
while IFS=$'\t' read -r id stage paths producer consumers modes absence; do
case "$id" in ''|'#'*|artifact) continue ;; esac
[ "$stage" = "$st" ] || continue
if ! _co_owed "$modes" "$mode"; then
[ "$absence" = "optin" ] || printf -- '- ⏭ `%s` — N/A: entry mode %s does not owe it\n' "$id" "$mode"
continue
fi
optin=""
if [ "$absence" = "optin" ]; then
optin="$(_art_field "$reg" "opt-in artifact $id" 2>/dev/null || true)"
Expand Down Expand Up @@ -418,6 +435,7 @@ mxtk_closeout_report() {
while IFS=$'\t' read -r id stage paths producer consumers modes absence; do
case "$id" in ''|'#'*|artifact) continue ;; esac
[ "$stage" = "$next" ] && [ "$absence" = "optin" ] || continue
_co_owed "$modes" "$mode" || continue
n_opt=$((n_opt+1))
optin="$(_art_field "$reg" "opt-in artifact $id" 2>/dev/null || true)"
if [ -n "$optin" ]; then
Expand Down
18 changes: 14 additions & 4 deletions bin/lib/images-to-md.py
Original file line number Diff line number Diff line change
Expand Up @@ -564,6 +564,11 @@ def main(argv):
def rel_project(p):
return os.path.relpath(p, project).replace(os.sep, '/')

# A --out run must be re-checked with the same --out, or --check reads the default root.
default_out = os.path.join(project, 'analysis', 'knowledge-base', 'images')
out_flag = '' if os.path.normpath(images_out) == os.path.normpath(default_out) \
else ' --out %s' % rel_project(images_out)

manifest_path = os.path.join(images_out, 'manifest.json')
sha_to_id = {} if force else load_old_manifest(manifest_path)
used_numbers = set(int(v.split('-')[1]) for v in sha_to_id.values())
Expand Down Expand Up @@ -756,8 +761,9 @@ def ingest(occ):
print(' worklist: %s' % rel_project(worklist_path))
print('Images to describe: %d%s' % (
n_content,
(' — write analysis/knowledge-base/images/<id>.md per the template in '
'skills/image-transcription.md, then: bin/images-to-md.sh <p> --check') if n_content else ''))
(' — write %s/<id>.md per the template in '
'skills/image-transcription.md, then: bin/images-to-md.sh <p>%s --check'
% (rel_project(images_out), out_flag)) if n_content else ''))

if do_check or do_inline:
return run_check(project, images_out, entries, order, do_inline=(do_inline or do_check))
Expand Down Expand Up @@ -804,12 +810,16 @@ def run_check(project, images_out, entries, order, do_inline):
for sha, ent in content:
for loc in ent.locations:
owners.setdefault(loc['source'], set()).add(ent.id)
# The --artifact path is the manifest this run actually wrote — under --out when one was
# given. It used to be the default root, hard-coded, so a `--out` run printed ledger marks
# citing a manifest that did not exist (2026-09-25, card-disbursement requirements-driven build).
rel_manifest = os.path.relpath(os.path.join(images_out, 'manifest.json'), project).replace(os.sep, '/')
if owners:
print('')
print(' Coverage complete. Ledger marks owed, per source file:')
for owner in sorted(owners):
print(' bin/source-ledger.sh mark <p> \'%s\' --artifact analysis/knowledge-base/images/manifest.json '
'--evidence "<fill in>" --media %d --by <who>' % (owner, len(owners[owner])))
print(' bin/source-ledger.sh mark <p> \'%s\' --artifact %s '
'--evidence "<fill in>" --media %d --by <who>' % (owner, rel_manifest, len(owners[owner])))
return 0


Expand Down
Loading
Loading