Skip to content

Commit 6305395

Browse files
waleedlatif1claude
andcommitted
test(executor): add route-level tests for Response block auth gating
Verify that internal JWT callers receive standard format while external callers (API key, session) get Response block formatting. Tests the server-side condition directly using workflowHasResponseBlock and createHttpResponseFromBlock with AuthType constants. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
1 parent 0673dbe commit 6305395

File tree

1 file changed

+115
-0
lines changed

1 file changed

+115
-0
lines changed
Lines changed: 115 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,115 @@
1+
/**
2+
* Tests that internal JWT callers receive the standard response format
3+
* even when the child workflow has a Response block.
4+
*
5+
* @vitest-environment node
6+
*/
7+
8+
import { beforeEach, describe, expect, it } from 'vitest'
9+
import { AuthType } from '@/lib/auth/hybrid'
10+
import type { ExecutionResult } from '@/lib/workflows/types'
11+
import { createHttpResponseFromBlock, workflowHasResponseBlock } from '@/lib/workflows/utils'
12+
13+
function buildExecutionResult(overrides: Partial<ExecutionResult> = {}): ExecutionResult {
14+
return {
15+
success: true,
16+
output: { data: { issues: [] }, status: 200, headers: {} },
17+
logs: [
18+
{
19+
blockId: 'response-1',
20+
blockType: 'response',
21+
blockName: 'Response',
22+
success: true,
23+
output: { data: { issues: [] }, status: 200, headers: {} },
24+
startedAt: '2026-01-01T00:00:00Z',
25+
endedAt: '2026-01-01T00:00:01Z',
26+
},
27+
],
28+
metadata: {
29+
duration: 500,
30+
startTime: '2026-01-01T00:00:00Z',
31+
endTime: '2026-01-01T00:00:01Z',
32+
},
33+
...overrides,
34+
}
35+
}
36+
37+
describe('Response block gating by auth type', () => {
38+
let resultWithResponseBlock: ExecutionResult
39+
40+
beforeEach(() => {
41+
resultWithResponseBlock = buildExecutionResult()
42+
})
43+
44+
it('should detect a Response block in execution result', () => {
45+
expect(workflowHasResponseBlock(resultWithResponseBlock)).toBe(true)
46+
})
47+
48+
it('should not detect a Response block when none exists', () => {
49+
const resultWithoutResponseBlock = buildExecutionResult({
50+
output: { result: 'hello' },
51+
logs: [
52+
{
53+
blockId: 'agent-1',
54+
blockType: 'agent',
55+
blockName: 'Agent',
56+
success: true,
57+
output: { result: 'hello' },
58+
startedAt: '2026-01-01T00:00:00Z',
59+
endedAt: '2026-01-01T00:00:01Z',
60+
},
61+
],
62+
})
63+
expect(workflowHasResponseBlock(resultWithoutResponseBlock)).toBe(false)
64+
})
65+
66+
it('should skip Response block formatting for internal JWT callers', () => {
67+
const authType = AuthType.INTERNAL_JWT
68+
const hasResponseBlock = workflowHasResponseBlock(resultWithResponseBlock)
69+
70+
expect(hasResponseBlock).toBe(true)
71+
72+
// This mirrors the route.ts condition:
73+
// if (auth.authType !== AuthType.INTERNAL_JWT && workflowHasResponseBlock(...))
74+
const shouldFormatAsResponseBlock = authType !== AuthType.INTERNAL_JWT && hasResponseBlock
75+
expect(shouldFormatAsResponseBlock).toBe(false)
76+
})
77+
78+
it('should apply Response block formatting for API key callers', () => {
79+
const authType = AuthType.API_KEY
80+
const hasResponseBlock = workflowHasResponseBlock(resultWithResponseBlock)
81+
82+
const shouldFormatAsResponseBlock = authType !== AuthType.INTERNAL_JWT && hasResponseBlock
83+
expect(shouldFormatAsResponseBlock).toBe(true)
84+
85+
const response = createHttpResponseFromBlock(resultWithResponseBlock)
86+
expect(response.status).toBe(200)
87+
})
88+
89+
it('should apply Response block formatting for session callers', () => {
90+
const authType = AuthType.SESSION
91+
const hasResponseBlock = workflowHasResponseBlock(resultWithResponseBlock)
92+
93+
const shouldFormatAsResponseBlock = authType !== AuthType.INTERNAL_JWT && hasResponseBlock
94+
expect(shouldFormatAsResponseBlock).toBe(true)
95+
})
96+
97+
it('should return raw user data via createHttpResponseFromBlock', async () => {
98+
const response = createHttpResponseFromBlock(resultWithResponseBlock)
99+
const body = await response.json()
100+
101+
// Response block returns the user-defined data directly (no success/executionId wrapper)
102+
expect(body).toEqual({ issues: [] })
103+
expect(body.success).toBeUndefined()
104+
expect(body.executionId).toBeUndefined()
105+
})
106+
107+
it('should respect custom status codes from Response block', () => {
108+
const result = buildExecutionResult({
109+
output: { data: { error: 'Not found' }, status: 404, headers: {} },
110+
})
111+
112+
const response = createHttpResponseFromBlock(result)
113+
expect(response.status).toBe(404)
114+
})
115+
})

0 commit comments

Comments
 (0)