Add 24 ACR-derived rules and fix pre-existing rule tests#29
Open
xiwenc wants to merge 9 commits into
Open
Conversation
Implement six new rules derived from the CLEVR ACR (Application Consistency Rules) catalog, mapped onto the Mendix model export formats that mxlint already parses. Each rule ships with a passing _test.yaml covering compliant and non-compliant cases. Microflows (005): - 005_0006 MicroflowCallsSelf: detect direct recursion (self-call), including calls nested inside loops. - 005_0007 LoopInLoop: detect loops nested inside another loop. - 005_0008 CommitWithoutEvents: detect commit/change actions that commit without events. - 005_0009 MicroflowDocumentation: require documentation on microflows above a minimum number of actions. Domain model (002): - 002_0010 AssociationOwnerBoth: discourage associations owned by Both. - 002_0011 EntityDocumentation: require documentation on entities above a minimum number of attributes. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_018DNq3pmSsKsrV77qQ6tUcW
Add two more ACR-derived rules, including the first cross-file rule that reads related model files via mxlint.io.readYaml. - 002_0012 MultiLevelInheritance (JavaScript, cross-file): walks the generalization chain across module domain models and flags entities that inherit through more than two levels. Ships with a fixture domain model (Inheritance/) that the test resolves via mxlint.io.readYaml. - 005_0010 CreateSystemEntity: flags microflows that instantiate System entities (e.g. System.User, System.Session) directly instead of using Administration.Account. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_018DNq3pmSsKsrV77qQ6tUcW
Add six more ACR-derived rules across project settings, domain model, pages and microflows. Project settings (001): - 001_0010 SecurityLevelCheckEverything: require SecurityLevel = CheckEverything. - 001_0011 StrictPageUrlCheck: require strict page URL check enabled. - 001_0012 AllowOneSessionPerUser: discourage multiple sessions per user. Domain model (002): - 002_0013 AttributeNaming: attributes should be PascalCase. Pages (004): - 004_0005 PageDocumentation: pages should have documentation. Microflows (005): - 005_0011 TodoAnnotations: flag leftover TODO/FIXME annotations. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_018DNq3pmSsKsrV77qQ6tUcW
001_0013 UnassignedModuleRole (JavaScript, cross-file): lists every module's Security$ModuleSecurity via mxlint.io.listdir/isdir/readYaml and flags module roles that are not assigned to any user role in the project security. Ships with ModuleA/ModuleB fixtures for the test. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_018DNq3pmSsKsrV77qQ6tUcW
- 002_0014 AmountAccessRules: limit access rules per entity. - 005_0012 ParameterAmount: limit microflow parameters. - 006_0002 ModuleRolesAmount: limit module roles per module. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_018DNq3pmSsKsrV77qQ6tUcW
- 006_0003 MicroflowEntityAccess: exposed microflows performing database operations should apply entity access. - 005_0013 SplitCaption: exclusive/inclusive splits should have a caption. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_018DNq3pmSsKsrV77qQ6tUcW
- 007_0001 EnumerationPrefix (new enumerations category): enumerations should start with a recognizable prefix (ENU). - 003_0002 MinimumMendixVersion: flag unsupported Mendix major versions read from Metadata ProductVersion. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_018DNq3pmSsKsrV77qQ6tUcW
- 005_0014 NoContinueErrorHandling: flag activities that continue on error without handling it. - 005_0015 LoopHeavyAction: flag heavy actions (retrieve, microflow call, web service, mapping, etc.) inside a loop. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_018DNq3pmSsKsrV77qQ6tUcW
The three rego rules 001_0007, 001_0008 and 005_0005 shipped OPA-native _test.rego files, which `mxlint test-rules` does not execute (it looks for _test.yaml). Convert them to _test.yaml so they are actually exercised. The 001_0009 strict-mode JavaScript rule reads Security$ProjectSecurity via mxlint.io; its test used an unsupported `files:` key and the wrong input shape, so it never passed. Rewrite the test to use the real ProjectSettings shape plus a Security$ProjectSecurity.yaml fixture. Also fix scripts/run-policy-tests.sh: newer mxlint-cli releases removed the `--rules` flag, so `test-rules --rules ./rules` errored out and the script reported success without running any tests. Point test-rules at a generated config instead so the suite actually runs (176 test cases pass). Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_018DNq3pmSsKsrV77qQ6tUcW
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.
Summary
Implements a batch of rules derived from the CLEVR ACR (Application Consistency Rules) catalog (https://sdf-docs.clevr.com/?docs=acr-rules), mapped onto the Mendix model export formats that mxlint already parses. Also fixes four pre-existing rule tests and a CI-script bug that caused the test step to pass without running.
24 new rules, each with a passing
_test.yaml, spanning all six ACR categories.New rules
Project settings (001)
001_0010SecurityLevelCheckEverything — requireSecurityLevel = CheckEverything001_0011StrictPageUrlCheck — require strict page URL check enabled001_0012AllowOneSessionPerUser — discourage multiple sessions per user001_0013UnassignedModuleRole (cross-file JS) — module roles not assigned to any user roleDomain model (002)
002_0010AssociationOwnerBoth — discourage many-to-many owned by Both002_0011EntityDocumentation — large entities should be documented002_0012MultiLevelInheritance (cross-file JS) — inheritance limited to 2 levels002_0013AttributeNaming — attributes should be PascalCase002_0014AmountAccessRules — limit access rules per entityModules (003)
003_0002MinimumMendixVersion — flag unsupported Mendix major versionsPages (004)
004_0005PageDocumentation — pages should be documentedMicroflows (005)
005_0006MicroflowCallsSelf — detect direct recursion005_0007LoopInLoop — detect nested loops005_0008CommitWithoutEvents — commit/change without events005_0009MicroflowDocumentation — complex microflows need documentation005_0010CreateSystemEntity — don't instantiate System entities directly005_0011TodoAnnotations — flag leftover TODO/FIXME annotations005_0012ParameterAmount — limit microflow parameters005_0013SplitCaption — splits should have a caption005_0014NoContinueErrorHandling — don't silently continue on errors005_0015LoopHeavyAction — heavy actions (retrieve, microflow call, etc.) inside a loopSecurity (006)
006_0002ModuleRolesAmount — limit module roles per module006_0003MicroflowEntityAccess — exposed microflows doing DB ops should apply entity accessEnumerations (007, new category)
007_0001EnumerationPrefix — enumerations should have a recognizable prefixCross-file rules
Three rules resolve related model files via
mxlint.io.readYaml/listdir/isdir:002_0012walks generalization chains across module domain models001_0013enumerates every module'sSecurity$ModuleSecurity001_0009(existing) readsSecurity$ProjectSecurityBecause the test harness runs with the rule's own directory as the working directory, these tests rely on small fixture model files committed next to the rule (
Inheritance/,ModuleA/,ModuleB/,Security$ProjectSecurity.yaml). The rule scanner only loads.rego/.js/.ts, so the fixtures are ignored as rules. Note: the release workflow only excludes*_test.*, so these fixture.yamlfiles would currently be included in the published ruleset zip — harmless (inert), but a maintainer may want to exclude them.Fixes to pre-existing failures
001_0007,001_0008,005_0005shipped OPA-native_test.regofiles, whichmxlint test-rulesnever executes (it looks for_test.yaml). Converted to_test.yaml.001_0009StrictModeWithReactClient: its test used an unsupportedfiles:key and aninputshape that did not match the rule, so it always failed. Rewritten against the realProjectSettingsshape with aSecurity$ProjectSecurity.yamlfixture.scripts/run-policy-tests.sh: newer mxlint-cli releases removed the--rulesflag, sotest-rules --rules ./ruleserrored out — and because the error text isn'tFAIL, the script reported success without running any tests. Now pointstest-rulesat a generated config so the suite actually runs.Verification
All 176 test cases pass (
exit 0, no failures) under both a build frommxlint-cliHEAD and the released v3.16.0 binary, run exactly as CI does via the updatedrun-policy-tests.sh.Scope note
Rules were selected where the intent maps cleanly to model structures confirmable from real Mendix exports. ACR rules requiring expression/dataflow analysis (unused variables, empty-object dereference, identical branches, xpath analysis) are not implemented, as they don't fit mxlint's per-file rego/JS model. Threshold-based rules use clearly-named constants at the top of each rule for easy tuning.
🤖 Generated with Claude Code
https://claude.ai/code/session_018DNq3pmSsKsrV77qQ6tUcW
Generated by Claude Code