Skip to content

Commit c0e3ee5

Browse files
committed
Hmm
1 parent a69635f commit c0e3ee5

File tree

4 files changed

+47
-38
lines changed

4 files changed

+47
-38
lines changed

packages/graphql-yoga/src/plugins/types.ts

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -57,7 +57,7 @@ export type Plugin<
5757
* Use this hook with your own risk. It is still experimental and may change in the future.
5858
* @internal
5959
*/
60-
onResultProcess?: OnResultProcess
60+
onResultProcess?: OnResultProcess<TServerContext>
6161
}
6262

6363
export type OnYogaInitHook<TServerContext extends Record<string, any>> = (
@@ -122,8 +122,8 @@ export interface OnParamsEventPayload {
122122
fetchAPI: FetchAPI
123123
}
124124

125-
export type OnResultProcess = (
126-
payload: OnResultProcessEventPayload,
125+
export type OnResultProcess<TServerContext> = (
126+
payload: OnResultProcessEventPayload<TServerContext>,
127127
) => PromiseOrValue<void>
128128

129129
export type ResultProcessorInput =
@@ -136,7 +136,7 @@ export type ResultProcessor = (
136136
acceptedMediaType: string,
137137
) => PromiseOrValue<Response>
138138

139-
export interface OnResultProcessEventPayload {
139+
export interface OnResultProcessEventPayload<TServerContext> {
140140
request: Request
141141
result: ResultProcessorInput
142142
setResult(result: ResultProcessorInput): void
@@ -147,6 +147,7 @@ export interface OnResultProcessEventPayload {
147147
acceptedMediaType: string,
148148
): void
149149
fetchAPI: FetchAPI
150+
serverContext: TServerContext
150151
endResponse(response: Response): void
151152
}
152153

packages/graphql-yoga/src/process-request.ts

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,19 +8,21 @@ import {
88
} from './plugins/types.js'
99
import { FetchAPI, GraphQLParams } from './types.js'
1010

11-
export async function processResult({
11+
export async function processResult<TServerContext>({
1212
request,
1313
result,
1414
fetchAPI,
15+
serverContext,
1516
onResultProcessHooks,
1617
}: {
1718
request: Request
1819
result: ResultProcessorInput
1920
fetchAPI: FetchAPI
21+
serverContext: TServerContext
2022
/**
2123
* Response Hooks
2224
*/
23-
onResultProcessHooks: OnResultProcess[]
25+
onResultProcessHooks: OnResultProcess<TServerContext>[]
2426
}) {
2527
let resultProcessor: ResultProcessor | undefined
2628

@@ -42,6 +44,7 @@ export async function processResult({
4244
acceptedMediaType = newAcceptedMimeType
4345
},
4446
fetchAPI,
47+
serverContext,
4548
endResponse(response) {
4649
earlyResponse = response
4750
},

packages/graphql-yoga/src/server.ts

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -216,7 +216,7 @@ export class YogaServer<
216216
>
217217
private onRequestParseHooks: OnRequestParseHook<TServerContext>[]
218218
private onParamsHooks: OnParamsHook[]
219-
private onResultProcessHooks: OnResultProcess[]
219+
private onResultProcessHooks: OnResultProcess<TServerContext>[]
220220
private maskedErrorsOpts: YogaMaskedErrorOpts | null
221221
private id: string
222222

@@ -356,7 +356,7 @@ export class YogaServer<
356356
useResultProcessors({
357357
legacySSE: options?.legacySse !== false,
358358
}),
359-
useErrorHandling((error, request) => {
359+
useErrorHandling((error, request, serverContext) => {
360360
const errors = handleError(error, this.maskedErrorsOpts, this.logger)
361361

362362
const result = {
@@ -368,6 +368,7 @@ export class YogaServer<
368368
result,
369369
fetchAPI: this.fetchAPI,
370370
onResultProcessHooks: this.onResultProcessHooks,
371+
serverContext,
371372
})
372373
}),
373374
...(options?.plugins ?? []),
@@ -603,6 +604,7 @@ export class YogaServer<
603604
result,
604605
fetchAPI: this.fetchAPI,
605606
onResultProcessHooks: this.onResultProcessHooks,
607+
serverContext,
606608
})
607609
}
608610
}

packages/plugins/graphql-sse/src/index.ts

Lines changed: 33 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@ export function useGraphQLSSE(
2424
options: GraphQLSSEPluginOptions = {
2525
pubsub: createPubSub(),
2626
},
27-
): Plugin<YogaInitialContext> {
27+
): Plugin<YogaInitialContext, { waitUntil(p: Promise<unknown>): void }> {
2828
const { pubsub } = options
2929
const tokenByRequest = new WeakMap<Request, string>()
3030
const operationIdByRequest = new WeakMap<Request, string>()
@@ -80,51 +80,54 @@ export function useGraphQLSSE(
8080
operationIdByRequest.set(request, params.extensions.operationId)
8181
}
8282
},
83-
onResultProcess({ request, result, fetchAPI, endResponse }) {
83+
onResultProcess({ request, result, fetchAPI, serverContext, endResponse }) {
8484
const token = tokenByRequest.get(request)
8585
if (token) {
8686
const operationId = operationIdByRequest.get(request)
8787
// Batching is not supported by GraphQL SSE yet
8888
if (operationId && !Array.isArray(result)) {
89-
Promise.resolve().then(async () => {
90-
if (isAsyncIterable(result)) {
91-
const asyncIterator = result[Symbol.asyncIterator]()
92-
pubsub
93-
.subscribe('graphql-sse-unsubscribe', operationId)
94-
.next()
95-
.finally(() => {
96-
asyncIterator.return?.()
97-
})
98-
let iteratorValue: IteratorResult<ExecutionResult>
99-
while (!(iteratorValue = await asyncIterator.next()).done) {
100-
const chunk = iteratorValue.value
89+
serverContext.waitUntil(
90+
Promise.resolve().then(async () => {
91+
if (isAsyncIterable(result)) {
92+
const asyncIterator = result[Symbol.asyncIterator]()
93+
pubsub
94+
.subscribe('graphql-sse-unsubscribe', operationId)
95+
.next()
96+
.finally(() => {
97+
asyncIterator.return?.()
98+
})
99+
let iteratorValue: IteratorResult<ExecutionResult>
100+
while (!(iteratorValue = await asyncIterator.next()).done) {
101+
const chunk = iteratorValue.value
102+
const messageJson = {
103+
id: operationId,
104+
payload: chunk,
105+
}
106+
const messageStr = `event: next\nid: ${operationId}\ndata: ${JSON.stringify(
107+
messageJson,
108+
)}\n\n`
109+
pubsub.publish('graphql-sse-subscribe', token, messageStr)
110+
}
111+
} else {
101112
const messageJson = {
102113
id: operationId,
103-
payload: chunk,
114+
payload: result,
104115
}
105116
const messageStr = `event: next\nid: ${operationId}\ndata: ${JSON.stringify(
106117
messageJson,
107118
)}\n\n`
108119
pubsub.publish('graphql-sse-subscribe', token, messageStr)
109120
}
110-
} else {
111-
const messageJson = {
121+
const completeMessageJson = {
112122
id: operationId,
113-
payload: result,
114123
}
115-
const messageStr = `event: next\nid: ${operationId}\ndata: ${JSON.stringify(
116-
messageJson,
124+
const completeMessageStr = `event: complete\ndata: ${JSON.stringify(
125+
completeMessageJson,
117126
)}\n\n`
118-
pubsub.publish('graphql-sse-subscribe', token, messageStr)
119-
}
120-
const completeMessageJson = {
121-
id: operationId,
122-
}
123-
const completeMessageStr = `event: complete\ndata: ${JSON.stringify(
124-
completeMessageJson,
125-
)}\n\n`
126-
pubsub.publish('graphql-sse-subscribe', token, completeMessageStr)
127-
})
127+
pubsub.publish('graphql-sse-subscribe', token, completeMessageStr)
128+
}),
129+
)
130+
128131
endResponse(
129132
new fetchAPI.Response(null, {
130133
status: 202,

0 commit comments

Comments
 (0)