-
Notifications
You must be signed in to change notification settings - Fork 6
Expand file tree
/
Copy pathadapter.ts
More file actions
100 lines (91 loc) · 2.73 KB
/
adapter.ts
File metadata and controls
100 lines (91 loc) · 2.73 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
/**
* SuperTest GraphQL Adapter
*
* Provides a GraphQLAdapter implementation for use with graphql-server-test,
* allowing the generated ORM client to work with HTTP server testing
* while maintaining cookies across requests.
*/
import type supertest from 'supertest';
import type {
GraphQLAdapter,
GraphQLError,
QueryResult,
} from '@constructive-io/graphql-types';
/**
* GraphQL adapter that wraps a SuperTest agent for HTTP-based testing.
* This implements the GraphQLAdapter interface, allowing the SDK
* to work with the graphql-server-test infrastructure with full HTTP support.
*
* Key features:
* - Maintains cookies across requests (via SuperTest's cookie jar)
* - Supports custom headers (including CSRF tokens)
* - Full HTTP request/response cycle for testing middleware
*
* @example
* ```typescript
* import { getConnections, SuperTestAdapter } from 'graphql-server-test';
* import { createClient } from '@my-org/my-sdk';
*
* const { request, teardown } = await getConnections({ schemas: ['app_public'] });
*
* const sdk = createClient({ adapter: new SuperTestAdapter(request) });
*
* // Sign in - cookies are automatically stored
* const signInResult = await sdk.mutation.signIn({
* input: { email: 'test@example.com', password: 'password123' }
* }).execute();
*
* // Subsequent requests include cookies automatically
* const currentUser = await sdk.user.findFirst({
* select: { id: true, email: true }
* }).execute();
* ```
*/
export class SuperTestAdapter implements GraphQLAdapter {
private headers: Record<string, string> = {};
constructor(private agent: supertest.Agent) {}
async execute<T>(
document: string,
variables?: Record<string, unknown>
): Promise<QueryResult<T>> {
const response = await this.agent
.post('/graphql')
.set('Content-Type', 'application/json')
.set('Accept', 'application/json')
.set(this.headers)
.send({
query: document,
variables: variables ?? {},
});
const body = response.body as {
data?: T;
errors?: GraphQLError[];
};
if (body.errors && body.errors.length > 0) {
return {
ok: false,
data: null,
errors: body.errors,
};
}
return {
ok: true,
data: body.data as T,
errors: undefined,
};
}
/**
* Set headers to include in all subsequent requests.
* Useful for setting CSRF tokens or other custom headers.
*/
setHeaders(headers: Record<string, string>): void {
this.headers = { ...this.headers, ...headers };
}
/**
* Get the SuperTest agent for direct HTTP access.
* Useful for non-GraphQL requests (e.g., REST endpoints, file uploads).
*/
getAgent(): supertest.Agent {
return this.agent;
}
}