Repository navigation
Sync ako/mxcli: typed retrieve constraints, security reference checks, model-level MDL-MAP04 - #1336
Conversation
The lint rules cannot import the executor, and a model-level MDL-MAP04 (mendixlabs#1319) needs to decide a mapping's root shape exactly the way the builder and the check-time rule do. The executor keeps thin delegating wrappers so its call sites and tests are unchanged. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01BCeVsRwSYaVoEtimYbKJAi
… mistyped variable A retrieve constraint comparing an attribute with a variable of another type (`Kind = $Filter` with $Filter a String, `Email >= $Since` with a DateTime, `Visits = $Text` with a String) passed `check --references` and exec, then mx check reported CE0161 "Error(s) in XPath constraint." (mendixlabs#1325). The reference pass now types each `attribute <op> $var` comparison from the retrieved entity (script declaration or stored domain model) and the flow's parameters and declared variables. The compatibility table is measured on mxbuild 11.14.0 over 8 attribute x 8 variable types for `=` and `>=`: it is not type equality — a String variable against a DateTime attribute builds clean, Integer/Long/Decimal mix freely, and an enumeration needs the same enumeration. Untyped sides stay silent. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01EsWAxrmEd7MBkay2zNpXNS
…odel (MDL-MAP04) mendixlabs#1319: an import activity already in the model that stores Studio Pro's First (ForceSingleOccurrence / Range.SingleObject) over an OBJECT-rooted mapping passed lint ("No issues found.") and mx check (0 errors), then threw key not found: Path(QName(None,),None,) when it ran. check's MDL-MAP04 refuses the statement, but only in a script, so activities written by v0.24.0 or with exec --no-check were found by nothing. lint now runs MDL-MAP04 against stored import-from-mapping and REST returns-mapping activities. It keys on the mapping's root shape via the shared types.JsonMappingRootIsList, so a list-rooted mapping's legitimate First (same flag pair) is not reported, and a shape that cannot be established is left alone. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01BCeVsRwSYaVoEtimYbKJAi
…iation `validation feedback $Input/Input_Person` named an association by its bare name, but the builder decided attribute vs association from the dot count alone, so it wrote the attribute reference G45.Input.Input_Person and mx check failed: [CE1613] "The selected attribute 'G45.Input.Input_Person' no longer exists." A dotless member now resolves as an attribute in the generalization chain first (unchanged), then as an association the entity or an ancestor owns (new DeclaringAssociationRef, searching Associations and CrossAssociations in each link's module), else keeps the old spelling. The result is the same BSON the qualified $Input/G45.Input_Person produces. Verified on Mendix 11.14.0: pre-fix binary reproduces the reported CE1613, fixed binary checks at 0 errors (both mdl 0 and mdl 1 scripts). Fixes mendixlabs#1322 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_014WGYmiHmEHxNSfCt2XjHVu
`mxcli check -p --references` resolved none of a security statement's references: a grant on System.Nope or M.Nope, to M.NopeRole, on a missing microflow/nanoflow/page/service, or naming a missing member all printed "Check passed!". exec refused the grants after the earlier statements were written, and wrote the unknown roles of `create user role`, `alter user role … add` and `create demo user` into project security unresolved, for MxBuild to report as CE1613. validateGrantReferences walks the program in statement order and resolves each statement's entity, document, member, module roles and user roles against the project and what the script has created so far — including the <Module>.User role exec auto-creates with the first document of a role-less module. It refuses what exec refuses, form by form: an unknown role on a document REVOKE, which exec reports as a no-op, still passes, and so does a System module role in a user role; a grant on any System entity is refused, as exec refuses it. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Brings in #1020 (signature-type checks, same validate.go) and resolves the findings-file conflict GitHub's server-side merge reports for appends to mdl-executor.jsonl. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…is read as the name (mendixlabs#1282) `call java action M.A(Flow = M.SUB_Target⏎ );` was reported storing the line break in the reference (CE1613 "The selected microflow 'MyModule.SUB_Target⏎' no longer exists"). The visitor keeps whitespace before `)` on the argument as an ast.SourceExpr; the Microflow-typed path switched on that wrapper. #898 had since trimmed the stored text, so on this tree the same script is instead refused by check --references and exec as "not MyModule.SUB_Target" (mendixlabs#1210's guard saw a SourceExpr, not a QualifiedNameExpr), and `Flow = empty⏎)` was refused too. javaActionArgumentValue unwraps the SourceExpr for the refusal, the `empty` marker and the stored name. Expression (basic) arguments keep their source text unchanged. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01F6s3o3b9ZxCtX2Fgw2MRMc
`create published odata service M.S ( …, Authentication: (basic, session, microflow M.F) )` replaces the trailing `authentication …` clause (R9), matching the published REST service. The property also takes `none`, which the clause could not say, and `alter published odata service … set ( Authentication: … )` now sets it — before, the only way to change a service's authentication was to restate it. Left out, create-or-modify and alter keep the stored setting. The clause is a registered alias (MDL-DEPR139): it builds the same statement, warns, is refused from mdl 2, and `fmt --upgrade` moves it into the list, on its own line when the list is one property per line. A clause naming a method MDL has no keyword for is reported, not rewritten. The examples, skills, syntax help and quick references are migrated with it, so the conformance gate holds. describe prints the property in the stored order. A setting MDL cannot state (a microflow without the Microflow method, or the reverse) is now a comment: printing `Microflow M.F` for it added the method on replay. describe → exec of ako/TestApp's three Studio Pro OData services writes no unit. mx check on 11.14.0 (security production) is clean for (session, basic) with a role, none without roles, and a service switched to none by alter. Follow-up to mendixlabs#1331. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01M7kpwBjefUzJwfyembWZKh
…labs#1281) `Entity[a][b]` inside a constraint was a parse error — "missing ']' at '['" when the path ended on the step, "mismatched input '/' expecting ';'" when it went on — because xpathStep admitted at most one predicate. Mendix accepts the form. xpathStep now takes any number; ast.XPathStep.Predicate becomes Predicates, in source order, and every serializer and walker loops over them. They are kept apart rather than and-ed, so describe reproduces what was written and a `[reversed()]` step predicate is never folded into a condition. Control: before the fix the new test failed with the reported errors, and ParseXPathConstraint returned ok while dropping the second predicate. mx check (11.6.6): 0 errors for the two-predicate form and for the single-predicate `and` control. Refs mendixlabs#1281 Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01Lo6eVewuCWHhHZZrE9LPoy
A lint rule had no way to read the enabled project languages: strings() has a row for every stored translation, and a fresh en_US-only app already carries nl_NL texts, so enabling a language changed nothing a rule could see, and a rule calling languages() failed with "undefined: languages". languages() returns one `language` struct (code, is_default, check_completeness) per language enabled in the project settings, read through LintReader.GetProjectSettings like project_security(). It needs no full catalog build; a failed settings read fails the rule rather than answering []. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CEhfut5q23z8UtgD762ZPc
Open question 1 of the published REST authentication proposal is done on this branch: the OData clause is now the Authentication property, with the clause as alias MDL-DEPR139. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01M7kpwBjefUzJwfyembWZKh
activities_for() and CATALOG.ACTIVITIES returned every microflow, nanoflow, Java action and JavaScript action call with action_ref="" and every delete with entity_ref="", although refs_from() had both targets (mendixlabs#1305). describeAction had cases only for REST/web service/OData calls and create/retrieve. - ActionRef is the called document for a microflow, nanoflow, Java or JavaScript action call. - EntityRef is a delete's entity, resolved through the same per-flow variable map refs_from()'s delete edge uses (buildVarEntityMap). - New QueueRef column / queue_ref field: the task queue a microflow or Java action call runs in, so a loop-scoped rule can skip a call that runs asynchronously. - A JavaScript action call gets a refs `call` row (JAVASCRIPT_ACTION), so show callers and refs_from() see it. Catalog schema bumped to 23. Control: the HEAD binary on the issue's repro prints exactly the reported empty rows; with describeAction's new cases removed, TestActivityCallAndDeleteTargets fails with every target "". Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01FuqAgqwKgZXJWEUZWbZSpV
Add MDL-MAP04 lint rule to detect import activities on object-rooted mappings
Validate retrieve constraint operand types against mxbuild rules
fix(check): resolve what GRANT/REVOKE and user-role statements name
AI Code ReviewReview SummaryThis PR syncs changes from ako/mxcli:main to mendixlabs/mxcli:main, implementing three key improvements:
Critical IssuesNone found. Moderate IssuesNone found. Minor IssuesNone found. What Looks Good
RecommendationApprove - The PR successfully addresses the reported issues with high-quality implementations that follow project patterns and improve the tool's ability to catch problems early. All validation is properly integrated, tests are comprehensive, and documentation is updated appropriately. No critical issues identified. Automated review via OpenRouter (Nemotron Super 120B) — workflow source |
fix(catalog): name a call's and a delete's target in activities
AI Code ReviewReview SummaryThis PR syncs changes from
The changes are well-scoped, thoroughly tested, and follow the project's architectural patterns. No critical issues were found. What Looks Good
Minor Issues
RecommendationApprove the PR. The changes:
The PR successfully implements the required full-stack validation for the fixed issues while maintaining the project's quality standards. The minor issues noted are documentation/refinement opportunities that don't block merging. Automated review via OpenRouter (Nemotron Super 120B) — workflow source |
feat(odata): published OData authentication as a property
AI Code ReviewReview SummaryCritical IssuesNone found. Moderate IssuesNone found. Minor Issues
What Looks Good
Automated review via OpenRouter (Nemotron Super 120B) — workflow source |
fix(grammar): accept consecutive predicates on one XPath step (mendixlabs#1281)
AI Code ReviewReview Summary: This PR syncs changes from a fork implementing three main features: typed retrieve constraints (#1325), security reference checks (grant/revoke statements), and model-level MDL-MAP04 lint rule. It also includes unrelated OData authentication property improvements. The changes follow good practices with thorough testing and full-stack wiring where applicable. Critical IssuesNone found. Moderate IssuesNone found. Minor IssuesAutomated review via OpenRouter (Nemotron Super 120B) — workflow source |
Every expression spelling of a column's `Visible:` — `$showPrices`, `if … then … else …`, `not(…)`, `[cond]` — passed check and exec and was stored as `true`, so the column was always visible. The visitor lowers an expression to the key VisibleIf and keeps only plain values under Visible; the column writers read only visible/Visible. - types.ItemPropertyAliases: `visible` <- `VisibleIf`, used by the widget engine on create and by ALTER `set (Visible: …) on grid column(…)`, which refused it as "column property VisibleIf not found". Widget defs regenerate at generator version 18. - columnSpecProperties: ALTER insert/replace column hands the builder Visible (and DynamicCellClass in any case) as the string it reads; a `Visible: false` bool was dropped there too. - describe prints the bare expression, which now round-trips. - MDL-WIDGET43: a column's visibility is evaluated once for the grid, with no row object, so $currentObject there is CE0117 (measured on 11.14.0). check refuses it on create, insert and set. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01P65SqmwwvbWdJVRwhYiMQw
fix: store a bare association name in validation feedback as an association (mendixlabs#1322)
fix: a Microflow-typed Java action argument followed by a line break is read as the name (mendixlabs#1282)
AI Code ReviewReview SummaryThis PR syncs changes from
The changes are well-scoped, thoroughly tested, and follow project conventions. No critical issues were found. What Looks Good
Minor Issues
RecommendationApprove. The changes are:
The minor issues noted are trivial and do not affect correctness. No changes are requested. Note: As this is a sync PR, the changes were previously reviewed in the fork repository. This review focuses on verifying the changes meet mxcli's contribution standards as outlined in CLAUDE.md. All validation and linting changes are properly scoped and tested. Automated review via OpenRouter (Nemotron Super 120B) — workflow source |
Add languages() to the Starlark lint API (mendixlabs#1306)
fix: write a DataGrid 2 column's Visible expression
Syncs
ako/mxcli:mainintomendixlabs/mxcli:main: 4 commits since #1334, landed in the fork through PRs ako#1021, ako#1023 and ako#1027.Check
check --references(Retrieve XPath comparing an attribute with a variable of another type (enum vs String, String vs DateTime, Integer vs String) passes check; mx check CE0161 #1325). Examples areKind = $Filterwith$Filtera String, orEmail >= $Sincewith a DateTime; these were CE0161 at build time. The compatibility table is measured on mxbuild 11.14.0 over 8 attribute × 8 variable types, and it is not plain type equality (a String variable against a DateTime attribute builds clean; Integer/Long/Decimal mix freely).create user role/alter user role … add/create demo userwrote unknown roles for mxbuild to report as CE1613.Lint
Firstover an object-rooted mapping passed lint and mx check, then threwkey not found: Path(QName(None,),None,)at runtime. check refused it only in a script, so activities written by v0.24.0 or withexec --no-checkwere found by nothing. lint now checks stored import-from-mapping and REST returns-mapping activities.mdl/types, so the lint rule, the builder and check share one decision