@rt-tools/agent-kit 0.5.2 → 0.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 (52) hide show
  1. package/README.md +34 -6
  2. package/assets/checks/check-file-size.mjs +127 -0
  3. package/assets/checks/rt-kit-checks.config.mjs +10 -0
  4. package/assets/defaults/gate-map.sh +90 -34
  5. package/assets/defaults/project.sh +26 -3
  6. package/assets/hooks/skill-gate-layers.sh +156 -0
  7. package/assets/hooks/skill-gate.sh +11 -2
  8. package/assets/laws/code-structure.md +3 -0
  9. package/assets/laws/delivery.md +9 -0
  10. package/assets/laws/observability.md +46 -0
  11. package/assets/laws/project-documentation.md +4 -0
  12. package/assets/laws/reuse-first.md +2 -0
  13. package/assets/laws/verifiability.md +5 -0
  14. package/assets/patterns/browser-verification-stand.md +22 -2
  15. package/assets/patterns/doc-style-trace.md +111 -0
  16. package/assets/patterns/git-workflow-commit.github.md +1 -1
  17. package/assets/patterns/git-workflow-docker.md +203 -0
  18. package/assets/patterns/git-workflow-secrets.md +93 -0
  19. package/assets/patterns/observability-record.md +114 -0
  20. package/assets/patterns/ownership-session-procedure.md +102 -0
  21. package/assets/patterns/seo-verify.md +1 -1
  22. package/assets/patterns/spec-driven-rule.md +5 -0
  23. package/assets/patterns/styling-bem-sheet.md +178 -0
  24. package/assets/patterns/task-flow-close.md +20 -0
  25. package/assets/patterns/task-flow-resume.md +5 -0
  26. package/assets/patterns/translations-content.md +107 -0
  27. package/assets/patterns/translations-key.md +1 -1
  28. package/assets/rules/angular-patterns.md +5 -0
  29. package/assets/rules/browser-verification.md +17 -12
  30. package/assets/rules/component-structure.md +6 -2
  31. package/assets/rules/doc-style.md +16 -0
  32. package/assets/rules/git-workflow.azure.md +45 -1
  33. package/assets/rules/git-workflow.github.md +52 -1
  34. package/assets/rules/git-workflow.gitlab.md +46 -1
  35. package/assets/rules/lists.md +13 -0
  36. package/assets/rules/observability.md +147 -0
  37. package/assets/rules/ownership-scope.md +5 -2
  38. package/assets/rules/ownership-session.md +124 -0
  39. package/assets/rules/permissions.md +23 -0
  40. package/assets/rules/pricing.md +4 -0
  41. package/assets/rules/reuse-first.md +9 -0
  42. package/assets/rules/seo.md +57 -9
  43. package/assets/rules/shared-code.md +6 -0
  44. package/assets/rules/spec-driven.md +9 -0
  45. package/assets/rules/styling-bem.md +34 -1
  46. package/assets/rules/task-flow.md +5 -0
  47. package/assets/rules/testing.md +46 -8
  48. package/assets/rules/translations.md +11 -5
  49. package/assets/rules/typescript-conventions.md +5 -0
  50. package/package.json +1 -1
  51. package/rt-tools-agent-kit-0.6.0.tgz +0 -0
  52. package/rt-tools-agent-kit-0.5.2.tgz +0 -0
@@ -2,7 +2,7 @@
2
2
  name: testing
3
3
  kind: rule
4
4
  law: verifiability
5
- description: Правило под «Закон о проверяемости». Брать при правке любого *.spec.ts и всего, что лежит в apps/site-e2e и apps/admin-e2e. Называет Vitest и Playwright, идентификатор сценария в заголовке, вынос решения в чистую функцию и то, что закрывается сквозной спекой. Готовый код — в паттернах testing-unit и testing-e2e.
5
+ description: Правило под «Закон о проверяемости». Брать при правке любого *.spec.ts и всего, что лежит в сквозных наборах дерева. Называет Vitest и Playwright, идентификатор сценария в заголовке, вынос решения в чистую функцию и то, что закрывается сквозной спекой. Готовый код — в паттернах testing-unit и testing-e2e.
6
6
  ---
7
7
 
8
8
  # Проверяемость — как это устроено здесь
@@ -45,8 +45,21 @@ description: Правило под «Закон о проверяемости».
45
45
  переименованный или выкинутый сценарий: тесты при этом остаются зелёными.
46
46
  - **Решение выносится в чистую функцию и проверяется вызовом.** Компонент и сервис остаются
47
47
  тонкой обёрткой и отдельно не проверяются, пока своего ветвления у них нет.
48
+ - **Решение, зависящее от текущего момента, принимает момент параметром.** Часы машины оно не
49
+ читает: правило проверяется вызовом, а не подкруткой времени вокруг теста. Умолчание
50
+ `= new Date()` ставится на границе — там, где решение зовёт процедура или служба.
48
51
  - **Процедура Connect проверяется вызовом своего метода с рукописным двойником базы.**
49
52
  Контейнер и роутер поднимать не надо: спека проверяет решение, а не раскладку полей.
53
+ - **Сид заводит то, без чего экран не открыть, и ничего, что гость примет за настоящее.**
54
+ Содержимое, у которого есть автор, — отзывы, вопросы, обсуждения — гость читает как
55
+ написанное людьми, а стенд собирается из той же базы, что и проверка глазами: три выдуманные
56
+ цитаты дожили до отдельной задачи и всё это время выглядели отзывами. Настройки владельца —
57
+ контакты, адрес отправителя, ключи внешних служб — сид не заводит тоже: их вписывают в
58
+ приложении. То, что нужно редко, включается признаком в окружении, а не сеется всем.
59
+ - **Заведённая проверка встаёт в гейт пуша или в конвейер, а не только в сводную цель.**
60
+ Сводная цель запускается руками, и проверка, которая живёт только в ней, отвечает тому, кто
61
+ её вспомнил: молчание такой проверки читается как её зелёный ответ. Три проверки простояли
62
+ вне гейта, объявляя в собственных списках известного, что падают на новом.
50
63
  - **Спека, необратимо меняющая данные стенда, выключена по умолчанию.** `BASE_URL` уводит
51
64
  прогон одной переменной, и без выключателя такая спека правила бы данные чужого стенда.
52
65
  - **Спеки, которым нужен nginx перед приложением, просыпаются вместе с `BASE_URL`.** Голый
@@ -56,6 +69,24 @@ description: Правило под «Закон о проверяемости».
56
69
  `playwright/no-skipped-test` запретил бы его сразу в шестидесяти пяти местах. Рядом со
57
70
  строкой отключения пишут причину, а точечный `eslint-disable` остаётся для того, что
58
71
  запрещено по делу.
72
+ - **Гард отпускает действие, когда сам сломался.** Нет разборщика входа, пустой ввод, не тот
73
+ каталог, любая своя ошибка — гард выходит нулём и пропускает: сломанная проверка не имеет
74
+ права заклинить работу. Объявляется это строкой `FAIL-OPEN` в шапке самого гарда, рядом с
75
+ перечислением случаев, и туда же дописывается новый случай, когда он находится.
76
+ - **Список известного у проверки именной и объясняет себя сам.** Первым полем перечня стоит имя
77
+ проверки и слово о том, что перечисленное отказом не считается. Дальше либо два ключа —
78
+ принятое остаётся навсегда, долг накоплен к заведению проверки и только сокращается, — либо
79
+ столько ключей, сколько у записей родов. Причина обязательна: снятая проверка без причины
80
+ через месяц неотличима от недосмотра.
81
+ - **Тест, утверждающий отсутствие, зелен и тогда, когда ищет не то.** Совпадения нет ни у
82
+ верного текста, ни у опечатки в образце, ни у переименованного ключа — отличить их по цвету
83
+ прогона нечем. Отрицательное утверждение поэтому идёт в паре с положительным: сначала
84
+ проверяется, что искомое место вообще найдено, и только потом — что в нём нет того, чего быть
85
+ не должно.
86
+ - **Заголовок теста обещает больше, чем тело проверяет, и сверка этого не видит.** Номер
87
+ сценария в заголовке стоит — сценарий числится покрытым, а что именно утверждается, не
88
+ спрашивает никто. Тело читается вместе с заголовком: обещание в заголовке и утверждение в
89
+ теле — два разных текста, и расходятся они молча.
59
90
 
60
91
  ## Чего из закона здесь нет
61
92
 
@@ -76,23 +107,30 @@ description: Правило под «Закон о проверяемости».
76
107
  - **Зелёный `nx test <проект>` не значит, что хоть один файл исполнялся.** Либа без своего
77
108
  `vitest.config.mts` не запускает ничего — так тесты домена броней не запускались ни разу.
78
109
  Либа с конфигом, но без единого `*.spec.ts`, проходит зелёной из-за `passWithNoTests: true`,
79
- который стоит во всех 203 конфигах дерева, и на глаз эти два случая неотличимы: в обоих
80
- прогон успешен. Без единого теста живут 131 либа из 203 почти две трети. Перед правкой в
110
+ который обычно стоит в каждом конфиге дерева, и на глаз эти два случая неотличимы: в обоих
111
+ прогон успешен. Доля либ без единого теста меряется пересчётом нижев дереве, где его
112
+ завели впервые, она вышла почти в две трети. Перед правкой в
81
113
  незнакомой либе проверяется, есть ли в ней хоть один `*.spec.ts`; если нет — первый
82
114
  заводится этой же правкой, а не откладывается: откладывать здесь не с чего, долг уже
83
115
  накоплен. Пересчёт: `for d in $(find libs -name vitest.config.mts -exec dirname {} \;); do
84
116
  [ -z "$(find "$d" -name '*.spec.ts')" ] && echo "$d"; done | wc -l`.
117
+ - **Зелёная сводка покрытия не значит, что тесты проходят.** Сверка читает заголовки тестов и
118
+ сопоставляет их со сценариями спека; исполняется ли тест и чем он кончается — она не знает
119
+ вовсе, и падающий тест значится в ней покрытием. Три сценария одной панели падали и до правки
120
+ экрана, а нашлось это только прогоном. Перед правкой экрана его сквозные тесты гоняются один
121
+ раз до первой строки кода: иначе чужое падение читается как своя регрессия, а своё — как
122
+ чужое.
85
123
  - **«Executable doesn't exist» — состояние машины, а не дефект правки.** Установлен только
86
124
  chromium, `firefox` и `webkit` падают всегда: гонять `--project=chromium`, узкий экран —
87
125
  `--project=mobile-chrome`. Та же ошибка приходит после смены версии Playwright: браузер
88
126
  ставится под конкретную версию, и после подъёма нужен повторный
89
127
  `npx playwright install chromium`. Девять тестов так и упали, и это выглядело регрессией
90
128
  обновления.
91
- - **Первому прогону сразу после установки браузера верить нельзя.** Два падения `admin-e2e`
92
- не повторились ни при отдельном прогоне тех же тестов, ни при втором полном. Такой прогон
93
- повторяют, а выводы делают по второму.
94
- - Сквозные тесты админки без `E2E_ADMIN_EMAIL` и `E2E_ADMIN_PASSWORD` пропускаются молча — в
95
- отчёте они значатся `skipped`, и прогон выглядит успешным.
129
+ - **Первому прогону сразу после установки браузера верить нельзя.** Два падения сквозного
130
+ набора не повторились ни при отдельном прогоне тех же тестов, ни при втором полном. Такой
131
+ прогон повторяют, а выводы делают по второму.
132
+ - Сквозная спека, которой нужен вход, без учётных данных в окружении пропускается молча — в
133
+ отчёте она значится `skipped`, и прогон выглядит успешным. Имена переменных — при дереве.
96
134
  - **Справочник флоу вторых сценариев не заводит.** В `docs/E2E_<ДОМЕН>_FLOWS.md` кладут то,
97
135
  чего в спеке домена нет и быть не должно: `qa-dataid` элементов, состояния разметки, ловушки
98
136
  стенда. Обещанное поведение остаётся сценарием в `scenarios.md`: если списать его во второе
@@ -2,7 +2,7 @@
2
2
  name: translations
3
3
  kind: rule
4
4
  law: locales
5
- description: Правило под «Закон о локалях и переводах». Брать при заведении любого видимого текста, правке словарей libs/common/i18n, префиксов локалей сайта и перевода контента объекта. Называет восемь локалей, Transloco, производные переводы и начальную валюту локали. Готовый код — в паттерне translations-key.
5
+ description: Правило под «Закон о локалях и переводах». Брать при заведении любого видимого текста, правке словарей libs/common/i18n, префиксов локалей сайта и перевода контента объекта. Называет локали перевода, словари, производные переводы и начальную валюту локали. Готовый код — в паттерне translations-key.
6
6
  ---
7
7
 
8
8
  # Локали и переводы — как это устроено здесь
@@ -15,7 +15,7 @@ description: Правило под «Закон о локалях и перев
15
15
 
16
16
  | В законе | Здесь |
17
17
  | -------------------- | --------------------------------------------------------------------------------------------------- |
18
- | локаль сайта | одна из восьми: `en`, `ru`, `de`, `zh-Hans`, `zh-Hant`, `ko`, `th`, `hi` |
18
+ | локаль сайта | одна из локалей перевода; их набор в `implementation.md` рядом |
19
19
  | локаль по умолчанию | `en` — отдаётся из корня, без префикса в адресе |
20
20
  | локаль ввода | `source_locale` в запросе сохранения объекта; берётся из языка админки |
21
21
  | словарь | JSON-словари Transloco в `libs/common/i18n/src/lib/dictionaries/<локаль>/`, разложенные по разделам |
@@ -54,6 +54,8 @@ description: Правило под «Закон о локалях и перев
54
54
  ## Паттерны
55
55
 
56
56
  - `translations-key` — заведение ключа во всех локалях перевода и подстановка в разметку.
57
+ - `translations-content` — перевод содержимого записи: производный перевод, запись локали
58
+ руками, отказ провайдера, сброс кэша отданных страниц.
57
59
 
58
60
  ## Ловушки
59
61
 
@@ -63,7 +65,11 @@ description: Правило под «Закон о локалях и перев
63
65
  на общий, сайт, письма и админку.
64
66
  - **Перевод контента идёт до транзакции сохранения:** страница объекта не должна оказаться
65
67
  наполовину переведённой. Кэш сбрасывается после записи и один раз.
66
- - **Без ключа `ANTHROPIC_API_KEY` сохранение проходит,** но переводы остаются прежними, и
67
- владелец видит предупреждение `propertySaveTranslationFailed`.
68
+ - **Без ключа переводов сохранение проходит,** но переводы остаются прежними, и владелец видит
69
+ предупреждение об этом на своём экране. Ключ лежит секретом владения в хранилище, а не
70
+ переменной окружения, и заводит его владелец экраном интеграций: одноимённая переменная в
71
+ составе прода приложением не читается. Состояния ключа — паттерн `git-workflow-secrets`.
72
+ - **Ветки локалей надеты не на все маршруты сайта, и новый раздел в них не попадает** —
73
+ раскладка, её ловушка и готовый код лежат в правиле `seo` и паттерне `seo-page`.
68
74
  - Новый маршрут сайта без ветки под каждую локаль существует только в локали по умолчанию:
69
- `/de/<путь>` отдаст 404 и поисковику, и гостю.
75
+ путь под префиксом другой локали отдаст 404 и поисковику, и гостю.
@@ -33,6 +33,11 @@ description: Правило под «Закон об устройстве код
33
33
  различаются в месте использования, а не переходом к объявлению.
34
34
  - **Суффикс имени файла находит в нём обещанное объявление.** Список суффиксов закрыт: слово,
35
35
  которого в нём нет, суффиксом не считается, и такой файл правило не судит.
36
+ - **Файл не длиннее 500 строк, и считаются все строки — пустые и комментарии тоже.** Файл,
37
+ который не влезает на экран целиком, читают по частям, и правку в нём делают, не увидев
38
+ остального. Для `.ts` это держит правило линтера; файлы обвязки — сценарии и скрипты — до
39
+ него не доходят и судятся отдельной проверкой дерева. Накопленное к дню включения
40
+ перечислено поимённо, и строка оттуда снимается вместе с делением своего файла.
36
41
  - **Тип берётся из того пакета, где объявлен.** Своя копия чужого типа расходится с оригиналом
37
42
  молча, а компилируется из них только одна.
38
43
  - **Двухступенчатое приведение `as unknown as` запрещено правилом линтера.** Вместо него —
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@rt-tools/agent-kit",
3
- "version": "0.5.2",
3
+ "version": "0.6.0",
4
4
  "description": "Переносимый слой правил для агента: законы, хуки, проверки и агенты, раскладываемые в репозиторий одной командой",
5
5
  "author": "RT Team",
6
6
  "license": "Apache-2.0",
Binary file
Binary file