@camaradesuk/git-worktree-tools 1.7.0 → 1.8.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 (190) hide show
  1. package/README.md +69 -8
  2. package/dist/cli/cleanpr.js +11 -5
  3. package/dist/cli/cleanpr.js.map +1 -1
  4. package/dist/cli/cleanpr.test.js +10 -1
  5. package/dist/cli/cleanpr.test.js.map +1 -1
  6. package/dist/cli/newpr.js +100 -28
  7. package/dist/cli/newpr.js.map +1 -1
  8. package/dist/cli/newpr.test.js +24 -6
  9. package/dist/cli/newpr.test.js.map +1 -1
  10. package/dist/cli/prs.d.ts +22 -0
  11. package/dist/cli/prs.d.ts.map +1 -0
  12. package/dist/cli/prs.js +275 -0
  13. package/dist/cli/prs.js.map +1 -0
  14. package/dist/cli/prs.test.d.ts +8 -0
  15. package/dist/cli/prs.test.d.ts.map +1 -0
  16. package/dist/cli/prs.test.js +408 -0
  17. package/dist/cli/prs.test.js.map +1 -0
  18. package/dist/cli/wt/interactive-menu.d.ts +2 -0
  19. package/dist/cli/wt/interactive-menu.d.ts.map +1 -1
  20. package/dist/cli/wt/interactive-menu.js +17 -0
  21. package/dist/cli/wt/interactive-menu.js.map +1 -1
  22. package/dist/cli/wt/interactive-menu.test.js +25 -0
  23. package/dist/cli/wt/interactive-menu.test.js.map +1 -1
  24. package/dist/cli/wt/prs.d.ts +21 -0
  25. package/dist/cli/wt/prs.d.ts.map +1 -0
  26. package/dist/cli/wt/prs.js +251 -0
  27. package/dist/cli/wt/prs.js.map +1 -0
  28. package/dist/cli/wt/prs.test.d.ts +5 -0
  29. package/dist/cli/wt/prs.test.d.ts.map +1 -0
  30. package/dist/cli/wt/prs.test.js +410 -0
  31. package/dist/cli/wt/prs.test.js.map +1 -0
  32. package/dist/cli/wt.d.ts +1 -0
  33. package/dist/cli/wt.d.ts.map +1 -1
  34. package/dist/cli/wt.js +5 -0
  35. package/dist/cli/wt.js.map +1 -1
  36. package/dist/cli/wtconfig.test.js +3 -0
  37. package/dist/cli/wtconfig.test.js.map +1 -1
  38. package/dist/cli/wtlink.d.ts +2 -1
  39. package/dist/cli/wtlink.d.ts.map +1 -1
  40. package/dist/cli/wtlink.js +41 -2
  41. package/dist/cli/wtlink.js.map +1 -1
  42. package/dist/e2e/cli.e2e.test.js +6 -2
  43. package/dist/e2e/cli.e2e.test.js.map +1 -1
  44. package/dist/e2e/helpers/cli-runner.d.ts.map +1 -1
  45. package/dist/e2e/helpers/cli-runner.js +1 -0
  46. package/dist/e2e/helpers/cli-runner.js.map +1 -1
  47. package/dist/e2e/helpers/gh-mock.d.ts.map +1 -1
  48. package/dist/e2e/helpers/gh-mock.js +55 -1
  49. package/dist/e2e/helpers/gh-mock.js.map +1 -1
  50. package/dist/e2e/helpers/pty-wrapper.d.ts +15 -0
  51. package/dist/e2e/helpers/pty-wrapper.d.ts.map +1 -1
  52. package/dist/e2e/helpers/pty-wrapper.js +65 -0
  53. package/dist/e2e/helpers/pty-wrapper.js.map +1 -1
  54. package/dist/e2e/newpr-full-flow.e2e.test.js +1 -0
  55. package/dist/e2e/newpr-full-flow.e2e.test.js.map +1 -1
  56. package/dist/e2e/prs/prs.e2e.test.d.ts +7 -0
  57. package/dist/e2e/prs/prs.e2e.test.d.ts.map +1 -0
  58. package/dist/e2e/prs/prs.e2e.test.js +606 -0
  59. package/dist/e2e/prs/prs.e2e.test.js.map +1 -0
  60. package/dist/e2e/wt/interactive-menu.e2e.test.d.ts +8 -0
  61. package/dist/e2e/wt/interactive-menu.e2e.test.d.ts.map +1 -0
  62. package/dist/e2e/wt/interactive-menu.e2e.test.js +583 -0
  63. package/dist/e2e/wt/interactive-menu.e2e.test.js.map +1 -0
  64. package/dist/e2e/wt/wt.e2e.test.js +217 -4
  65. package/dist/e2e/wt/wt.e2e.test.js.map +1 -1
  66. package/dist/integration/prs.integration.test.d.ts +8 -0
  67. package/dist/integration/prs.integration.test.d.ts.map +1 -0
  68. package/dist/integration/prs.integration.test.js +478 -0
  69. package/dist/integration/prs.integration.test.js.map +1 -0
  70. package/dist/lib/config-validation.d.ts.map +1 -1
  71. package/dist/lib/config-validation.js +56 -0
  72. package/dist/lib/config-validation.js.map +1 -1
  73. package/dist/lib/config.d.ts +34 -0
  74. package/dist/lib/config.d.ts.map +1 -1
  75. package/dist/lib/config.js +10 -0
  76. package/dist/lib/config.js.map +1 -1
  77. package/dist/lib/git.d.ts +32 -0
  78. package/dist/lib/git.d.ts.map +1 -1
  79. package/dist/lib/git.js +95 -1
  80. package/dist/lib/git.js.map +1 -1
  81. package/dist/lib/git.test.js +118 -1
  82. package/dist/lib/git.test.js.map +1 -1
  83. package/dist/lib/github.d.ts +41 -0
  84. package/dist/lib/github.d.ts.map +1 -1
  85. package/dist/lib/github.js +109 -0
  86. package/dist/lib/github.js.map +1 -1
  87. package/dist/lib/global-check.d.ts +2 -2
  88. package/dist/lib/global-check.js +3 -3
  89. package/dist/lib/global-check.js.map +1 -1
  90. package/dist/lib/global-check.test.js +3 -6
  91. package/dist/lib/global-check.test.js.map +1 -1
  92. package/dist/lib/json-output.d.ts +1 -0
  93. package/dist/lib/json-output.d.ts.map +1 -1
  94. package/dist/lib/json-output.js +2 -0
  95. package/dist/lib/json-output.js.map +1 -1
  96. package/dist/lib/lswt/action-executors.d.ts.map +1 -1
  97. package/dist/lib/lswt/action-executors.js +2 -1
  98. package/dist/lib/lswt/action-executors.js.map +1 -1
  99. package/dist/lib/lswt/action-executors.test.js +1 -0
  100. package/dist/lib/lswt/action-executors.test.js.map +1 -1
  101. package/dist/lib/lswt/actions.d.ts +1 -0
  102. package/dist/lib/lswt/actions.d.ts.map +1 -1
  103. package/dist/lib/lswt/actions.js +38 -10
  104. package/dist/lib/lswt/actions.js.map +1 -1
  105. package/dist/lib/lswt/actions.test.js +34 -22
  106. package/dist/lib/lswt/actions.test.js.map +1 -1
  107. package/dist/lib/lswt/interactive.js +8 -8
  108. package/dist/lib/lswt/interactive.js.map +1 -1
  109. package/dist/lib/prompts.d.ts.map +1 -1
  110. package/dist/lib/prompts.js +16 -12
  111. package/dist/lib/prompts.js.map +1 -1
  112. package/dist/lib/prs/actions.d.ts +70 -0
  113. package/dist/lib/prs/actions.d.ts.map +1 -0
  114. package/dist/lib/prs/actions.js +444 -0
  115. package/dist/lib/prs/actions.js.map +1 -0
  116. package/dist/lib/prs/actions.test.d.ts +5 -0
  117. package/dist/lib/prs/actions.test.d.ts.map +1 -0
  118. package/dist/lib/prs/actions.test.js +313 -0
  119. package/dist/lib/prs/actions.test.js.map +1 -0
  120. package/dist/lib/prs/data.d.ts +48 -0
  121. package/dist/lib/prs/data.d.ts.map +1 -0
  122. package/dist/lib/prs/data.js +171 -0
  123. package/dist/lib/prs/data.js.map +1 -0
  124. package/dist/lib/prs/data.test.d.ts +5 -0
  125. package/dist/lib/prs/data.test.d.ts.map +1 -0
  126. package/dist/lib/prs/data.test.js +417 -0
  127. package/dist/lib/prs/data.test.js.map +1 -0
  128. package/dist/lib/prs/details.d.ts +57 -0
  129. package/dist/lib/prs/details.d.ts.map +1 -0
  130. package/dist/lib/prs/details.js +246 -0
  131. package/dist/lib/prs/details.js.map +1 -0
  132. package/dist/lib/prs/details.test.d.ts +5 -0
  133. package/dist/lib/prs/details.test.d.ts.map +1 -0
  134. package/dist/lib/prs/details.test.js +325 -0
  135. package/dist/lib/prs/details.test.js.map +1 -0
  136. package/dist/lib/prs/filters.d.ts +56 -0
  137. package/dist/lib/prs/filters.d.ts.map +1 -0
  138. package/dist/lib/prs/filters.js +171 -0
  139. package/dist/lib/prs/filters.js.map +1 -0
  140. package/dist/lib/prs/filters.test.d.ts +5 -0
  141. package/dist/lib/prs/filters.test.d.ts.map +1 -0
  142. package/dist/lib/prs/filters.test.js +312 -0
  143. package/dist/lib/prs/filters.test.js.map +1 -0
  144. package/dist/lib/prs/formatters.d.ts +83 -0
  145. package/dist/lib/prs/formatters.d.ts.map +1 -0
  146. package/dist/lib/prs/formatters.js +389 -0
  147. package/dist/lib/prs/formatters.js.map +1 -0
  148. package/dist/lib/prs/formatters.test.d.ts +2 -0
  149. package/dist/lib/prs/formatters.test.d.ts.map +1 -0
  150. package/dist/lib/prs/formatters.test.js +387 -0
  151. package/dist/lib/prs/formatters.test.js.map +1 -0
  152. package/dist/lib/prs/interactive.d.ts +50 -0
  153. package/dist/lib/prs/interactive.d.ts.map +1 -0
  154. package/dist/lib/prs/interactive.js +453 -0
  155. package/dist/lib/prs/interactive.js.map +1 -0
  156. package/dist/lib/prs/interactive.test.d.ts +5 -0
  157. package/dist/lib/prs/interactive.test.d.ts.map +1 -0
  158. package/dist/lib/prs/interactive.test.js +364 -0
  159. package/dist/lib/prs/interactive.test.js.map +1 -0
  160. package/dist/lib/prs/types.d.ts +152 -0
  161. package/dist/lib/prs/types.d.ts.map +1 -0
  162. package/dist/lib/prs/types.js +17 -0
  163. package/dist/lib/prs/types.js.map +1 -0
  164. package/dist/lib/wtlink/config-manifest.d.ts +101 -0
  165. package/dist/lib/wtlink/config-manifest.d.ts.map +1 -0
  166. package/dist/lib/wtlink/config-manifest.js +219 -0
  167. package/dist/lib/wtlink/config-manifest.js.map +1 -0
  168. package/dist/lib/wtlink/config-manifest.test.d.ts +2 -0
  169. package/dist/lib/wtlink/config-manifest.test.d.ts.map +1 -0
  170. package/dist/lib/wtlink/config-manifest.test.js +460 -0
  171. package/dist/lib/wtlink/config-manifest.test.js.map +1 -0
  172. package/dist/lib/wtlink/link-configs.d.ts.map +1 -1
  173. package/dist/lib/wtlink/link-configs.js +36 -11
  174. package/dist/lib/wtlink/link-configs.js.map +1 -1
  175. package/dist/lib/wtlink/main-menu.d.ts.map +1 -1
  176. package/dist/lib/wtlink/main-menu.js +58 -50
  177. package/dist/lib/wtlink/main-menu.js.map +1 -1
  178. package/dist/lib/wtlink/main-menu.test.js +42 -40
  179. package/dist/lib/wtlink/main-menu.test.js.map +1 -1
  180. package/dist/lib/wtlink/manage-manifest.d.ts +9 -0
  181. package/dist/lib/wtlink/manage-manifest.d.ts.map +1 -1
  182. package/dist/lib/wtlink/manage-manifest.js +346 -25
  183. package/dist/lib/wtlink/manage-manifest.js.map +1 -1
  184. package/dist/lib/wtlink/manage-manifest.test.js +52 -1
  185. package/dist/lib/wtlink/manage-manifest.test.js.map +1 -1
  186. package/dist/lib/wtlink/validate-manifest.d.ts.map +1 -1
  187. package/dist/lib/wtlink/validate-manifest.js +27 -6
  188. package/dist/lib/wtlink/validate-manifest.js.map +1 -1
  189. package/package.json +1 -1
  190. package/schemas/worktreerc.schema.json +26 -1
@@ -0,0 +1,478 @@
1
+ /**
2
+ * Integration tests for standalone prs CLI command (src/cli/prs.ts)
3
+ *
4
+ * These tests verify the standalone prs command works correctly when called directly,
5
+ * not through the `wt prs` subcommand.
6
+ */
7
+ import { describe, it, expect, beforeAll, afterAll, beforeEach, afterEach } from 'vitest';
8
+ import { execSync, spawnSync } from 'child_process';
9
+ import fs from 'fs';
10
+ import path from 'path';
11
+ import os from 'os';
12
+ import { setupGhMock } from '../e2e/helpers/gh-mock.js';
13
+ // Path to the compiled standalone prs CLI
14
+ const PRS_CLI_PATH = path.resolve(__dirname, '../../dist/cli/prs.js');
15
+ /**
16
+ * Helper to run the standalone prs CLI command
17
+ */
18
+ function runPrs(args = [], options = {}) {
19
+ const result = spawnSync('node', [PRS_CLI_PATH, ...args], {
20
+ cwd: options.cwd || process.cwd(),
21
+ encoding: 'utf-8',
22
+ timeout: options.timeout || 30000,
23
+ env: {
24
+ ...process.env,
25
+ ...options.env,
26
+ FORCE_COLOR: '0',
27
+ NO_COLOR: '1',
28
+ },
29
+ });
30
+ return {
31
+ stdout: result.stdout || '',
32
+ stderr: result.stderr || '',
33
+ exitCode: result.status ?? 1,
34
+ };
35
+ }
36
+ describe('standalone prs CLI - help and usage', () => {
37
+ it('shows help message with --help', () => {
38
+ const result = runPrs(['--help']);
39
+ expect(result.exitCode).toBe(0);
40
+ expect(result.stdout).toContain('prs');
41
+ expect(result.stdout).toContain('Browse repository pull requests');
42
+ });
43
+ it('shows all available options in help', () => {
44
+ const result = runPrs(['--help']);
45
+ expect(result.exitCode).toBe(0);
46
+ expect(result.stdout).toContain('--state');
47
+ expect(result.stdout).toContain('--author');
48
+ expect(result.stdout).toContain('--label');
49
+ expect(result.stdout).toContain('--json');
50
+ expect(result.stdout).toContain('--interactive');
51
+ expect(result.stdout).toContain('--refresh');
52
+ expect(result.stdout).toContain('--draft');
53
+ expect(result.stdout).toContain('--with-worktree');
54
+ expect(result.stdout).toContain('--limit');
55
+ });
56
+ it('shows -h alias for --help', () => {
57
+ const result = runPrs(['-h']);
58
+ expect(result.exitCode).toBe(0);
59
+ expect(result.stdout).toContain('prs');
60
+ });
61
+ });
62
+ describe('standalone prs CLI - error conditions', () => {
63
+ let nonGitDir;
64
+ beforeEach(() => {
65
+ nonGitDir = fs.mkdtempSync(path.join(os.tmpdir(), 'prs-not-git-'));
66
+ });
67
+ afterEach(() => {
68
+ fs.rmSync(nonGitDir, { recursive: true, force: true });
69
+ });
70
+ it('fails outside git repository with clear error message', () => {
71
+ const ghMock = setupGhMock();
72
+ try {
73
+ const result = runPrs(['--no-interactive'], {
74
+ cwd: nonGitDir,
75
+ env: ghMock.mockEnv,
76
+ });
77
+ expect(result.exitCode).not.toBe(0);
78
+ expect(result.stderr.toLowerCase()).toMatch(/git|repository/i);
79
+ }
80
+ finally {
81
+ ghMock.cleanup();
82
+ }
83
+ });
84
+ it('outputs JSON error when --json flag is used outside git repo', () => {
85
+ const ghMock = setupGhMock();
86
+ try {
87
+ const result = runPrs(['--json', '--no-interactive'], {
88
+ cwd: nonGitDir,
89
+ env: ghMock.mockEnv,
90
+ });
91
+ expect(result.exitCode).not.toBe(0);
92
+ // Should output valid JSON error
93
+ try {
94
+ const jsonOutput = JSON.parse(result.stdout);
95
+ expect(jsonOutput.success).toBe(false);
96
+ expect(jsonOutput.error).toBeDefined();
97
+ expect(jsonOutput.error.code).toBe('NOT_GIT_REPO');
98
+ }
99
+ catch {
100
+ // If JSON parsing fails, at least verify no stack traces
101
+ expect(result.stderr).not.toMatch(/at\s+\w+\s+\(/);
102
+ }
103
+ }
104
+ finally {
105
+ ghMock.cleanup();
106
+ }
107
+ });
108
+ it('outputs JSON error with -j flag (short form)', () => {
109
+ const ghMock = setupGhMock();
110
+ try {
111
+ const result = runPrs(['-j', '--no-interactive'], {
112
+ cwd: nonGitDir,
113
+ env: ghMock.mockEnv,
114
+ });
115
+ expect(result.exitCode).not.toBe(0);
116
+ try {
117
+ const jsonOutput = JSON.parse(result.stdout);
118
+ expect(jsonOutput.success).toBe(false);
119
+ }
120
+ catch {
121
+ // JSON parsing may fail
122
+ }
123
+ }
124
+ finally {
125
+ ghMock.cleanup();
126
+ }
127
+ });
128
+ });
129
+ describe('standalone prs CLI - git repository tests', () => {
130
+ let tempDir;
131
+ let repoDir;
132
+ let ghMock;
133
+ beforeAll(() => {
134
+ tempDir = fs.realpathSync.native(fs.mkdtempSync(path.join(os.tmpdir(), 'prs-integration-')));
135
+ // Create a git repository
136
+ repoDir = path.join(tempDir, 'test-repo');
137
+ fs.mkdirSync(repoDir);
138
+ execSync('git init', { cwd: repoDir });
139
+ execSync('git config user.email "test@test.com"', { cwd: repoDir });
140
+ execSync('git config user.name "Test User"', { cwd: repoDir });
141
+ // Create initial commit
142
+ fs.writeFileSync(path.join(repoDir, 'README.md'), '# Test Repo\n');
143
+ execSync('git add .', { cwd: repoDir });
144
+ execSync('git commit -m "Initial commit"', { cwd: repoDir });
145
+ execSync('git branch -M main', { cwd: repoDir, stdio: 'ignore' });
146
+ // Setup gh mock
147
+ ghMock = setupGhMock();
148
+ });
149
+ afterAll(() => {
150
+ ghMock?.cleanup();
151
+ if (tempDir) {
152
+ fs.rmSync(tempDir, { recursive: true, force: true });
153
+ }
154
+ });
155
+ describe('argument parsing', () => {
156
+ it('rejects invalid --state value', () => {
157
+ const result = runPrs(['--state=invalid', '--no-interactive'], {
158
+ cwd: repoDir,
159
+ env: ghMock.mockEnv,
160
+ });
161
+ expect(result.exitCode).not.toBe(0);
162
+ expect(result.stderr.toLowerCase()).toMatch(/invalid|choices/i);
163
+ });
164
+ it('accepts valid --state values', () => {
165
+ for (const state of ['open', 'closed', 'merged', 'all']) {
166
+ const result = runPrs([`--state=${state}`, '--no-interactive'], {
167
+ cwd: repoDir,
168
+ env: ghMock.mockEnv,
169
+ });
170
+ // Should not fail on argument parsing
171
+ expect(result.stderr).not.toMatch(/invalid argument|unknown argument/i);
172
+ }
173
+ });
174
+ it('accepts -s alias for --state', () => {
175
+ const result = runPrs(['-s', 'all', '--no-interactive'], {
176
+ cwd: repoDir,
177
+ env: ghMock.mockEnv,
178
+ });
179
+ expect(result.stderr).not.toMatch(/unknown argument/i);
180
+ });
181
+ it('accepts -a alias for --author', () => {
182
+ const result = runPrs(['-a', 'testuser', '--no-interactive'], {
183
+ cwd: repoDir,
184
+ env: ghMock.mockEnv,
185
+ });
186
+ expect(result.stderr).not.toMatch(/unknown argument/i);
187
+ });
188
+ it('accepts -l alias for --label', () => {
189
+ const result = runPrs(['-l', 'bug', '--no-interactive'], {
190
+ cwd: repoDir,
191
+ env: ghMock.mockEnv,
192
+ });
193
+ expect(result.stderr).not.toMatch(/unknown argument/i);
194
+ });
195
+ it('accepts -n alias for --limit', () => {
196
+ const result = runPrs(['-n', '25', '--no-interactive'], {
197
+ cwd: repoDir,
198
+ env: ghMock.mockEnv,
199
+ });
200
+ expect(result.stderr).not.toMatch(/unknown argument/i);
201
+ });
202
+ it('accepts -r alias for --refresh', () => {
203
+ const result = runPrs(['-r', '--no-interactive'], {
204
+ cwd: repoDir,
205
+ env: ghMock.mockEnv,
206
+ });
207
+ expect(result.stderr).not.toMatch(/unknown argument/i);
208
+ });
209
+ it('accepts multiple --label flags', () => {
210
+ const result = runPrs(['--label=bug', '--label=urgent', '--no-interactive'], {
211
+ cwd: repoDir,
212
+ env: ghMock.mockEnv,
213
+ });
214
+ expect(result.stderr).not.toMatch(/unknown argument/i);
215
+ });
216
+ });
217
+ describe('filter combinations', () => {
218
+ it('accepts --draft and --state together', () => {
219
+ const result = runPrs(['--draft', '--state=open', '--no-interactive'], {
220
+ cwd: repoDir,
221
+ env: ghMock.mockEnv,
222
+ });
223
+ expect(result.stderr).not.toMatch(/unknown argument/i);
224
+ });
225
+ it('accepts --no-draft and --with-worktree together', () => {
226
+ const result = runPrs(['--no-draft', '--with-worktree', '--no-interactive'], {
227
+ cwd: repoDir,
228
+ env: ghMock.mockEnv,
229
+ });
230
+ expect(result.stderr).not.toMatch(/unknown argument/i);
231
+ });
232
+ it('accepts all filters together', () => {
233
+ const result = runPrs([
234
+ '--state=all',
235
+ '--author=@me',
236
+ '--label=preview',
237
+ '--no-draft',
238
+ '--with-worktree',
239
+ '--limit=10',
240
+ '--no-interactive',
241
+ ], {
242
+ cwd: repoDir,
243
+ env: ghMock.mockEnv,
244
+ });
245
+ expect(result.stderr).not.toMatch(/unknown argument/i);
246
+ });
247
+ });
248
+ describe('JSON output mode', () => {
249
+ it('outputs valid JSON structure on success', () => {
250
+ // Add mock PRs
251
+ ghMock.addPr({
252
+ number: 1,
253
+ state: 'OPEN',
254
+ title: 'Test PR',
255
+ headRefName: 'feat/test',
256
+ isDraft: false,
257
+ });
258
+ const result = runPrs(['--json', '--no-interactive'], {
259
+ cwd: repoDir,
260
+ env: ghMock.mockEnv,
261
+ });
262
+ try {
263
+ const jsonOutput = JSON.parse(result.stdout);
264
+ expect(jsonOutput).toHaveProperty('success');
265
+ expect(jsonOutput).toHaveProperty('command', 'prs');
266
+ expect(jsonOutput).toHaveProperty('timestamp');
267
+ if (jsonOutput.success) {
268
+ expect(jsonOutput).toHaveProperty('data');
269
+ expect(jsonOutput.data).toHaveProperty('total');
270
+ expect(jsonOutput.data).toHaveProperty('filters');
271
+ expect(jsonOutput.data).toHaveProperty('prs');
272
+ }
273
+ }
274
+ catch {
275
+ // JSON parsing may fail in some mock scenarios
276
+ expect(typeof result.exitCode).toBe('number');
277
+ }
278
+ });
279
+ it('JSON output includes filter state', () => {
280
+ const result = runPrs(['--json', '--state=all', '--no-draft', '--no-interactive'], {
281
+ cwd: repoDir,
282
+ env: ghMock.mockEnv,
283
+ });
284
+ try {
285
+ const jsonOutput = JSON.parse(result.stdout);
286
+ if (jsonOutput.success && jsonOutput.data?.filters) {
287
+ expect(jsonOutput.data.filters.showDrafts).toBe(false);
288
+ expect(jsonOutput.data.filters.states).toContain('OPEN');
289
+ expect(jsonOutput.data.filters.states).toContain('MERGED');
290
+ expect(jsonOutput.data.filters.states).toContain('CLOSED');
291
+ }
292
+ }
293
+ catch {
294
+ // JSON parsing may fail
295
+ }
296
+ });
297
+ it('JSON output has ISO timestamp format', () => {
298
+ const result = runPrs(['--json', '--no-interactive'], {
299
+ cwd: repoDir,
300
+ env: ghMock.mockEnv,
301
+ });
302
+ try {
303
+ const jsonOutput = JSON.parse(result.stdout);
304
+ if (jsonOutput.timestamp) {
305
+ // Should be valid ISO date string
306
+ const date = new Date(jsonOutput.timestamp);
307
+ expect(date.toISOString()).toBe(jsonOutput.timestamp);
308
+ }
309
+ }
310
+ catch {
311
+ // JSON parsing may fail
312
+ }
313
+ });
314
+ });
315
+ describe('non-interactive mode', () => {
316
+ it('--no-interactive prevents blocking', () => {
317
+ const startTime = Date.now();
318
+ const result = runPrs(['--no-interactive'], {
319
+ cwd: repoDir,
320
+ env: ghMock.mockEnv,
321
+ timeout: 5000,
322
+ });
323
+ const duration = Date.now() - startTime;
324
+ // Should complete quickly without waiting for input
325
+ expect(duration).toBeLessThan(5000);
326
+ expect(typeof result.exitCode).toBe('number');
327
+ });
328
+ it('TERM=dumb triggers non-interactive behavior', () => {
329
+ const result = spawnSync('node', [PRS_CLI_PATH], {
330
+ cwd: repoDir,
331
+ encoding: 'utf-8',
332
+ timeout: 5000,
333
+ env: {
334
+ ...ghMock.mockEnv,
335
+ TERM: 'dumb',
336
+ FORCE_COLOR: '0',
337
+ NO_COLOR: '1',
338
+ },
339
+ });
340
+ // Should complete without blocking
341
+ expect(typeof result.status).toBe('number');
342
+ });
343
+ });
344
+ });
345
+ describe('standalone prs CLI - gh authentication', () => {
346
+ let tempDir;
347
+ let repoDir;
348
+ beforeAll(() => {
349
+ tempDir = fs.realpathSync.native(fs.mkdtempSync(path.join(os.tmpdir(), 'prs-auth-')));
350
+ repoDir = path.join(tempDir, 'test-repo');
351
+ fs.mkdirSync(repoDir);
352
+ execSync('git init', { cwd: repoDir });
353
+ execSync('git config user.email "test@test.com"', { cwd: repoDir });
354
+ execSync('git config user.name "Test User"', { cwd: repoDir });
355
+ fs.writeFileSync(path.join(repoDir, 'README.md'), '# Test\n');
356
+ execSync('git add .', { cwd: repoDir });
357
+ execSync('git commit -m "Initial"', { cwd: repoDir });
358
+ execSync('git branch -M main', { cwd: repoDir, stdio: 'ignore' });
359
+ });
360
+ afterAll(() => {
361
+ if (tempDir) {
362
+ fs.rmSync(tempDir, { recursive: true, force: true });
363
+ }
364
+ });
365
+ // Skip on Windows CI due to gh.cmd/gh.exe path resolution issues
366
+ it.skipIf(process.platform === 'win32' && process.env.CI === 'true')('fails when gh is not authenticated', () => {
367
+ const ghMock = setupGhMock({ authenticated: false });
368
+ try {
369
+ const result = runPrs(['--no-interactive'], {
370
+ cwd: repoDir,
371
+ env: ghMock.mockEnv,
372
+ });
373
+ expect(result.exitCode).not.toBe(0);
374
+ expect(result.stderr.toLowerCase()).toMatch(/auth|login|authenticated/i);
375
+ }
376
+ finally {
377
+ ghMock.cleanup();
378
+ }
379
+ });
380
+ it('outputs JSON error when not authenticated with --json', () => {
381
+ const ghMock = setupGhMock({ authenticated: false });
382
+ try {
383
+ const result = runPrs(['--json', '--no-interactive'], {
384
+ cwd: repoDir,
385
+ env: ghMock.mockEnv,
386
+ });
387
+ expect(result.exitCode).not.toBe(0);
388
+ try {
389
+ const jsonOutput = JSON.parse(result.stdout);
390
+ expect(jsonOutput.success).toBe(false);
391
+ expect(jsonOutput.error?.code).toBe('GH_NOT_AUTHENTICATED');
392
+ }
393
+ catch {
394
+ // JSON parsing may fail
395
+ }
396
+ }
397
+ finally {
398
+ ghMock.cleanup();
399
+ }
400
+ });
401
+ });
402
+ describe('standalone prs CLI - worktree context', () => {
403
+ let tempDir;
404
+ let mainRepoDir;
405
+ let worktreeDir;
406
+ let ghMock;
407
+ beforeAll(() => {
408
+ tempDir = fs.realpathSync.native(fs.mkdtempSync(path.join(os.tmpdir(), 'prs-worktree-')));
409
+ // Create main repo
410
+ mainRepoDir = path.join(tempDir, 'main-repo');
411
+ fs.mkdirSync(mainRepoDir);
412
+ execSync('git init', { cwd: mainRepoDir });
413
+ execSync('git config user.email "test@test.com"', { cwd: mainRepoDir });
414
+ execSync('git config user.name "Test User"', { cwd: mainRepoDir });
415
+ fs.writeFileSync(path.join(mainRepoDir, 'README.md'), '# Test\n');
416
+ execSync('git add .', { cwd: mainRepoDir });
417
+ execSync('git commit -m "Initial"', { cwd: mainRepoDir });
418
+ execSync('git branch -M main', { cwd: mainRepoDir, stdio: 'ignore' });
419
+ // Create feature branch and worktree
420
+ execSync('git checkout -b feat/test-pr', { cwd: mainRepoDir });
421
+ execSync('git checkout main', { cwd: mainRepoDir });
422
+ worktreeDir = path.join(tempDir, 'main-repo.pr1');
423
+ execSync(`git worktree add "${worktreeDir}" feat/test-pr`, { cwd: mainRepoDir });
424
+ ghMock = setupGhMock();
425
+ ghMock.addPr({
426
+ number: 1,
427
+ state: 'OPEN',
428
+ title: 'Test PR',
429
+ headRefName: 'feat/test-pr',
430
+ isDraft: false,
431
+ });
432
+ });
433
+ afterAll(() => {
434
+ ghMock?.cleanup();
435
+ if (tempDir) {
436
+ // Remove worktree first
437
+ try {
438
+ execSync(`git worktree remove "${worktreeDir}" --force`, {
439
+ cwd: mainRepoDir,
440
+ stdio: 'ignore',
441
+ });
442
+ }
443
+ catch {
444
+ // Ignore
445
+ }
446
+ fs.rmSync(tempDir, { recursive: true, force: true });
447
+ }
448
+ });
449
+ it('works from main worktree', () => {
450
+ const result = runPrs(['--no-interactive'], {
451
+ cwd: mainRepoDir,
452
+ env: ghMock.mockEnv,
453
+ });
454
+ expect(typeof result.exitCode).toBe('number');
455
+ });
456
+ it('works from PR worktree', () => {
457
+ const result = runPrs(['--no-interactive'], {
458
+ cwd: worktreeDir,
459
+ env: ghMock.mockEnv,
460
+ });
461
+ expect(typeof result.exitCode).toBe('number');
462
+ });
463
+ it('JSON output works from worktree', () => {
464
+ const result = runPrs(['--json', '--no-interactive'], {
465
+ cwd: worktreeDir,
466
+ env: ghMock.mockEnv,
467
+ });
468
+ try {
469
+ const jsonOutput = JSON.parse(result.stdout);
470
+ expect(jsonOutput).toHaveProperty('command', 'prs');
471
+ }
472
+ catch {
473
+ // JSON parsing may fail
474
+ expect(typeof result.exitCode).toBe('number');
475
+ }
476
+ });
477
+ });
478
+ //# sourceMappingURL=prs.integration.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"prs.integration.test.js","sourceRoot":"","sources":["../../src/integration/prs.integration.test.ts"],"names":[],"mappings":"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"}
@@ -1 +1 @@
1
- {"version":3,"file":"config-validation.d.ts","sourceRoot":"","sources":["../../src/lib/config-validation.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAIH;;GAEG;AACH,MAAM,WAAW,eAAe;IAC9B,IAAI,EAAE,MAAM,CAAC;IACb,OAAO,EAAE,MAAM,CAAC;CACjB;AAED;;GAEG;AACH,MAAM,WAAW,gBAAgB;IAC/B,KAAK,EAAE,OAAO,CAAC;IACf,MAAM,EAAE,eAAe,EAAE,CAAC;CAC3B;AAuED;;GAEG;AACH,wBAAgB,cAAc,CAAC,MAAM,EAAE,OAAO,GAAG,gBAAgB,CAuHhE;AAsYD;;GAEG;AACH,wBAAgB,sBAAsB,CAAC,MAAM,EAAE,eAAe,EAAE,GAAG,MAAM,CASxE"}
1
+ {"version":3,"file":"config-validation.d.ts","sourceRoot":"","sources":["../../src/lib/config-validation.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAIH;;GAEG;AACH,MAAM,WAAW,eAAe;IAC9B,IAAI,EAAE,MAAM,CAAC;IACb,OAAO,EAAE,MAAM,CAAC;CACjB;AAED;;GAEG;AACH,MAAM,WAAW,gBAAgB;IAC/B,KAAK,EAAE,OAAO,CAAC;IACf,MAAM,EAAE,eAAe,EAAE,CAAC;CAC3B;AA2ED;;GAEG;AACH,wBAAgB,cAAc,CAAC,MAAM,EAAE,OAAO,GAAG,gBAAgB,CA4HhE;AAybD;;GAEG;AACH,wBAAgB,sBAAsB,CAAC,MAAM,EAAE,eAAe,EAAE,GAAG,MAAM,CASxE"}
@@ -58,6 +58,7 @@ const KNOWN_TOP_LEVEL_KEYS = [
58
58
  'worktreeParent',
59
59
  'syncPatterns',
60
60
  'branchPrefix',
61
+ 'previewLabel',
61
62
  'preferredEditor',
62
63
  'ai',
63
64
  'hooks',
@@ -65,6 +66,9 @@ const KNOWN_TOP_LEVEL_KEYS = [
65
66
  'plugins',
66
67
  'generators',
67
68
  'integrations',
69
+ 'logging',
70
+ 'global',
71
+ 'wtlink',
68
72
  ];
69
73
  /**
70
74
  * Validate a worktree config object
@@ -172,6 +176,10 @@ export function validateConfig(config) {
172
176
  if (obj.integrations !== undefined) {
173
177
  validateIntegrationsConfig(obj.integrations, errors);
174
178
  }
179
+ // Validate wtlink config
180
+ if (obj.wtlink !== undefined) {
181
+ validateWtlinkConfig(obj.wtlink, errors);
182
+ }
175
183
  return { valid: errors.length === 0, errors };
176
184
  }
177
185
  /**
@@ -519,6 +527,54 @@ function validateSlackConfig(slack, errors) {
519
527
  }
520
528
  }
521
529
  }
530
+ /**
531
+ * Validate wtlink config section
532
+ */
533
+ function validateWtlinkConfig(wtlink, errors) {
534
+ if (typeof wtlink !== 'object' || wtlink === null) {
535
+ errors.push({ path: 'wtlink', message: 'wtlink must be an object' });
536
+ return;
537
+ }
538
+ const obj = wtlink;
539
+ const allowedKeys = ['enabled', 'disabled'];
540
+ for (const key of Object.keys(obj)) {
541
+ if (!allowedKeys.includes(key)) {
542
+ errors.push({ path: `wtlink.${key}`, message: `Unknown wtlink property: ${key}` });
543
+ }
544
+ }
545
+ // Validate enabled array
546
+ if (obj.enabled !== undefined) {
547
+ if (!Array.isArray(obj.enabled)) {
548
+ errors.push({ path: 'wtlink.enabled', message: 'wtlink.enabled must be an array' });
549
+ }
550
+ else {
551
+ obj.enabled.forEach((item, i) => {
552
+ if (typeof item !== 'string') {
553
+ errors.push({
554
+ path: `wtlink.enabled[${i}]`,
555
+ message: 'wtlink.enabled items must be strings',
556
+ });
557
+ }
558
+ });
559
+ }
560
+ }
561
+ // Validate disabled array
562
+ if (obj.disabled !== undefined) {
563
+ if (!Array.isArray(obj.disabled)) {
564
+ errors.push({ path: 'wtlink.disabled', message: 'wtlink.disabled must be an array' });
565
+ }
566
+ else {
567
+ obj.disabled.forEach((item, i) => {
568
+ if (typeof item !== 'string') {
569
+ errors.push({
570
+ path: `wtlink.disabled[${i}]`,
571
+ message: 'wtlink.disabled items must be strings',
572
+ });
573
+ }
574
+ });
575
+ }
576
+ }
577
+ }
522
578
  /**
523
579
  * Format validation errors for display
524
580
  */