From ad3ca4c60ae5a0b74ec08b357ccee53149289ebe Mon Sep 17 00:00:00 2001 From: MendixMau Date: Fri, 16 Oct 2026 15:39:40 +0800 Subject: [PATCH 1/5] docs(release): v1.0 notes, performance first Co-Authored-By: Claude Opus 5.5 --- CHANGELOG.md | 1 + docs/releases/v1.0.md | 445 ++++++++++++++++++++++++++---------------- 2 files changed, 283 insertions(+), 163 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 91ed25aa..ee4f3550 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -19,6 +19,7 @@ Sections dated before 2026-09-19 predate the cycle and stay as they are. Named m ## Unreleased +- docs(release): **`docs/releases/v1.0.md` rewritten to the maintainer's structure: performance first (testing at key moments with the measured numbers), the settings a project owner controls, context packs, everything else, how to update.** Docs only; no routed or always-loaded file touched. — MendixMau - learn(workflow skills): **a Jump has one fixed target, so one failure handler for N steps is a child workflow, not a shared node; plus three probed workflow errors (CE0117 on a `System.Workflow` argument means map `$WorkflowInstance`, CE1613 means the called workflow's parameter must be `$WorkflowContext`, and `returns` goes before `exposed as workflow action`).** `workflow-structure-rules.md` §1 and `learned-workflow-patterns.md` §9. The §9 rows were probed on mxcli v0.26.0 / Mendix 11.15.0 with native `mx check`. The third row corrects the reading that a called microflow cannot return a value. Upstream issues: mendixlabs/mxcli#1529 (CE0117), #1530 (CE1613, and `syntax workflow call-workflow` shows the failing form), #1531 (describe drops every call workflow mapping), #1533 (`returns` parse messages). Source: a five-app lab project (Mendix 11.15, mxcli v0.26.0) — five-app lab report, WF-1 - learn(fixture-seeding): **resetting workflow data: abort instances through the runtime (Workflow Commons admin or *Change workflow state*); if SQL is unavoidable, delete the link tables first (`system$workflow_currentactivity`, `system$workflow_workflowdefinition`, `system$workflowusertask_assignees`, `system$workflowusertask_targetusers`, `system$workflowusertask_targetgroups`, plus the `system$workflowendedusertask_*` equivalents; names read from a Mendix 11.15 database), and reset a context object only after its instances are gone.** A seed reset that deleted workflow rows by SQL failed on those links (WF-5). Text only, `ondemand` skill. — five-app lab report, WF-5 - fix(e2e/helpers): **`navTo` throws `navigation item "" not found` instead of clicking nothing.** A missing menu item was a silent no-op, so when the target page was also the persona's home page the landing guard stayed green and a broken-control journey (a control that must FAIL) passed. The parent group stays soft (an open flyout needs no click); the item itself must be found. The message names the active user and the visible menu items, so the reader can tell a renamed item (fix the journey) from a role that cannot open the page (fix the grants). Callers: journey steps fail with the message, design-audit rung 7 records a fault, full-app-walkthrough records a failed `nav` step (the walk stops only when the step is `fatal`), monkey's `land` swallows the error and still checks `.mx-page`, so monkey is unchanged. `tests/wave2/test-navto-missing-item.sh` (stub page, no browser) fails on master (absent item resolves) and passes here. Field report: a five-app lab project (Mendix 11.15, mxcli v0.26.0), TK-012 — MendixMau diff --git a/docs/releases/v1.0.md b/docs/releases/v1.0.md index 46b7f75d..79d40c9b 100644 --- a/docs/releases/v1.0.md +++ b/docs/releases/v1.0.md @@ -5,179 +5,298 @@ agent and [mxcli](https://github.com/mendixlabs/mxcli). It gives the agent a sta with recorded decisions (`PROJECT.md`), skills it loads only when a task calls for them, and mechanical gates (`bin/gate-check.sh`, lint, mxbuild, end-to-end journeys) that report what is actually in your project. It runs for migrations, requirements-driven builds, greenfield builds -and changes to a live app, or à la carte to audit and test an app you already have. - -1.0 is the first named milestone on top of the release train. It is not a rewrite: these notes -pick out what changed in the two weeks before it (2026-09-30 to 2026-10-14). Every line traces to -an entry in [`CHANGELOG.md`](../../CHANGELOG.md), which has the full detail and field evidence. -How milestones relate to the `vYYYY.MM.DD` tags: [`docs/RELEASE-PROCESS.md`](../RELEASE-PROCESS.md) -§8. - -1.0 is the first release-train tag published to GitHub, cut with `bin/cut-release.sh` when this -release is announced. Earlier `vYYYY.MM.DD` headings in CHANGELOG were never pushed as tags. - -Most PRs linked below landed together through -[#329](https://github.com/MendixMau/mxcli-project-toolkit/pull/329) and show as closed on GitHub; their -changes are on master. - -## Highlights - -### Every merge is reviewed by someone who did not write it - -A PR now gets an independent review (MERGE / MERGE-AFTER-FIX / HOLD, on value, regression risk -after sync, correctness and context cost) before it lands; green CI and the author's own report no -longer count as one. Nine PRs had merged on 2026-10-13 without one -([#316](https://github.com/MendixMau/mxcli-project-toolkit/pull/316)). Several fixes in this -release came out of those reviews (the exec lock race, the final-LOOK timing, the -`test-stack-up` exit codes). - -**For you:** what reaches your project on `git pull` has been read by a second reviewer, not just -tested by its author. - -### Less text in every session - -The always-loaded skill tier had reached 79,997 words against an 80,000-word cap. Incident stories -moved behind pointers into `process/baseline-incident-history.md` and the tier dropped to 76,259 -words with no rule removed ([#315](https://github.com/MendixMau/mxcli-project-toolkit/pull/315)). -New rule: room is made by moving text, never by deleting rules. `change-intake.md` became a -331-word core with an on-demand detail file -([#327](https://github.com/MendixMau/mxcli-project-toolkit/pull/327)), dispatch guidance moved to -its own small file ([#320](https://github.com/MendixMau/mxcli-project-toolkit/pull/320)), a -scaffolded `CLAUDE.local.md` is 17% shorter -([#292](https://github.com/MendixMau/mxcli-project-toolkit/pull/292)), routing in -`CLAUDE.local.md` carries triggers only -([#226](https://github.com/MendixMau/mxcli-project-toolkit/pull/226)), helper stubs read about 18% -less per dispatch ([#223](https://github.com/MendixMau/mxcli-project-toolkit/pull/223)), and a -build helper can get one context-pack file per build step instead of a reading list -([#198](https://github.com/MendixMau/mxcli-project-toolkit/pull/198)). - -**For you:** run `bin/sync-project.sh` and existing projects pick up the shorter wiring; sessions -start with less to read. - -### `exec.sh`: per-project lock, restart verdicts, safer restarts - -In a 20-task field run, 57 of 148 `exec.sh` runs applied nothing, and a machine-wide guard blocked -writes because a *different* project was writing. `exec.sh` now locks per project with a stale-lock -takeover, offers an opt-in `--commit-first`, and ends every applied script with a verdict: restart -needed, watch can apply this, or unknown -([#304](https://github.com/MendixMau/mxcli-project-toolkit/pull/304), -[#324](https://github.com/MendixMau/mxcli-project-toolkit/pull/324)). The review of #304 found the -takeover could let up to three contenders hold the lock; it is now serialised, and a fixture runs -10 rounds of 12 contenders and asserts at most one holder. New `bin/app-restart.sh` (#304) restarts only -this project's own `mxcli run --local`; since -[#322](https://github.com/MendixMau/mxcli-project-toolkit/pull/322) it also refuses over a leftover `mxcli test` injection. - -**For you:** two projects on one machine no longer block each other, and the agent is told when a -change needs an app restart instead of guessing. - -### Lint you can trust and tune - -UX001/002 plus Batches 1–4 landed: UX001/UX002, then ERR001/LOOP001, PERF001/002/004, -TXT001/TXT002/UI001, and Batch 4 with **SEC014** (an external role that can write status, audit or ownership members) and a -CONV009 that reads its `maxObjects` option -([#238](https://github.com/MendixMau/mxcli-project-toolkit/pull/238), -[#248](https://github.com/MendixMau/mxcli-project-toolkit/pull/248), -[#270](https://github.com/MendixMau/mxcli-project-toolkit/pull/270), -[#305](https://github.com/MendixMau/mxcli-project-toolkit/pull/305), -[#312](https://github.com/MendixMau/mxcli-project-toolkit/pull/312)). When `mxcli init` reverts -toolkit rules to stock, the lint gate now stops as **BLIND** instead of blaming the next script -for the jump, and sync restores them -([#308](https://github.com/MendixMau/mxcli-project-toolkit/pull/308)). Turning a rule off has one -supported route (`enabled: false` in `lint-config.yaml`, recorded in `PROJECT.md`). A metrics -ledger records outcome, speed, lint total and `mxcli report` score for every exec -([#265](https://github.com/MendixMau/mxcli-project-toolkit/pull/265)). - -**For you:** SEC014 asks one question (which roles are external) and prints a NOTE until you -answer it. - -### End-to-end proof that fails for the right reason - -The journey runner preflights the suite (a refused admin credential aborts before the first -journey) and journeys can declare `requires` / `leaves` / `consumes` -([#302](https://github.com/MendixMau/mxcli-project-toolkit/pull/302)). OQL rows are read by SELECT -alias, an app that dies mid-suite reads APP-DOWN rather than FAIL, and negative-only claims get a -liveness reference ([#310](https://github.com/MendixMau/mxcli-project-toolkit/pull/310)). -`test-stack-up.sh` identifies this project's own `run --local` by its command line -([#319](https://github.com/MendixMau/mxcli-project-toolkit/pull/319)). Re-runs are scoped to what -a change touched, UI-only changes get a light lane, and unit tests are off by default -([#290](https://github.com/MendixMau/mxcli-project-toolkit/pull/290)). The page-fidelity scorer -matches what a page displays, on whole words -([#318](https://github.com/MendixMau/mxcli-project-toolkit/pull/318)). - -**For you:** fewer false reds from the harness, and less time re-proving changes nobody touched. -**Check after upgrading:** `oqlScalar` now returns the first SELECT alias. - -### Stage 3 designs how users reach each page - -Stage 3 now writes `design/interaction-model.md` before the first wireframe: a home per role, an -inbox per user task, and for each page how it is reached and what it receives. Every wireframe -opens with a contract block ([#317](https://github.com/MendixMau/mxcli-project-toolkit/pull/317), -part 1 of [#291](https://github.com/MendixMau/mxcli-project-toolkit/issues/291)). Three apps had -passed every gate while one rooted 8 pages on a parameterless retrieve and gave all 6 roles one -home page. - -**For you:** navigation and page-parameter defects surface at design time, when they are cheap. - -### Changing an existing app: delivery rounds and mid-build changes - -In change-an-existing-app mode, `bin/status.sh` reports the delivery round from a `## Rounds` -table in `PROJECT.md`, drops noise that does not apply there, and counts targeted manual Studio -Pro steps written from `templates/manual-steps.md` -([#326](https://github.com/MendixMau/mxcli-project-toolkit/pull/326)). In every mode, feedback -typed mid-build is logged as a change-log row in `PROJECT.md` before any edit, and the -requirement or design is changed before the MDL -([#306](https://github.com/MendixMau/mxcli-project-toolkit/pull/306)). A final whole-app LOOK is -now owed at Stage 6 ([#303](https://github.com/MendixMau/mxcli-project-toolkit/pull/303), -[#321](https://github.com/MendixMau/mxcli-project-toolkit/pull/321)). - -**For you:** "where are we" has an answer in rounds, not a stage number that never moves. - -## Upgrading - -```bash -git -C ~/Mendix/mxcli-project-toolkit pull -~/Mendix/mxcli-project-toolkit/bin/sync-project.sh <project-root> -``` - -Skills update with the pull; sync refreshes what was copied into the project (intake questions, -untouched agent stubs, `bin/` and `tests/e2e/` copies nobody edited, lint rules). Once release tags -are published (from 1.0 on) it prints the `Toolkit release:` line you are on; before that it -prints `Toolkit release: none tagged yet`. Then: - -- Answer SEC014's question (which roles are external), then re-baseline lint once, as the sync - NOTE says. -- On mxcli v0.26 or later, sync runs a read-only property-set check (models written by mxcli up - to v0.25 can break Studio Pro's merge). If it reports a repair is needed, run - `bin/doctor.sh --fix-property-sets <project>` - ([#314](https://github.com/MendixMau/mxcli-project-toolkit/pull/314)). -- Projects with per-BRD coverage ledgers: run conformance once after the upgrade; old rows are - re-keyed ([#307](https://github.com/MendixMau/mxcli-project-toolkit/pull/307)). - -## Known gaps - -- **Field runs still owed.** Fixtures pass, but no real-project run is cited yet for: the - property-set check, the page-fidelity rescoring, PROOF-OF-LOOK per section, per-BRD conformance - ledgers, the graph-sweep catalog guard on mxcli v0.24, and the metrics ledger inside a live - `exec.sh`. +and changes to a live app, or a la carte to audit and test an app you already have. + +1.0 is the first named milestone on top of the release train, and the first tag published to +GitHub (`vYYYY.MM.DD`, cut with `bin/cut-release.sh`). Earlier dated headings in the CHANGELOG +were never pushed as tags. Every line below traces to an entry in +[`CHANGELOG.md`](../../CHANGELOG.md) or to a linked PR. How milestones relate to tags: +[`docs/RELEASE-PROCESS.md`](../RELEASE-PROCESS.md) §8. + +## 1. Performance improvements + +### Testing at key moments + +A twenty-task UX-fix retro measured what testing every change costs +([#274](https://github.com/MendixMau/mxcli-project-toolkit/issues/274)): UI-only changes were +re-proven 5 to 10 times (their own journey, the regression journeys of 4 to 5 other modules, +reviewer re-runs), a full `mxcli test` took about 6 minutes at every batch close, and 143 minutes +of unit tests found stale strings and credential problems, not logic bugs. In the same project +one exec took 28 to 41 seconds. + +The toolkit now runs tests at fixed moments and keeps a change small. Per change, the build gate +plus what the change touched. The full run happens once when the build is complete and once +before every later deploy. Unit tests are off by default and switched on only for a module whose +logic needs them +([#290](https://github.com/MendixMau/mxcli-project-toolkit/pull/290), +[#417](https://github.com/MendixMau/mxcli-project-toolkit/pull/417)). + +| Moment | What runs | +|---|---| +| Every change (build and feedback) | The gate, plus what the change touched | +| Module done | That module's journeys | +| Build complete | Everything, once | +| Before every later deploy | Everything, once again | +| You ask | Everything | + +"What the change touched" is computed, not guessed. `./bin/affected-tests.sh <script.mdl>` lists +the unit tests and journeys a change owes, from the elements the script writes and their +transitive callers +([#416](https://github.com/MendixMau/mxcli-project-toolkit/pull/416)). On three real change +scripts in a five-app project it selected 0 to 1 of 20 journey files and 0 to 1 unit test files +per change. It is advisory and exits 0. It also reports `journeys unmapped N of M` for journey +files that name-based selection cannot reach (12 of the 20 held no qualified name), so an empty +selection is never read as "nothing owed". `exec.sh` prints the `affected tests:` hint on every +MDL run. The first call takes about 19 seconds (it builds the mxcli catalog), later calls about 3 +seconds. + +### Other speed items + +- **Where an exec spends its time.** The run summary and `docs/BUILD-LOG.md` now carry per-step + seconds (`steps: guards Ns check Ns snapshot Ns baseline Ns exec Ns gate Ns lint Ns score Ns`), + and a run whose gate fails keeps its gate seconds. Those failed or rolled-back runs were 47 of + 238 rows in the measured project and its costliest 20%. The timing costs about 0.2 seconds per + exec, 0.5 to 0.7% of a 28 to 41 second exec + ([#413](https://github.com/MendixMau/mxcli-project-toolkit/pull/413)). +- **Fewer build rows.** A `BUILD` row is now one use case, and a script is the rollback unit. + Two Stage 4 runs on the same requirements had produced 137 and 246 rows (2.5 rows per use + case); build cost followed the row count, 11 versus 25 model calls per row and about 11 versus + about 40 hours. A Stage 4 A/B on two fixture modules (22 use cases) gave 1.05 rows per use case + with the new text and 2.27 to 2.45 with the old. +- **Less to read at the start.** The always-loaded skill tier went from 79,997 to 76,259 words + with no rule removed + ([#315](https://github.com/MendixMau/mxcli-project-toolkit/pull/315)). A helper reads only the + baseline rows for its own role. The mdl helper at Stage 5 went from 56,236 to 43,599 words + (the runbook slice for its stage) and then to 30,647 (a routing row on demand for one role). + Routing tables are trigger lists, so a session no longer re-reads the whole runbook (about 24k + tokens) on every later call. +- **The app map refreshes only what changed.** On a 17,500-unit app the loop sweep re-described + every loop-containing microflow: 1,917 describes in 2 hours 45 minutes at 6 workers, while about + 80 units had changed between rounds. It now describes only changed units. On a synthetic + 2,000-unit app with 1% changed that is 20 describes instead of 2,000, and `bin/status.sh` shows + how stale the map is. No field run of the incremental sweep yet. +- **Context packs** cut helper tool calls and time; see section 3. + +## 2. You decide how your project runs + +These settings are yours. They survive `git pull` and `bin/sync-project.sh`. + +| What you want | The line or command | Where it lives | +|---|---|---| +| Unit tests across the project | `Unit tests default: no` (the default) or `yes` | `PROJECT.md`, intake Q13 | +| Unit tests for one module | Set the Unit row of the module brief's Test plan to `yes` and name why: `\| Unit (.test.mdl) \| yes \| <the calculation, mapping, Java or REST logic, or the fixed bug> \|` | `architecture/modules/<Module>/module-brief.md`, `skills/module-brief.md` | +| What runs at each moment | `## Test strategy` table, offered at CAC-5 (architecture and offer, before the build). Status `CONFIRMED`, or `ASSUMED` in auto mode. Change any cell in your answer to the offer | `PROJECT.md`, `checkpoint-build.md` | +| Everything, now | Say "run everything". The full suite runs once on request | in chat | +| Per-change test selection depth | `./bin/affected-tests.sh <script> --depth N`, or `MXTK_AFFECTED_DEPTH` (default 1) | shell | +| Context packs | `Context packs: on` (default), `no-brain` or `off`; `MXTK_CONTEXT_PACKS` for one command | `PROJECT.md` | +| Ask before each exec | `bin/exec-approval.sh <project> --set auto` (default) or `--set ask`; `--clear` removes it | `.mxtk/exec-approval`, or `Exec approval:` in `PROJECT.md` | +| Fewer or more questions | `bin/interview-mode.sh <project> --set steering\|assist\|auto` | `Interview mode:` in `PROJECT.md` | +| Keep sync from restoring the look-ledger hook | Create the file `.mxtk/no-hook-repair` | project root | +| Check staged files for real secret values | `bin/check-staged-secrets.sh` (staged blobs) or `--tree` (everything tracked). Opt-in; not part of the pre-commit hook | project | +| Install only some scripts on sync | `bin/sync-project.sh <project> --only-bin <script.sh>` | toolkit clone | +| Commit before an exec that needs a clean model | `bin/exec.sh --commit-first` | shell | +| Longer verify-module rungs on a big app | `VM_TMO_GRAPH`, `VM_TMO_COVERAGE`, `VM_TMO_JOURNEYS` (defaults 300, 300, 900 seconds) | shell | +| A lint rule off | `enabled: false` under `rules:` in `.claude/lint-config.yaml`, recorded in `PROJECT.md` | project | + +The test strategy and the unit default are two settings. The strategy says when a test set runs. +The unit default says whether unit tests exist in that set. `affected` selects from the tests +that exist and does not ask for new ones. + +## 3. Context packs + +A helper that builds one step of a module used to get a reading list. With context packs it gets +one file. The module brief has a `### Build steps` table, one row per dispatch: what the step +builds, which existing elements it reads, the app's own example to copy, and the `mxcli brain` +slice. `bin/context-pack.sh <Module> <Step>` turns that row into a pack made of the folder from +the brief's folder plan, the why from `mxcli brain brief`, the brief's architecture constraints, +and a live `DESCRIBE` of every element the step reads, of the example, and of anything it +changes. The pack also lists the rule files the step must read, the attributes a `TEXTBOX` +cannot bind on a page step (mxcli `check` passes them, `mx check` fails with CE2421), and the +`mxcli impact` list when the step changes an existing element. The pack is regenerated per +dispatch and never committed. + +**Why it helps, as measured.** On a real app's scratch copy, 3 helper runs with a pack against 3 +without, same brief and brain: about 9% fewer tokens (130k against 144k), about 40% fewer tool +calls (13 against 21) and about 40% less time (60 seconds against 101). Every run passed +`mxcli check` and executed with no new mx errors. Page steps with the later pack used about 25% +fewer tool calls and about 30% less time (n=2 each, too few runs to quote tokens). + +**The switch.** `Context packs: on | no-brain | off` in `PROJECT.md`, default `on`. +`no-brain` leaves out the `mxcli brain` section. `off` makes `context-pack.sh` exit 3 and the +dispatcher falls back to the reading list in `iterative-build-loop.md`, so a CLI change that +breaks `DESCRIBE` or `brain brief` costs one register line, not a revert. + +**Older briefs.** A module brief with no `### Build steps` table, written before packs existed, +also exits 3 and falls back to the reading list. A project mid-build keeps going after a pull +without retrofitting its briefs. + +## 4. Everything else + +### Safety and recovery + +- **A crashed mxbuild rolls the write back.** When a baseline was measured and mxbuild then + exits non-zero without an error list, `exec.sh` restores the snapshot and logs one row, instead + of keeping a model nothing can load + ([#424](https://github.com/MendixMau/mxcli-project-toolkit/pull/424)). +- **Sync keeps your `.claude/settings.json` rules.** A re-wire runs `mxcli init`, which + overwrites that file. `wire-agents.sh` now merges: your entries win and keep their order, and + entries only the new file has are appended + ([#421](https://github.com/MendixMau/mxcli-project-toolkit/pull/421)). +- **The macOS sync fix.** The item-3 rewrite failed on stock macOS awk while sync printed + "Rewrote" on every run. It now works there and prints a `WARN:` when a rewrite fails + ([#427](https://github.com/MendixMau/mxcli-project-toolkit/pull/427)). +- **The right JDK for your Mendix version.** `find_java` asks for JDK 25 on Mendix 11.14 and + newer, JDK 21 otherwise, and a warning names a missing JDK + ([#410](https://github.com/MendixMau/mxcli-project-toolkit/pull/410)). It adds about 45 ms + per exec when `JAVA_HOME` is unset. +- **The look-ledger hook comes back.** A project whose `.claude/settings.json` lost the + look-ledger hook (so the ledger read 0 of 31 pages seen with 22 screenshots on disk) gets it + restored by sync, and `doctor.sh` warns. Opt out with `.mxtk/no-hook-repair` + ([#414](https://github.com/MendixMau/mxcli-project-toolkit/pull/414)). +- **A staged-secrets check.** `check-staged-secrets.sh` compares your project's real secret + values against staged blobs and prints the file and key name, never the value. On a synthetic + 6,000-file repo, 230 staged files take 1.0 seconds and a whole-tree scan 2.6 + ([#411](https://github.com/MendixMau/mxcli-project-toolkit/pull/411)). +- **`exec.sh` locks per project**, offers `--commit-first`, ends every applied script with a + restart verdict, and `bin/app-restart.sh` restarts only this project's own `run --local` + ([#304](https://github.com/MendixMau/mxcli-project-toolkit/pull/304), + [#324](https://github.com/MendixMau/mxcli-project-toolkit/pull/324), + [#322](https://github.com/MendixMau/mxcli-project-toolkit/pull/322)). In a 20-task field run, + 57 of 148 `exec.sh` runs had applied nothing, and a different project's write had blocked + another. A fixture runs 10 rounds of 12 contenders and asserts at most one lock holder. +- **Merges no longer need `--no-verify`.** The doc numbering check examines only files a merge + itself changes + ([#418](https://github.com/MendixMau/mxcli-project-toolkit/pull/418)). + +### Quality gates + +- **Every merge is reviewed by someone who did not write it** (MERGE, MERGE-AFTER-FIX or HOLD, + on value, regression risk after sync, correctness and context cost). Nine PRs had merged on + 2026-10-13 without one ([#316](https://github.com/MendixMau/mxcli-project-toolkit/pull/316)). + Several fixes in this release came out of those reviews. Every PR now also states its cost in a + five-row Impact block ([`docs/RELEASE-PROCESS.md`](../RELEASE-PROCESS.md) §4a). +- **A missing navigation item fails the journey.** `navTo` throws + `navigation item "<title>" not found` instead of clicking nothing, so a control that must fail + can no longer pass. Replayed on a five-app project, none of the 26 real journeys turned red and + the 4 deliberately broken controls now fail + ([#412](https://github.com/MendixMau/mxcli-project-toolkit/pull/412)). +- **Lint you can trust and tune.** UX001/002 and Batches 1 to 4, including SEC014 (an external + role that can write status, audit or ownership members). When `mxcli init` reverts toolkit + rules to stock, the lint gate stops as BLIND instead of blaming the next script + ([#238](https://github.com/MendixMau/mxcli-project-toolkit/pull/238), + [#305](https://github.com/MendixMau/mxcli-project-toolkit/pull/305), + [#308](https://github.com/MendixMau/mxcli-project-toolkit/pull/308), + [#312](https://github.com/MendixMau/mxcli-project-toolkit/pull/312)). +- **End-to-end proof that fails for the right reason.** The journey runner preflights the suite + and journeys can declare `requires`, `leaves` and `consumes`. OQL rows are read by SELECT alias, + an app that dies mid-suite reads APP-DOWN rather than FAIL + ([#302](https://github.com/MendixMau/mxcli-project-toolkit/pull/302), + [#310](https://github.com/MendixMau/mxcli-project-toolkit/pull/310), + [#319](https://github.com/MendixMau/mxcli-project-toolkit/pull/319)). +- **Themed palettes compare correctly.** `check-design-reaches-app.sh` compares a design system + whose palette lives in scoped blocks such as `:root.theme-light` block for block, and no longer + warns "0 of N tokens carry the design's value" on a correct port + ([#423](https://github.com/MendixMau/mxcli-project-toolkit/pull/423)). +- **Stage 3 designs how users reach each page.** `design/interaction-model.md` comes before the + first wireframe: a home per role, an inbox per user task, and per page how it is reached and + what it receives ([#317](https://github.com/MendixMau/mxcli-project-toolkit/pull/317)). +- **Changing an existing app** reports the delivery round from a `## Rounds` table, logs + mid-build feedback as a change-log row before any edit, and owes a final whole-app LOOK at + Stage 6 ([#326](https://github.com/MendixMau/mxcli-project-toolkit/pull/326), + [#306](https://github.com/MendixMau/mxcli-project-toolkit/pull/306), + [#303](https://github.com/MendixMau/mxcli-project-toolkit/pull/303)). + +### Skills + +- **`rest-between-mendix-apps`**: for two or more Mendix apps that read each other over REST. A + contract to write down before the first script, 17 publisher and consumer rules, and a + six-rung cross-app test ladder + ([#273](https://github.com/MendixMau/mxcli-project-toolkit/pull/273)). +- **`demo-recording-polish`**: 60 fps capture, a drawn cursor with a click ripple, eased scroll, + and a zoom rendered after the take, so re-framing re-renders the same take + ([#404](https://github.com/MendixMau/mxcli-project-toolkit/pull/404)). +- **Workflow notes**: a Jump has one fixed target, so one failure handler for several steps is a + child workflow; three probed build errors; workflow seed reset + ([#415](https://github.com/MendixMau/mxcli-project-toolkit/pull/415)). +- **Skill trims.** Five skill findings (detection gaps, date tokens, Atlas selectors, grants for + the default home page, CSS traps) landed as compact rows paid for by trimming provenance + prose, so the always-loaded total went from 75,225 to 75,204 words + ([#422](https://github.com/MendixMau/mxcli-project-toolkit/pull/422)). + +### Multi-app + +`rest-between-mendix-apps` above is the multi-app skill. `affected-tests.sh` in a multi-app +folder scans every app's tests and needs `MPR_FILE`; see Known gaps. + +### Docs and field notes + +Eight field notes from an existing-app widget rebuild went to the inbox for triage +([#309](https://github.com/MendixMau/mxcli-project-toolkit/pull/309)). This file, the versioning +rule and the README for adopters came with the 1.0 notes. + +### Known gaps + +- **Field runs still owed.** Fixtures pass, but no real-project run is cited yet for the + property-set check, the page-fidelity rescoring, per-BRD conformance ledgers, the incremental + app map, and the test strategy end to end (the A/B that compares a scripted change on a lab + copy against master). +- **A defect a module-close full run used to catch may now surface only at the full run** before + deploy. That is the trade the test strategy makes. - **[#291](https://github.com/MendixMau/mxcli-project-toolkit/issues/291) parts 2 and 3** (gate facts for the interaction model, and the model-side check) are not built. -- The exec stale-lock takeover can still race if a holder is killed mid-takeover. It is rare; a - designed fix and a regression test are owed. +- **`affected-tests.sh` in a multi-app folder** over-reaches because module names can repeat + across apps. - `mxcli fix hashes` as an `exec.sh --patch` post-step is pending ([#295](https://github.com/MendixMau/mxcli-project-toolkit/issues/295)). -- No shipped pipeline writes an extraction-quality score file yet; the Stage 1 report shows that - section as "manual". - On Windows and Linux without Studio Pro, `exec.sh` skips its mxbuild gate unless mxbuild is found; run `bin/doctor.sh --install <project>` or set `MXBUILD_PATH`. -## Credits +### Credits Thanks to everyone whose field reports, fixes and reviews fed this release: **MendixMau** (maintainer), **AlvinnYeo** (the lint stock-revert guard, the catalog edge guard, -per-BRD conformance ledgers, the port-holder report, a microflow preflight STOP row, a leftover -test-injection case), and **jopterhorst** (`mxcli fix property-sets` in the upgrade path, -delivery rounds in change-an-existing-app mode, two UI detection gaps, token-burn rates and -windows). Independent reviewers caught several of the defects fixed here before they shipped. +per-BRD conformance ledgers, the port-holder report), and **jopterhorst** (`mxcli fix +property-sets` in the upgrade path, delivery rounds, the incremental app map, token-burn rates +and windows). Independent reviewers caught several defects before they shipped. + +## 5. How to update + +Pin the toolkit clone to the release tag, then sync each project: + +```bash +git -C ~/Mendix/mxcli-project-toolkit fetch --tags +git -C ~/Mendix/mxcli-project-toolkit checkout vYYYY.MM.DD +~/Mendix/mxcli-project-toolkit/bin/sync-project.sh <project-root> --repair-intake +``` + +The checkout is detached on purpose: a pinned clone stays on the tag, and the session-start +warning that the clone is not on `master` is expected. To unpin: +`git -C ~/Mendix/mxcli-project-toolkit checkout master && git -C ~/Mendix/mxcli-project-toolkit pull`. +Skills update with the checkout. Sync refreshes what was copied into the project and prints the +`Toolkit release:` you are on. `--repair-intake` appends the questions older projects lack, +including Q13 (unit tests default). The README's plain update is `git pull` followed by +`bin/sync-project.sh <project-root>`; the pinned form above is the one for stability +([`docs/RELEASE-PROCESS.md`](../RELEASE-PROCESS.md) §8). + +**After updating:** + +- Answer SEC014's question (which roles are external), then re-baseline lint once, as the sync + NOTE says. +- On mxcli v0.26 or later, sync runs a read-only property-set check. If it reports a repair is + needed, run `bin/doctor.sh --fix-property-sets <project>` + ([#314](https://github.com/MendixMau/mxcli-project-toolkit/pull/314)). +- Projects with per-BRD coverage ledgers: run conformance once; old rows are re-keyed + ([#307](https://github.com/MendixMau/mxcli-project-toolkit/pull/307)). +- `oqlScalar` now returns the first SELECT alias. A journey that relied on `navTo` silently + clicking a missing item now fails at the nav step. +- `PROJECT.md` `## Test strategy` is not written by sync. A project with no such section uses + the printed defaults and says so. + +**If you cannot update today**, paste this into your session: + +> Do not run mxcli test, unit tests or the full journey suite after individual fixes. After each +> fix, run only the affected tests (./bin/affected-tests.sh <script>). Run the full suite only +> when I say the app is ready to deploy. Found something? See [CONTRIBUTING.md](../../CONTRIBUTING.md). The bar is "it happened and you wrote it down". From 2b26c739110cf4e8bc209c8881b720b4e9c9e85d Mon Sep 17 00:00:00 2001 From: MendixMau <mauritscgvisser@gmail.com> Date: Sat, 17 Oct 2026 03:00:16 +0800 Subject: [PATCH 2/5] docs(release): v1.0 notes match what ships on release/v1.0 Every named PR has merged; adds the process map, BRD report, per-flow unit tests, load test, progress report, multilingual skill and the legacy-widget notes; tag v1.0. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --- docs/releases/v1.0.md | 156 +++++++++++++++++++++++++++++------------- 1 file changed, 108 insertions(+), 48 deletions(-) diff --git a/docs/releases/v1.0.md b/docs/releases/v1.0.md index 79d40c9b..fbffe899 100644 --- a/docs/releases/v1.0.md +++ b/docs/releases/v1.0.md @@ -8,8 +8,9 @@ actually in your project. It runs for migrations, requirements-driven builds, gr and changes to a live app, or a la carte to audit and test an app you already have. 1.0 is the first named milestone on top of the release train, and the first tag published to -GitHub (`vYYYY.MM.DD`, cut with `bin/cut-release.sh`). Earlier dated headings in the CHANGELOG -were never pushed as tags. Every line below traces to an entry in +GitHub (`v1.0`). Earlier dated headings in the CHANGELOG were never pushed as tags. All v1.0 +work merged into the `release/v1.0` branch while master stayed frozen; the tag marks that +branch. Every PR named below has merged, and every line traces to an entry in [`CHANGELOG.md`](../../CHANGELOG.md) or to a linked PR. How milestones relate to tags: [`docs/RELEASE-PROCESS.md`](../RELEASE-PROCESS.md) §8. @@ -26,10 +27,13 @@ one exec took 28 to 41 seconds. The toolkit now runs tests at fixed moments and keeps a change small. Per change, the build gate plus what the change touched. The full run happens once when the build is complete and once -before every later deploy. Unit tests are off by default and switched on only for a module whose -logic needs them +before every later deploy. Unit tests are off by default and switched on only where logic needs them ([#290](https://github.com/MendixMau/mxcli-project-toolkit/pull/290), -[#417](https://github.com/MendixMau/mxcli-project-toolkit/pull/417)). +[#417](https://github.com/MendixMau/mxcli-project-toolkit/pull/417)). They are chosen per flow, not per module: a module brief lists the +`Unit flows:` worth a test, one line each with a reason, and `affected-tests.sh` runs only the +listed flows a change touched. That follows the maintainer's policy that unit-testing everything +is overkill: logic and integrations get unit tests, and UI journeys catch the rest +([#435](https://github.com/MendixMau/mxcli-project-toolkit/pull/435), [#436](https://github.com/MendixMau/mxcli-project-toolkit/pull/436)). | Moment | What runs | |---|---| @@ -77,9 +81,10 @@ seconds. how stale the map is. No field run of the incremental sweep yet. - **Context packs** cut helper tool calls and time; see section 3. -## 2. You decide how your project runs +## 2. You manage your own testing -These settings are yours. They survive `git pull` and `bin/sync-project.sh`. +These are the settings a project owner controls: what runs and when, how much the agent +asks, and what it is allowed to touch. They survive `git pull` and `bin/sync-project.sh`. | What you want | The line or command | Where it lives | |---|---|---| @@ -87,6 +92,7 @@ These settings are yours. They survive `git pull` and `bin/sync-project.sh`. | Unit tests for one module | Set the Unit row of the module brief's Test plan to `yes` and name why: `\| Unit (.test.mdl) \| yes \| <the calculation, mapping, Java or REST logic, or the fixed bug> \|` | `architecture/modules/<Module>/module-brief.md`, `skills/module-brief.md` | | What runs at each moment | `## Test strategy` table, offered at CAC-5 (architecture and offer, before the build). Status `CONFIRMED`, or `ASSUMED` in auto mode. Change any cell in your answer to the offer | `PROJECT.md`, `checkpoint-build.md` | | Everything, now | Say "run everything". The full suite runs once on request | in chat | +| Which flows get a unit test | List them in the module brief as `Unit flows:`, one `- ACT_X: reason` line each. A list wins for its module even under `Unit tests default: yes` | `architecture/modules/<Module>/module-brief.md` | | Per-change test selection depth | `./bin/affected-tests.sh <script> --depth N`, or `MXTK_AFFECTED_DEPTH` (default 1) | shell | | Context packs | `Context packs: on` (default), `no-brain` or `off`; `MXTK_CONTEXT_PACKS` for one command | `PROJECT.md` | | Ask before each exec | `bin/exec-approval.sh <project> --set auto` (default) or `--set ask`; `--clear` removes it | `.mxtk/exec-approval`, or `Exec approval:` in `PROJECT.md` | @@ -132,7 +138,83 @@ without retrofitting its briefs. ## 4. Everything else -### Safety and recovery +### Reports and visibility + +- **One progress report replaces `build-plan.html`.** `architecture/progress-report.html` is a + single self-contained page. It keeps what the old page showed (phases, built and proven) and + adds stages P to 6 with links to their artifacts, a progress bar and a stage nav + ([#434](https://github.com/MendixMau/mxcli-project-toolkit/pull/434)). + - Stage times come from the metrics ledger that `exec.sh` writes, so build facts (runs, + applied, failed, blocked, restored, exec time, wall span) show with or without a session log. + With a Claude Code session log it adds time per stage, sub-agent use, context size and an + estimated token cost, labelled as an estimate. + - A session cache makes a refresh take about a second. + - Autoreload keeps your scroll position, and only runs while a build is active. + - Tips sit in a narrow side column, grouped by theme and collapsed. Red is rare: only a key + script failing every run, or a hang over 30 minutes. + - An old `build-plan.html` is still accepted and never deleted. +- **`build-plan.json` stays current.** `build-plan-status.sh --refresh` updates an existing + `build-plan.json`, so a day of building no longer reads as 0 built + ([#437](https://github.com/MendixMau/mxcli-project-toolkit/pull/437)). +- **A bug log you can file safely.** `docs/bugs.jsonl` per project and `bin/file-bugs.sh`, which + redacts every title and body, searches for duplicates, and posts only after you confirm each + bug at a terminal ([#433](https://github.com/MendixMau/mxcli-project-toolkit/pull/433)). +- **Change requests stay visible.** A change request updates the module brief and shows as + "waiting" at session start and module close until it is built + ([#430](https://github.com/MendixMau/mxcli-project-toolkit/pull/430)). + +### Process map and BRD report + +- **Process map.** One swimlane map per business process, each step on its wireframe once + screens exist, every open question and `ASSUMED` decision pinned to the step it is about. It is + drawn twice: a draft at Stage 2 close (shown at CAC-3) and the full map at Stage 3. In the + field run that prompted it, the reviewer could not tell where sixty questions fit; the map + placed 102 items with 0 unplaced ([#429](https://github.com/MendixMau/mxcli-project-toolkit/pull/429)). +- **BRD report with the map on top.** The Stage 2 report opens with the process map and lists + requirements and open questions under it, each tied to its step. A click on a step filters the + list, and what no step covers stays under "whole app". `open-questions.html` is retired, and + the Stage 3 prototype and the map link to each other + ([#438](https://github.com/MendixMau/mxcli-project-toolkit/pull/438)). +- **Follow-ups.** Migrating an old anchors file no longer trusts a regex: it checks what changed, + says what it did, accepts a string `targets`, and lists unfilled entries instead of dropping + them ([#453](https://github.com/MendixMau/mxcli-project-toolkit/pull/453)). + +### Skills learned + +- **`rest-between-mendix-apps`**: for two or more Mendix apps that read each other over REST. A + contract to write down before the first script, 17 publisher and consumer rules, and a + six-rung cross-app test ladder + ([#273](https://github.com/MendixMau/mxcli-project-toolkit/pull/273)). +- **`demo-recording-polish`**: 60 fps capture, a drawn cursor with a click ripple, eased scroll, + and a zoom rendered after the take, so re-framing re-renders the same take + ([#404](https://github.com/MendixMau/mxcli-project-toolkit/pull/404)). +- **Workflow notes**: a Jump has one fixed target, so one failure handler for several steps is a + child workflow; three probed build errors; workflow seed reset + ([#415](https://github.com/MendixMau/mxcli-project-toolkit/pull/415)). +- **Skill trims.** Five skill findings (detection gaps, date tokens, Atlas selectors, grants for + the default home page, CSS traps) landed as compact rows paid for by trimming provenance + prose, so the always-loaded total went from 75,225 to 75,204 words + ([#422](https://github.com/MendixMau/mxcli-project-toolkit/pull/422)). +- **`load-test`**: load test a page without correlating Mendix's client protocol by hand. + Playwright records the real `/xas/` calls, a probe maps each opaque `runtimeOperation` to its + microflow through Jaeger, and the chosen call is replayed with the session's own cookie and + CSRF token. It lists ten field traps and a four-line report that says what the run does not + prove. No instrument ships yet, only the skill + ([#431](https://github.com/MendixMau/mxcli-project-toolkit/pull/431)). +- **`unit-test`**: how to write and run a microflow unit test whose assertion is live: what is + worth a test and what is not, equality-only `@expect`, a positive control that must fail, and a + four-line report. Whether and when unit tests run stays with the project's test strategy + ([#432](https://github.com/MendixMau/mxcli-project-toolkit/pull/432)). +- **`multilingual-app`**: a second language is four decisions the translations never see: source + language, enabled languages, the user's starting language, and a switch a normal role can use. + A field run wrote 418 strings per language correctly and the language picker still failed with + every check green. The skill gives the recipe and the traps + ([#449](https://github.com/MendixMau/mxcli-project-toolkit/pull/449), from a proposal by CarlesZ). +- **Five legacy-widget field notes** from an existing-app rebuild went to the inbox for triage + (first proposed as [#309](https://github.com/MendixMau/mxcli-project-toolkit/pull/309), landed + as [#450](https://github.com/MendixMau/mxcli-project-toolkit/pull/450), thanks to AlvinnYeo). + +### Fixes - **A crashed mxbuild rolls the write back.** When a baseline was measured and mxbuild then exits non-zero without an error list, `exec.sh` restores the snapshot and logs one row, instead @@ -168,7 +250,7 @@ without retrofitting its briefs. itself changes ([#418](https://github.com/MendixMau/mxcli-project-toolkit/pull/418)). -### Quality gates +#### Quality gates - **Every merge is reviewed by someone who did not write it** (MERGE, MERGE-AFTER-FIX or HOLD, on value, regression risk after sync, correctness and context cost). Nine PRs had merged on @@ -206,34 +288,6 @@ without retrofitting its briefs. [#306](https://github.com/MendixMau/mxcli-project-toolkit/pull/306), [#303](https://github.com/MendixMau/mxcli-project-toolkit/pull/303)). -### Skills - -- **`rest-between-mendix-apps`**: for two or more Mendix apps that read each other over REST. A - contract to write down before the first script, 17 publisher and consumer rules, and a - six-rung cross-app test ladder - ([#273](https://github.com/MendixMau/mxcli-project-toolkit/pull/273)). -- **`demo-recording-polish`**: 60 fps capture, a drawn cursor with a click ripple, eased scroll, - and a zoom rendered after the take, so re-framing re-renders the same take - ([#404](https://github.com/MendixMau/mxcli-project-toolkit/pull/404)). -- **Workflow notes**: a Jump has one fixed target, so one failure handler for several steps is a - child workflow; three probed build errors; workflow seed reset - ([#415](https://github.com/MendixMau/mxcli-project-toolkit/pull/415)). -- **Skill trims.** Five skill findings (detection gaps, date tokens, Atlas selectors, grants for - the default home page, CSS traps) landed as compact rows paid for by trimming provenance - prose, so the always-loaded total went from 75,225 to 75,204 words - ([#422](https://github.com/MendixMau/mxcli-project-toolkit/pull/422)). - -### Multi-app - -`rest-between-mendix-apps` above is the multi-app skill. `affected-tests.sh` in a multi-app -folder scans every app's tests and needs `MPR_FILE`; see Known gaps. - -### Docs and field notes - -Eight field notes from an existing-app widget rebuild went to the inbox for triage -([#309](https://github.com/MendixMau/mxcli-project-toolkit/pull/309)). This file, the versioning -rule and the README for adopters came with the 1.0 notes. - ### Known gaps - **Field runs still owed.** Fixtures pass, but no real-project run is cited yet for the @@ -251,21 +305,13 @@ rule and the README for adopters came with the 1.0 notes. - On Windows and Linux without Studio Pro, `exec.sh` skips its mxbuild gate unless mxbuild is found; run `bin/doctor.sh --install <project>` or set `MXBUILD_PATH`. -### Credits - -Thanks to everyone whose field reports, fixes and reviews fed this release: -**MendixMau** (maintainer), **AlvinnYeo** (the lint stock-revert guard, the catalog edge guard, -per-BRD conformance ledgers, the port-holder report), and **jopterhorst** (`mxcli fix -property-sets` in the upgrade path, delivery rounds, the incremental app map, token-burn rates -and windows). Independent reviewers caught several defects before they shipped. - ## 5. How to update -Pin the toolkit clone to the release tag, then sync each project: +Pin the toolkit clone to the tag `v1.0`, then sync each project: ```bash git -C ~/Mendix/mxcli-project-toolkit fetch --tags -git -C ~/Mendix/mxcli-project-toolkit checkout vYYYY.MM.DD +git -C ~/Mendix/mxcli-project-toolkit checkout v1.0 ~/Mendix/mxcli-project-toolkit/bin/sync-project.sh <project-root> --repair-intake ``` @@ -273,7 +319,7 @@ The checkout is detached on purpose: a pinned clone stays on the tag, and the se warning that the clone is not on `master` is expected. To unpin: `git -C ~/Mendix/mxcli-project-toolkit checkout master && git -C ~/Mendix/mxcli-project-toolkit pull`. Skills update with the checkout. Sync refreshes what was copied into the project and prints the -`Toolkit release:` you are on. `--repair-intake` appends the questions older projects lack, +`Toolkit release:` you are on. `--repair-intake` is needed where the project predates the new intake questions: it appends the questions older projects lack, including Q13 (unit tests default). The README's plain update is `git pull` followed by `bin/sync-project.sh <project-root>`; the pinned form above is the one for stability ([`docs/RELEASE-PROCESS.md`](../RELEASE-PROCESS.md) §8). @@ -300,3 +346,17 @@ including Q13 (unit tests default). The README's plain update is `git pull` foll Found something? See [CONTRIBUTING.md](../../CONTRIBUTING.md). The bar is "it happened and you wrote it down". + +## 6. Thanks + +Thanks to the contributors whose work is in this release: + +- **CarlesZ** wrote up the multilingual app findings from a field run, now the + `multilingual-app` skill ([#449](https://github.com/MendixMau/mxcli-project-toolkit/pull/449)). +- **AlvinnYeo** sent the legacy-widget field notes that landed as [#450](https://github.com/MendixMau/mxcli-project-toolkit/pull/450), and earlier the + lint stock-revert guard, the catalog edge guard, per-BRD conformance ledgers and the + port-holder report. + +Thanks also to jopterhorst for `mxcli fix property-sets` in the upgrade path, delivery rounds, the +incremental app map and token-burn rates. Independent reviewers caught several defects before +they shipped. From 4e8665061250f7a74ef3bf38c063acd00ecbee3f Mon Sep 17 00:00:00 2001 From: MendixMau <mauritscgvisser@gmail.com> Date: Sat, 17 Oct 2026 03:35:48 +0800 Subject: [PATCH 3/5] docs(release): fix v1.0 notes after review of #428 Remove conflict markers in CHANGELOG, correct the exec timing source, the merged claim and the #434 claims, add the decompose, rehost and mxpatch bullets, and apply the cheap wording fixes. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --- CHANGELOG.md | 3 -- docs/releases/v1.0.md | 69 ++++++++++++++++++++++++++----------------- 2 files changed, 42 insertions(+), 30 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 0fae7fcd..d7429269 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -19,9 +19,7 @@ Sections dated before 2026-09-19 predate the cycle and stay as they are. Named m ## Unreleased -<<<<<<< HEAD - docs(release): **`docs/releases/v1.0.md` rewritten to the maintainer's structure: performance first (testing at key moments with the measured numbers), the settings a project owner controls, context packs, everything else, how to update.** Docs only; no routed or always-loaded file touched. — MendixMau -======= - fix(process-map): migrate no longer trusts a regex for the model key: it checks the top-level `anchors` changed and otherwise re-writes the model, and says so instead of claiming "only that key was changed"; a string `targets` in an old file counts as a one-item list instead of crashing; unfilled entries already in the current anchors file are listed, not dropped silently (follow-up to #438 review) — MendixMau - new(brd-report): the Stage 2 report opens with the pass-1 process map (drawn by `process-map.js build --embed`, not a copy) and lists requirements and open questions under it, each tied to its step; a click on a step filters the list, what no step covers stays under "whole app". `open-questions.html` and `bin/questions-report.sh` are retired: the gate and the interview hook write `analysis/brd-report.html`, and an old project's `docs/open-questions.html` is never an error, only pointed away from. Stage 3: the prototype links to the full map and the map links back — a business owner could not tell where in the work a question fits (field run, 2026-10-16) — MendixMau @@ -45,7 +43,6 @@ Sections dated before 2026-09-19 predate the cycle and stay as they are. Named m - fix(tests): **`test-exec-hash-verify.sh` case K passes on macOS.** `$TMPDIR` ends in `/`, so the bare `mktemp` path held `//` and the exact `MXPATCH_BACKUP_DIR` path assert could not match; `WORK` is now `cd`-ed into and read back with `pwd -P`. Test only, no script change. 42 pass / 1 fail before, 43 / 0 after — #384 review - fix(exec): **when mxbuild crashes on the written model (non-zero exit, no error list) after a baseline that mxbuild did measure, exec.sh now rolls the write back instead of keeping it.** Before, the default path kept the write, the next exec printed "Baseline NOT measured" and built on a model nothing could load. One BUILD-LOG row says the script was rolled back and carries the mxbuild exit code; without a measured baseline (the crash may be the machine) and in `--patch` mode the old behaviour is unchanged. No new refusal, no guard. Extracted from the crash-rollback hunk of #311. Test: `tests/wave2/test-exec-crash-rollback.sh` (synthetic stub mxbuild; 4 of its checks fail on master) — field incident 2026-10-13 (#309) - fix(_common): **`find_java` on macOS picks the JDK that matches the model's Mendix version: 25 for 11.14 and above, 21 below (and when the version cannot be read).** It always asked for `java_home -v 21`, a pin added for 11.12.2 (JDK 25 breaks that build's gradle 8.5). On 11.15 the same pin broke the other way: mxbuild failed `release version 25 not supported` (exit 3) on the first Java-action build, 21 times in one lab phase, until `JAVA_HOME` was set by hand in `toolkit.env`. Mendix's system requirements list JDK 21 for Studio Pro 11.13 and below and JDK 25 for 11.14 and above. The version comes from `mxtk_model_version` (the .mpr's `_MetaData`). Detection uses `java_home -F -v N`, because plain `-v N` never fails on macOS (a missing JDK silently returns the default, exit 0). When the wanted JDK is missing, the default is still used, and the new `find_java_note` line is printed by exec.sh, verify-model.sh and doctor.sh (they all discard find_java's stderr). `JAVA_HOME` still wins; `MXTK_JAVA_HOME_BIN` overrides the java_home binary for tests. `tests/wave2/test-find-java-version.sh` (fake java_home that mimics the real fallback-with-exit-0, 14 cases) fails on master for 11.14, 11.15 and 12.x. Not run: a real two-JDK Mac build; the version table is taken from the Mendix docs. Field report: a five-app lab project (Mendix 11.15, mxcli v0.26.0), TK-018 — MendixMau ->>>>>>> origin/release/v1.0 - learn(workflow skills): **a Jump has one fixed target, so one failure handler for N steps is a child workflow, not a shared node; plus three probed workflow errors (CE0117 on a `System.Workflow` argument means map `$WorkflowInstance`, CE1613 means the called workflow's parameter must be `$WorkflowContext`, and `returns` goes before `exposed as workflow action`).** `workflow-structure-rules.md` §1 and `learned-workflow-patterns.md` §9. The §9 rows were probed on mxcli v0.26.0 / Mendix 11.15.0 with native `mx check`. The third row corrects the reading that a called microflow cannot return a value. Upstream issues: mendixlabs/mxcli#1529 (CE0117), #1530 (CE1613, and `syntax workflow call-workflow` shows the failing form), #1531 (describe drops every call workflow mapping), #1533 (`returns` parse messages). Source: a five-app lab project (Mendix 11.15, mxcli v0.26.0) — five-app lab report, WF-1 - learn(fixture-seeding): **resetting workflow data: abort instances through the runtime (Workflow Commons admin or *Change workflow state*); if SQL is unavoidable, delete the link tables first (`system$workflow_currentactivity`, `system$workflow_workflowdefinition`, `system$workflowusertask_assignees`, `system$workflowusertask_targetusers`, `system$workflowusertask_targetgroups`, plus the `system$workflowendedusertask_*` equivalents; names read from a Mendix 11.15 database), and reset a context object only after its instances are gone.** A seed reset that deleted workflow rows by SQL failed on those links (WF-5). Text only, `ondemand` skill. — five-app lab report, WF-5 - fix(e2e/helpers): **`navTo` throws `navigation item "<title>" not found` instead of clicking nothing.** A missing menu item was a silent no-op, so when the target page was also the persona's home page the landing guard stayed green and a broken-control journey (a control that must FAIL) passed. The parent group stays soft (an open flyout needs no click); the item itself must be found. The message names the active user and the visible menu items, so the reader can tell a renamed item (fix the journey) from a role that cannot open the page (fix the grants). Callers: journey steps fail with the message, design-audit rung 7 records a fault, full-app-walkthrough records a failed `nav` step (the walk stops only when the step is `fatal`), monkey's `land` swallows the error and still checks `.mx-page`, so monkey is unchanged. `tests/wave2/test-navto-missing-item.sh` (stub page, no browser) fails on master (absent item resolves) and passes here. Field report: a five-app lab project (Mendix 11.15, mxcli v0.26.0), TK-012 — MendixMau diff --git a/docs/releases/v1.0.md b/docs/releases/v1.0.md index fbffe899..f4db345e 100644 --- a/docs/releases/v1.0.md +++ b/docs/releases/v1.0.md @@ -10,7 +10,8 @@ and changes to a live app, or a la carte to audit and test an app you already ha 1.0 is the first named milestone on top of the release train, and the first tag published to GitHub (`v1.0`). Earlier dated headings in the CHANGELOG were never pushed as tags. All v1.0 work merged into the `release/v1.0` branch while master stayed frozen; the tag marks that -branch. Every PR named below has merged, and every line traces to an entry in +branch. Every PR named below has merged, some through the integration batch +[#329](https://github.com/MendixMau/mxcli-project-toolkit/pull/329); [#434](https://github.com/MendixMau/mxcli-project-toolkit/pull/434) merges before the tag. Every line traces to an entry in [`CHANGELOG.md`](../../CHANGELOG.md) or to a linked PR. How milestones relate to tags: [`docs/RELEASE-PROCESS.md`](../RELEASE-PROCESS.md) §8. @@ -22,14 +23,12 @@ A twenty-task UX-fix retro measured what testing every change costs ([#274](https://github.com/MendixMau/mxcli-project-toolkit/issues/274)): UI-only changes were re-proven 5 to 10 times (their own journey, the regression journeys of 4 to 5 other modules, reviewer re-runs), a full `mxcli test` took about 6 minutes at every batch close, and 143 minutes -of unit tests found stale strings and credential problems, not logic bugs. In the same project -one exec took 28 to 41 seconds. - +of unit tests found stale strings and credential problems, not logic bugs. The toolkit now runs tests at fixed moments and keeps a change small. Per change, the build gate plus what the change touched. The full run happens once when the build is complete and once before every later deploy. Unit tests are off by default and switched on only where logic needs them ([#290](https://github.com/MendixMau/mxcli-project-toolkit/pull/290), -[#417](https://github.com/MendixMau/mxcli-project-toolkit/pull/417)). They are chosen per flow, not per module: a module brief lists the +[#417](https://github.com/MendixMau/mxcli-project-toolkit/pull/417)). They are chosen per flow: a module brief lists the `Unit flows:` worth a test, one line each with a reason, and `affected-tests.sh` runs only the listed flows a change touched. That follows the maintainer's policy that unit-testing everything is overkill: logic and integrations get unit tests, and UI journeys catch the rest @@ -43,9 +42,9 @@ is overkill: logic and integrations get unit tests, and UI journeys catch the re | Before every later deploy | Everything, once again | | You ask | Everything | -"What the change touched" is computed, not guessed. `./bin/affected-tests.sh <script.mdl>` lists -the unit tests and journeys a change owes, from the elements the script writes and their -transitive callers +"What the change touched" comes from the script itself: `./bin/affected-tests.sh <script.mdl>` lists +the unit tests and journeys a change owes, from the elements the script writes and the flows +that call them ([#416](https://github.com/MendixMau/mxcli-project-toolkit/pull/416)). On three real change scripts in a five-app project it selected 0 to 1 of 20 journey files and 0 to 1 unit test files per change. It is advisory and exits 0. It also reports `journeys unmapped N of M` for journey @@ -67,6 +66,10 @@ seconds. case); build cost followed the row count, 11 versus 25 model calls per row and about 11 versus about 40 hours. A Stage 4 A/B on two fixture modules (22 use cases) gave 1.05 rows per use case with the new text and 2.27 to 2.45 with the old. +- **Stage 5 drafts in parallel.** Every build-plan row whose dependencies are applied, minus rows + that write the same document, is drafted at once, one helper per script. Applies stay one at a + time through `bin/exec.sh`, and the ready set is recomputed after each + ([#343](https://github.com/MendixMau/mxcli-project-toolkit/pull/343)). - **Less to read at the start.** The always-loaded skill tier went from 79,997 to 76,259 words with no rule removed ([#315](https://github.com/MendixMau/mxcli-project-toolkit/pull/315)). A helper reads only the @@ -111,7 +114,7 @@ that exist and does not ask for new ones. ## 3. Context packs A helper that builds one step of a module used to get a reading list. With context packs it gets -one file. The module brief has a `### Build steps` table, one row per dispatch: what the step +one file ([#198](https://github.com/MendixMau/mxcli-project-toolkit/pull/198)). The module brief has a `### Build steps` table, one row per dispatch: what the step builds, which existing elements it reads, the app's own example to copy, and the `mxcli brain` slice. `bin/context-pack.sh <Module> <Step>` turns that row into a pack made of the folder from the brief's folder plan, the why from `mxcli brain brief`, the brief's architecture constraints, @@ -130,10 +133,10 @@ fewer tool calls and about 30% less time (n=2 each, too few runs to quote tokens **The switch.** `Context packs: on | no-brain | off` in `PROJECT.md`, default `on`. `no-brain` leaves out the `mxcli brain` section. `off` makes `context-pack.sh` exit 3 and the dispatcher falls back to the reading list in `iterative-build-loop.md`, so a CLI change that -breaks `DESCRIBE` or `brain brief` costs one register line, not a revert. +breaks `DESCRIBE` or `brain brief` is switched off with one line in `PROJECT.md`. **Older briefs.** A module brief with no `### Build steps` table, written before packs existed, -also exits 3 and falls back to the reading list. A project mid-build keeps going after a pull +also exits 3 and falls back to the reading list ([#202](https://github.com/MendixMau/mxcli-project-toolkit/pull/202)). A project mid-build keeps going after a pull without retrofitting its briefs. ## 4. Everything else @@ -144,14 +147,12 @@ without retrofitting its briefs. single self-contained page. It keeps what the old page showed (phases, built and proven) and adds stages P to 6 with links to their artifacts, a progress bar and a stage nav ([#434](https://github.com/MendixMau/mxcli-project-toolkit/pull/434)). - - Stage times come from the metrics ledger that `exec.sh` writes, so build facts (runs, - applied, failed, blocked, restored, exec time, wall span) show with or without a session log. - With a Claude Code session log it adds time per stage, sub-agent use, context size and an - estimated token cost, labelled as an estimate. + - Session logs are optional. Without one, time and token data are marked unavailable. With a + Claude Code session log it adds time per stage, sub-agent use, context size and an estimated + token and cost figure. - A session cache makes a refresh take about a second. - Autoreload keeps your scroll position, and only runs while a build is active. - - Tips sit in a narrow side column, grouped by theme and collapsed. Red is rare: only a key - script failing every run, or a hang over 30 minutes. + - Tips sit in a side column, grouped by theme and collapsed by default, with calm severity. - An old `build-plan.html` is still accepted and never deleted. - **`build-plan.json` stays current.** `build-plan-status.sh --refresh` updates an existing `build-plan.json`, so a day of building no longer reads as 0 built @@ -209,10 +210,23 @@ without retrofitting its briefs. language, enabled languages, the user's starting language, and a switch a normal role can use. A field run wrote 418 strings per language correctly and the language picker still failed with every check green. The skill gives the recipe and the traps - ([#449](https://github.com/MendixMau/mxcli-project-toolkit/pull/449), from a proposal by CarlesZ). + ([#449](https://github.com/MendixMau/mxcli-project-toolkit/pull/449), from #387 by CarlesZ). - **Five legacy-widget field notes** from an existing-app rebuild went to the inbox for triage (first proposed as [#309](https://github.com/MendixMau/mxcli-project-toolkit/pull/309), landed as [#450](https://github.com/MendixMau/mxcli-project-toolkit/pull/450), thanks to AlvinnYeo). +- **Decompose and rehost.** Three on-demand skills for working from an existing Mendix app: + `decompose-app` (split a monolith into several apps, choosing the cut on business fit and + coupling), `rehost-app` (regenerate a whole `.mpr` into a fresh app with `pipelines/mendix-mpr/` + and read the fidelity ledger) and `mendix-service-seam` (OData and REST patterns between two + Mendix apps). `bin/cut-score.sh` scores a proposed split and prints a clean, costly or blocked + verdict per partition, and `bin/cut-ledger.sh` writes one row per crossing edge and exits 1 + while any edge has no resolution + ([#341](https://github.com/MendixMau/mxcli-project-toolkit/pull/341), [#342](https://github.com/MendixMau/mxcli-project-toolkit/pull/342), [#345](https://github.com/MendixMau/mxcli-project-toolkit/pull/345), [#346](https://github.com/MendixMau/mxcli-project-toolkit/pull/346)). +- **`mxpatch` and the hash check.** `project-bin/mxpatch.py` is a shared patch core that finds a + unit or element, changes a value and writes the unit and its `.mpr` ContentsHash in one step. + `exec.sh --patch` now runs `mxcli fix hashes` before and after the script, so the two shipped + workflow patchers no longer leave a stale hash + ([#374](https://github.com/MendixMau/mxcli-project-toolkit/pull/374), from jopterhorst). ### Fixes @@ -224,7 +238,7 @@ without retrofitting its briefs. overwrites that file. `wire-agents.sh` now merges: your entries win and keep their order, and entries only the new file has are appended ([#421](https://github.com/MendixMau/mxcli-project-toolkit/pull/421)). -- **The macOS sync fix.** The item-3 rewrite failed on stock macOS awk while sync printed +- **The macOS sync fix.** The exec-approval rewrite failed on stock macOS awk while sync printed "Rewrote" on every run. It now works there and prints a `WARN:` when a rewrite fails ([#427](https://github.com/MendixMau/mxcli-project-toolkit/pull/427)). - **The right JDK for your Mendix version.** `find_java` asks for JDK 25 on Mendix 11.14 and @@ -300,8 +314,6 @@ without retrofitting its briefs. facts for the interaction model, and the model-side check) are not built. - **`affected-tests.sh` in a multi-app folder** over-reaches because module names can repeat across apps. -- `mxcli fix hashes` as an `exec.sh --patch` post-step is pending - ([#295](https://github.com/MendixMau/mxcli-project-toolkit/issues/295)). - On Windows and Linux without Studio Pro, `exec.sh` skips its mxbuild gate unless mxbuild is found; run `bin/doctor.sh --install <project>` or set `MXBUILD_PATH`. @@ -315,12 +327,15 @@ git -C ~/Mendix/mxcli-project-toolkit checkout v1.0 ~/Mendix/mxcli-project-toolkit/bin/sync-project.sh <project-root> --repair-intake ``` -The checkout is detached on purpose: a pinned clone stays on the tag, and the session-start -warning that the clone is not on `master` is expected. To unpin: +The checkout is detached on purpose: a pinned clone stays on the tag. The session-start ritual +runs `git pull --ff-only`, which fails off a branch and warns that the clone is not on `master`; +that warning is expected. To unpin: `git -C ~/Mendix/mxcli-project-toolkit checkout master && git -C ~/Mendix/mxcli-project-toolkit pull`. Skills update with the checkout. Sync refreshes what was copied into the project and prints the -`Toolkit release:` you are on. `--repair-intake` is needed where the project predates the new intake questions: it appends the questions older projects lack, -including Q13 (unit tests default). The README's plain update is `git pull` followed by +`Toolkit release:` you are on. `--repair-intake` is needed where the project predates the new intake questions: it appends the +questions older projects lack, numbered after the highest one present (Q13, unit tests default, +in a fresh project). An appended question must be answered, because an unanswered one fails the +Stage P gate. The README's plain update is `git pull` followed by `bin/sync-project.sh <project-root>`; the pinned form above is the one for stability ([`docs/RELEASE-PROCESS.md`](../RELEASE-PROCESS.md) §8). @@ -355,8 +370,8 @@ Thanks to the contributors whose work is in this release: `multilingual-app` skill ([#449](https://github.com/MendixMau/mxcli-project-toolkit/pull/449)). - **AlvinnYeo** sent the legacy-widget field notes that landed as [#450](https://github.com/MendixMau/mxcli-project-toolkit/pull/450), and earlier the lint stock-revert guard, the catalog edge guard, per-BRD conformance ledgers and the - port-holder report. + port-holder report ([#313](https://github.com/MendixMau/mxcli-project-toolkit/pull/313)). -Thanks also to jopterhorst for `mxcli fix property-sets` in the upgrade path, delivery rounds, the +Thanks also to jopterhorst for `mxpatch` and the hash check, `mxcli fix property-sets` in the upgrade path, delivery rounds, the incremental app map and token-burn rates. Independent reviewers caught several defects before they shipped. From 47c92e85512074a89429f518798777f8b5837683 Mon Sep 17 00:00:00 2001 From: MendixMau <mauritscgvisser@gmail.com> Date: Sat, 17 Oct 2026 10:38:06 +0800 Subject: [PATCH 4/5] docs(release): 1.0 uses the dated train tag v2026.10.19, GitHub Release titled 1.0 Follows docs/RELEASE-PROCESS.md section 8: milestones add a name, not a tag scheme. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --- docs/releases/v1.0.md | 13 +++++++------ 1 file changed, 7 insertions(+), 6 deletions(-) diff --git a/docs/releases/v1.0.md b/docs/releases/v1.0.md index 6edac3d8..1d903a7f 100644 --- a/docs/releases/v1.0.md +++ b/docs/releases/v1.0.md @@ -7,10 +7,11 @@ mechanical gates (`bin/gate-check.sh`, lint, mxbuild, end-to-end journeys) that actually in your project. It runs for migrations, requirements-driven builds, greenfield builds and changes to a live app, or a la carte to audit and test an app you already have. -1.0 is the first named milestone on top of the release train, and the first tag published to -GitHub (`v1.0`). Earlier dated headings in the CHANGELOG were never pushed as tags. All v1.0 -work merged into the `release/v1.0` branch while master stayed frozen; the tag marks that -branch. Every PR named below has merged, some through the integration batch +1.0 is the first named milestone on top of the release train. Its cut is tagged `v2026.10.19`, +the first tag published to GitHub, and the GitHub Release on that tag is titled "1.0". Earlier +dated headings in the CHANGELOG were never pushed as tags. All 1.0 work merged into the +`release/v1.0` branch while master stayed frozen; that branch then merged to master, where the +cut and its tag were made. Every PR named below has merged, some through the integration batch [#329](https://github.com/MendixMau/mxcli-project-toolkit/pull/329). Every line traces to an entry in [`CHANGELOG.md`](../../CHANGELOG.md) or to a linked PR. How milestones relate to tags: [`docs/RELEASE-PROCESS.md`](../RELEASE-PROCESS.md) §8. @@ -330,11 +331,11 @@ without retrofitting its briefs. ## 5. How to update -Pin the toolkit clone to the tag `v1.0`, then sync each project: +Pin the toolkit clone to the 1.0 tag `v2026.10.19`, then sync each project: ```bash git -C ~/Mendix/mxcli-project-toolkit fetch --tags -git -C ~/Mendix/mxcli-project-toolkit checkout v1.0 +git -C ~/Mendix/mxcli-project-toolkit checkout v2026.10.19 ~/Mendix/mxcli-project-toolkit/bin/sync-project.sh <project-root> --repair-intake ``` From 10ee003c1742ef8a9ad70ec1691514c49287e9ff Mon Sep 17 00:00:00 2001 From: MendixMau <mauritscgvisser@gmail.com> Date: Sat, 17 Oct 2026 11:07:31 +0800 Subject: [PATCH 5/5] docs(release): thank Alvinn, Jop, Carles and Joshua by name Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --- docs/releases/v1.0.md | 25 ++++++++++++++++--------- 1 file changed, 16 insertions(+), 9 deletions(-) diff --git a/docs/releases/v1.0.md b/docs/releases/v1.0.md index 1d903a7f..82f7855c 100644 --- a/docs/releases/v1.0.md +++ b/docs/releases/v1.0.md @@ -386,14 +386,21 @@ wrote it down". ## 6. Thanks -Thanks to the contributors whose work is in this release: - -- **CarlesZ** wrote up the multilingual app findings from a field run, now the +A big thank you to the four people whose field work shaped this release: + +- **Alvinn Yeo** (@AlvinnYeo) sent the legacy-widget field notes that landed as + [#450](https://github.com/MendixMau/mxcli-project-toolkit/pull/450), and earlier the lint stock-revert + guard, the catalog edge guard, per-BRD conformance ledgers and the port-holder report + ([#313](https://github.com/MendixMau/mxcli-project-toolkit/pull/313)). The bug reports #259 to #264 + found gate and harness faults that only show on a real project. +- **Jop ter Horst** (@jopterhorst) brought `mxpatch` and the hash check, `mxcli fix property-sets` in the + upgrade path, delivery rounds, the incremental app map and token-burn rates + ([#374](https://github.com/MendixMau/mxcli-project-toolkit/pull/374), field notes #294 to #301). +- **Carles** (@CarlesZ) wrote up the multilingual app findings from a field run, now the `learned-multilingual-app` skill ([#449](https://github.com/MendixMau/mxcli-project-toolkit/pull/449)). -- **AlvinnYeo** sent the legacy-widget field notes that landed as [#450](https://github.com/MendixMau/mxcli-project-toolkit/pull/450), and earlier the - lint stock-revert guard, the catalog edge guard, per-BRD conformance ledgers and the - port-holder report ([#313](https://github.com/MendixMau/mxcli-project-toolkit/pull/313)). +- **Joshua Moesa** (@joshuamoesa) filed ten precise reports (#356 to #361, #381 to #383): the journey + screenshot names ([#408](https://github.com/MendixMau/mxcli-project-toolkit/pull/408)), sync and + install-manifest warnings, the test-agent journey path, the missing checkpoint files, and MDL + learnings that are now STOP rows in the preflight. -Thanks also to jopterhorst for `mxpatch` and the hash check, `mxcli fix property-sets` in the upgrade path, delivery rounds, the -incremental app map and token-burn rates. Independent reviewers caught several defects before -they shipped. +Independent reviewers caught several defects before they shipped.