@7n/rules 1.5.0 → 1.6.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 (113) hide show
  1. package/.claude-template/hooks/.gitignore.snippet +9 -0
  2. package/CHANGELOG.md +12 -0
  3. package/bin/n-rules.js +83 -21
  4. package/package.json +1 -1
  5. package/rules/abie/main.mdc +0 -6
  6. package/rules/js/check/docs/main.md +1 -1
  7. package/rules/js/check/main.mjs +6 -10
  8. package/rules/js/main.mdc +0 -1
  9. package/rules/js/vscode_extensions/template/extensions.json.snippet.json +4 -1
  10. package/rules/npm-module/main.mdc +0 -2
  11. package/rules/php/tooling/docs/main.md +1 -1
  12. package/rules/php/tooling/main.mjs +2 -7
  13. package/rules/python/tooling/docs/main.md +1 -1
  14. package/rules/python/tooling/main.mjs +2 -7
  15. package/rules/rego/lib/docs/run-external-tool.md +1 -2
  16. package/rules/rego/lib/run-external-tool.mjs +4 -1
  17. package/rules/security/main.mdc +0 -1
  18. package/rules/style/main.mdc +0 -1
  19. package/rules/style/tooling/docs/main.md +1 -1
  20. package/rules/style/tooling/main.mjs +2 -7
  21. package/rules/tauri/release/release.mdc +1 -1
  22. package/rules/text/formatting/docs/main.md +1 -1
  23. package/rules/text/formatting/main.mjs +11 -11
  24. package/rules/text/main.mdc +0 -1
  25. package/scripts/docs/skills-cli.md +3 -3
  26. package/scripts/docs/sync-claude-config.md +1 -1
  27. package/scripts/lib/acp-runner.mjs +8 -10
  28. package/scripts/lib/docs/acp-runner.md +5 -5
  29. package/scripts/lib/docs/mirror-parity.md +1 -1
  30. package/scripts/lib/mirror-parity.mjs +49 -16
  31. package/scripts/skills-cli.mjs +1 -1
  32. package/scripts/sync-claude-config.mjs +2 -2
  33. package/rules/abie/clean_merged_ignore_branches/clean_merged_ignore_branches.mdc +0 -19
  34. package/rules/abie/clean_merged_ignore_branches/clean_merged_ignore_branches.rego +0 -81
  35. package/rules/abie/clean_merged_ignore_branches/concern.json +0 -11
  36. package/rules/abie/clean_merged_ignore_branches/docs/fix-clean_merged_ignore_branches.md +0 -31
  37. package/rules/abie/clean_merged_ignore_branches/docs/index.md +0 -9
  38. package/rules/abie/clean_merged_ignore_branches/fix-clean_merged_ignore_branches.mjs +0 -8
  39. package/rules/abie/clean_merged_ignore_branches/template/clean-merged-branch.yml.snippet.yml +0 -9
  40. package/rules/docker/lint_docker_yml/concern.json +0 -12
  41. package/rules/docker/lint_docker_yml/docs/fix-lint_docker_yml.md +0 -31
  42. package/rules/docker/lint_docker_yml/docs/index.md +0 -9
  43. package/rules/docker/lint_docker_yml/fix-lint_docker_yml.mjs +0 -5
  44. package/rules/docker/lint_docker_yml/lint_docker_yml.mdc +0 -14
  45. package/rules/docker/lint_docker_yml/lint_docker_yml.rego +0 -79
  46. package/rules/docker/lint_docker_yml/template/lint-docker.yml.snippet.yml +0 -41
  47. package/rules/js/lint_js_yml/concern.json +0 -12
  48. package/rules/js/lint_js_yml/docs/fix-lint_js_yml.md +0 -28
  49. package/rules/js/lint_js_yml/docs/index.md +0 -9
  50. package/rules/js/lint_js_yml/fix-lint_js_yml.mjs +0 -5
  51. package/rules/js/lint_js_yml/lint_js_yml.mdc +0 -14
  52. package/rules/js/lint_js_yml/lint_js_yml.rego +0 -117
  53. package/rules/js/lint_js_yml/template/lint-js.yml.snippet.yml +0 -40
  54. package/rules/k8s/lint_k8s_yml/concern.json +0 -12
  55. package/rules/k8s/lint_k8s_yml/docs/fix-lint_k8s_yml.md +0 -30
  56. package/rules/k8s/lint_k8s_yml/docs/index.md +0 -9
  57. package/rules/k8s/lint_k8s_yml/fix-lint_k8s_yml.mjs +0 -5
  58. package/rules/k8s/lint_k8s_yml/lint_k8s_yml.rego +0 -57
  59. package/rules/k8s/lint_k8s_yml/template/lint-k8s.yml.snippet.yml +0 -43
  60. package/rules/npm-module/npm_publish_yml/concern.json +0 -13
  61. package/rules/npm-module/npm_publish_yml/docs/fix-npm_publish_yml.md +0 -28
  62. package/rules/npm-module/npm_publish_yml/docs/index.md +0 -9
  63. package/rules/npm-module/npm_publish_yml/fix-npm_publish_yml.mjs +0 -8
  64. package/rules/npm-module/npm_publish_yml/template/npm-publish.yml.snippet.yml +0 -49
  65. package/rules/php/lint_php_yml/concern.json +0 -12
  66. package/rules/php/lint_php_yml/docs/fix-lint_php_yml.md +0 -28
  67. package/rules/php/lint_php_yml/docs/index.md +0 -9
  68. package/rules/php/lint_php_yml/fix-lint_php_yml.mjs +0 -5
  69. package/rules/php/lint_php_yml/lint_php_yml.mdc +0 -23
  70. package/rules/php/lint_php_yml/lint_php_yml.rego +0 -34
  71. package/rules/php/lint_php_yml/template/lint-php.yml.snippet.yml +0 -47
  72. package/rules/python/lint_python_yml/concern.json +0 -12
  73. package/rules/python/lint_python_yml/docs/fix-lint_python_yml.md +0 -27
  74. package/rules/python/lint_python_yml/docs/index.md +0 -9
  75. package/rules/python/lint_python_yml/fix-lint_python_yml.mjs +0 -5
  76. package/rules/python/lint_python_yml/lint_python_yml.mdc +0 -12
  77. package/rules/python/lint_python_yml/lint_python_yml.rego +0 -68
  78. package/rules/python/lint_python_yml/template/lint-python.yml.snippet.yml +0 -41
  79. package/rules/rust/lint_rust_yml/concern.json +0 -14
  80. package/rules/rust/lint_rust_yml/docs/fix-lint_rust_yml.md +0 -28
  81. package/rules/rust/lint_rust_yml/docs/index.md +0 -9
  82. package/rules/rust/lint_rust_yml/fix-lint_rust_yml.mjs +0 -5
  83. package/rules/rust/lint_rust_yml/lint_rust_yml.mdc +0 -17
  84. package/rules/rust/lint_rust_yml/lint_rust_yml.rego +0 -79
  85. package/rules/rust/lint_rust_yml/template/lint-rust.yml.snippet.yml +0 -44
  86. package/rules/rust/toolchain_cache/concern.json +0 -14
  87. package/rules/rust/toolchain_cache/docs/fix-toolchain_cache.md +0 -35
  88. package/rules/rust/toolchain_cache/docs/index.md +0 -12
  89. package/rules/rust/toolchain_cache/docs/main.md +0 -57
  90. package/rules/rust/toolchain_cache/fix-toolchain_cache.mjs +0 -117
  91. package/rules/rust/toolchain_cache/main.mjs +0 -177
  92. package/rules/rust/toolchain_cache/toolchain_cache.mdc +0 -23
  93. package/rules/security/lint_security_yml/concern.json +0 -14
  94. package/rules/security/lint_security_yml/docs/fix-lint_security_yml.md +0 -31
  95. package/rules/security/lint_security_yml/docs/index.md +0 -9
  96. package/rules/security/lint_security_yml/fix-lint_security_yml.mjs +0 -8
  97. package/rules/security/lint_security_yml/lint_security_yml.mdc +0 -7
  98. package/rules/security/lint_security_yml/lint_security_yml.rego +0 -33
  99. package/rules/security/lint_security_yml/template/lint-security.yml.snippet.yml +0 -31
  100. package/rules/style/lint_style_yml/concern.json +0 -12
  101. package/rules/style/lint_style_yml/docs/fix-lint_style_yml.md +0 -31
  102. package/rules/style/lint_style_yml/docs/index.md +0 -9
  103. package/rules/style/lint_style_yml/fix-lint_style_yml.mjs +0 -5
  104. package/rules/style/lint_style_yml/lint_style_yml.mdc +0 -13
  105. package/rules/style/lint_style_yml/lint_style_yml.rego +0 -38
  106. package/rules/style/lint_style_yml/template/lint-style.yml.snippet.yml +0 -39
  107. package/rules/text/lint_text/concern.json +0 -11
  108. package/rules/text/lint_text/docs/fix-lint_text.md +0 -28
  109. package/rules/text/lint_text/docs/index.md +0 -9
  110. package/rules/text/lint_text/fix-lint_text.mjs +0 -5
  111. package/rules/text/lint_text/lint_text.mdc +0 -19
  112. package/rules/text/lint_text/lint_text.rego +0 -104
  113. package/rules/text/lint_text/template/lint-text.yml.snippet.yml +0 -61
@@ -1,117 +0,0 @@
1
- # Перевірка `.github/workflows/lint-js.yml` (js.mdc).
2
- #
3
- # Канон надходить через --data: { "template": { "snippet": ... } }
4
- # Структура --data сформована з template/lint-js.yml.snippet.yml.
5
- # Required uses + run substrings зчитуються з template's eslint-job steps.
6
- # Універсальні workflow-перевірки — у `ga.workflow_common`.
7
- #
8
- # Логіка, що ЛИШАЄТЬСЯ у rego (inverse anti-patterns):
9
- # - `oxlint --fix` / `eslint --fix` у CI заборонено;
10
- # - actions/checkout (будь-який ref) має мати `with.persist-credentials: false`.
11
- #
12
- # Pin-aware: SHA-пін `owner/action@<40-hex>` (zizmor ref-pin; тег-коментар після
13
- # `#` YAML-парсер відкидає) ЗАДОВОЛЬНЯЄ канонічний `owner/action@vN` з template —
14
- # не вимагаємо (і не даунгрейдимо) назад до тега.
15
- package js.lint_js_yml
16
-
17
- import rego.v1
18
-
19
- # Required `uses:` зі template — фільтруємо тільки кроки з uses.
20
- expected_uses_set contains u if {
21
- some step in data.template.snippet.jobs.eslint.steps
22
- u := object.get(step, "uses", "")
23
- u != ""
24
- }
25
-
26
- # Required `run:` substrings (per-line з template).
27
- expected_run_substrings contains line if {
28
- some step in data.template.snippet.jobs.eslint.steps
29
- r := object.get(step, "run", "")
30
- r != ""
31
- some raw in split(r, "\n")
32
- line := trim_space(raw)
33
- line != ""
34
- }
35
-
36
- # Аліаси на input.
37
- all_steps contains step if {
38
- some job in object.get(input, "jobs", {})
39
- some step in object.get(job, "steps", [])
40
- }
41
-
42
- all_uses_set contains u if {
43
- some step in all_steps
44
- u := object.get(step, "uses", "")
45
- u != ""
46
- }
47
-
48
- all_run_blob := concat("\n", [r |
49
- some step in all_steps
50
- r := step_run_text(step)
51
- ])
52
-
53
- # ── deny: required uses ─────────────────────────────────────────────────
54
-
55
- deny contains msg if {
56
- some required_use in expected_uses_set
57
- not has_use_satisfying(required_use)
58
- msg := sprintf("lint-js.yml: відсутній крок uses: %s (js.mdc)", [required_use])
59
- }
60
-
61
- # ── deny: required run substrings ───────────────────────────────────────
62
-
63
- deny contains msg if {
64
- some required_run in expected_run_substrings
65
- not contains(all_run_blob, required_run)
66
- msg := sprintf("lint-js.yml: у run немає %q (js.mdc)", [required_run])
67
- }
68
-
69
- # ── deny: actions/checkout has persist-credentials: false (inverse) ─────
70
-
71
- deny contains msg if {
72
- not has_checkout_persist_credentials_false
73
- msg := "lint-js.yml: actions/checkout має бути з with.persist-credentials: false (js.mdc)"
74
- }
75
-
76
- # ── deny: --fix у CI заборонено (inverse) ───────────────────────────────
77
-
78
- deny contains msg if {
79
- regex.match(`bunx\s+oxlint[^\n]*--fix`, all_run_blob)
80
- msg := "lint-js.yml: у run є oxlint з `--fix` (у CI заборонено) (js.mdc)"
81
- }
82
-
83
- deny contains msg if {
84
- contains(all_run_blob, "eslint --fix")
85
- msg := "lint-js.yml: у run є `eslint --fix` (у CI заборонено) (js.mdc)"
86
- }
87
-
88
- # ── helpers ─────────────────────────────────────────────────────────────
89
-
90
- has_checkout_persist_credentials_false if {
91
- some step in all_steps
92
- startswith(object.get(step, "uses", ""), "actions/checkout@")
93
- step.with["persist-credentials"] == false
94
- }
95
-
96
- # `uses:` з input задовольняє канонічний `owner/action@tag`: точний збіг…
97
- uses_satisfies(actual, expected) if actual == expected
98
-
99
- # …або той самий action-slug і ref — повний 40-hex commit SHA (zizmor ref-pin).
100
- # Відповідність версії гарантує сам пін (тег-коментар `# vX` парсер відкидає).
101
- uses_satisfies(actual, expected) if {
102
- slug := split(expected, "@")[0]
103
- startswith(actual, concat("", [slug, "@"]))
104
- parts := split(actual, "@")
105
- regex.match(`^[0-9a-fA-F]{40}$`, parts[count(parts) - 1])
106
- }
107
-
108
- has_use_satisfying(required) if {
109
- some u in all_uses_set
110
- uses_satisfies(u, required)
111
- }
112
-
113
- step_run_text(step) := step.run if is_string(step.run)
114
-
115
- else := concat("\n", [s | some s in step.run]) if is_array(step.run)
116
-
117
- else := ""
@@ -1,40 +0,0 @@
1
- name: Lint JS
2
-
3
- on:
4
- push:
5
- branches:
6
- - dev
7
- - main
8
- paths:
9
- - '**/*.js'
10
- - '**/*.mjs'
11
- - '**/*.cjs'
12
- - '**/*.jsx'
13
- - '**/*.ts'
14
- - '**/*.tsx'
15
- - '**/*.vue'
16
- - '**/eslint.config.*'
17
-
18
- pull_request:
19
- branches:
20
- - dev
21
- - main
22
-
23
- concurrency:
24
- group: ${{ github.ref }}-${{ github.workflow }}
25
- cancel-in-progress: true
26
-
27
- jobs:
28
- eslint:
29
- runs-on: ubuntu-latest
30
- permissions:
31
- contents: read
32
- steps:
33
- - uses: actions/checkout@v6
34
- with:
35
- persist-credentials: false
36
-
37
- - uses: ./.github/actions/setup-bun-deps
38
-
39
- - name: Eslint
40
- run: bunx n-rules lint js --no-fix
@@ -1,12 +0,0 @@
1
- {
2
- "$schema": "https://unpkg.com/@7n/rules/schemas/concern.json",
3
- "fixability": "config",
4
- "policy": {
5
- "files": {
6
- "single": ".github/workflows/lint-k8s.yml"
7
- }
8
- },
9
- "requires": {
10
- "capability": "ci:github"
11
- }
12
- }
@@ -1,30 +0,0 @@
1
- ---
2
- type: JS Module
3
- title: fix-lint_k8s_yml.mjs
4
- resource: npm/rules/k8s/lint_k8s_yml/fix-lint_k8s_yml.mjs
5
- docgen:
6
- crc: 220f0740
7
- model: openai-codex/gpt-5.5
8
- score: 100
9
- issues: judge:inaccurate:0.98
10
- judgeModel: openai-codex/gpt-5.4-mini
11
- ---
12
-
13
- ## Огляд
14
-
15
- Надає `patterns` як read-only опис очікуваних збігів для перевірки репозиторію без змін у файловій системі чи інших сховищах. Свідомо пропускає `.github` і `.git`, щоб не аналізувати службові шляхи та зосереджувати перевірку на релевантному вмісті.
16
-
17
- ## Поведінка
18
-
19
- 1. `patterns` оголошує набір правил автоматичного виправлення для workflow перевірки Kubernetes YAML.
20
-
21
- 2. `patterns` забезпечує наявність стандартного шаблону `.github/workflows/lint-k8s.yml`, щоб репозиторій мав узгоджену CI-перевірку Kubernetes-маніфестів.
22
-
23
- 3. `patterns` працює як read-only опис очікуваного виправлення: сам файл не виконує запис у файлову систему чи базу даних.
24
-
25
- 4. `patterns` свідомо не охоплює обходом службові шляхи `.github` і `.git`; цільовий workflow у `.github/workflows/lint-k8s.yml` задається як конкретний шаблонний артефакт.
26
-
27
- ## Гарантії поведінки
28
-
29
- - Read-only: не виконує операцій запису (ФС/БД).
30
- - Свідомо пропускає шляхи: `.github`, `.git`.
@@ -1,9 +0,0 @@
1
- ---
2
- type: Directory Index
3
- title: npm/rules/k8s/lint_k8s_yml
4
- resource: npm/rules/k8s/lint_k8s_yml/
5
- ---
6
-
7
- | Файл | Тип |
8
- | ------------------------------------------- | --------- |
9
- | [fix-lint_k8s_yml.mjs](fix-lint_k8s_yml.md) | JS Module |
@@ -1,5 +0,0 @@
1
- import { createTemplateFixPattern } from '../../../scripts/lib/fix/template-deep-merge.mjs'
2
-
3
- export const patterns = [
4
- createTemplateFixPattern({ id: 'k8s-lint_k8s_yml-template', targetPath: '.github/workflows/lint-k8s.yml' })
5
- ]
@@ -1,57 +0,0 @@
1
- # Перевірка `.github/workflows/lint-k8s.yml` (k8s.mdc).
2
- #
3
- # Канон надходить через --data: { "template": { "snippet": ... } }
4
- # Структура --data сформована з template/lint-k8s.yml.snippet.yml.
5
- # Перевіряємо (drift-safe — усе ведеться з template, без inline-літералів):
6
- # - кожен `uses` з template: actions/checkout@v6, setup-bun-deps;
7
- # - кожен `run` з template (як substring): install kubeconform, kubescape,
8
- # n-rules lint k8s --no-fix.
9
- # Універсальні workflow-перевірки (name, concurrency, branches,
10
- # persist-credentials) — у `ga.workflow_common`.
11
- package k8s.lint_k8s_yml
12
-
13
- import rego.v1
14
-
15
- # Усі `uses` з канону workflow (по всіх job'ах template).
16
- expected_uses contains u if {
17
- some job in data.template.snippet.jobs
18
- some step in job.steps
19
- u := object.get(step, "uses", "")
20
- u != ""
21
- }
22
-
23
- # Усі `uses` з input workflow.
24
- actual_uses contains u if {
25
- some job in object.get(input, "jobs", {})
26
- some step in object.get(job, "steps", [])
27
- u := object.get(step, "uses", "")
28
- u != ""
29
- }
30
-
31
- # Конкатенація всіх `run`-кроків з input workflow.
32
- all_run_text := concat("\n", [run_text |
33
- some job in object.get(input, "jobs", {})
34
- some step in object.get(job, "steps", [])
35
- run_text := step_run_to_text(step)
36
- ])
37
-
38
- deny contains msg if {
39
- some required_use in expected_uses
40
- not required_use in actual_uses
41
- msg := sprintf("lint-k8s.yml: відсутній step з `uses: %s` (k8s.mdc)", [required_use])
42
- }
43
-
44
- deny contains msg if {
45
- some job in data.template.snippet.jobs
46
- some step in job.steps
47
- expected_run := object.get(step, "run", "")
48
- expected_run != ""
49
- not contains(all_run_text, expected_run)
50
- msg := sprintf("lint-k8s.yml: жоден крок run не містить %q (k8s.mdc)", [expected_run])
51
- }
52
-
53
- step_run_to_text(step) := step.run if is_string(step.run)
54
-
55
- else := concat("\n", [s | some s in step.run]) if is_array(step.run)
56
-
57
- else := ""
@@ -1,43 +0,0 @@
1
- name: Lint K8s
2
-
3
- on:
4
- push:
5
- branches:
6
- - dev
7
- - main
8
- paths:
9
- - '**/k8s/**/*.yaml'
10
-
11
- pull_request:
12
- branches:
13
- - dev
14
- - main
15
-
16
- concurrency:
17
- group: ${{ github.ref }}-${{ github.workflow }}
18
- cancel-in-progress: true
19
-
20
- jobs:
21
- lint-k8s:
22
- runs-on: ubuntu-latest
23
- permissions:
24
- contents: read
25
- steps:
26
- - uses: actions/checkout@v6
27
- with:
28
- persist-credentials: false
29
-
30
- - uses: ./.github/actions/setup-bun-deps
31
-
32
- - name: Install kubeconform
33
- run: |
34
- curl -sSL "https://github.com/yannh/kubeconform/releases/download/v0.7.0/kubeconform-linux-amd64.tar.gz" | tar xz
35
- sudo mv kubeconform /usr/local/bin/
36
-
37
- - name: Install kubescape
38
- run: |
39
- curl -s https://raw.githubusercontent.com/kubescape/kubescape/master/install.sh | /bin/bash
40
- echo "$HOME/.kubescape/bin" >> $GITHUB_PATH
41
-
42
- - name: Lint K8s
43
- run: bunx n-rules lint k8s --no-fix
@@ -1,13 +0,0 @@
1
- {
2
- "$schema": "https://unpkg.com/@7n/rules/schemas/concern.json",
3
- "fixability": "config",
4
- "policy": {
5
- "files": {
6
- "single": ".github/workflows/npm-publish.yml"
7
- },
8
- "check": "template"
9
- },
10
- "requires": {
11
- "capability": "ci:github"
12
- }
13
- }
@@ -1,28 +0,0 @@
1
- ---
2
- type: JS Module
3
- title: fix-npm_publish_yml.mjs
4
- resource: npm/rules/npm-module/npm_publish_yml/fix-npm_publish_yml.mjs
5
- docgen:
6
- crc: 6db6decf
7
- model: openai-codex/gpt-5.4-mini
8
- tier: cloud-min
9
- score: 100
10
- issues: judge:inaccurate:0.98
11
- judgeModel: openai-codex/gpt-5.4-mini
12
- ---
13
-
14
- ## Огляд
15
-
16
- `patterns` визначає правила зіставлення вмісту для `/.github/workflows/npm-publish.yml` у межах репозиторію. Файл потрібен, щоб узгоджувати цей workflow із очікуваною структурою та вмістом.
17
-
18
- ## Поведінка
19
-
20
- 1. `patterns` формує набір правил для підтримання узгодженого стану шаблонного workflow-файла `/.github/workflows/npm-publish.yml`.
21
- 2. `patterns` працює у режимі read-only: він не змінює ФС або БД.
22
- 3. `patterns` свідомо не охоплює шляхи `.github` і `.git`, щоб не зачіпати службові каталоги репозиторію.
23
- 4. `patterns` повертає готову конфігурацію для застосування до цільового файла, щоб стандартизувати його вміст у межах репозиторію.
24
-
25
- ## Гарантії поведінки
26
-
27
- - Read-only: не виконує операцій запису (ФС/БД).
28
- - Свідомо пропускає шляхи: `.github`, `.git`.
@@ -1,9 +0,0 @@
1
- ---
2
- type: Directory Index
3
- title: npm/rules/npm-module/npm_publish_yml
4
- resource: npm/rules/npm-module/npm_publish_yml/
5
- ---
6
-
7
- | Файл | Тип |
8
- | ------------------------------------------------- | --------- |
9
- | [fix-npm_publish_yml.mjs](fix-npm_publish_yml.md) | JS Module |
@@ -1,8 +0,0 @@
1
- import { createTemplateFixPattern } from '../../../scripts/lib/fix/template-deep-merge.mjs'
2
-
3
- export const patterns = [
4
- createTemplateFixPattern({
5
- id: 'npm-module-npm_publish_yml-template',
6
- targetPath: '.github/workflows/npm-publish.yml'
7
- })
8
- ]
@@ -1,49 +0,0 @@
1
- name: npm-publish
2
-
3
- on:
4
- push:
5
- paths:
6
- - 'npm/**'
7
- branches:
8
- - main
9
-
10
- concurrency:
11
- group: ${{ github.ref }}-${{ github.workflow }}
12
- cancel-in-progress: true
13
-
14
- jobs:
15
- release-publish:
16
- runs-on: ubuntu-latest
17
- permissions:
18
- contents: write # commit-back версії + git-тег
19
- id-token: write # КРИТИЧНО для OIDC!
20
-
21
- steps:
22
- - uses: actions/checkout@v6
23
- with:
24
- persist-credentials: false
25
- fetch-depth: 0
26
-
27
- - uses: ./.github/actions/setup-bun-deps
28
-
29
- - uses: actions/setup-node@v6
30
- with:
31
- node-version: '24' # includes npm@11.6.0
32
- registry-url: 'https://registry.npmjs.org'
33
-
34
- - name: Configure git identity + push auth
35
- # persist-credentials лишається false (ga-rule, безпека): checkout не зберігає токен.
36
- # Release робить commit-back `git push`, тож даємо job-scoped ephemeral GITHUB_TOKEN
37
- # явно через remote-url (а не persisted у git config усього прогону).
38
- run: |
39
- git config user.name "github-actions[bot]"
40
- git config user.email "github-actions[bot]@users.noreply.github.com"
41
- git remote set-url origin "https://x-access-token:${{ secrets.GITHUB_TOKEN }}@github.com/${{ github.repository }}.git"
42
-
43
- - name: Release (bump + CHANGELOG + tag)
44
- run: bunx n-rules release
45
-
46
- - name: Publish package
47
- uses: JS-DevTools/npm-publish@v4.1.5
48
- with:
49
- package: npm/package.json
@@ -1,12 +0,0 @@
1
- {
2
- "$schema": "https://unpkg.com/@7n/rules/schemas/concern.json",
3
- "fixability": "config",
4
- "policy": {
5
- "files": {
6
- "single": ".github/workflows/lint-php.yml"
7
- }
8
- },
9
- "requires": {
10
- "capability": "ci:github"
11
- }
12
- }
@@ -1,28 +0,0 @@
1
- ---
2
- type: JS Module
3
- title: fix-lint_php_yml.mjs
4
- resource: npm/rules/php/lint_php_yml/fix-lint_php_yml.mjs
5
- docgen:
6
- crc: d0335dac
7
- model: openai-codex/gpt-5.4-mini
8
- tier: cloud-min
9
- score: 100
10
- issues: judge:inaccurate:0.99
11
- judgeModel: openai-codex/gpt-5.4-mini
12
- ---
13
-
14
- ## Огляд
15
-
16
- `patterns` описує правила для робочих шляхів у межах репозиторію та свідомо пропускає `.github` і `.git`. Функція працює read-only і не пише у ФС чи БД.
17
-
18
- ## Поведінка
19
-
20
- 1. `patterns` визначає набір правил для узгодженого виправлення шаблону `lint-php.yml` у межах репозиторію.
21
- 2. `patterns` орієнтований на підтримку одного цільового workflow-файлу в `.github/workflows/lint-php.yml`, свідомо обходячи службові шляхи `.github` і `.git`.
22
- 3. `patterns` працює в режимі read-only: він формує опис змін, але не виконує запис у файлову систему чи базу даних.
23
- 4. `patterns` потрібен для стандартизації та відновлення очікуваного стану workflow-конфігурації без втручання в інші частини проєкту.
24
-
25
- ## Гарантії поведінки
26
-
27
- - Read-only: не виконує операцій запису (ФС/БД).
28
- - Свідомо пропускає шляхи: `.github`, `.git`.
@@ -1,9 +0,0 @@
1
- ---
2
- type: Directory Index
3
- title: npm/rules/php/lint_php_yml
4
- resource: npm/rules/php/lint_php_yml/
5
- ---
6
-
7
- | Файл | Тип |
8
- | ------------------------------------------- | --------- |
9
- | [fix-lint_php_yml.mjs](fix-lint_php_yml.md) | JS Module |
@@ -1,5 +0,0 @@
1
- import { createTemplateFixPattern } from '../../../scripts/lib/fix/template-deep-merge.mjs'
2
-
3
- export const patterns = [
4
- createTemplateFixPattern({ id: 'php-lint_php_yml-template', targetPath: '.github/workflows/lint-php.yml' })
5
- ]
@@ -1,23 +0,0 @@
1
- ## Структура `.github/workflows/lint-php.yml`
2
-
3
- Rego-пакет: `php.lint_php_yml`
4
-
5
- Цільовий файл: `.github/workflows/lint-php.yml` (парситься як YAML).
6
-
7
- Перевіряє, що у workflow присутні всі канонічні `run:`-кроки з template-сніпету — крок `n-rules lint php --no-fix` має бути в одному зі steps jobs.
8
-
9
- Канонічний template-сніпет: [lint-php.yml.snippet.yml](./template/lint-php.yml.snippet.yml)
10
-
11
- **✓ Правильно** — job `php` містить крок:
12
-
13
- ```yaml
14
- - name: Lint PHP
15
- run: n-rules lint php --no-fix
16
- ```
17
-
18
- **✗ Неправильно** — крок відсутній або містить інший run-рядок:
19
-
20
- ```yaml
21
- - name: Lint PHP
22
- run: echo something
23
- ```
@@ -1,34 +0,0 @@
1
- # Перевірка `lint-php.yml` (php.mdc).
2
- #
3
- # Канон надходить через --data: { "template": { "snippet": ... } }
4
- # Структура --data сформована з template/lint-php.yml.snippet.yml.
5
- # Маркер `run:` збирається з template's php-job steps.
6
- # Універсальні workflow-перевірки — у `ga.workflow_common`.
7
- package php.lint_php_yml
8
-
9
- import rego.v1
10
-
11
- # Очікуваний `run:` маркер — конкатенація всіх run-блоків з template.
12
- expected_run_blob := concat("\n", [r |
13
- some step in data.template.snippet.jobs.php.steps
14
- r := object.get(step, "run", "")
15
- r != ""
16
- ])
17
-
18
- all_run_text := concat("\n", [run_text |
19
- some job in object.get(input, "jobs", {})
20
- some step in object.get(job, "steps", [])
21
- run_text := step_run_to_text(step)
22
- ])
23
-
24
- deny contains msg if {
25
- expected_run_blob != ""
26
- not contains(all_run_text, expected_run_blob)
27
- msg := sprintf("lint-php.yml: жоден крок run не містить %q (php.mdc)", [expected_run_blob])
28
- }
29
-
30
- step_run_to_text(step) := step.run if is_string(step.run)
31
-
32
- else := concat("\n", [s | some s in step.run]) if is_array(step.run)
33
-
34
- else := ""
@@ -1,47 +0,0 @@
1
- name: Lint PHP
2
-
3
- on:
4
- push:
5
- branches:
6
- - dev
7
- - main
8
- paths:
9
- - '**/*.php'
10
- - 'composer.json'
11
- - 'composer.lock'
12
- - 'phpstan.neon'
13
- - 'phpstan.neon.dist'
14
- - 'psalm.xml'
15
- - '.github/workflows/lint-php.yml'
16
-
17
- pull_request:
18
- branches:
19
- - dev
20
- - main
21
-
22
- concurrency:
23
- group: ${{ github.ref }}-${{ github.workflow }}
24
- cancel-in-progress: true
25
-
26
- jobs:
27
- php:
28
- runs-on: ubuntu-latest
29
- permissions:
30
- contents: read
31
- steps:
32
- - uses: actions/checkout@v6
33
- with:
34
- persist-credentials: false
35
-
36
- - uses: ./.github/actions/setup-bun-deps
37
-
38
- - name: Install PHP
39
- uses: shivammathur/setup-php@v2
40
- with:
41
- php-version: '8.5'
42
-
43
- - name: Install Composer dependencies
44
- run: composer install --no-interaction --no-progress --prefer-dist
45
-
46
- - name: Lint PHP
47
- run: bunx n-rules lint php --no-fix
@@ -1,12 +0,0 @@
1
- {
2
- "$schema": "https://unpkg.com/@7n/rules/schemas/concern.json",
3
- "fixability": "config",
4
- "policy": {
5
- "files": {
6
- "single": ".github/workflows/lint-python.yml"
7
- }
8
- },
9
- "requires": {
10
- "capability": "ci:github"
11
- }
12
- }
@@ -1,27 +0,0 @@
1
- ---
2
- type: JS Module
3
- title: fix-lint_python_yml.mjs
4
- resource: npm/rules/python/lint_python_yml/fix-lint_python_yml.mjs
5
- docgen:
6
- crc: 9ad8fb17
7
- model: openai-codex/gpt-5.4-mini
8
- tier: cloud-min
9
- score: 100
10
- issues: judge:inaccurate:0.99
11
- judgeModel: openai-codex/gpt-5.4-mini
12
- ---
13
-
14
- ## Огляд
15
-
16
- `patterns` описує стандартні правила для роботи з workflow-файлами у репозиторії, щоб узгоджувати очікувану поведінку перевірок. Модуль свідомо пропускає `.github` і `.git`, залишається read-only та не змінює файлову систему чи базу даних.
17
-
18
- ## Поведінка
19
-
20
- 1. `patterns` формує перелік стандартних правил виправлення для `lint-python.yml`, щоб уніфікувати структуру цього workflow-файла.
21
- 2. Під час роботи орієнтується на цільовий шлях `.github/workflows/lint-python.yml` і свідомо не зачіпає `.github` та `.git`.
22
- 3. Працює в read-only режимі: сам не змінює файлову систему чи базу даних, а лише описує, що треба виправити.
23
-
24
- ## Гарантії поведінки
25
-
26
- - Read-only: не виконує операцій запису (ФС/БД).
27
- - Свідомо пропускає шляхи: `.github`, `.git`.
@@ -1,9 +0,0 @@
1
- ---
2
- type: Directory Index
3
- title: npm/rules/python/lint_python_yml
4
- resource: npm/rules/python/lint_python_yml/
5
- ---
6
-
7
- | Файл | Тип |
8
- | ------------------------------------------------- | --------- |
9
- | [fix-lint_python_yml.mjs](fix-lint_python_yml.md) | JS Module |
@@ -1,5 +0,0 @@
1
- import { createTemplateFixPattern } from '../../../scripts/lib/fix/template-deep-merge.mjs'
2
-
3
- export const patterns = [
4
- createTemplateFixPattern({ id: 'python-lint_python_yml-template', targetPath: '.github/workflows/lint-python.yml' })
5
- ]