@lamentis/naome 1.2.1 → 1.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (57) hide show
  1. package/Cargo.lock +2 -2
  2. package/README.md +108 -47
  3. package/bin/naome.js +16 -1
  4. package/crates/naome-cli/Cargo.toml +1 -1
  5. package/crates/naome-cli/src/dispatcher.rs +6 -2
  6. package/crates/naome-cli/src/main.rs +35 -23
  7. package/crates/naome-cli/src/quality_commands.rs +230 -11
  8. package/crates/naome-cli/src/workflow_commands.rs +21 -1
  9. package/crates/naome-core/Cargo.toml +1 -1
  10. package/crates/naome-core/src/git.rs +4 -2
  11. package/crates/naome-core/src/install_plan.rs +2 -0
  12. package/crates/naome-core/src/lib.rs +11 -7
  13. package/crates/naome-core/src/quality/baseline.rs +8 -0
  14. package/crates/naome-core/src/quality/cache.rs +153 -0
  15. package/crates/naome-core/src/quality/checks/duplicate_blocks.rs +25 -11
  16. package/crates/naome-core/src/quality/checks/near_duplicates.rs +4 -2
  17. package/crates/naome-core/src/quality/checks.rs +7 -8
  18. package/crates/naome-core/src/quality/cleanup.rs +36 -3
  19. package/crates/naome-core/src/quality/mod.rs +57 -9
  20. package/crates/naome-core/src/quality/scanner/analysis/normalize.rs +78 -0
  21. package/crates/naome-core/src/quality/scanner/analysis.rs +160 -0
  22. package/crates/naome-core/src/quality/scanner/repo_paths.rs +39 -3
  23. package/crates/naome-core/src/quality/scanner.rs +193 -220
  24. package/crates/naome-core/src/quality/semantic/checks.rs +134 -0
  25. package/crates/naome-core/src/quality/semantic/extract.rs +158 -0
  26. package/crates/naome-core/src/quality/semantic/model.rs +85 -0
  27. package/crates/naome-core/src/quality/semantic/route.rs +52 -0
  28. package/crates/naome-core/src/quality/semantic.rs +68 -0
  29. package/crates/naome-core/src/quality/structure/checks/directory.rs +9 -19
  30. package/crates/naome-core/src/quality/structure/checks.rs +1 -1
  31. package/crates/naome-core/src/quality/structure/classify.rs +52 -0
  32. package/crates/naome-core/src/quality/structure/mod.rs +2 -2
  33. package/crates/naome-core/src/quality/structure/model.rs +8 -1
  34. package/crates/naome-core/src/quality/types.rs +40 -2
  35. package/crates/naome-core/src/route/builtin_checks.rs +1 -15
  36. package/crates/naome-core/src/workflow/doctor.rs +144 -0
  37. package/crates/naome-core/src/workflow/mod.rs +2 -0
  38. package/crates/naome-core/src/workflow/mutation.rs +1 -2
  39. package/crates/naome-core/tests/install_plan.rs +2 -0
  40. package/crates/naome-core/tests/quality.rs +14 -5
  41. package/crates/naome-core/tests/quality_performance.rs +231 -0
  42. package/crates/naome-core/tests/quality_structure_policy.rs +19 -0
  43. package/crates/naome-core/tests/route_user_diff.rs +10 -6
  44. package/crates/naome-core/tests/semantic_legacy.rs +140 -0
  45. package/crates/naome-core/tests/workflow_doctor.rs +24 -0
  46. package/crates/naome-core/tests/workflow_policy.rs +6 -1
  47. package/installer/git-boundary.js +1 -0
  48. package/native/darwin-arm64/naome +0 -0
  49. package/native/linux-x64/naome +0 -0
  50. package/package.json +1 -1
  51. package/templates/naome-root/.naome/bin/check-harness-health.js +2 -2
  52. package/templates/naome-root/.naome/bin/check-task-state.js +2 -2
  53. package/templates/naome-root/.naome/bin/naome.js +11 -4
  54. package/templates/naome-root/.naome/manifest.json +2 -2
  55. package/templates/naome-root/.naomeignore +1 -0
  56. package/templates/naome-root/docs/naome/agent-workflow.md +16 -14
  57. package/templates/naome-root/docs/naome/repository-quality.md +63 -4
@@ -0,0 +1,24 @@
1
+ mod workflow_support;
2
+
3
+ use naome_core::doctor_report;
4
+ use workflow_support::WorkflowFixture;
5
+
6
+ #[test]
7
+ fn doctor_report_explains_active_task_and_policy_files() {
8
+ let repo = WorkflowFixture::new("doctor-active-task");
9
+ repo.init_git();
10
+ repo.write(".naome/repository-quality.json", "{}\n");
11
+ repo.write(".naome/repository-structure.json", "{}\n");
12
+ repo.write_task_state("implementing", &["README.md"], &["diff-check"]);
13
+
14
+ let report = doctor_report(repo.path()).unwrap();
15
+
16
+ assert_eq!(report.schema, "naome.doctor.v1");
17
+ assert!(!report.ok);
18
+ assert_eq!(report.task_state.status, "blocked");
19
+ assert_eq!(report.repository_quality.config_present, true);
20
+ assert_eq!(report.repository_structure.config_present, true);
21
+ assert!(report
22
+ .next_action
23
+ .contains("Finish or resolve the active task"));
24
+ }
@@ -115,6 +115,7 @@ fn mutation_classifier_recognizes_core_classes() {
115
115
  ".naome/archive/repair/AGENTS.md".to_string(),
116
116
  "coverage/report.json".to_string(),
117
117
  "packages/naome/native/darwin-arm64/naome".to_string(),
118
+ "packages/naome/templates/naome-root/AGENTS.md".to_string(),
118
119
  "notes/manual.md".to_string(),
119
120
  ],
120
121
  )
@@ -133,7 +134,11 @@ fn mutation_classifier_recognizes_core_classes() {
133
134
  assert_eq!(by_path["coverage/report.json"], "test artifact");
134
135
  assert_eq!(
135
136
  by_path["packages/naome/native/darwin-arm64/naome"],
136
- "release artifact"
137
+ "user edit"
138
+ );
139
+ assert_eq!(
140
+ by_path["packages/naome/templates/naome-root/AGENTS.md"],
141
+ "user edit"
137
142
  );
138
143
  assert_eq!(by_path["notes/manual.md"], "user edit");
139
144
  }
@@ -149,6 +149,7 @@ function legacyLocalOnlyGitIgnoreEntries(ctx) {
149
149
  "# NAOME local machine-owned harness files.",
150
150
  ".naome/archive/",
151
151
  ".naome/bin/naome-rust*",
152
+ ".naome/cache/",
152
153
  ...ctx.localOnlyMachineOwnedPaths,
153
154
  ...ctx.localOnlyGitIgnoreEntries,
154
155
  ];
Binary file
Binary file
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@lamentis/naome",
3
- "version": "1.2.1",
3
+ "version": "1.3.0",
4
4
  "description": "Native-first CLI for the NAOME agent harness.",
5
5
  "license": "Apache-2.0",
6
6
  "type": "module",
@@ -11,11 +11,11 @@ const nativeBinaryName = process.platform === "win32" ? "naome.exe" : "naome";
11
11
  const expectedMachineOwnedIntegrity = Object.freeze({
12
12
  ".naome/bin/check-harness-health.js": "sha256:dc4de52b79c69600b9ba47b924e2c2b8de61a2cbfab6d1ccc0f1924d963db657",
13
13
  ".naome/bin/check-task-state.js": "sha256:43c02868072d0d13499aefba2e9a5ec9517d59539fd19ff0f11e3e4623a51b44",
14
- ".naome/bin/naome.js": "sha256:87eabd690bf55f0b0195446db46fa7c19bfa17395d31c2f34a9ef9339d2229e2",
14
+ ".naome/bin/naome.js": "sha256:3d2edd9cf7b04ffb8845db2c55ce1b9c243bd3aba112f53af4af3c11fae5b8e1",
15
15
  ".naome/package.json": "sha256:8005a3491db7d92f36ac66369861589f9c47123d3a7c71e643fc2c06168cd45a",
16
16
  ".naome/task-contract.schema.json": "sha256:1b3b62350328d0d6d660e36d1d1baaa2b88718530db774f9ab2a9e2fcba369c8",
17
17
  "AGENTS.md": "sha256:9192ea81f90bb19f8043513c49b5da9e9598ee694da8356f345e7ccbca0e28df",
18
- "docs/naome/agent-workflow.md": "sha256:802eb34cf268fc9c5e7aefc28192efef4bf60302d30b3f78e5a61b876ce8a098",
18
+ "docs/naome/agent-workflow.md": "sha256:97788255e26282ca1b7fcaaf86c9408c9040246727e3de96b4126fcb68c10b38",
19
19
  "docs/naome/execution.md": "sha256:bfc5d55838942ec8e3d790b59e3c634ff5bf6a2298265cef3dca9788a097eafb",
20
20
  "docs/naome/first-run.md": "sha256:a1dd0bd17ec9d71955a473cd2c4a615538e89a7d81e8f4e1015a50ab9efe3558",
21
21
  "docs/naome/index.md": "sha256:a674102cc801702dc77102afb59be0f5ab189dc638caf0bef358b9d6087d0742",
@@ -11,11 +11,11 @@ const nativeBinaryName = process.platform === "win32" ? "naome.exe" : "naome";
11
11
  const expectedMachineOwnedIntegrity = Object.freeze({
12
12
  ".naome/bin/check-harness-health.js": "sha256:dc4de52b79c69600b9ba47b924e2c2b8de61a2cbfab6d1ccc0f1924d963db657",
13
13
  ".naome/bin/check-task-state.js": "sha256:43c02868072d0d13499aefba2e9a5ec9517d59539fd19ff0f11e3e4623a51b44",
14
- ".naome/bin/naome.js": "sha256:87eabd690bf55f0b0195446db46fa7c19bfa17395d31c2f34a9ef9339d2229e2",
14
+ ".naome/bin/naome.js": "sha256:3d2edd9cf7b04ffb8845db2c55ce1b9c243bd3aba112f53af4af3c11fae5b8e1",
15
15
  ".naome/package.json": "sha256:8005a3491db7d92f36ac66369861589f9c47123d3a7c71e643fc2c06168cd45a",
16
16
  ".naome/task-contract.schema.json": "sha256:1b3b62350328d0d6d660e36d1d1baaa2b88718530db774f9ab2a9e2fcba369c8",
17
17
  "AGENTS.md": "sha256:9192ea81f90bb19f8043513c49b5da9e9598ee694da8356f345e7ccbca0e28df",
18
- "docs/naome/agent-workflow.md": "sha256:802eb34cf268fc9c5e7aefc28192efef4bf60302d30b3f78e5a61b876ce8a098",
18
+ "docs/naome/agent-workflow.md": "sha256:97788255e26282ca1b7fcaaf86c9408c9040246727e3de96b4126fcb68c10b38",
19
19
  "docs/naome/execution.md": "sha256:bfc5d55838942ec8e3d790b59e3c634ff5bf6a2298265cef3dca9788a097eafb",
20
20
  "docs/naome/first-run.md": "sha256:a1dd0bd17ec9d71955a473cd2c4a615538e89a7d81e8f4e1015a50ab9efe3558",
21
21
  "docs/naome/index.md": "sha256:a674102cc801702dc77102afb59be0f5ab189dc638caf0bef358b9d6087d0742",
@@ -27,7 +27,7 @@ function main(argv) {
27
27
  return;
28
28
  }
29
29
 
30
- if (["status", "next", "intent", "route", "explain", "quality", "structure", "cleanup", "refresh-integrity", "workflow"].includes(command)) {
30
+ if (["status", "next", "intent", "route", "explain", "doctor", "quality", "semantic", "structure", "cleanup", "refresh-integrity", "workflow"].includes(command)) {
31
31
  runNativeDecisionCommand(command, args);
32
32
  return;
33
33
  }
@@ -358,9 +358,16 @@ function printHelp() {
358
358
  "naome route --prompt <text> [--execute] [--json]",
359
359
  "naome explain --prompt-file <path> [--json]",
360
360
  "naome explain --prompt <text> [--json]",
361
- "naome quality init [--json]",
362
- "naome quality check --changed [--json]",
363
- "naome quality report [--json]",
361
+ "naome doctor [--json]",
362
+ "naome quality init [--baseline|--deep-baseline] [--json]",
363
+ "naome quality check --changed [--include-scanned-paths] [--json]",
364
+ "naome quality report [--deep] [--include-scanned-paths] [--json]",
365
+ "naome quality cache status [--json]",
366
+ "naome quality cache clear",
367
+ "naome semantic report [--deep] [--json]",
368
+ "naome semantic check --changed [--json]",
369
+ "naome semantic route --finding <id> [--json]",
370
+ "naome semantic loop [--json]",
364
371
  "naome structure report [--json]",
365
372
  "naome structure explain --path <path> [--json]",
366
373
  "naome cleanup plan [--json]",
@@ -4,11 +4,11 @@
4
4
  "integrity": {
5
5
  ".naome/bin/check-harness-health.js": "sha256:dc4de52b79c69600b9ba47b924e2c2b8de61a2cbfab6d1ccc0f1924d963db657",
6
6
  ".naome/bin/check-task-state.js": "sha256:43c02868072d0d13499aefba2e9a5ec9517d59539fd19ff0f11e3e4623a51b44",
7
- ".naome/bin/naome.js": "sha256:87eabd690bf55f0b0195446db46fa7c19bfa17395d31c2f34a9ef9339d2229e2",
7
+ ".naome/bin/naome.js": "sha256:3d2edd9cf7b04ffb8845db2c55ce1b9c243bd3aba112f53af4af3c11fae5b8e1",
8
8
  ".naome/package.json": "sha256:8005a3491db7d92f36ac66369861589f9c47123d3a7c71e643fc2c06168cd45a",
9
9
  ".naome/task-contract.schema.json": "sha256:1b3b62350328d0d6d660e36d1d1baaa2b88718530db774f9ab2a9e2fcba369c8",
10
10
  "AGENTS.md": "sha256:9192ea81f90bb19f8043513c49b5da9e9598ee694da8356f345e7ccbca0e28df",
11
- "docs/naome/agent-workflow.md": "sha256:802eb34cf268fc9c5e7aefc28192efef4bf60302d30b3f78e5a61b876ce8a098",
11
+ "docs/naome/agent-workflow.md": "sha256:97788255e26282ca1b7fcaaf86c9408c9040246727e3de96b4126fcb68c10b38",
12
12
  "docs/naome/execution.md": "sha256:bfc5d55838942ec8e3d790b59e3c634ff5bf6a2298265cef3dca9788a097eafb",
13
13
  "docs/naome/first-run.md": "sha256:a1dd0bd17ec9d71955a473cd2c4a615538e89a7d81e8f4e1015a50ab9efe3558",
14
14
  "docs/naome/index.md": "sha256:a674102cc801702dc77102afb59be0f5ab189dc638caf0bef358b9d6087d0742",
@@ -2,3 +2,4 @@
2
2
  # Agents must not read, summarize, scan, import, or use these paths as context.
3
3
 
4
4
  .naome/archive/
5
+ .naome/cache/
@@ -20,37 +20,39 @@ Use this workflow after first-run intake is complete.
20
20
  debugging why a policy won.
21
21
  4. Run `node .naome/bin/naome.js status --json` when reporting state without
22
22
  routing a new request.
23
- 5. Run `node .naome/bin/check-harness-health.js`.
24
- 6. If harness health fails, do not start new feature work. Ask the user to
23
+ 5. Run `node .naome/bin/naome.js doctor --json` when state is unclear or a
24
+ gate blocks unexpectedly; use its `nextAction` as the first diagnostic.
25
+ 6. Run `node .naome/bin/check-harness-health.js`.
26
+ 7. If harness health fails, do not start new feature work. Ask the user to
25
27
  choose `repair_harness`, `review_harness_diff`, or
26
28
  `cancel_repair_baseline`.
27
- 7. Run `node .naome/bin/check-task-state.js --admission`.
28
- 8. If task admission fails for a natural-language work request, use
29
+ 8. Run `node .naome/bin/check-task-state.js --admission`.
30
+ 9. If task admission fails for a natural-language work request, use
29
31
  `naome route --execute --json`. Route may baseline valid completed setup or
30
32
  task diffs, create an isolated task worktree around unrelated user edits,
31
33
  baseline pure harness refreshes in the current worktree, and rerun
32
34
  admission. Ask the user only when `humanOptions` is non-empty,
33
35
  route blocks as unsafe/ambiguous, or automatic baselining fails.
34
- 9. If route blocks or returns no mutation, do not use raw `git commit`, IDE
36
+ 10. If route blocks or returns no mutation, do not use raw `git commit`, IDE
35
37
  commit, `git add`, or hook bypass commands as a fallback. Unowned changes
36
38
  are user-owned unless NAOME route explicitly isolates around them or
37
39
  baselines a deterministic harness/task diff. If the user explicitly asks to
38
40
  commit their own unowned changes, route must run the configured quality gate
39
41
  first, require committed verification coverage for every path, and commit
40
42
  only the final stabilized paths it evaluated.
41
- 10. Record the passed admission check in `.naome/task-state.json` when starting
43
+ 11. Record the passed admission check in `.naome/task-state.json` when starting
42
44
  the task.
43
- 11. Restate the task in concrete terms.
44
- 12. Read `.naomeignore`.
45
- 13. Exclude every path matched by `.naomeignore` from context gathering.
46
- 14. For broad searches, use `node .naome/bin/naome.js workflow search-profile`
45
+ 12. Restate the task in concrete terms.
46
+ 13. Read `.naomeignore`.
47
+ 14. Exclude every path matched by `.naomeignore` from context gathering.
48
+ 15. For broad searches, use `node .naome/bin/naome.js workflow search-profile`
47
49
  or equivalent excludes for `.git`, `.naome/archive`, dependencies, build
48
50
  outputs, caches, and `.naomeignore` paths.
49
- 15. Read only the `requiredContext` returned by route/status plus the smallest
51
+ 16. Read only the `requiredContext` returned by route/status plus the smallest
50
52
  task-relevant NAOME docs.
51
- 16. Inspect the existing code or docs before proposing changes.
52
- 17. Read `testing.md` and `.naome/verification.json`.
53
- 18. Identify the required proof before claiming success.
53
+ 17. Inspect the existing code or docs before proposing changes.
54
+ 18. Read `testing.md` and `.naome/verification.json`.
55
+ 19. Identify the required proof before claiming success.
54
56
 
55
57
  ## Instruction Boundaries
56
58
 
@@ -7,15 +7,26 @@ NAOME keeps legacy debt visible without blocking unrelated feature work.
7
7
  - `naome quality check --changed` blocks only on files changed in the current
8
8
  diff. If a legacy file is touched, that file must satisfy the configured
9
9
  quality rules before commit.
10
- - `naome quality report` scans the repository and reports debt without failing
11
- normal feature work.
10
+ - `naome quality report` scans the repository with normal budgets and reports
11
+ debt without failing feature work. Full repository duplicate,
12
+ near-duplicate, and semantic grouping checks are deep-only.
13
+ - `naome quality report --deep` runs the intentionally expensive full
14
+ repository checks.
12
15
  - `naome cleanup plan` groups report findings into deterministic cleanup tasks.
13
16
  - `naome cleanup route --path <path>` returns agent instructions for one file.
17
+ Structure findings include rule-specific guidance such as moving misplaced
18
+ tests, pairing source with nearby tests, splitting dumping-ground folders, or
19
+ resolving case collisions.
14
20
 
15
21
  ## Configuration
16
22
 
17
23
  Repository-specific rules live in `.naome/repository-quality.json`.
18
24
 
25
+ `quality init` writes only policy files and an empty baseline placeholder. It
26
+ does not deep-scan the repository. To record existing debt intentionally, run
27
+ `quality init --baseline`; use `quality init --deep-baseline` only when broad
28
+ duplicate and semantic grouping checks are expected.
29
+
19
30
  `quality init` selects deterministic built-in adapters from repository files.
20
31
  Adapters are plug-and-play profiles such as `rust` or
21
32
  `javascript-typescript`. They add stack-specific ignored/generated paths and
@@ -26,6 +37,20 @@ Local `pathRules` are project overrides, not product defaults. They may document
26
37
  repo-specific debt or special file roles, but loosening a rule to pass a feature
27
38
  diff requires human review.
28
39
 
40
+ The scanner has three modes:
41
+
42
+ - `ChangedFast`: changed files are read fully; unchanged files may contribute
43
+ cached facts for duplicate comparison.
44
+ - `Report`: repository-wide, budgeted debt visibility. If budgets are hit, JSON
45
+ sets `summary.truncated` and includes stable `reasonCodes`.
46
+ - `DeepReport`: explicit expensive scan for full duplicate, near-duplicate, and
47
+ semantic grouping work.
48
+
49
+ Per-file analysis facts are cached under `.naome/cache/quality/`. Cache entries
50
+ are local-only, keyed by NAOME version, config hash, adapter version, path, and
51
+ content hash. Cache corruption or misses cause a rescan, not a gate failure.
52
+ Use `quality cache status --json` and `quality cache clear` for maintenance.
53
+
29
54
  The default scanner is language-agnostic and uses text plus symbol heuristics:
30
55
  file length, diff growth, function or component length, top-level symbol count,
31
56
  duplicate regions, and near-duplicate functions. Duplicate regions are grouped
@@ -39,8 +64,42 @@ path roles, module/layer policy, adapters, and cleanup routing.
39
64
  Agents may propose stricter repo-specific rules after inspecting the language
40
65
  and stack.
41
66
 
67
+ ## Planned Semantic Cleanup
68
+
69
+ Some maintainability debt is semantic rather than purely syntactic. Examples
70
+ include inline legacy compatibility fixtures, copied config objects, stale test
71
+ builders, hand-written schema snapshots, and helper data that should move into a
72
+ shared factory after enough call sites accumulate.
73
+
74
+ NAOME should detect these with a generic semantic-cleanup layer instead of
75
+ hard-coding product paths or deleting compatibility fixtures opportunistically.
76
+ The planned model is:
77
+
78
+ - detect repeated object shapes, schema literals, fixture builders, and config
79
+ snapshots across changed and report-mode files;
80
+ - classify each finding as `legacy fixture`, `duplicated fixture`,
81
+ `schema snapshot`, `generated metadata`, or `inline builder`;
82
+ - keep existing report-mode debt visible without blocking unrelated work;
83
+ - block only changed/new semantic debt unless local policy marks it report-only;
84
+ - route cleanup to extract a shared fixture, builder, schema writer, or generated
85
+ metadata refresh command;
86
+ - preserve behavior by requiring tests before removing or consolidating legacy
87
+ compatibility fixtures.
88
+
89
+ The first implementation exposes this as a scout, not an auto-fixer:
90
+
91
+ - `naome semantic report --json` runs a budgeted semantic report.
92
+ - `naome semantic report --deep --json` runs repo-wide semantic grouping.
93
+ - `naome semantic check --changed --json` checks only changed semantic debt for
94
+ gate use.
95
+ - `naome semantic route --finding <id> --json` gives an agent the complete
96
+ affected path list, cleanup intent, and required checks for one finding group.
97
+ - `naome semantic loop --json` selects the next deterministic cleanup action:
98
+ changed-code findings first, then report-only legacy debt.
99
+
42
100
  ## Baseline
43
101
 
44
102
  Existing debt is recorded in `.naome/repository-quality-baseline.json` by
45
- `naome quality init`. Baseline debt remains visible in reports, but only changed
46
- files are blocking during feature work.
103
+ `naome quality init --baseline` or `naome quality init --deep-baseline`.
104
+ Baseline debt remains visible in reports, but only changed files are blocking
105
+ during feature work.