@claudetree/core 0.4.4 → 0.4.5

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.
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=AIReviewGenerator.test.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"AIReviewGenerator.test.d.ts","sourceRoot":"","sources":["../../../src/infra/ai/AIReviewGenerator.test.ts"],"names":[],"mappings":""}
@@ -0,0 +1,231 @@
1
+ import { describe, it, expect, vi, beforeEach, afterEach } from 'vitest';
2
+ import { generateAIReviewSummary } from './AIReviewGenerator.js';
3
+ import * as childProcess from 'node:child_process';
4
+ import { EventEmitter } from 'node:events';
5
+ // Mock child_process.spawn
6
+ vi.mock('node:child_process', () => ({
7
+ spawn: vi.fn(),
8
+ }));
9
+ describe('AIReviewGenerator', () => {
10
+ let spawnMock;
11
+ const createMockProcess = (stdout, stderr, exitCode, options) => {
12
+ const stdoutEmitter = new EventEmitter();
13
+ const stderrEmitter = new EventEmitter();
14
+ const proc = new EventEmitter();
15
+ // Cast to unknown first, then to the required type
16
+ proc.stdout = stdoutEmitter;
17
+ proc.stderr = stderrEmitter;
18
+ proc.kill = vi.fn();
19
+ // Schedule data and close events
20
+ setTimeout(() => {
21
+ if (options?.shouldError) {
22
+ proc.emit('error', new Error(options.errorMessage || 'Process error'));
23
+ }
24
+ else {
25
+ stdoutEmitter.emit('data', Buffer.from(stdout));
26
+ stderrEmitter.emit('data', Buffer.from(stderr));
27
+ proc.emit('close', exitCode);
28
+ }
29
+ }, 0);
30
+ return proc;
31
+ };
32
+ beforeEach(() => {
33
+ spawnMock = vi.mocked(childProcess.spawn);
34
+ spawnMock.mockReset();
35
+ vi.spyOn(console, 'error').mockImplementation(() => { });
36
+ });
37
+ afterEach(() => {
38
+ vi.clearAllMocks();
39
+ vi.restoreAllMocks();
40
+ });
41
+ describe('generateAIReviewSummary', () => {
42
+ const baseOptions = {
43
+ sessionId: 'test-session-123',
44
+ workingDir: '/test/project',
45
+ baseBranch: 'main',
46
+ };
47
+ it('should return null when there are no changes', async () => {
48
+ // First call: git diff --stat returns empty
49
+ spawnMock.mockImplementationOnce(() => createMockProcess('', '', 0));
50
+ // Second call: git diff (detailed) - should not be reached if first is empty
51
+ spawnMock.mockImplementationOnce(() => createMockProcess('', '', 0));
52
+ const result = await generateAIReviewSummary(baseOptions);
53
+ expect(result).toBeNull();
54
+ });
55
+ it('should generate review summary successfully', async () => {
56
+ const diffStat = ' src/test.ts | 10 +++++-----\n 1 file changed';
57
+ const detailedDiff = 'diff --git a/src/test.ts\n+added line\n-removed line';
58
+ const claudeResponse = JSON.stringify({
59
+ summary: 'Added new feature',
60
+ whatChanged: ['Added test file'],
61
+ whyChanged: 'To improve coverage',
62
+ potentialIssues: [],
63
+ suggestions: ['Add more tests'],
64
+ riskLevel: 'low',
65
+ });
66
+ // git diff --stat
67
+ spawnMock.mockImplementationOnce(() => createMockProcess(diffStat, '', 0));
68
+ // git diff (detailed)
69
+ spawnMock.mockImplementationOnce(() => createMockProcess(detailedDiff, '', 0));
70
+ // claude CLI
71
+ spawnMock.mockImplementationOnce(() => createMockProcess(claudeResponse, '', 0));
72
+ const result = await generateAIReviewSummary(baseOptions);
73
+ expect(result).not.toBeNull();
74
+ expect(result?.sessionId).toBe('test-session-123');
75
+ expect(result?.summary).toBe('Added new feature');
76
+ expect(result?.whatChanged).toContain('Added test file');
77
+ expect(result?.whyChanged).toBe('To improve coverage');
78
+ expect(result?.suggestions).toContain('Add more tests');
79
+ expect(result?.riskLevel).toBe('low');
80
+ expect(result?.generatedAt).toBeInstanceOf(Date);
81
+ });
82
+ it('should use develop as default base branch', async () => {
83
+ const optionsWithoutBranch = {
84
+ sessionId: 'test-session',
85
+ workingDir: '/test',
86
+ };
87
+ spawnMock.mockImplementation((cmd, args) => {
88
+ if (cmd === 'git' && args.includes('diff')) {
89
+ // Check that develop is used
90
+ expect(args).toContain('develop');
91
+ }
92
+ return createMockProcess('', '', 0);
93
+ });
94
+ await generateAIReviewSummary(optionsWithoutBranch);
95
+ expect(spawnMock).toHaveBeenCalledWith('git', expect.arrayContaining(['develop']), expect.any(Object));
96
+ });
97
+ it('should handle git command failure', async () => {
98
+ spawnMock.mockImplementationOnce(() => createMockProcess('', 'fatal: not a git repository', 1));
99
+ const result = await generateAIReviewSummary(baseOptions);
100
+ expect(result).toBeNull();
101
+ });
102
+ it('should handle claude CLI failure', async () => {
103
+ // git diff --stat
104
+ spawnMock.mockImplementationOnce(() => createMockProcess('file.ts | 5 +++++', '', 0));
105
+ // git diff detailed
106
+ spawnMock.mockImplementationOnce(() => createMockProcess('+line', '', 0));
107
+ // claude CLI fails
108
+ spawnMock.mockImplementationOnce(() => createMockProcess('', 'API error', 1));
109
+ const result = await generateAIReviewSummary(baseOptions);
110
+ expect(result).toBeNull();
111
+ });
112
+ it('should handle invalid JSON response from Claude', async () => {
113
+ // git diff --stat
114
+ spawnMock.mockImplementationOnce(() => createMockProcess('file.ts | 5 +++++', '', 0));
115
+ // git diff detailed
116
+ spawnMock.mockImplementationOnce(() => createMockProcess('+line', '', 0));
117
+ // claude returns invalid JSON
118
+ spawnMock.mockImplementationOnce(() => createMockProcess('This is not JSON', '', 0));
119
+ const result = await generateAIReviewSummary(baseOptions);
120
+ expect(result).toBeNull();
121
+ });
122
+ it('should extract JSON from Claude response with extra text', async () => {
123
+ // git diff --stat
124
+ spawnMock.mockImplementationOnce(() => createMockProcess('file.ts | 5 +++++', '', 0));
125
+ // git diff detailed
126
+ spawnMock.mockImplementationOnce(() => createMockProcess('+line', '', 0));
127
+ // claude returns JSON with surrounding text
128
+ const responseWithExtra = `Here's my analysis:
129
+ ${JSON.stringify({
130
+ summary: 'Test summary',
131
+ whatChanged: ['change 1'],
132
+ whyChanged: 'reason',
133
+ potentialIssues: [],
134
+ suggestions: [],
135
+ riskLevel: 'low',
136
+ })}
137
+ Let me know if you need more details.`;
138
+ spawnMock.mockImplementationOnce(() => createMockProcess(responseWithExtra, '', 0));
139
+ const result = await generateAIReviewSummary(baseOptions);
140
+ expect(result).not.toBeNull();
141
+ expect(result?.summary).toBe('Test summary');
142
+ });
143
+ it('should handle missing fields in Claude response with defaults', async () => {
144
+ // git diff --stat
145
+ spawnMock.mockImplementationOnce(() => createMockProcess('file.ts | 5 +++++', '', 0));
146
+ // git diff detailed
147
+ spawnMock.mockImplementationOnce(() => createMockProcess('+line', '', 0));
148
+ // claude returns partial JSON
149
+ spawnMock.mockImplementationOnce(() => createMockProcess('{}', '', 0));
150
+ const result = await generateAIReviewSummary(baseOptions);
151
+ expect(result).not.toBeNull();
152
+ expect(result?.summary).toBe('No summary available');
153
+ expect(result?.whatChanged).toEqual([]);
154
+ expect(result?.whyChanged).toBe('Unknown');
155
+ expect(result?.potentialIssues).toEqual([]);
156
+ expect(result?.suggestions).toEqual([]);
157
+ expect(result?.riskLevel).toBe('low');
158
+ });
159
+ it('should parse potential issues correctly', async () => {
160
+ // git diff --stat
161
+ spawnMock.mockImplementationOnce(() => createMockProcess('file.ts | 5 +++++', '', 0));
162
+ // git diff detailed
163
+ spawnMock.mockImplementationOnce(() => createMockProcess('+line', '', 0));
164
+ // claude returns response with issues
165
+ const responseWithIssues = JSON.stringify({
166
+ summary: 'Test',
167
+ whatChanged: [],
168
+ whyChanged: 'test',
169
+ potentialIssues: [
170
+ {
171
+ severity: 'warning',
172
+ title: 'Security issue',
173
+ description: 'Potential XSS vulnerability',
174
+ file: 'src/component.tsx',
175
+ line: 42,
176
+ },
177
+ {
178
+ severity: 'info',
179
+ title: 'Style suggestion',
180
+ description: 'Consider using const',
181
+ },
182
+ ],
183
+ suggestions: [],
184
+ riskLevel: 'medium',
185
+ });
186
+ spawnMock.mockImplementationOnce(() => createMockProcess(responseWithIssues, '', 0));
187
+ const result = await generateAIReviewSummary(baseOptions);
188
+ expect(result?.potentialIssues).toHaveLength(2);
189
+ expect(result?.potentialIssues[0]).toEqual({
190
+ severity: 'warning',
191
+ title: 'Security issue',
192
+ description: 'Potential XSS vulnerability',
193
+ file: 'src/component.tsx',
194
+ line: 42,
195
+ });
196
+ expect(result?.potentialIssues[1]?.file).toBeUndefined();
197
+ });
198
+ it('should handle process spawn error', async () => {
199
+ spawnMock.mockImplementationOnce(() => createMockProcess('', '', 0, { shouldError: true, errorMessage: 'spawn failed' }));
200
+ const result = await generateAIReviewSummary(baseOptions);
201
+ expect(result).toBeNull();
202
+ });
203
+ it('should truncate very long diffs in prompt', async () => {
204
+ const longDiff = 'A'.repeat(20000); // Longer than maxDiffLength (15000)
205
+ // git diff --stat
206
+ spawnMock.mockImplementationOnce(() => createMockProcess('file.ts | 5 +++++', '', 0));
207
+ // git diff detailed - very long
208
+ spawnMock.mockImplementationOnce(() => createMockProcess(longDiff, '', 0));
209
+ // claude CLI
210
+ spawnMock.mockImplementationOnce((cmd, args) => {
211
+ // Verify the prompt contains truncation marker
212
+ if (cmd === 'claude') {
213
+ const prompt = args[1]; // -p <prompt>
214
+ expect(prompt).toContain('... (truncated)');
215
+ }
216
+ return createMockProcess(JSON.stringify({
217
+ summary: 'test',
218
+ whatChanged: [],
219
+ whyChanged: 'test',
220
+ potentialIssues: [],
221
+ suggestions: [],
222
+ riskLevel: 'low',
223
+ }), '', 0);
224
+ });
225
+ await generateAIReviewSummary(baseOptions);
226
+ // The test passes if no errors and the mock verifications pass
227
+ expect(spawnMock).toHaveBeenCalledTimes(3);
228
+ });
229
+ });
230
+ });
231
+ //# sourceMappingURL=AIReviewGenerator.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"AIReviewGenerator.test.js","sourceRoot":"","sources":["../../../src/infra/ai/AIReviewGenerator.test.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=ci-workflow.test.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ci-workflow.test.d.ts","sourceRoot":"","sources":["../../../src/infra/ci/ci-workflow.test.ts"],"names":[],"mappings":""}
@@ -0,0 +1,98 @@
1
+ import { describe, it, expect } from 'vitest';
2
+ import { readFile } from 'node:fs/promises';
3
+ import { join, dirname } from 'node:path';
4
+ import { fileURLToPath } from 'node:url';
5
+ import { parse } from 'yaml';
6
+ describe('CI Workflow Configuration', () => {
7
+ const __filename = fileURLToPath(import.meta.url);
8
+ const __dirname = dirname(__filename);
9
+ // Navigate from packages/core/src/infra/ci to root
10
+ const rootDir = join(__dirname, '..', '..', '..', '..', '..');
11
+ const workflowPath = join(rootDir, '.github', 'workflows', 'ci.yml');
12
+ async function loadWorkflow() {
13
+ const content = await readFile(workflowPath, 'utf-8');
14
+ return parse(content);
15
+ }
16
+ describe('triggers', () => {
17
+ it('should trigger on push to main and develop branches', async () => {
18
+ const workflow = await loadWorkflow();
19
+ expect(workflow.on.push?.branches).toContain('main');
20
+ expect(workflow.on.push?.branches).toContain('develop');
21
+ });
22
+ it('should trigger on pull_request to main and develop branches', async () => {
23
+ const workflow = await loadWorkflow();
24
+ expect(workflow.on.pull_request?.branches).toContain('main');
25
+ expect(workflow.on.pull_request?.branches).toContain('develop');
26
+ });
27
+ });
28
+ describe('test job', () => {
29
+ it('should run on ubuntu-latest', async () => {
30
+ const workflow = await loadWorkflow();
31
+ expect(workflow.jobs.test?.['runs-on']).toBe('ubuntu-latest');
32
+ });
33
+ it('should checkout code', async () => {
34
+ const workflow = await loadWorkflow();
35
+ const steps = workflow.jobs.test?.steps ?? [];
36
+ const checkoutStep = steps.find((s) => s.uses?.startsWith('actions/checkout'));
37
+ expect(checkoutStep).toBeDefined();
38
+ });
39
+ it('should setup pnpm', async () => {
40
+ const workflow = await loadWorkflow();
41
+ const steps = workflow.jobs.test?.steps ?? [];
42
+ const pnpmStep = steps.find((s) => s.uses?.startsWith('pnpm/action-setup'));
43
+ expect(pnpmStep).toBeDefined();
44
+ });
45
+ it('should setup Node.js with version 22', async () => {
46
+ const workflow = await loadWorkflow();
47
+ const steps = workflow.jobs.test?.steps ?? [];
48
+ const nodeStep = steps.find((s) => s.uses?.startsWith('actions/setup-node'));
49
+ expect(nodeStep).toBeDefined();
50
+ expect(nodeStep?.with?.['node-version']).toBe(22);
51
+ });
52
+ it('should install dependencies with frozen lockfile', async () => {
53
+ const workflow = await loadWorkflow();
54
+ const steps = workflow.jobs.test?.steps ?? [];
55
+ const installStep = steps.find((s) => s.run?.includes('pnpm install') && s.run?.includes('--frozen-lockfile'));
56
+ expect(installStep).toBeDefined();
57
+ });
58
+ it('should run lint', async () => {
59
+ const workflow = await loadWorkflow();
60
+ const steps = workflow.jobs.test?.steps ?? [];
61
+ const lintStep = steps.find((s) => s.run?.includes('pnpm lint'));
62
+ expect(lintStep).toBeDefined();
63
+ });
64
+ it('should run typecheck', async () => {
65
+ const workflow = await loadWorkflow();
66
+ const steps = workflow.jobs.test?.steps ?? [];
67
+ const typecheckStep = steps.find((s) => s.run?.includes('tsc') && s.run?.includes('--noEmit'));
68
+ expect(typecheckStep).toBeDefined();
69
+ });
70
+ it('should build the project', async () => {
71
+ const workflow = await loadWorkflow();
72
+ const steps = workflow.jobs.test?.steps ?? [];
73
+ const buildStep = steps.find((s) => s.run?.includes('pnpm build'));
74
+ expect(buildStep).toBeDefined();
75
+ });
76
+ it('should run tests', async () => {
77
+ const workflow = await loadWorkflow();
78
+ const steps = workflow.jobs.test?.steps ?? [];
79
+ const testStep = steps.find((s) => s.run?.includes('pnpm test:run'));
80
+ expect(testStep).toBeDefined();
81
+ });
82
+ it('should run steps in correct order: install -> lint -> build -> typecheck -> test', async () => {
83
+ const workflow = await loadWorkflow();
84
+ const steps = workflow.jobs.test?.steps ?? [];
85
+ const installIndex = steps.findIndex((s) => s.run?.includes('pnpm install'));
86
+ const lintIndex = steps.findIndex((s) => s.run?.includes('pnpm lint'));
87
+ const buildIndex = steps.findIndex((s) => s.run?.includes('pnpm build'));
88
+ const typecheckIndex = steps.findIndex((s) => s.run?.includes('tsc'));
89
+ const testIndex = steps.findIndex((s) => s.run?.includes('pnpm test:run'));
90
+ // Build must come before typecheck so @claudetree/shared types are available
91
+ expect(installIndex).toBeLessThan(lintIndex);
92
+ expect(lintIndex).toBeLessThan(buildIndex);
93
+ expect(buildIndex).toBeLessThan(typecheckIndex);
94
+ expect(typecheckIndex).toBeLessThan(testIndex);
95
+ });
96
+ });
97
+ });
98
+ //# sourceMappingURL=ci-workflow.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ci-workflow.test.js","sourceRoot":"","sources":["../../../src/infra/ci/ci-workflow.test.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=Logger.test.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"Logger.test.d.ts","sourceRoot":"","sources":["../../../src/infra/logger/Logger.test.ts"],"names":[],"mappings":""}
@@ -0,0 +1,55 @@
1
+ import { describe, it, expect, beforeEach } from 'vitest';
2
+ import { createLogger } from './Logger.js';
3
+ describe('Logger', () => {
4
+ describe('createLogger', () => {
5
+ it('should create logger with correct namespace', () => {
6
+ const logger = createLogger('test-module');
7
+ expect(logger).toBeDefined();
8
+ expect(logger.info).toBeDefined();
9
+ expect(logger.error).toBeDefined();
10
+ expect(logger.debug).toBeDefined();
11
+ });
12
+ it('should create logger with info, error, debug methods', () => {
13
+ const logger = createLogger('mymodule');
14
+ expect(typeof logger.info).toBe('function');
15
+ expect(typeof logger.error).toBe('function');
16
+ expect(typeof logger.debug).toBe('function');
17
+ });
18
+ it('should use claudetree namespace prefix', () => {
19
+ const logger = createLogger('session');
20
+ // debug module sets namespace on the function
21
+ expect(logger.info.namespace).toBe('claudetree:session:info');
22
+ expect(logger.error.namespace).toBe('claudetree:session:error');
23
+ expect(logger.debug.namespace).toBe('claudetree:session:debug');
24
+ });
25
+ it('should create independent loggers for different modules', () => {
26
+ const logger1 = createLogger('module1');
27
+ const logger2 = createLogger('module2');
28
+ expect(logger1.info.namespace).not.toBe(logger2.info.namespace);
29
+ expect(logger1.info.namespace).toBe('claudetree:module1:info');
30
+ expect(logger2.info.namespace).toBe('claudetree:module2:info');
31
+ });
32
+ });
33
+ describe('Logger interface', () => {
34
+ let logger;
35
+ beforeEach(() => {
36
+ logger = createLogger('test');
37
+ });
38
+ it('should have info method that is callable', () => {
39
+ // Should not throw
40
+ expect(() => logger.info('test message')).not.toThrow();
41
+ });
42
+ it('should have error method that is callable', () => {
43
+ expect(() => logger.error('error message')).not.toThrow();
44
+ });
45
+ it('should have debug method that is callable', () => {
46
+ expect(() => logger.debug('debug message')).not.toThrow();
47
+ });
48
+ it('should support format strings', () => {
49
+ expect(() => logger.info('User %s logged in', 'john')).not.toThrow();
50
+ expect(() => logger.error('Error code: %d', 500)).not.toThrow();
51
+ expect(() => logger.debug('Object: %O', { key: 'value' })).not.toThrow();
52
+ });
53
+ });
54
+ });
55
+ //# sourceMappingURL=Logger.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"Logger.test.js","sourceRoot":"","sources":["../../../src/infra/logger/Logger.test.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=ValidationGateRunner.test.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ValidationGateRunner.test.d.ts","sourceRoot":"","sources":["../../../src/infra/validation/ValidationGateRunner.test.ts"],"names":[],"mappings":""}
@@ -0,0 +1,279 @@
1
+ import { describe, it, expect, vi, beforeEach, afterEach } from 'vitest';
2
+ import { ValidationGateRunner, DEFAULT_GATES, detectProjectGates, } from './ValidationGateRunner.js';
3
+ import * as childProcess from 'node:child_process';
4
+ vi.mock('node:child_process', () => ({
5
+ exec: vi.fn(),
6
+ }));
7
+ vi.mock('../logger/index.js', () => ({
8
+ createLogger: () => ({
9
+ info: vi.fn(),
10
+ error: vi.fn(),
11
+ debug: vi.fn(),
12
+ }),
13
+ }));
14
+ describe('ValidationGateRunner', () => {
15
+ let runner;
16
+ let execMock;
17
+ beforeEach(() => {
18
+ runner = new ValidationGateRunner();
19
+ execMock = vi.mocked(childProcess.exec);
20
+ execMock.mockReset();
21
+ });
22
+ afterEach(() => {
23
+ vi.clearAllMocks();
24
+ });
25
+ describe('runGate', () => {
26
+ const gate = {
27
+ name: 'test',
28
+ command: 'npm test',
29
+ required: true,
30
+ };
31
+ const options = {
32
+ cwd: '/test/project',
33
+ maxRetries: 3,
34
+ timeout: 10000,
35
+ };
36
+ it('should run gate successfully on first attempt', async () => {
37
+ execMock.mockImplementation((_cmd, _opts, callback) => {
38
+ if (typeof callback === 'function') {
39
+ callback(null, { stdout: 'All tests passed', stderr: '' });
40
+ }
41
+ return { on: vi.fn(), stdout: null, stderr: null };
42
+ });
43
+ const result = await runner.runGate(gate, options);
44
+ expect(result.gateName).toBe('test');
45
+ expect(result.passed).toBe(true);
46
+ expect(result.attempts).toBe(1);
47
+ expect(result.output).toContain('All tests passed');
48
+ expect(result.completedAt).toBeInstanceOf(Date);
49
+ });
50
+ it('should retry on failure and eventually pass', async () => {
51
+ let callCount = 0;
52
+ execMock.mockImplementation((_cmd, _opts, callback) => {
53
+ callCount++;
54
+ if (typeof callback === 'function') {
55
+ if (callCount < 2) {
56
+ callback(new Error('Test failed'), { stdout: '', stderr: 'Error' });
57
+ }
58
+ else {
59
+ callback(null, { stdout: 'Tests passed', stderr: '' });
60
+ }
61
+ }
62
+ return { on: vi.fn(), stdout: null, stderr: null };
63
+ });
64
+ const result = await runner.runGate(gate, options);
65
+ expect(result.passed).toBe(true);
66
+ expect(result.attempts).toBe(2);
67
+ });
68
+ it('should fail after max retries exceeded', async () => {
69
+ execMock.mockImplementation((_cmd, _opts, callback) => {
70
+ if (typeof callback === 'function') {
71
+ callback(new Error('Test failed'), { stdout: '', stderr: 'Error output' });
72
+ }
73
+ return { on: vi.fn(), stdout: null, stderr: null };
74
+ });
75
+ const result = await runner.runGate(gate, options);
76
+ expect(result.passed).toBe(false);
77
+ expect(result.attempts).toBe(3);
78
+ });
79
+ it('should truncate long output', async () => {
80
+ const longOutput = 'A'.repeat(2000);
81
+ execMock.mockImplementation((_cmd, _opts, callback) => {
82
+ if (typeof callback === 'function') {
83
+ callback(null, { stdout: longOutput, stderr: '' });
84
+ }
85
+ return { on: vi.fn(), stdout: null, stderr: null };
86
+ });
87
+ const result = await runner.runGate(gate, options);
88
+ expect(result.output?.length).toBeLessThan(longOutput.length);
89
+ expect(result.output).toContain('... (truncated)');
90
+ });
91
+ it('should use default timeout when not specified', async () => {
92
+ execMock.mockImplementation((_cmd, opts, callback) => {
93
+ // Check that timeout is set
94
+ expect(opts.timeout).toBe(5 * 60 * 1000);
95
+ if (typeof callback === 'function') {
96
+ callback(null, { stdout: 'OK', stderr: '' });
97
+ }
98
+ return { on: vi.fn(), stdout: null, stderr: null };
99
+ });
100
+ const optionsWithoutTimeout = {
101
+ cwd: '/test',
102
+ maxRetries: 1,
103
+ };
104
+ await runner.runGate(gate, optionsWithoutTimeout);
105
+ });
106
+ });
107
+ describe('runAll', () => {
108
+ const gates = [
109
+ { name: 'install', command: 'npm ci', required: true },
110
+ { name: 'test', command: 'npm test', required: true },
111
+ { name: 'lint', command: 'npm run lint', required: false },
112
+ ];
113
+ const options = {
114
+ cwd: '/test',
115
+ maxRetries: 1,
116
+ };
117
+ it('should run all gates in sequence', async () => {
118
+ const executionOrder = [];
119
+ execMock.mockImplementation((cmd, _opts, callback) => {
120
+ executionOrder.push(cmd);
121
+ if (typeof callback === 'function') {
122
+ callback(null, { stdout: 'OK', stderr: '' });
123
+ }
124
+ return { on: vi.fn(), stdout: null, stderr: null };
125
+ });
126
+ const result = await runner.runAll(gates, options);
127
+ expect(result.results).toHaveLength(3);
128
+ expect(result.allPassed).toBe(true);
129
+ expect(result.totalTime).toBeGreaterThanOrEqual(0);
130
+ expect(executionOrder).toEqual(['npm ci', 'npm test', 'npm run lint']);
131
+ });
132
+ it('should stop on required gate failure', async () => {
133
+ execMock.mockImplementation((cmd, _opts, callback) => {
134
+ if (typeof callback === 'function') {
135
+ if (cmd === 'npm test') {
136
+ callback(new Error('Failed'), { stdout: '', stderr: 'Error' });
137
+ }
138
+ else {
139
+ callback(null, { stdout: 'OK', stderr: '' });
140
+ }
141
+ }
142
+ return { on: vi.fn(), stdout: null, stderr: null };
143
+ });
144
+ const result = await runner.runAll(gates, options);
145
+ expect(result.allPassed).toBe(false);
146
+ expect(result.results).toHaveLength(2); // Stops after failed required gate
147
+ expect(result.results[1]?.passed).toBe(false);
148
+ });
149
+ it('should continue on optional gate failure', async () => {
150
+ const gatesWithOptional = [
151
+ { name: 'test', command: 'npm test', required: true },
152
+ { name: 'lint', command: 'npm run lint', required: false },
153
+ { name: 'build', command: 'npm run build', required: true },
154
+ ];
155
+ execMock.mockImplementation((cmd, _opts, callback) => {
156
+ if (typeof callback === 'function') {
157
+ if (cmd === 'npm run lint') {
158
+ callback(new Error('Lint failed'), { stdout: '', stderr: '' });
159
+ }
160
+ else {
161
+ callback(null, { stdout: 'OK', stderr: '' });
162
+ }
163
+ }
164
+ return { on: vi.fn(), stdout: null, stderr: null };
165
+ });
166
+ const result = await runner.runAll(gatesWithOptional, options);
167
+ expect(result.allPassed).toBe(true);
168
+ expect(result.results).toHaveLength(3);
169
+ expect(result.results[1]?.passed).toBe(false);
170
+ expect(result.results[2]?.passed).toBe(true);
171
+ });
172
+ });
173
+ describe('runWithAutoRetry', () => {
174
+ const gates = [
175
+ { name: 'test', command: 'npm test', required: true },
176
+ ];
177
+ it('should retry full validation on failure', async () => {
178
+ let overallCalls = 0;
179
+ execMock.mockImplementation((_cmd, _opts, callback) => {
180
+ overallCalls++;
181
+ if (typeof callback === 'function') {
182
+ if (overallCalls < 2) {
183
+ callback(new Error('Failed'), { stdout: '', stderr: '' });
184
+ }
185
+ else {
186
+ callback(null, { stdout: 'OK', stderr: '' });
187
+ }
188
+ }
189
+ return { on: vi.fn(), stdout: null, stderr: null };
190
+ });
191
+ const options = {
192
+ cwd: '/test',
193
+ maxRetries: 3,
194
+ };
195
+ const result = await runner.runWithAutoRetry(gates, options);
196
+ expect(result.allPassed).toBe(true);
197
+ });
198
+ it('should call onRetry callback on failure', async () => {
199
+ // runWithAutoRetry calls runAll, which calls runGate
200
+ // runGate itself retries maxRetries times before failing
201
+ // Then runWithAutoRetry retries the whole runAll
202
+ // So we need to fail enough times to:
203
+ // 1. Fail runGate's retries (maxRetries times)
204
+ // 2. Then onRetry is called
205
+ // 3. Then succeed on next overall attempt
206
+ let callCount = 0;
207
+ execMock.mockImplementation((_cmd, _opts, callback) => {
208
+ callCount++;
209
+ if (typeof callback === 'function') {
210
+ // With maxRetries=2:
211
+ // - runGate tries 2 times (calls 1-2), fails
212
+ // - onRetry(1, 'test') is called
213
+ // - runGate tries 2 times (calls 3-4), succeeds on 3rd
214
+ if (callCount <= 2) {
215
+ callback(new Error('Failed'), { stdout: '', stderr: '' });
216
+ }
217
+ else {
218
+ callback(null, { stdout: 'OK', stderr: '' });
219
+ }
220
+ }
221
+ return { on: vi.fn(), stdout: null, stderr: null };
222
+ });
223
+ const onRetry = vi.fn();
224
+ const options = {
225
+ cwd: '/test',
226
+ maxRetries: 2,
227
+ onRetry,
228
+ };
229
+ const result = await runner.runWithAutoRetry(gates, options);
230
+ expect(onRetry).toHaveBeenCalledWith(1, 'test');
231
+ expect(result.allPassed).toBe(true);
232
+ });
233
+ it('should fail after overall max retries', async () => {
234
+ execMock.mockImplementation((_cmd, _opts, callback) => {
235
+ if (typeof callback === 'function') {
236
+ callback(new Error('Always fail'), { stdout: '', stderr: '' });
237
+ }
238
+ return { on: vi.fn(), stdout: null, stderr: null };
239
+ });
240
+ const options = {
241
+ cwd: '/test',
242
+ maxRetries: 2,
243
+ };
244
+ const result = await runner.runWithAutoRetry(gates, options);
245
+ expect(result.allPassed).toBe(false);
246
+ });
247
+ });
248
+ describe('DEFAULT_GATES', () => {
249
+ it('should have node gates defined', () => {
250
+ expect(DEFAULT_GATES.node).toBeDefined();
251
+ expect(DEFAULT_GATES.node).toHaveLength(4);
252
+ expect(DEFAULT_GATES.node[0]?.name).toBe('install');
253
+ expect(DEFAULT_GATES.node[1]?.name).toBe('test');
254
+ expect(DEFAULT_GATES.node[2]?.name).toBe('type');
255
+ expect(DEFAULT_GATES.node[3]?.name).toBe('lint');
256
+ });
257
+ it('should have pnpm gates defined', () => {
258
+ expect(DEFAULT_GATES.pnpm).toBeDefined();
259
+ expect(DEFAULT_GATES.pnpm).toHaveLength(4);
260
+ expect(DEFAULT_GATES.pnpm[0]?.command).toContain('pnpm install');
261
+ });
262
+ it('should have python gates defined', () => {
263
+ expect(DEFAULT_GATES.python).toBeDefined();
264
+ expect(DEFAULT_GATES.python[0]?.name).toBe('test');
265
+ expect(DEFAULT_GATES.python[0]?.command).toBe('pytest');
266
+ });
267
+ it('should mark required gates correctly', () => {
268
+ expect(DEFAULT_GATES.node[0]?.required).toBe(true);
269
+ expect(DEFAULT_GATES.node[3]?.required).toBe(false);
270
+ });
271
+ });
272
+ describe('detectProjectGates', () => {
273
+ it('should return pnpm gates by default', () => {
274
+ const gates = detectProjectGates('/some/path');
275
+ expect(gates).toEqual(DEFAULT_GATES.pnpm);
276
+ });
277
+ });
278
+ });
279
+ //# sourceMappingURL=ValidationGateRunner.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ValidationGateRunner.test.js","sourceRoot":"","sources":["../../../src/infra/validation/ValidationGateRunner.test.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@claudetree/core",
3
- "version": "0.4.4",
3
+ "version": "0.4.5",
4
4
  "description": "Core domain and infrastructure for claudetree",
5
5
  "type": "module",
6
6
  "main": "./dist/index.js",
@@ -23,17 +23,18 @@
23
23
  "homepage": "https://github.com/wonjangcloud9/claude-tree#readme",
24
24
  "license": "MIT",
25
25
  "dependencies": {
26
- "debug": "^4.4.0",
27
- "execa": "^9.5.0",
28
- "octokit": "^4.1.0",
29
- "ws": "^8.18.0",
30
- "@claudetree/shared": "0.4.4"
26
+ "debug": "^4.4.3",
27
+ "execa": "^9.6.1",
28
+ "octokit": "^5.0.5",
29
+ "ws": "^8.19.0",
30
+ "@claudetree/shared": "0.4.5"
31
31
  },
32
32
  "devDependencies": {
33
33
  "@types/debug": "^4.1.12",
34
- "@types/ws": "^8.5.0",
35
- "typescript": "^5.7.0",
36
- "vitest": "^3.0.0"
34
+ "@types/ws": "^8.18.1",
35
+ "typescript": "^5.9.3",
36
+ "vitest": "^3.2.4",
37
+ "yaml": "^2.8.2"
37
38
  },
38
39
  "scripts": {
39
40
  "build": "tsc",