@camaradesuk/git-worktree-tools 1.5.0 → 1.7.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 (274) hide show
  1. package/README.md +330 -370
  2. package/dist/cli/cleanpr.js +35 -4
  3. package/dist/cli/cleanpr.js.map +1 -1
  4. package/dist/cli/cleanpr.test.js +256 -0
  5. package/dist/cli/cleanpr.test.js.map +1 -1
  6. package/dist/cli/lswt.js +54 -6
  7. package/dist/cli/lswt.js.map +1 -1
  8. package/dist/cli/lswt.test.js +207 -0
  9. package/dist/cli/lswt.test.js.map +1 -1
  10. package/dist/cli/newpr.js +135 -76
  11. package/dist/cli/newpr.js.map +1 -1
  12. package/dist/cli/newpr.test.js +35 -16
  13. package/dist/cli/newpr.test.js.map +1 -1
  14. package/dist/cli/wt/clean.d.ts +17 -0
  15. package/dist/cli/wt/clean.d.ts.map +1 -0
  16. package/dist/cli/wt/clean.js +74 -0
  17. package/dist/cli/wt/clean.js.map +1 -0
  18. package/dist/cli/wt/completion.d.ts +12 -0
  19. package/dist/cli/wt/completion.d.ts.map +1 -0
  20. package/dist/cli/wt/completion.js +246 -0
  21. package/dist/cli/wt/completion.js.map +1 -0
  22. package/dist/cli/wt/completion.test.d.ts +5 -0
  23. package/dist/cli/wt/completion.test.d.ts.map +1 -0
  24. package/dist/cli/wt/completion.test.js +173 -0
  25. package/dist/cli/wt/completion.test.js.map +1 -0
  26. package/dist/cli/wt/config.d.ts +13 -0
  27. package/dist/cli/wt/config.d.ts.map +1 -0
  28. package/dist/cli/wt/config.js +175 -0
  29. package/dist/cli/wt/config.js.map +1 -0
  30. package/dist/cli/wt/config.test.d.ts +5 -0
  31. package/dist/cli/wt/config.test.d.ts.map +1 -0
  32. package/dist/cli/wt/config.test.js +260 -0
  33. package/dist/cli/wt/config.test.js.map +1 -0
  34. package/dist/cli/wt/entry.test.d.ts +8 -0
  35. package/dist/cli/wt/entry.test.d.ts.map +1 -0
  36. package/dist/cli/wt/entry.test.js +201 -0
  37. package/dist/cli/wt/entry.test.js.map +1 -0
  38. package/dist/cli/wt/init.d.ts +14 -0
  39. package/dist/cli/wt/init.d.ts.map +1 -0
  40. package/dist/cli/wt/init.js +209 -0
  41. package/dist/cli/wt/init.js.map +1 -0
  42. package/dist/cli/wt/init.test.d.ts +5 -0
  43. package/dist/cli/wt/init.test.d.ts.map +1 -0
  44. package/dist/cli/wt/init.test.js +165 -0
  45. package/dist/cli/wt/init.test.js.map +1 -0
  46. package/dist/cli/wt/init.unit.test.d.ts +5 -0
  47. package/dist/cli/wt/init.unit.test.d.ts.map +1 -0
  48. package/dist/cli/wt/init.unit.test.js +432 -0
  49. package/dist/cli/wt/init.unit.test.js.map +1 -0
  50. package/dist/cli/wt/interactive-menu.d.ts +41 -0
  51. package/dist/cli/wt/interactive-menu.d.ts.map +1 -0
  52. package/dist/cli/wt/interactive-menu.js +639 -0
  53. package/dist/cli/wt/interactive-menu.js.map +1 -0
  54. package/dist/cli/wt/interactive-menu.test.d.ts +10 -0
  55. package/dist/cli/wt/interactive-menu.test.d.ts.map +1 -0
  56. package/dist/cli/wt/interactive-menu.test.js +711 -0
  57. package/dist/cli/wt/interactive-menu.test.js.map +1 -0
  58. package/dist/cli/wt/link.d.ts +22 -0
  59. package/dist/cli/wt/link.d.ts.map +1 -0
  60. package/dist/cli/wt/link.js +115 -0
  61. package/dist/cli/wt/link.js.map +1 -0
  62. package/dist/cli/wt/list.d.ts +16 -0
  63. package/dist/cli/wt/list.d.ts.map +1 -0
  64. package/dist/cli/wt/list.js +65 -0
  65. package/dist/cli/wt/list.js.map +1 -0
  66. package/dist/cli/wt/new.d.ts +24 -0
  67. package/dist/cli/wt/new.d.ts.map +1 -0
  68. package/dist/cli/wt/new.js +130 -0
  69. package/dist/cli/wt/new.js.map +1 -0
  70. package/dist/cli/wt/run-command.d.ts +31 -0
  71. package/dist/cli/wt/run-command.d.ts.map +1 -0
  72. package/dist/cli/wt/run-command.js +49 -0
  73. package/dist/cli/wt/run-command.js.map +1 -0
  74. package/dist/cli/wt/run-command.test.d.ts +5 -0
  75. package/dist/cli/wt/run-command.test.d.ts.map +1 -0
  76. package/dist/cli/wt/run-command.test.js +88 -0
  77. package/dist/cli/wt/run-command.test.js.map +1 -0
  78. package/dist/cli/wt/state.d.ts +13 -0
  79. package/dist/cli/wt/state.d.ts.map +1 -0
  80. package/dist/cli/wt/state.js +38 -0
  81. package/dist/cli/wt/state.js.map +1 -0
  82. package/dist/cli/wt/wt.test.d.ts +8 -0
  83. package/dist/cli/wt/wt.test.d.ts.map +1 -0
  84. package/dist/cli/wt/wt.test.js +521 -0
  85. package/dist/cli/wt/wt.test.js.map +1 -0
  86. package/dist/cli/wt.d.ts +26 -0
  87. package/dist/cli/wt.d.ts.map +1 -0
  88. package/dist/cli/wt.js +169 -0
  89. package/dist/cli/wt.js.map +1 -0
  90. package/dist/cli/wt.unit.test.d.ts +7 -0
  91. package/dist/cli/wt.unit.test.d.ts.map +1 -0
  92. package/dist/cli/wt.unit.test.js +182 -0
  93. package/dist/cli/wt.unit.test.js.map +1 -0
  94. package/dist/cli/wtconfig.js +22 -8
  95. package/dist/cli/wtconfig.js.map +1 -1
  96. package/dist/cli/wtconfig.test.js +18 -16
  97. package/dist/cli/wtconfig.test.js.map +1 -1
  98. package/dist/cli/wtlink.js +66 -9
  99. package/dist/cli/wtlink.js.map +1 -1
  100. package/dist/cli/wtlink.test.js +101 -0
  101. package/dist/cli/wtlink.test.js.map +1 -1
  102. package/dist/e2e/cli.e2e.test.js +97 -1
  103. package/dist/e2e/cli.e2e.test.js.map +1 -1
  104. package/dist/e2e/lswt/lswt.e2e.test.js +33 -0
  105. package/dist/e2e/lswt/lswt.e2e.test.js.map +1 -1
  106. package/dist/e2e/newpr/scenarios.e2e.test.js +7 -7
  107. package/dist/e2e/newpr/scenarios.e2e.test.js.map +1 -1
  108. package/dist/e2e/wt/wt.e2e.test.d.ts +9 -0
  109. package/dist/e2e/wt/wt.e2e.test.d.ts.map +1 -0
  110. package/dist/e2e/wt/wt.e2e.test.js +384 -0
  111. package/dist/e2e/wt/wt.e2e.test.js.map +1 -0
  112. package/dist/e2e/wtlink/wtlink.e2e.test.js +52 -0
  113. package/dist/e2e/wtlink/wtlink.e2e.test.js.map +1 -1
  114. package/dist/lib/ai/base-provider.d.ts +22 -0
  115. package/dist/lib/ai/base-provider.d.ts.map +1 -1
  116. package/dist/lib/ai/base-provider.js +180 -99
  117. package/dist/lib/ai/base-provider.js.map +1 -1
  118. package/dist/lib/ai/base-provider.test.js +13 -14
  119. package/dist/lib/ai/base-provider.test.js.map +1 -1
  120. package/dist/lib/ai/cli-provider.d.ts +11 -7
  121. package/dist/lib/ai/cli-provider.d.ts.map +1 -1
  122. package/dist/lib/ai/cli-provider.js +19 -49
  123. package/dist/lib/ai/cli-provider.js.map +1 -1
  124. package/dist/lib/ai/cli-provider.test.js +47 -49
  125. package/dist/lib/ai/cli-provider.test.js.map +1 -1
  126. package/dist/lib/ai/index.d.ts +2 -1
  127. package/dist/lib/ai/index.d.ts.map +1 -1
  128. package/dist/lib/ai/index.js +2 -0
  129. package/dist/lib/ai/index.js.map +1 -1
  130. package/dist/lib/ai/provider-manager.js +2 -2
  131. package/dist/lib/ai/provider-manager.js.map +1 -1
  132. package/dist/lib/ai/repo-docs.d.ts +43 -0
  133. package/dist/lib/ai/repo-docs.d.ts.map +1 -0
  134. package/dist/lib/ai/repo-docs.js +274 -0
  135. package/dist/lib/ai/repo-docs.js.map +1 -0
  136. package/dist/lib/ai/repo-docs.test.d.ts +5 -0
  137. package/dist/lib/ai/repo-docs.test.d.ts.map +1 -0
  138. package/dist/lib/ai/repo-docs.test.js +357 -0
  139. package/dist/lib/ai/repo-docs.test.js.map +1 -0
  140. package/dist/lib/ai/types.d.ts +18 -2
  141. package/dist/lib/ai/types.d.ts.map +1 -1
  142. package/dist/lib/ai/types.js.map +1 -1
  143. package/dist/lib/config-editor.d.ts +21 -0
  144. package/dist/lib/config-editor.d.ts.map +1 -0
  145. package/dist/lib/config-editor.js +729 -0
  146. package/dist/lib/config-editor.js.map +1 -0
  147. package/dist/lib/config-editor.test.d.ts +11 -0
  148. package/dist/lib/config-editor.test.d.ts.map +1 -0
  149. package/dist/lib/config-editor.test.js +526 -0
  150. package/dist/lib/config-editor.test.js.map +1 -0
  151. package/dist/lib/config-validation.d.ts +28 -0
  152. package/dist/lib/config-validation.d.ts.map +1 -0
  153. package/dist/lib/config-validation.js +534 -0
  154. package/dist/lib/config-validation.js.map +1 -0
  155. package/dist/lib/config-validation.test.d.ts +5 -0
  156. package/dist/lib/config-validation.test.d.ts.map +1 -0
  157. package/dist/lib/config-validation.test.js +398 -0
  158. package/dist/lib/config-validation.test.js.map +1 -0
  159. package/dist/lib/config.d.ts +115 -6
  160. package/dist/lib/config.d.ts.map +1 -1
  161. package/dist/lib/config.js +251 -55
  162. package/dist/lib/config.js.map +1 -1
  163. package/dist/lib/config.test.js +2 -1
  164. package/dist/lib/config.test.js.map +1 -1
  165. package/dist/lib/constants.d.ts +50 -1
  166. package/dist/lib/constants.d.ts.map +1 -1
  167. package/dist/lib/constants.js +67 -1
  168. package/dist/lib/constants.js.map +1 -1
  169. package/dist/lib/constants.test.d.ts +5 -0
  170. package/dist/lib/constants.test.d.ts.map +1 -0
  171. package/dist/lib/constants.test.js +121 -0
  172. package/dist/lib/constants.test.js.map +1 -0
  173. package/dist/lib/git.d.ts +12 -0
  174. package/dist/lib/git.d.ts.map +1 -1
  175. package/dist/lib/git.js +26 -0
  176. package/dist/lib/git.js.map +1 -1
  177. package/dist/lib/global-check.d.ts +38 -0
  178. package/dist/lib/global-check.d.ts.map +1 -0
  179. package/dist/lib/global-check.js +135 -0
  180. package/dist/lib/global-check.js.map +1 -0
  181. package/dist/lib/global-check.test.d.ts +5 -0
  182. package/dist/lib/global-check.test.d.ts.map +1 -0
  183. package/dist/lib/global-check.test.js +153 -0
  184. package/dist/lib/global-check.test.js.map +1 -0
  185. package/dist/lib/global-config.d.ts +102 -0
  186. package/dist/lib/global-config.d.ts.map +1 -0
  187. package/dist/lib/global-config.js +234 -0
  188. package/dist/lib/global-config.js.map +1 -0
  189. package/dist/lib/global-config.test.d.ts +5 -0
  190. package/dist/lib/global-config.test.d.ts.map +1 -0
  191. package/dist/lib/global-config.test.js +282 -0
  192. package/dist/lib/global-config.test.js.map +1 -0
  193. package/dist/lib/json-output.d.ts +11 -1
  194. package/dist/lib/json-output.d.ts.map +1 -1
  195. package/dist/lib/json-output.js +42 -1
  196. package/dist/lib/json-output.js.map +1 -1
  197. package/dist/lib/json-output.test.js +2 -0
  198. package/dist/lib/json-output.test.js.map +1 -1
  199. package/dist/lib/logger.d.ts +175 -0
  200. package/dist/lib/logger.d.ts.map +1 -0
  201. package/dist/lib/logger.js +475 -0
  202. package/dist/lib/logger.js.map +1 -0
  203. package/dist/lib/logger.test.d.ts +5 -0
  204. package/dist/lib/logger.test.d.ts.map +1 -0
  205. package/dist/lib/logger.test.js +292 -0
  206. package/dist/lib/logger.test.js.map +1 -0
  207. package/dist/lib/lswt/action-executors.test.js +2 -0
  208. package/dist/lib/lswt/action-executors.test.js.map +1 -1
  209. package/dist/lib/lswt/formatters.d.ts +1 -0
  210. package/dist/lib/lswt/formatters.d.ts.map +1 -1
  211. package/dist/lib/lswt/formatters.js +6 -1
  212. package/dist/lib/lswt/formatters.js.map +1 -1
  213. package/dist/lib/lswt/formatters.test.js +2 -2
  214. package/dist/lib/lswt/formatters.test.js.map +1 -1
  215. package/dist/lib/lswt/fuzzy-search.d.ts +27 -0
  216. package/dist/lib/lswt/fuzzy-search.d.ts.map +1 -0
  217. package/dist/lib/lswt/fuzzy-search.js +130 -0
  218. package/dist/lib/lswt/fuzzy-search.js.map +1 -0
  219. package/dist/lib/lswt/fuzzy-search.test.d.ts +5 -0
  220. package/dist/lib/lswt/fuzzy-search.test.d.ts.map +1 -0
  221. package/dist/lib/lswt/fuzzy-search.test.js +207 -0
  222. package/dist/lib/lswt/fuzzy-search.test.js.map +1 -0
  223. package/dist/lib/lswt/index.d.ts +1 -0
  224. package/dist/lib/lswt/index.d.ts.map +1 -1
  225. package/dist/lib/lswt/index.js +2 -0
  226. package/dist/lib/lswt/index.js.map +1 -1
  227. package/dist/lib/lswt/interactive.d.ts +8 -0
  228. package/dist/lib/lswt/interactive.d.ts.map +1 -1
  229. package/dist/lib/lswt/interactive.js +169 -20
  230. package/dist/lib/lswt/interactive.js.map +1 -1
  231. package/dist/lib/newpr/action-deps.test.d.ts +5 -0
  232. package/dist/lib/newpr/action-deps.test.d.ts.map +1 -0
  233. package/dist/lib/newpr/action-deps.test.js +111 -0
  234. package/dist/lib/newpr/action-deps.test.js.map +1 -0
  235. package/dist/lib/newpr/args.d.ts.map +1 -1
  236. package/dist/lib/newpr/args.js +15 -4
  237. package/dist/lib/newpr/args.js.map +1 -1
  238. package/dist/lib/newpr/args.test.js +210 -2
  239. package/dist/lib/newpr/args.test.js.map +1 -1
  240. package/dist/lib/newpr/types.d.ts +2 -0
  241. package/dist/lib/newpr/types.d.ts.map +1 -1
  242. package/dist/lib/prompts.d.ts +10 -0
  243. package/dist/lib/prompts.d.ts.map +1 -1
  244. package/dist/lib/prompts.js +200 -1
  245. package/dist/lib/prompts.js.map +1 -1
  246. package/dist/lib/prompts.test.js +351 -1
  247. package/dist/lib/prompts.test.js.map +1 -1
  248. package/dist/lib/schema.test.d.ts +10 -0
  249. package/dist/lib/schema.test.d.ts.map +1 -0
  250. package/dist/lib/schema.test.js +309 -0
  251. package/dist/lib/schema.test.js.map +1 -0
  252. package/dist/lib/wtconfig/environment.d.ts.map +1 -1
  253. package/dist/lib/wtconfig/environment.js +6 -4
  254. package/dist/lib/wtconfig/environment.js.map +1 -1
  255. package/dist/lib/wtconfig/environment.test.js +2 -7
  256. package/dist/lib/wtconfig/environment.test.js.map +1 -1
  257. package/dist/lib/wtconfig/types.d.ts +3 -1
  258. package/dist/lib/wtconfig/types.d.ts.map +1 -1
  259. package/dist/lib/wtlink/link-configs.test.js +282 -2
  260. package/dist/lib/wtlink/link-configs.test.js.map +1 -1
  261. package/dist/lib/wtlink/main-menu.js +1 -0
  262. package/dist/lib/wtlink/main-menu.js.map +1 -1
  263. package/dist/lib/wtlink/main-menu.test.d.ts +5 -0
  264. package/dist/lib/wtlink/main-menu.test.d.ts.map +1 -0
  265. package/dist/lib/wtlink/main-menu.test.js +124 -0
  266. package/dist/lib/wtlink/main-menu.test.js.map +1 -0
  267. package/dist/lib/wtlink/manage-manifest.d.ts +5 -0
  268. package/dist/lib/wtlink/manage-manifest.d.ts.map +1 -1
  269. package/dist/lib/wtlink/manage-manifest.js +65 -2
  270. package/dist/lib/wtlink/manage-manifest.js.map +1 -1
  271. package/dist/lib/wtlink/manage-manifest.test.js +282 -2
  272. package/dist/lib/wtlink/manage-manifest.test.js.map +1 -1
  273. package/package.json +3 -1
  274. package/schemas/worktreerc.schema.json +416 -0
@@ -0,0 +1,398 @@
1
+ /**
2
+ * Tests for config validation module
3
+ */
4
+ import { describe, it, expect } from 'vitest';
5
+ import { validateConfig, formatValidationErrors, } from './config-validation.js';
6
+ describe('validateConfig', () => {
7
+ describe('top-level properties', () => {
8
+ it('should accept valid empty config', () => {
9
+ const result = validateConfig({});
10
+ expect(result.valid).toBe(true);
11
+ expect(result.errors).toHaveLength(0);
12
+ });
13
+ it('should accept valid minimal config', () => {
14
+ const result = validateConfig({
15
+ baseBranch: 'main',
16
+ draftPr: false,
17
+ });
18
+ expect(result.valid).toBe(true);
19
+ expect(result.errors).toHaveLength(0);
20
+ });
21
+ it('should reject non-object config', () => {
22
+ const result = validateConfig('not an object');
23
+ expect(result.valid).toBe(false);
24
+ expect(result.errors[0].message).toContain('must be an object');
25
+ });
26
+ it('should reject null config', () => {
27
+ const result = validateConfig(null);
28
+ expect(result.valid).toBe(false);
29
+ });
30
+ it('should warn on unknown top-level keys', () => {
31
+ const result = validateConfig({
32
+ baseBranch: 'main',
33
+ unknownKey: 'value',
34
+ });
35
+ expect(result.valid).toBe(false);
36
+ expect(result.errors.some((e) => e.path === 'unknownKey')).toBe(true);
37
+ });
38
+ it('should validate baseBranch type', () => {
39
+ const result = validateConfig({ baseBranch: 123 });
40
+ expect(result.valid).toBe(false);
41
+ expect(result.errors.some((e) => e.path === 'baseBranch')).toBe(true);
42
+ });
43
+ it('should validate draftPr type', () => {
44
+ const result = validateConfig({ draftPr: 'yes' });
45
+ expect(result.valid).toBe(false);
46
+ expect(result.errors.some((e) => e.path === 'draftPr')).toBe(true);
47
+ });
48
+ it('should validate preferredEditor enum', () => {
49
+ const result = validateConfig({ preferredEditor: 'vim' });
50
+ expect(result.valid).toBe(false);
51
+ expect(result.errors.some((e) => e.path === 'preferredEditor')).toBe(true);
52
+ });
53
+ it('should accept valid preferredEditor values', () => {
54
+ expect(validateConfig({ preferredEditor: 'vscode' }).valid).toBe(true);
55
+ expect(validateConfig({ preferredEditor: 'cursor' }).valid).toBe(true);
56
+ expect(validateConfig({ preferredEditor: 'auto' }).valid).toBe(true);
57
+ });
58
+ });
59
+ describe('array properties', () => {
60
+ it('should accept valid sharedRepos array', () => {
61
+ const result = validateConfig({
62
+ sharedRepos: ['repo1', 'repo2'],
63
+ });
64
+ expect(result.valid).toBe(true);
65
+ });
66
+ it('should reject non-array sharedRepos', () => {
67
+ const result = validateConfig({ sharedRepos: 'repo1' });
68
+ expect(result.valid).toBe(false);
69
+ expect(result.errors.some((e) => e.path === 'sharedRepos')).toBe(true);
70
+ });
71
+ it('should reject non-string items in sharedRepos', () => {
72
+ const result = validateConfig({ sharedRepos: ['repo1', 123] });
73
+ expect(result.valid).toBe(false);
74
+ expect(result.errors.some((e) => e.path === 'sharedRepos[1]')).toBe(true);
75
+ });
76
+ it('should accept valid syncPatterns array', () => {
77
+ const result = validateConfig({
78
+ syncPatterns: ['.env.local', '.vscode/settings.json'],
79
+ });
80
+ expect(result.valid).toBe(true);
81
+ });
82
+ it('should accept valid plugins array', () => {
83
+ const result = validateConfig({
84
+ plugins: ['@worktree-tools/plugin-linear', './plugins/custom.js'],
85
+ });
86
+ expect(result.valid).toBe(true);
87
+ });
88
+ });
89
+ describe('ai config', () => {
90
+ it('should accept valid ai config', () => {
91
+ const result = validateConfig({
92
+ ai: {
93
+ provider: 'claude',
94
+ branchName: true,
95
+ prTitle: true,
96
+ prDescription: false,
97
+ commitMessage: false,
98
+ },
99
+ });
100
+ expect(result.valid).toBe(true);
101
+ });
102
+ it('should reject invalid ai provider', () => {
103
+ const result = validateConfig({
104
+ ai: { provider: 'invalid-provider' },
105
+ });
106
+ expect(result.valid).toBe(false);
107
+ expect(result.errors.some((e) => e.path === 'ai.provider')).toBe(true);
108
+ });
109
+ it('should accept all valid ai providers', () => {
110
+ const providers = [
111
+ 'auto',
112
+ 'claude',
113
+ 'gemini',
114
+ 'openai',
115
+ 'ollama',
116
+ 'script',
117
+ 'fallback',
118
+ 'none',
119
+ ];
120
+ for (const provider of providers) {
121
+ const result = validateConfig({ ai: { provider } });
122
+ expect(result.valid).toBe(true);
123
+ }
124
+ });
125
+ it('should reject non-boolean ai feature flags', () => {
126
+ const result = validateConfig({
127
+ ai: { branchName: 'yes' },
128
+ });
129
+ expect(result.valid).toBe(false);
130
+ expect(result.errors.some((e) => e.path === 'ai.branchName')).toBe(true);
131
+ });
132
+ it('should validate ai branchStyle enum', () => {
133
+ expect(validateConfig({ ai: { branchStyle: 'conventional' } }).valid).toBe(true);
134
+ expect(validateConfig({ ai: { branchStyle: 'kebab' } }).valid).toBe(true);
135
+ expect(validateConfig({ ai: { branchStyle: 'snake' } }).valid).toBe(true);
136
+ expect(validateConfig({ ai: { branchStyle: 'invalid' } }).valid).toBe(false);
137
+ });
138
+ it('should validate ai commitStyle enum', () => {
139
+ expect(validateConfig({ ai: { commitStyle: 'conventional' } }).valid).toBe(true);
140
+ expect(validateConfig({ ai: { commitStyle: 'gitmoji' } }).valid).toBe(true);
141
+ expect(validateConfig({ ai: { commitStyle: 'simple' } }).valid).toBe(true);
142
+ expect(validateConfig({ ai: { commitStyle: 'invalid' } }).valid).toBe(false);
143
+ });
144
+ it('should validate ai provider-specific configs', () => {
145
+ const result = validateConfig({
146
+ ai: {
147
+ claude: { model: 'claude-3-sonnet' },
148
+ gemini: { model: 'gemini-pro' },
149
+ ollama: { model: 'llama2', host: 'http://localhost:11434' },
150
+ },
151
+ });
152
+ expect(result.valid).toBe(true);
153
+ });
154
+ it('should require path in script config', () => {
155
+ const result = validateConfig({
156
+ ai: { script: {} },
157
+ });
158
+ expect(result.valid).toBe(false);
159
+ expect(result.errors.some((e) => e.path === 'ai.script.path')).toBe(true);
160
+ });
161
+ it('should warn on unknown ai keys', () => {
162
+ const result = validateConfig({
163
+ ai: { unknownKey: 'value' },
164
+ });
165
+ expect(result.valid).toBe(false);
166
+ expect(result.errors.some((e) => e.path === 'ai.unknownKey')).toBe(true);
167
+ });
168
+ });
169
+ describe('hooks config', () => {
170
+ it('should accept simple string hook', () => {
171
+ const result = validateConfig({
172
+ hooks: { 'post-worktree': 'npm install' },
173
+ });
174
+ expect(result.valid).toBe(true);
175
+ });
176
+ it('should accept array of commands hook', () => {
177
+ const result = validateConfig({
178
+ hooks: { 'post-worktree': ['npm install', 'npm run build'] },
179
+ });
180
+ expect(result.valid).toBe(true);
181
+ });
182
+ it('should accept complex hook object', () => {
183
+ const result = validateConfig({
184
+ hooks: {
185
+ 'post-worktree': {
186
+ command: 'npm install',
187
+ timeout: 60000,
188
+ failOnError: true,
189
+ if: 'test -f package.json',
190
+ env: { NODE_ENV: 'development' },
191
+ },
192
+ },
193
+ });
194
+ expect(result.valid).toBe(true);
195
+ });
196
+ it('should reject invalid hook name', () => {
197
+ const result = validateConfig({
198
+ hooks: { 'invalid-hook': 'echo test' },
199
+ });
200
+ expect(result.valid).toBe(false);
201
+ expect(result.errors.some((e) => e.path === 'hooks.invalid-hook')).toBe(true);
202
+ });
203
+ it('should accept all valid hook names', () => {
204
+ const hookNames = [
205
+ 'pre-analyze',
206
+ 'post-analyze',
207
+ 'pre-branch',
208
+ 'post-branch',
209
+ 'pre-commit',
210
+ 'post-commit',
211
+ 'pre-push',
212
+ 'post-push',
213
+ 'pre-pr',
214
+ 'post-pr',
215
+ 'pre-worktree',
216
+ 'post-worktree',
217
+ 'cleanup',
218
+ ];
219
+ const hooks = {};
220
+ for (const name of hookNames) {
221
+ hooks[name] = 'echo test';
222
+ }
223
+ const result = validateConfig({ hooks });
224
+ expect(result.valid).toBe(true);
225
+ });
226
+ it('should validate hook timeout is non-negative', () => {
227
+ const result = validateConfig({
228
+ hooks: { 'post-worktree': { command: 'npm install', timeout: -1 } },
229
+ });
230
+ expect(result.valid).toBe(false);
231
+ expect(result.errors.some((e) => e.path === 'hooks.post-worktree.timeout')).toBe(true);
232
+ });
233
+ it('should validate hook env values are strings', () => {
234
+ const result = validateConfig({
235
+ hooks: { 'post-worktree': { command: 'npm install', env: { KEY: 123 } } },
236
+ });
237
+ expect(result.valid).toBe(false);
238
+ });
239
+ });
240
+ describe('hookDefaults config', () => {
241
+ it('should accept valid hookDefaults', () => {
242
+ const result = validateConfig({
243
+ hookDefaults: { timeout: 30000, maxTimeout: 60000 },
244
+ });
245
+ expect(result.valid).toBe(true);
246
+ });
247
+ it('should reject negative timeout', () => {
248
+ const result = validateConfig({
249
+ hookDefaults: { timeout: -1 },
250
+ });
251
+ expect(result.valid).toBe(false);
252
+ });
253
+ it('should warn on unknown hookDefaults keys', () => {
254
+ const result = validateConfig({
255
+ hookDefaults: { unknownKey: 'value' },
256
+ });
257
+ expect(result.valid).toBe(false);
258
+ });
259
+ });
260
+ describe('generators config', () => {
261
+ it('should accept valid generators config', () => {
262
+ const result = validateConfig({
263
+ generators: {
264
+ branchName: './scripts/branch-name.js',
265
+ prTitle: './scripts/pr-title.js',
266
+ },
267
+ });
268
+ expect(result.valid).toBe(true);
269
+ });
270
+ it('should reject non-string generator paths', () => {
271
+ const result = validateConfig({
272
+ generators: { branchName: 123 },
273
+ });
274
+ expect(result.valid).toBe(false);
275
+ });
276
+ it('should warn on unknown generator keys', () => {
277
+ const result = validateConfig({
278
+ generators: { unknownGenerator: './script.js' },
279
+ });
280
+ expect(result.valid).toBe(false);
281
+ });
282
+ });
283
+ describe('integrations config', () => {
284
+ it('should accept valid linear integration', () => {
285
+ const result = validateConfig({
286
+ integrations: {
287
+ linear: { teamId: 'TEAM123', apiKeyEnv: 'LINEAR_API_KEY' },
288
+ },
289
+ });
290
+ expect(result.valid).toBe(true);
291
+ });
292
+ it('should accept valid jira integration', () => {
293
+ const result = validateConfig({
294
+ integrations: {
295
+ jira: {
296
+ projectKey: 'PROJ',
297
+ baseUrl: 'https://company.atlassian.net',
298
+ apiTokenEnv: 'JIRA_TOKEN',
299
+ },
300
+ },
301
+ });
302
+ expect(result.valid).toBe(true);
303
+ });
304
+ it('should accept valid slack integration', () => {
305
+ const result = validateConfig({
306
+ integrations: {
307
+ slack: {
308
+ webhookUrl: 'SLACK_WEBHOOK_URL',
309
+ channel: '#dev-notifications',
310
+ },
311
+ },
312
+ });
313
+ expect(result.valid).toBe(true);
314
+ });
315
+ it('should warn on unknown integration', () => {
316
+ const result = validateConfig({
317
+ integrations: { unknownService: {} },
318
+ });
319
+ expect(result.valid).toBe(false);
320
+ });
321
+ it('should reject non-string integration values', () => {
322
+ const result = validateConfig({
323
+ integrations: { linear: { teamId: 123 } },
324
+ });
325
+ expect(result.valid).toBe(false);
326
+ });
327
+ });
328
+ describe('full config validation', () => {
329
+ it('should accept comprehensive valid config', () => {
330
+ const result = validateConfig({
331
+ baseBranch: 'main',
332
+ draftPr: true,
333
+ branchPrefix: 'feat',
334
+ worktreePattern: '{repo}.pr{number}',
335
+ worktreeParent: '..',
336
+ preferredEditor: 'vscode',
337
+ sharedRepos: ['backend-api'],
338
+ syncPatterns: ['.env.local'],
339
+ ai: {
340
+ provider: 'claude',
341
+ branchName: true,
342
+ prTitle: true,
343
+ prDescription: true,
344
+ commitStyle: 'conventional',
345
+ },
346
+ hooks: {
347
+ 'post-worktree': 'npm install',
348
+ },
349
+ hookDefaults: {
350
+ timeout: 30000,
351
+ },
352
+ plugins: ['@worktree-tools/plugin-slack'],
353
+ generators: {},
354
+ integrations: {
355
+ slack: { channel: '#dev' },
356
+ },
357
+ });
358
+ expect(result.valid).toBe(true);
359
+ expect(result.errors).toHaveLength(0);
360
+ });
361
+ it('should collect multiple errors', () => {
362
+ const result = validateConfig({
363
+ baseBranch: 123,
364
+ draftPr: 'yes',
365
+ preferredEditor: 'vim',
366
+ unknownKey: 'value',
367
+ });
368
+ expect(result.valid).toBe(false);
369
+ expect(result.errors.length).toBeGreaterThanOrEqual(4);
370
+ });
371
+ });
372
+ });
373
+ describe('formatValidationErrors', () => {
374
+ it('should return empty string for no errors', () => {
375
+ expect(formatValidationErrors([])).toBe('');
376
+ });
377
+ it('should format single error', () => {
378
+ const errors = [{ path: 'baseBranch', message: 'must be a string' }];
379
+ const result = formatValidationErrors(errors);
380
+ expect(result).toContain('baseBranch');
381
+ expect(result).toContain('must be a string');
382
+ });
383
+ it('should format multiple errors', () => {
384
+ const errors = [
385
+ { path: 'baseBranch', message: 'must be a string' },
386
+ { path: 'draftPr', message: 'must be a boolean' },
387
+ ];
388
+ const result = formatValidationErrors(errors);
389
+ expect(result).toContain('baseBranch');
390
+ expect(result).toContain('draftPr');
391
+ });
392
+ it('should handle empty path', () => {
393
+ const errors = [{ path: '', message: 'Config must be an object' }];
394
+ const result = formatValidationErrors(errors);
395
+ expect(result).toContain('Config must be an object');
396
+ });
397
+ });
398
+ //# sourceMappingURL=config-validation.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"config-validation.test.js","sourceRoot":"","sources":["../../src/lib/config-validation.test.ts"],"names":[],"mappings":"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"}
@@ -1,5 +1,6 @@
1
1
  import type { AIConfig } from './ai/types.js';
2
2
  import type { HooksConfig } from './hooks/types.js';
3
+ import { type ValidationResult } from './config-validation.js';
3
4
  /**
4
5
  * Hook execution defaults configuration
5
6
  */
@@ -99,6 +100,42 @@ export interface IntegrationsConfig {
99
100
  */
100
101
  slack?: SlackIntegration;
101
102
  }
103
+ /**
104
+ * Logging configuration
105
+ */
106
+ export interface LoggingConfig {
107
+ /**
108
+ * Log level threshold
109
+ * Options: "silent", "error", "warn", "info", "debug", "trace"
110
+ * Default: "info"
111
+ */
112
+ level?: 'silent' | 'error' | 'warn' | 'info' | 'debug' | 'trace';
113
+ /**
114
+ * Path to log file for persistent logging
115
+ * If set, logs will be written to this file in addition to console
116
+ * Supports ~ for home directory
117
+ */
118
+ logFile?: string;
119
+ /**
120
+ * Enable timestamps in log output
121
+ * Default: true
122
+ */
123
+ timestamps?: boolean;
124
+ }
125
+ /**
126
+ * Global settings that typically live in the global config
127
+ */
128
+ export interface GlobalSettings {
129
+ /**
130
+ * Warn if the package is not installed globally
131
+ * Default: true
132
+ */
133
+ warnNotGlobal?: boolean;
134
+ /**
135
+ * Logging configuration (also applies to repo/local configs)
136
+ */
137
+ logging?: LoggingConfig;
138
+ }
102
139
  /**
103
140
  * Configuration for git-worktree-tools
104
141
  */
@@ -129,8 +166,8 @@ export interface WorktreeConfig {
129
166
  */
130
167
  worktreeParent?: string;
131
168
  /**
132
- * Files/directories to sync between worktrees using symlinks
133
- * e.g., ["node_modules", ".env.local"]
169
+ * Gitignored config files to sync between worktrees via hard links
170
+ * e.g., [".env.local", ".vscode/settings.json"]
134
171
  */
135
172
  syncPatterns?: string[];
136
173
  /**
@@ -177,16 +214,85 @@ export interface WorktreeConfig {
177
214
  * Third-party integrations configuration
178
215
  */
179
216
  integrations?: IntegrationsConfig;
217
+ /**
218
+ * Logging configuration
219
+ * Controls verbosity and log file output
220
+ */
221
+ logging?: LoggingConfig;
222
+ /**
223
+ * Global settings
224
+ * These are typically set in the global config file
225
+ */
226
+ global?: GlobalSettings;
180
227
  }
181
228
  /**
182
229
  * Get default configuration values
183
230
  */
184
231
  export declare function getDefaultConfig(): Required<WorktreeConfig>;
185
232
  /**
186
- * Load configuration from repository
187
- * Merges with defaults, repo config takes precedence
233
+ * Options for loading configuration
234
+ */
235
+ export interface LoadConfigOptions {
236
+ /** Whether to validate the config (default: true) */
237
+ validate?: boolean;
238
+ /** Whether to warn on validation errors (default: true) */
239
+ warnOnErrors?: boolean;
240
+ }
241
+ /**
242
+ * Information about a loaded config source
243
+ */
244
+ export interface LoadedConfigSource {
245
+ path: string;
246
+ level: 'global' | 'repo' | 'local';
247
+ config: WorktreeConfig;
248
+ validation: ValidationResult | null;
249
+ }
250
+ /**
251
+ * Result of loading and validating config
252
+ */
253
+ export interface LoadConfigResult {
254
+ config: Required<WorktreeConfig>;
255
+ /** Primary config path (for backward compatibility - now refers to highest priority loaded config) */
256
+ configPath: string | null;
257
+ /** Validation result for the merged config */
258
+ validation: ValidationResult | null;
259
+ /** All config sources that were loaded */
260
+ sources: LoadedConfigSource[];
261
+ }
262
+ /**
263
+ * Load configuration from repository (or global config only if no repoRoot)
264
+ * Implements three-tier hierarchy: defaults ← global ← repo ← local
265
+ */
266
+ export declare function loadConfig(repoRoot?: string, options?: LoadConfigOptions): Required<WorktreeConfig>;
267
+ /**
268
+ * Load configuration with full validation result
269
+ * Implements three-tier hierarchy: defaults ← global ← repo ← local
270
+ */
271
+ export declare function loadConfigWithValidation(repoRoot?: string, options?: LoadConfigOptions): LoadConfigResult;
272
+ /**
273
+ * Save configuration to repository
274
+ *
275
+ * @param repoRoot - Repository root path
276
+ * @param config - Configuration to save (partial config, will preserve existing values)
277
+ * @param options - Save options
278
+ * @returns Path to saved config file
279
+ */
280
+ export declare function saveConfig(repoRoot: string, config: WorktreeConfig, options?: {
281
+ validate?: boolean;
282
+ }): {
283
+ configPath: string;
284
+ validation: ValidationResult | null;
285
+ };
286
+ /**
287
+ * Get config file path for a repository (or null if none exists)
288
+ * Returns the highest priority config that exists (local > repo)
289
+ */
290
+ export declare function getConfigPath(repoRoot: string): string | null;
291
+ /**
292
+ * Get the schema URL for IDE support
293
+ * Uses unpkg.com to serve the schema directly from npm
188
294
  */
189
- export declare function loadConfig(repoRoot: string): Required<WorktreeConfig>;
295
+ export { getSchemaUrl } from './global-config.js';
190
296
  /**
191
297
  * Generate worktree path based on config pattern
192
298
  */
@@ -203,8 +309,9 @@ export declare function generateBranchName(config: Required<WorktreeConfig>, des
203
309
  * @param config - The worktree configuration
204
310
  * @param description - User-provided description for the branch
205
311
  * @param repoName - Repository name (optional, defaults to 'repo')
312
+ * @param repoRoot - Repository root path for documentation gathering (optional)
206
313
  */
207
- export declare function generateBranchNameAsync(config: Required<WorktreeConfig>, description: string, repoName?: string): Promise<string>;
314
+ export declare function generateBranchNameAsync(config: Required<WorktreeConfig>, description: string, repoName?: string, repoRoot?: string): Promise<string>;
208
315
  /**
209
316
  * Context for generating PR content
210
317
  */
@@ -215,6 +322,8 @@ export interface PRGenerationContext {
215
322
  diff?: string;
216
323
  changedFiles?: string[];
217
324
  commitMessages?: string[];
325
+ /** Repository root path for documentation gathering */
326
+ repoRoot?: string;
218
327
  }
219
328
  /**
220
329
  * Result of PR content generation
@@ -1 +1 @@
1
- {"version":3,"file":"config.d.ts","sourceRoot":"","sources":["../../src/lib/config.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"config.d.ts","sourceRoot":"","sources":["../../src/lib/config.ts"],"names":[],"mappings":"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"}