Repository navigation
Conversation
Two Starlark rules delivered through the existing lint-rules install/refresh path (install-manifest MXTK_LINT_RULES, README row each, delivery fixture count 4 -> 6). UX001 flags a button that deletes directly (Forms$DeleteClientAction has no confirmation setting) or calls a microflow/nanoflow without "Ask confirmation" when that flow deletes objects (bounded call-graph walk) or is named as an irreversible step (Approve/Reject/Submit/Archive/...). UX002 flags decisions left on their auto-generated caption and flows of 8+ top-level activities with neither an annotation nor a documentation text. Both need mxcli >= 0.25.0 (widget action_type/has_confirmation, activity caption/auto_generate_caption) and emit a `_rule` blindness finding on anything older, so lint-gate.sh never reads them as a clean pass. Vocabulary was read from the mxcli catalog builder source, not from the bundled API guide. No mxcli binary was reachable in the authoring session, so the first field calibration on a scratch copy of a real model is still owed; the README note says so and names the probe queries. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01VJgWP5vEoAsNsJYqCDMGNw
…reter tests/lint-rules/ runs both rules through go.starlark.net at mxcli's pinned version via a small Go harness (starrun) that rebuilds the mxcli projection structs from JSON fixtures and rejects any field the projection does not have. 33 hand-written fixtures cover self-checks, call depth on both sides of the bound, cycles, the destructive-name pattern, module skips, snippet locations and the version probe; a generated 3000-flow / 20000-widget model times each rule (~0.7 s). 35 cases, wired into CI as its own step. The suite caught two defects in UX002 before they shipped: StartEvent/EndEvent objects returned by activities_for() inflated the activity count, and the "needs mxcli >= 0.25.0" probe only fired on flows that had a decision. Both fixed here; UX001's depth comment now states what the bound means. Fixtures encode the projection as read from the mxcli source, not captured output: they prove the rule logic, not the catalog vocabulary. Field calibration on a real model is still owed and the README still says so. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01VJgWP5vEoAsNsJYqCDMGNw
check-portability.sh (in CI) rejects a hard-coded `python3`: on Windows a name on PATH may be the Store alias stub, not an interpreter. The suite now sources bin/lib/portable.sh, calls require_py and runs "$PY", like every other script here. 35/35 cases still pass; check-portability clean. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01VJgWP5vEoAsNsJYqCDMGNw
6 of 7 tasks
test-stock-hashes.sh T2 demanded a STOCK-HASHES.txt entry per version for every file in MXTK_LINT_RULES. mxcli init seeds only three of those; the toolkit-authored ux001/ux002 rules can never have a stock hash, so the fixture went red on every version (3 FAIL) the moment they joined the list. install-manifest.sh gains MXTK_LINT_RULES_STOCK (the three init-seeded rules). The fixture's coverage, listed-name and live-capture checks walk that set, and a new check asserts it is a subset of MXTK_LINT_RULES. Replayed T2's awk against the real list: all three versions cover all three stock rules; a listed non-stock name still fails. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01VJgWP5vEoAsNsJYqCDMGNw
…e manifest Case 1 asserted a literal 4 files in .claude/lint-rules/ after a fresh install. Two toolkit-authored rules joined MXTK_LINT_RULES, six landed, and the fixture reported them as a NOINSTALL leak. The expected count is now the size of MXTK_LINT_RULES + MXTK_LINT_RULES_CONFIGURABLE, with an explicit check that no MXTK_LINT_RULES_NOINSTALL file was installed. CI's own output on 40f2c00 listed exactly the six manifest rules. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01VJgWP5vEoAsNsJYqCDMGNw
5 tasks done
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Direct lane
What changed and why (one paragraph):
Two Starlark lint rules in
lint-rules/, delivered through the existing install/refresh path (MXTK_LINT_RULESinbin/lib/install-manifest.sh, one README row each, delivery fixture count 4 → 6). UX001 flags a button that deletes directly (Forms$DeleteClientAction, which has no confirmation setting at all) or calls a microflow/nanoflow without "Ask confirmation" when that flow deletes objects (bounded call-graph walk, depth 3) or is named as an irreversible step (Approve / Reject / Submit / Archive / …, CamelCase-strict soShowApprovedOrdersdoes not match). UX002 flags decisions left on their auto-generated caption and flows of 8+ top-level activities (start/end events and annotations not counted) with neither an annotation nor a documentation text. These are the house rules that so far lived only as prose in a project CLAUDE.md ("pop-up when approving", "annotate your flows") and therefore held no session to anything. Scope was deliberately narrowed: commit-without-feedback is already CONV020; popup-vs-page and close-before-show are not visible to Starlark (no page layout, no activity ordering). Both rules need mxcli ≥ 0.25.0 (widgetaction_type/has_confirmation, activitycaption/auto_generate_caption) and emit a_ruleblindness finding on anything older, solint-gate.shnever reads them as a clean pass.Second commit — unit suite.
tests/lint-rules/executes both rules under the real Starlark interpreter (go.starlark.netat mxcli's pinned version) through a ~270-line Go harness that rebuilds the mxcli projection structs from JSON fixtures and exits on any field the projection does not have. 33 hand-written fixtures + a generated 3000-flow / 20000-widget perf model: 35 cases, all passing, wired into CI as its own step. The suite caught two defects before they shipped:activities_for()returns StartEvent/EndEvent objects, which inflated UX002's activity count; and UX002's "needs ≥ 0.25.0" probe only fired on flows that had a decision. Both fixed in the same commit.Field evidence:
Logic proven, vocabulary not yet — still a draft for that reason. No mxcli binary was reachable in the authoring session (release assets out of scope, source build not permitted), so the rules were written from the mxcli catalog-builder source at 0.25.0 (
widgetPrimaryActionstores the action$Typeverbatim;getMicroflowObjectTypeyieldsExclusiveSplit/Annotation;Microflows$prefix stripped from action types). The fixtures encode that same reading, so they cannot catch a wrong reading. Perf under the harness: UX001 0.70 s, UX002 0.73 s on 3000 flows / 20000 widgets. The README note says the calibration is owed. To do it on a laptop, on a scratch copy of a real model with mxcli ≥ 0.25.0:If the probe shows a vocabulary mismatch, the constants at the top of each rule are the only thing to change (and the fixtures follow). Counts go into the README note, then the draft flips to ready.
tests/lint-rules/test-ux-rules.sh35/35 under the real interpreter (CI step added); T0 on top:bin/check-scripts.sh,bash -n,py_compile.tests/test-lint-delivery.shupdated for the new count.mxcli lint, delivery path unchanged; the suite needs Go and python3 and fails loudly without them.CHANGELOG.mdline appended in this PR, crediting the source project or person🤖 Generated with Claude Code
https://claude.ai/code/session_01VJgWP5vEoAsNsJYqCDMGNw