@nitra/cursor 5.3.4 → 5.4.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 (151) hide show
  1. package/.claude-template/settings.template.json +2 -2
  2. package/.pi-template/extensions/n-cursor-adr/docs/index.md +13 -24
  3. package/CHANGELOG.md +11 -0
  4. package/bin/n-cursor.js +43 -22
  5. package/lib/docs/models.md +29 -18
  6. package/lib/docs/omlx-trace.md +51 -0
  7. package/lib/docs/omlx.md +31 -15
  8. package/lib/omlx.mjs +2 -5
  9. package/package.json +1 -1
  10. package/rules/abie/docs/fix.md +17 -11
  11. package/rules/adr/docs/fix.md +25 -140
  12. package/rules/bun/docs/fix.md +18 -151
  13. package/rules/capacitor/docs/fix.md +16 -13
  14. package/rules/capacitor/js/docs/platforms.md +31 -43
  15. package/rules/changelog/docs/fix.md +25 -169
  16. package/rules/ci4/docs/fix.md +11 -14
  17. package/rules/doc-files/doc-files.mdc +60 -0
  18. package/rules/doc-files/docs/fix.md +31 -0
  19. package/rules/doc-files/fix.mjs +19 -0
  20. package/{skills → rules}/doc-files/js/docgen-extract.mjs +42 -19
  21. package/{skills → rules}/doc-files/js/docgen-ignore.mjs +2 -1
  22. package/{skills → rules}/doc-files/js/docgen-scan.mjs +9 -1
  23. package/{skills → rules}/doc-files/js/docs/docgen-crc.md +1 -1
  24. package/{skills → rules}/doc-files/js/docs/docgen-extract-anchors.md +1 -1
  25. package/{skills → rules}/doc-files/js/docs/docgen-extract.md +2 -2
  26. package/{skills → rules}/doc-files/js/docs/docgen-files-batch.md +1 -1
  27. package/{skills → rules}/doc-files/js/docs/docgen-gen.md +1 -1
  28. package/{skills → rules}/doc-files/js/docs/docgen-ignore.md +4 -4
  29. package/rules/doc-files/js/docs/docgen-prompts.md +39 -0
  30. package/rules/doc-files/js/docs/docgen-scan.md +54 -0
  31. package/rules/doc-files/js/docs/lint.md +36 -0
  32. package/rules/doc-files/js/docs/units-js.md +31 -0
  33. package/rules/doc-files/js/docs/units-rs.md +35 -0
  34. package/rules/doc-files/js/docs/units.md +30 -0
  35. package/rules/doc-files/js/lint.mjs +96 -0
  36. package/{skills → rules}/doc-files/js/units-rs.mjs +37 -17
  37. package/rules/doc-files/lint/docs/lint.md +37 -0
  38. package/rules/doc-files/lint/lint.mjs +105 -0
  39. package/rules/doc-files/meta.json +1 -0
  40. package/rules/docker/docs/fix.md +21 -161
  41. package/rules/efes/docs/fix.md +23 -194
  42. package/rules/feedback/docs/fix.md +10 -8
  43. package/rules/ga/docs/fix.md +10 -5
  44. package/rules/graphql/docs/fix.md +23 -119
  45. package/rules/hasura/docs/fix.md +19 -5
  46. package/rules/hasura/js/docs/internal_urls.md +34 -307
  47. package/rules/image-avif/docs/fix.md +16 -127
  48. package/rules/image-compress/docs/fix.md +20 -141
  49. package/rules/image-compress/js/docs/package_setup.md +22 -182
  50. package/rules/js-bun-db/docs/fix.md +23 -139
  51. package/rules/js-bun-db/js/docs/safety.md +33 -221
  52. package/rules/js-bun-redis/docs/fix.md +25 -114
  53. package/rules/js-bun-redis/js/docs/imports.md +18 -166
  54. package/rules/js-lint/docs/fix.md +30 -108
  55. package/rules/js-lint/js/docs/lint-findings.md +37 -17
  56. package/rules/js-lint/js/docs/lint.md +22 -238
  57. package/rules/js-lint/js/docs/tooling.md +34 -331
  58. package/rules/js-lint-ci/docs/fix.md +16 -149
  59. package/rules/js-lint-ci/js/docs/lint.md +16 -136
  60. package/rules/js-mssql/docs/fix.md +18 -123
  61. package/rules/js-mssql/js/docs/deps.md +28 -251
  62. package/rules/js-run/docs/fix.md +23 -138
  63. package/rules/js-run/js/docs/runtime.md +24 -378
  64. package/rules/k8s/docs/fix.md +18 -123
  65. package/rules/nginx-default-tpl/docs/fix.md +22 -118
  66. package/rules/nginx-default-tpl/js/docs/template.md +38 -360
  67. package/rules/npm-module/docs/fix.md +27 -89
  68. package/rules/npm-module/js/docs/header_doc_pointer.md +15 -15
  69. package/rules/npm-module/js/docs/package_structure.md +36 -258
  70. package/rules/npm-module/js/docs/rule_meta.md +25 -127
  71. package/rules/npm-module/js/docs/skill_meta.md +18 -180
  72. package/rules/php/docs/fix.md +21 -98
  73. package/rules/php/js/docs/tooling.md +20 -143
  74. package/rules/python/docs/fix.md +25 -157
  75. package/rules/python/js/docs/applies.md +20 -98
  76. package/rules/python/js/docs/tooling.md +27 -144
  77. package/rules/rego/docs/fix.md +24 -112
  78. package/rules/rego/js/docs/applies.md +20 -164
  79. package/rules/rego/js/docs/lint.md +15 -110
  80. package/rules/release/docs/fix.md +16 -114
  81. package/rules/rust/docs/fix.md +24 -119
  82. package/rules/rust/js/docs/applies.md +20 -129
  83. package/rules/security/docs/fix.md +21 -78
  84. package/rules/security/js/docs/sample_secret.md +23 -182
  85. package/rules/security/js/docs/trufflehog.md +19 -128
  86. package/rules/style-lint/docs/fix.md +16 -150
  87. package/rules/style-lint/js/docs/lint.md +21 -172
  88. package/rules/style-lint/js/docs/tooling.md +19 -184
  89. package/rules/tauri/docs/fix.md +26 -152
  90. package/rules/tauri/js/docs/cargo_mutants_config.md +21 -159
  91. package/rules/tauri/js/docs/tooling.md +20 -217
  92. package/rules/test/docs/fix.md +19 -127
  93. package/rules/test/js/data/stryker_config/docs/stryker.config.baseline.md +15 -127
  94. package/rules/test/js/data/stryker_config/docs/stryker.config.vue.baseline.md +17 -153
  95. package/rules/test/js/docs/cargo_mutants_config.md +24 -164
  96. package/rules/test/js/docs/location.md +24 -126
  97. package/rules/test/js/docs/no-process-chdir.md +20 -151
  98. package/rules/test/js/docs/no-relative-fs-path.md +24 -261
  99. package/rules/test/js/docs/stryker_config.md +48 -148
  100. package/rules/test/js/docs/vitest-config-pool-forks.md +21 -164
  101. package/rules/text/docs/fix.md +25 -113
  102. package/rules/text/js/docs/forbidden-prettier.md +21 -132
  103. package/rules/text/js/docs/formatting.md +60 -251
  104. package/rules/text/js/docs/lint.md +17 -114
  105. package/rules/vue/docs/fix.md +25 -118
  106. package/rules/vue/js/docs/packages.md +25 -323
  107. package/rules/worktree/docs/fix.md +31 -150
  108. package/scripts/coverage-classify/docs/index.md +23 -209
  109. package/scripts/coverage-classify/docs/verdict-schema.md +14 -159
  110. package/scripts/dispatcher/docs/trace.md +35 -0
  111. package/scripts/docs/auto-rules.md +37 -361
  112. package/scripts/docs/lint-cli.md +12 -13
  113. package/scripts/docs/post-tool-use-fix.md +16 -15
  114. package/scripts/docs/skills-cli.md +26 -23
  115. package/scripts/docs/sync-claude-config.md +94 -34
  116. package/scripts/docs/worktree-cli.md +11 -34
  117. package/scripts/lib/docs/assert-project-root.md +14 -16
  118. package/scripts/lib/docs/changed-files.md +24 -139
  119. package/scripts/lib/docs/discover-check-rules-from-cursor.md +14 -146
  120. package/scripts/lib/docs/rule-predicates.md +20 -17
  121. package/scripts/lib/docs/run-rule-cli.md +14 -18
  122. package/scripts/lib/docs/run-rule.md +13 -20
  123. package/scripts/lib/docs/run-standard-rule.md +12 -15
  124. package/scripts/lib/docs/sync-gitignore-worktree.md +15 -18
  125. package/scripts/lib/rule-predicates.mjs +1 -1
  126. package/scripts/sync-claude-config.mjs +4 -1
  127. package/scripts/utils/docs/with-lock.md +19 -12
  128. package/scripts/utils/with-lock.mjs +4 -2
  129. package/skills/doc-aggregate/SKILL.md +2 -2
  130. package/skills/doc-aggregate/js/docgen-ignore.mjs +6 -6
  131. package/skills/doc-aggregate/js/docs/docgen-ignore.md +1 -1
  132. package/skills/doc-aggregate/js/docs/docgen-scan.md +78 -0
  133. package/skills/doc-files/.changes/260612-0031.md +5 -0
  134. package/skills/doc-files/.changes/260612-0036.md +5 -0
  135. package/skills/doc-files/.changes/260612-0114.md +5 -0
  136. package/skills/doc-files/SKILL.md +6 -6
  137. package/skills/fix/js/docs/llm-worker.md +17 -15
  138. package/skills/fix/js/docs/orchestrator.md +30 -23
  139. package/skills/fix/js/docs/t0.md +26 -16
  140. package/skills/start-check/js/docs/check.md +26 -22
  141. package/skills/taze/js/docs/diff.md +44 -20
  142. package/skills/doc-files/js/docs/docgen-prompts.md +0 -32
  143. package/skills/doc-files/js/docs/docgen-scan.md +0 -25
  144. package/skills/doc-files/js/docs/units-rs.md +0 -35
  145. /package/{skills → rules}/doc-files/js/docgen-crc.mjs +0 -0
  146. /package/{skills → rules}/doc-files/js/docgen-extract-anchors.mjs +0 -0
  147. /package/{skills → rules}/doc-files/js/docgen-files-batch.mjs +0 -0
  148. /package/{skills → rules}/doc-files/js/docgen-gen.mjs +0 -0
  149. /package/{skills → rules}/doc-files/js/docgen-prompts.mjs +0 -0
  150. /package/{skills → rules}/doc-files/js/units-js.mjs +0 -0
  151. /package/{skills → rules}/doc-files/js/units.mjs +0 -0
@@ -1,122 +1,25 @@
1
+ ---
2
+ docgen:
3
+ source: npm/rules/text/js/lint.mjs
4
+ crc: 4ee054a0
5
+ score: 100
6
+ ---
7
+
1
8
  # lint.mjs
2
9
 
3
10
  ## Огляд
4
11
 
5
- Модуль `lint.mjs` це тонкий адаптер-обгортка, що реалізує CI-крок (контракт `lint(files)`) для правила `text` у складі n-cursor правил репозиторію. Його єдина роль делегувати виконання у внутрішній CLI правила `text`, який знаходиться поряд у директорії `../lint/lint.mjs`.
6
-
7
- Особливості модуля:
8
-
9
- - Працює в режимі **whole-repo**: незалежно від того, які файли передає викликаюча сторона (наприклад, обгортка `lint-js` чи CI-оркестратор), аналіз виконується по всьому репозиторію цілком.
10
- - Per-file режиму **немає**: вхідний параметр `files` навмисно ігнорується (підкреслено префіксом `_` у назві аргумента).
11
- - Повертає числовий exit code (Promise), сумісний з конвенцією Unix-процесів: `0` — успіх, ненульовий — помилки лінту.
12
- - Модуль не містить власної логіки перевірки тексту: вся реальна робота (запуск пов’язаних інструментів типу `dotenv-linter`, `shellcheck`, `v8r` тощо) — у `../lint/lint.mjs`.
13
-
14
- Файл написаний у форматі **ES Modules** (`.mjs`) з JSDoc-анотаціями для статичної типізації без TypeScript-компіляції.
15
-
16
- ## Експорти / API
17
-
18
- | Експорт | Тип | Призначення |
19
- | ------- | ------------------------------------------------------ | ---------------------------------------------------------------------- |
20
- | `lint` | `async function (files?: string[]) => Promise<number>` | CI-крок-делегат у `runLintTextCli`. Іменований експорт (named export). |
21
-
22
- Default-експорту немає. Сторонніх ефектів на рівні модуля (top-level side effects) також немає — лише імпорт залежності.
23
-
24
- ### Сигнатура
25
-
26
- ```js
27
- export async function lint(_files): Promise<number>
28
- ```
29
-
30
- ### Контракт CI-кроку
31
-
32
- Модуль реалізує загальний інтерфейс CI-крока правил n-cursor:
33
-
34
- - Назва експорту: `lint`.
35
- - Сигнатура приймає опціональний `files: string[] | undefined`.
36
- - Повертає `Promise<number>` — exit code.
37
- - Не кидає винятків у нормальному сценарії; помилки сигналізуються через ненульовий exit code, який повертає делегат `runLintTextCli`.
38
-
39
- ## Функції
40
-
41
- ### `lint(_files)`
42
-
43
- **Сигнатура:** `async function lint(_files: string[] | undefined): Promise<number>`
44
-
45
- **Параметри:**
46
-
47
- | Ім’я | Тип | Опис |
48
- | -------- | ----------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
49
- | `_files` | `string[] \| undefined` | Список файлів, які теоретично потрібно перевірити. **Ігнорується** — правило `text` працює у whole-repo режимі. Префікс `_` у назві аргументу — конвенція, що позначає невикористаний параметр (зокрема, щоб ESLint/lint-правила не лаялись на unused arg). |
50
-
51
- **Повертає:** `Promise<number>` — exit code, отриманий від виклику `runLintTextCli()`. Зазвичай `0` означає, що всі перевірки пройшли успішно, а будь-яке інше число — що знайдено порушення або сталася помилка інструмента.
52
-
53
- **Side effects:** Сам по собі `lint` додаткових ефектів не вносить. Усі побічні ефекти (запис у stdout/stderr, читання файлів, запуск зовнішніх процесів) виконуються всередині `runLintTextCli()`, на який делегується виклик.
54
-
55
- **Поведінка:**
56
-
57
- 1. Викликає `runLintTextCli()` без аргументів.
58
- 2. Повертає результат як є (через `await` неявно через `return await`-форму — `async`-функція автоматично «розгортає» Promise з тіла).
59
-
60
- Логіки трансформації параметрів, фільтрації, перевірки прапорців тощо — немає. Це навмисно мінімалістична функція-адаптер.
61
-
62
- ## Залежності
63
-
64
- ### Імпорти
65
-
66
- | Що | Звідки | Призначення |
67
- | ---------------- | ------------------ | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
68
- | `runLintTextCli` | `../lint/lint.mjs` | Запускає реальний CLI-обробник правила `text`. Саме він агрегує запуски під-інструментів (наприклад, `run-dotenv-linter.mjs`, `run-shellcheck.mjs`, `run-v8r.mjs`, які лежать у тій самій директорії `../lint/`). |
69
-
70
- ### Зовнішні (npm) залежності
71
-
72
- Прямих імпортів з npm у файлі немає. Усі npm-залежності (якщо такі є) приховані у транзитивній залежності — `../lint/lint.mjs`.
73
-
74
- ### Структурний контекст
75
-
76
- Файл лежить у `npm/rules/text/js/lint.mjs`. У тій самій директорії розташовані інші CI-крокові модулі правила `text` (наприклад, `formatting.mjs`, `forbidden-prettier.mjs`). Усі вони — однотипні делегати, що реалізують контракт CI-крока.
77
-
78
- Бенефіціар:
79
-
80
- - `../lint/lint.mjs` — справжній CLI правила `text`, що містить runner-логіку (parsing аргументів, оркестрація під-інструментів, формування звіту, exit code).
81
-
82
- ## Потік виконання / Використання
83
-
84
- ### Сценарій 1: виклик через CI-оркестратор правил
85
-
86
- 1. Оркестратор правил (наприклад, агрегований раннер у `lint-js` чи кореневий `bun run lint`) виявляє правило `text` і знаходить його CI-кроки в `npm/rules/text/js/*.mjs`.
87
- 2. Для кожного CI-крока (зокрема `lint.mjs`) оркестратор імпортує named export `lint`.
88
- 3. Викликає `await lint(filesArrayOrUndefined)`.
89
- 4. Адаптер ігнорує `files`, делегує виклик у `runLintTextCli()`.
90
- 5. Реальний CLI робить whole-repo аналіз: запускає `dotenv-linter`, `shellcheck`, `v8r` тощо (відповідно до того, що оголошено в `../lint/lint.mjs`).
91
- 6. Повертає exit code.
92
- 7. Оркестратор агрегує exit code-и всіх CI-кроків і приймає рішення про загальний успіх/невдачу.
93
-
94
- ### Сценарій 2: пряме виконання з коду
95
-
96
- ```js
97
- import { lint } from 'npm/rules/text/js/lint.mjs'
98
-
99
- const code = await lint()
100
- process.exit(code)
101
- ```
102
-
103
- Передача аргументу `files` нічого не змінює (буде проігнорована):
104
-
105
- ```js
106
- const code = await lint(['some/file.txt']) // _files ігнорується
107
- ```
108
-
109
- ### Чому per-file немає
110
-
111
- Правило `text` за своєю природою сканує весь репозиторій (наприклад, перевіряє `.env`-файли, shell-скрипти, JSON Schema-файли через v8r). Для нього передача обмеженого списку файлів від CI не має сенсу — обробляти треба весь робочий простір. Звідси й whole-repo режим, явно зафіксований у JSDoc-коментарі та підкреслений підкресленням у назві параметра.
12
+ Файл надає функцію lint, яка делегує завдання CLI правилам. Функція не підтримує режим per-file, і параметр files ігнорується. Функція повертає Promise з кодом виходу.
112
13
 
113
- ### Очікувані коди виходу
14
+ ## Поведінка
114
15
 
115
- | Code | Значення |
116
- | ----- | --------------------------------------------------------------------------------------------------- |
117
- | `0` | Усі під-перевірки правила `text` пройшли успішно. |
118
- | `0` | Знайдено порушення або помилка одного з інструментів. Конкретний код визначається `runLintTextCli`. |
16
+ 1. Викликається функція lint з аргументом files.
17
+ 2. Функція lint делегує виконання у CLI правила.
18
+ 3. Режим per-file не підтримується.
19
+ 4. Параметр files ігнорується.
20
+ 5. Функція повертає Promise з кодом виходу.
119
21
 
120
- ### Обробка помилок
22
+ ## Гарантії поведінки
121
23
 
122
- Адаптер не містить `try/catch`. Якщо `runLintTextCli` кине виняток (нештатна ситуація), він пробулькується нагору — до викликаючого. Це навмисний дизайн: оркестратор сам вирішує, як трактувати unhandled rejection.
24
+ - Read-only: файл не виконує операцій запису у файлову систему.
25
+ - Не звертається до мережі.
@@ -1,127 +1,34 @@
1
- # fix.mjs — entry-point правила `vue`
1
+ ---
2
+ docgen:
3
+ source: npm/rules/vue/fix.mjs
4
+ crc: 38cf876b
5
+ score: 90
6
+ ---
2
7
 
3
- ## Огляд
4
-
5
- Файл `npm/rules/vue/fix.mjs` — це **точка входу** (entry-point) для правила `vue` у системі `@nitra/cursor`. Файл одночасно виконує дві ролі:
6
-
7
- 1. **Library mode** — експортує функцію `run(ctx)`, яку викликає зовнішній оркестратор (CLI `@nitra/cursor`, інші правила, тести) з підготовленим контекстом прогону.
8
- 2. **Standalone mode** — якщо файл запущено напряму (наприклад, `bun npm/rules/vue/fix.mjs`), він самостійно піднімає повноцінний CLI-цикл, еквівалентний `npx @nitra/cursor fix vue`.
9
-
10
- Сам файл не містить специфічної для Vue логіки правил. Уся логіка делегується у спільні бібліотеки `runStandardRule` (виконання стандартних фаз правила) і `runRuleCli` (підготовка CLI-середовища). Завдяки цьому `fix.mjs` у директорії правила `vue` залишається тонким shim-файлом, який лише підставляє свою директорію як ідентифікатор правила.
11
-
12
- Стандартний пайплайн, який під цим запускається (через `runStandardRule`), складається з фаз:
13
-
14
- - `applies` — детекція файлів/області застосування правила,
15
- - `JS-concerns` — перевірки JS/JSX/TS-аспектів коду,
16
- - `policy` — застосування policy-чеків (warn/error),
17
- - `mdc-refs` — узгодженість MDC-документації та посилань.
18
-
19
- ## Експорти / API
20
-
21
- | Назва | Тип | Опис |
22
- | ----- | ---------- | ----------------------------------------------------------------------------------------------- |
23
- | `run` | `function` | Named export. Library-точка входу правила. Приймає опційний `ctx` і повертає `Promise<number>`. |
24
-
25
- **Side-effect експорт:** при виконанні модуля під CLI (умова `isRunAsCli(import.meta.url)`) модуль вмикає standalone-режим і завершує процес викликом `process.exit(...)` з exit-кодом, отриманим від `runRuleCli`. Цей побічний ефект виконується на верхньому рівні модуля (top-level `await`), тому імпорт файлу як ESM-модуля з іншого файлу **не** активує standalone-гілку — її активує лише пряме виконання інтерпретатором.
26
-
27
- ## Функції
28
-
29
- ### `run(ctx)`
30
-
31
- Library-функція правила. Делегує виконання у спільну реалізацію `runStandardRule`, передаючи їй власну директорію модуля (`import.meta.dirname`) як ідентифікатор правила та переданий контекст.
32
-
33
- - **Сигнатура:** `function run(ctx): Promise<number>`
34
- - **Параметри:**
35
- - `ctx` _(optional)_ — об'єкт типу `RuleContext` із модуля `../../scripts/lib/run-standard-rule.mjs`. У ньому, серед іншого, передається `walkCache` для уникнення повторного обходу файлової системи між послідовно запущеними правилами. Якщо `ctx` не передано, `runStandardRule` створює його самостійно.
36
- - **Повертає:** `Promise<number>` — exit-код прогону правила:
37
- - `0` — порушень немає (OK);
38
- - `1` — знайдено порушення (rule violations).
39
- - **Side effects:** усі побічні ефекти ховаються всередині `runStandardRule` (читання файлів проєкту, можливі автоматичні фікси, виведення summary в stdout/stderr). Сам `run` додаткових side-effects не має, поза тим, що значення повернення завжди є `Promise`, навіть якщо `runStandardRule` поверне синхронно — це гарантує контракт async-pipeline для оркестратора.
40
- - **Помилки:** функція не обгортає виняткові ситуації — будь-яка помилка з `runStandardRule` пробрасується нагору (rejection промісу) і має оброблятись на рівні CLI/орхестратора.
41
-
42
- ### Top-level standalone-блок
43
-
44
- Не функція, а top-level гілка модуля:
45
-
46
- ```js
47
- if (isRunAsCli(import.meta.url)) {
48
- process.exit(await runRuleCli(import.meta.dirname))
49
- }
50
- ```
8
+ # fix.mjs
51
9
 
52
- - **Семантика:** `isRunAsCli(import.meta.url)` повертає `true`, коли поточний модуль є entry-point процесу (тобто Node/Bun запустив саме цей файл, а не імпортував його). У такому разі викликається `runRuleCli` з директорією поточного правила; її exit-код передається у `process.exit(...)`, щоб CI/IDE отримали коректний статус.
53
- - **Side effects:**
54
- - синхронне завершення процесу через `process.exit`;
55
- - усе, що робить `runRuleCli` (завантаження конфігу, whitelist, summary).
56
- - **ESLint-винятки:** standalone-entry-point має право робити `process.exit`, тому над цим викликом стоять директиви `// eslint-disable-next-line n/no-process-exit, unicorn/no-process-exit`. Це штатна практика для двороле́вих fix.mjs.
57
-
58
- ## Залежності
59
-
60
- Імпорти модуля:
61
-
62
- - `isRunAsCli` — з `../../scripts/lib/run-rule-cli.mjs`. Утиліта-детектор: чи поточний модуль є entry-point (CLI mode), чи його імпортнули як бібліотеку.
63
- - `runRuleCli` — з `../../scripts/lib/run-rule-cli.mjs`. Виконує повну CLI-оркестрацію для одного правила: завантажує конфіг, формує whitelist, друкує summary та повертає exit-код. Використовується тільки у standalone-гілці.
64
- - `runStandardRule` — з `../../scripts/lib/run-standard-rule.mjs`. Виконує стандартний пайплайн правила: `applies → JS-concerns → policy → mdc-refs`. JSDoc-типи `RuleContext` теж приходять із цього модуля (через `@param`-import).
65
-
66
- Неявні залежності:
67
-
68
- - Структура директорії правила (`npm/rules/vue/`) має містити очікувані `runStandardRule` під-директорії/файли: `js/`, `lib/`, `policy/`, `meta.json`, `vue.mdc` тощо. Сам `fix.mjs` не звертається до них напряму — він лише підставляє свій `import.meta.dirname`, а решту виявляє shared-runner.
69
- - ESM-середовище (Node.js ≥ 20 / Bun) з підтримкою `import.meta.url` та `import.meta.dirname`.
70
-
71
- ## Потік виконання / Використання
72
-
73
- ### Library mode (виклик з оркестратора)
74
-
75
- ```js
76
- import { run } from './npm/rules/vue/fix.mjs'
77
-
78
- const exitCode = await run(ctx) // ctx — спільний RuleContext із walkCache
79
- if (exitCode !== 0) {
80
- // у правилі vue знайдено порушення → обробляємо
81
- }
82
- ```
83
-
84
- Послідовність:
85
-
86
- 1. Оркестратор імпортує `fix.mjs`. Гілка `if (isRunAsCli(...))` не виконується, бо `import.meta.url` не є entry-point.
87
- 2. Оркестратор викликає `run(ctx)`.
88
- 3. `run` передає `import.meta.dirname` (= `…/npm/rules/vue`) і `ctx` у `runStandardRule`.
89
- 4. `runStandardRule` виконує фази `applies → JS-concerns → policy → mdc-refs` для правила `vue`, використовуючи кеші з `ctx` (наприклад, `walkCache`).
90
- 5. Повертається exit-код (`0` або `1`), який оркестратор інтегрує у свій агрегований підсумок.
91
-
92
- ### Standalone mode (пряме виконання)
93
-
94
- ```bash
95
- bun npm/rules/vue/fix.mjs
96
- # або
97
- node npm/rules/vue/fix.mjs
98
- ```
99
-
100
- Послідовність:
101
-
102
- 1. Інтерпретатор завантажує модуль; виконуються імпорти.
103
- 2. Виконується top-level код: `isRunAsCli(import.meta.url)` повертає `true`.
104
- 3. Викликається `await runRuleCli(import.meta.dirname)` — це повний еквівалент `npx @nitra/cursor fix vue`:
105
- - читає конфіг,
106
- - застосовує whitelist,
107
- - усередині піднімає той самий `runStandardRule`-цикл (або сумісний з ним),
108
- - друкує summary.
109
- 4. Отриманий exit-код передається у `process.exit(...)`, процес завершується з відповідним кодом для CI/IDE.
10
+ ## Огляд
110
11
 
111
- ### Чому існують дві ролі
12
+ Файл застосовує правило `runStandardRule` до наданого контексту прогону через функцію `runStandardRule` і повертає отриманий результат. У режимі CLI він виконує команду `npx @nitra/cursor fix <id>` та визначає вихідний код процесу на основі отриманого результату.
112
13
 
113
- Подвійна реалізація (`run` + standalone) дозволяє:
14
+ ## Поведінка
114
15
 
115
- - викликати правило **разом з іншими** з єдиного оркестратора без зайвого spawn-у процесів і без втрати спільних кешів (бібліотечний шлях);
116
- - запускати правило **окремо** з командного рядка під час локальної розробки/дебагу, маючи повноцінний CLI-вивід (standalone-шлях).
16
+ 1. Запуск правила.
17
+ * Приймає контекст прогону.
18
+ * Використовує runStandardRule для застосування політики.
19
+ * Повертає результат прогону.
20
+ 2. Запуск у режимі CLI.
21
+ * Викликається через `import + run`.
22
+ * Виконує повний еквівалент `npx @nitra/cursor fix <id>`.
23
+ * Визначає вихідний код процесу на основі результату.
117
24
 
118
- ## Rebuild Test
25
+ ## Публічний API
119
26
 
120
- Можна повністю відтворити поведінку цього файлу з опису вище:
27
+ run запускає правило: applies JS-concerns policy → mdc-refs (через runStandardRule).
28
+ Library mode — викликається CLI orchestration через `import + run`.
121
29
 
122
- - Імпортуються тільки два символи з двох сусідніх бібліотек: `isRunAsCli`, `runRuleCli` з `../../scripts/lib/run-rule-cli.mjs` та `runStandardRule` з `../../scripts/lib/run-standard-rule.mjs`.
123
- - Експортується одна named-функція `run(ctx)`, яка повертає результат `runStandardRule(import.meta.dirname, ctx)` — отже, є async (повертає `Promise<number>`).
124
- - На рівні модуля стоїть умова `if (isRunAsCli(import.meta.url)) { process.exit(await runRuleCli(import.meta.dirname)) }` з відповідними ESLint-disable-коментарями для `n/no-process-exit` та `unicorn/no-process-exit`.
125
- - Жодних додаткових іменованих експортів, default-експортів, констант чи побічних викликів у файлі немає.
30
+ ## Гарантії поведінки
126
31
 
127
- Цього достатньо, щоб переписати файл байт-у-байт еквівалентно точністю до коментарів/форматування), не звертаючись до оригіналу.
32
+ - Read-only: файл не виконує операцій запису у файлову систему.
33
+ - Кешує результати в межах одного прогону.
34
+ - Не звертається до мережі.