@itcase/config 1.6.67 → 1.6.69

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.
package/README.md CHANGED
@@ -18,7 +18,7 @@ npm install --save-dev @itcase/config
18
18
  - `commitlint/commitizenAdapter.js` — адаптер Commitizen (type → scope → subScope → subject)
19
19
 
20
20
  - **Husky** — общие git-хуки в `husky-hooks/`
21
- - Логика хуков живёт в пакете; бинарь `itcase-config-husky-hooks` ставится при `npm i`. В репозитории остаются файлы `.husky/<hook>` и локальный `.husky/config`
21
+ - В git только `.husky/config`; обёртки и `_run.sh` создаёт `itcase-config-husky-install` при `npm i`
22
22
 
23
23
  - **Lint-staged** — запуск линтеров для измененных файлов
24
24
  - `lint-staged/index.js` — базовая конфигурация
@@ -85,30 +85,40 @@ npm install --save-dev commitizen @commitlint/cz-commitlint
85
85
 
86
86
  ## Подключение Husky
87
87
 
88
- В репозитории остаются файлы, на которые опираются git и husky. Логика лежит в `@itcase/config/husky-hooks`. При установке пакета npm кладёт бинарь `itcase-config-husky-hooks` в `node_modules/.bin` — husky уже добавляет этот путь в `PATH`.
88
+ В git кладите только `.husky/config`. Обёртки хуков и `_run.sh` создаёт `itcase-config-husky-install` при `npm i`. Логика хуков живёт в `@itcase/config/husky-hooks`.
89
89
 
90
- При `npm i` пакет копирует `.husky/_run.sh` и создаёт недостающие обёртки хуков. Свои полные хуки не перезаписывает. Добавьте в `.gitignore`:
91
-
92
- ```gitignore
93
- .husky/_run.sh
90
+ ```json
91
+ {
92
+ "scripts": {
93
+ "prepare": "husky && itcase-config-husky-install"
94
+ }
95
+ }
94
96
  ```
95
97
 
96
- Репы без обёрток и без одного только `.husky/config` скрипт не трогает. `npm i --ignore-scripts` файлы не создаст.
98
+ Пока бинарь ещё не в установленной версии пакета:
97
99
 
98
- В каждом git-hook оставьте обёртку:
100
+ ```json
101
+ {
102
+ "scripts": {
103
+ "prepare": "husky && node node_modules/@itcase/config/husky-hooks/install-launcher.js"
104
+ }
105
+ }
106
+ ```
99
107
 
100
- ```sh
101
- #!/usr/bin/env sh
102
- . "$(dirname "$0")/_run.sh"
108
+ В `.gitignore`:
109
+
110
+ ```gitignore
111
+ .husky/*
112
+ !.husky/config
103
113
  ```
104
114
 
105
- Нужны: `pre-commit`, `commit-msg`, `prepare-commit-msg`, `pre-push`, `post-merge`, `post-commit`. `set-release-message` тоже можно обернуть — его вызывает `post-merge`.
115
+ `itcase-config-husky-install` копирует `_run.sh`, создаёт обёртки и при отсутствии восстанавливает `config` из `config.example`. Свои полные хуки не перезаписывает. `npm i --ignore-scripts` файлы не создаст.
106
116
 
107
- Локальный `.husky/config` не оборачивайте. Образец: `husky-hooks/config.example`.
117
+ `.husky/config`:
108
118
 
109
119
  ```bash
110
120
  PROTECTED_BRANCHES="master"
111
121
  RELEASE_BRANCHES="master"
112
122
  ```
113
123
 
114
- `prepare` в `package.json` как обычно: `"prepare": "husky"`.
124
+ Образец: `husky-hooks/config.example`.
@@ -56,6 +56,13 @@ function isOldItcaseHook(text) {
56
56
  return text.includes('GIT_WORKFLOW') && text.includes('/config')
57
57
  }
58
58
 
59
+ function isEmptyHuskyDir(huskyDir) {
60
+ const names = fs
61
+ .readdirSync(huskyDir)
62
+ .filter((name) => name !== '_' && name !== '.DS_Store')
63
+ return names.length === 0
64
+ }
65
+
59
66
  function isItcaseHuskyDir(huskyDir) {
60
67
  if (fs.existsSync(path.join(huskyDir, 'config'))) {
61
68
  return true
@@ -65,6 +72,10 @@ function isItcaseHuskyDir(huskyDir) {
65
72
  return true
66
73
  }
67
74
 
75
+ if (isEmptyHuskyDir(huskyDir)) {
76
+ return true
77
+ }
78
+
68
79
  const hookContents = GIT_HOOKS.map((name) => readHook(huskyDir, name))
69
80
  return hookContents.some(
70
81
  (text) => text?.includes('_run.sh') || isOldItcaseHook(text),
@@ -75,9 +86,23 @@ function shouldWriteWrapper(text) {
75
86
  return text === null || text.includes('_run.sh') || isOldItcaseHook(text)
76
87
  }
77
88
 
78
- function writeWrapper(huskyDir, name) {
79
- const dest = path.join(huskyDir, name)
80
- fs.writeFileSync(dest, WRAPPER)
89
+ function writeExecutable(dest, contents) {
90
+ fs.writeFileSync(dest, contents)
91
+ try {
92
+ fs.chmodSync(dest, 0o755)
93
+ } catch {
94
+ // Windows may not support chmod; Git Bash still runs the file via sh.
95
+ }
96
+ }
97
+
98
+ function ensureConfig(huskyDir) {
99
+ const dest = path.join(huskyDir, 'config')
100
+ if (fs.existsSync(dest)) {
101
+ return
102
+ }
103
+
104
+ const example = path.join(import.meta.dirname, 'config.example')
105
+ fs.copyFileSync(example, dest)
81
106
  try {
82
107
  fs.chmodSync(dest, 0o755)
83
108
  } catch {
@@ -91,16 +116,14 @@ if (!fs.existsSync(huskyDir) || !isItcaseHuskyDir(huskyDir)) {
91
116
  process.exit(0)
92
117
  }
93
118
 
94
- const src = path.join(import.meta.dirname, '_run.sh')
95
- fs.copyFileSync(src, path.join(huskyDir, '_run.sh'))
96
- try {
97
- fs.chmodSync(path.join(huskyDir, '_run.sh'), 0o755)
98
- } catch {
99
- // Windows may not support chmod; Git Bash still runs the file via sh.
100
- }
119
+ writeExecutable(
120
+ path.join(huskyDir, '_run.sh'),
121
+ fs.readFileSync(path.join(import.meta.dirname, '_run.sh')),
122
+ )
123
+ ensureConfig(huskyDir)
101
124
 
102
125
  for (const name of GIT_HOOKS) {
103
126
  if (shouldWriteWrapper(readHook(huskyDir, name))) {
104
- writeWrapper(huskyDir, name)
127
+ writeExecutable(path.join(huskyDir, name), WRAPPER)
105
128
  }
106
129
  }
package/package.json CHANGED
@@ -1,16 +1,17 @@
1
1
  {
2
2
  "name": "@itcase/config",
3
- "version": "1.6.67",
3
+ "version": "1.6.69",
4
4
  "author": "ITCase",
5
5
  "description": "ITCase Config",
6
6
  "engines": {
7
7
  "node": ">=22.0.0"
8
8
  },
9
9
  "bin": {
10
- "itcase-config-husky-hooks": "./husky-hooks/run.js"
10
+ "itcase-config-husky-hooks": "./husky-hooks/run.js",
11
+ "itcase-config-husky-install": "./husky-hooks/install-launcher.js"
11
12
  },
12
13
  "scripts": {
13
- "prepare": "husky",
14
+ "prepare": "husky && node ./husky-hooks/install-launcher.js",
14
15
  "postinstall": "node ./husky-hooks/install-launcher.js",
15
16
  "semantic-release": "semantic-release"
16
17
  },