Skip to content

Commit 451d412

Browse files
committed
fixes
1. use throwIfAborted 2. use correct path when aborting for a fieldPath within executeFields 3. polish tests to throw a proper Error as the reason
1 parent ae108b2 commit 451d412

File tree

2 files changed

+39
-31
lines changed

2 files changed

+39
-31
lines changed

src/execution/__tests__/abort-signal-test.ts

Lines changed: 21 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -61,7 +61,7 @@ const schema = buildSchema(`
6161
`);
6262

6363
describe('Execute: Cancellation', () => {
64-
it('should stop the execution when aborted', async () => {
64+
it('should stop the execution when aborted during object field completion', async () => {
6565
const abortController = new AbortController();
6666
const document = parse(`
6767
query {
@@ -89,7 +89,7 @@ describe('Execute: Cancellation', () => {
8989
},
9090
});
9191

92-
abortController.abort('Aborted');
92+
abortController.abort(new Error('Aborted'));
9393

9494
const result = await resultPromise;
9595

@@ -100,8 +100,8 @@ describe('Execute: Cancellation', () => {
100100
errors: [
101101
{
102102
message: 'Aborted',
103-
path: ['todo'],
104-
locations: [{ line: 3, column: 9 }],
103+
path: ['todo', 'id'],
104+
locations: [{ line: 4, column: 11 }],
105105
},
106106
],
107107
});
@@ -135,7 +135,7 @@ describe('Execute: Cancellation', () => {
135135
},
136136
});
137137

138-
abortController.abort('Aborted');
138+
abortController.abort(new Error('Aborted'));
139139

140140
const result = await resultPromise;
141141

@@ -149,8 +149,8 @@ describe('Execute: Cancellation', () => {
149149
errors: [
150150
{
151151
message: 'Aborted',
152-
path: ['todo', 'author'],
153-
locations: [{ line: 5, column: 11 }],
152+
path: ['todo', 'author', 'id'],
153+
locations: [{ line: 6, column: 13 }],
154154
},
155155
],
156156
});
@@ -165,9 +165,7 @@ describe('Execute: Cancellation', () => {
165165
... on Todo @defer {
166166
text
167167
author {
168-
... on Author @defer {
169-
id
170-
}
168+
id
171169
}
172170
}
173171
}
@@ -189,7 +187,7 @@ describe('Execute: Cancellation', () => {
189187
abortSignal: abortController.signal,
190188
});
191189

192-
abortController.abort('Aborted');
190+
abortController.abort(new Error('Aborted'));
193191

194192
const result = await resultPromise;
195193

@@ -200,8 +198,8 @@ describe('Execute: Cancellation', () => {
200198
errors: [
201199
{
202200
message: 'Aborted',
203-
path: ['todo'],
204-
locations: [{ line: 3, column: 9 }],
201+
path: ['todo', 'id'],
202+
locations: [{ line: 4, column: 11 }],
205203
},
206204
],
207205
});
@@ -216,9 +214,7 @@ describe('Execute: Cancellation', () => {
216214
... on Todo @defer {
217215
text
218216
author {
219-
... on Author @defer {
220-
id
221-
}
217+
id
222218
}
223219
}
224220
}
@@ -232,9 +228,8 @@ describe('Execute: Cancellation', () => {
232228
Promise.resolve({
233229
id: '1',
234230
text: 'hello world',
235-
/* c8 ignore next 2 */
236-
author: async () =>
237-
Promise.resolve(() => expect.fail('Should not be called')),
231+
/* c8 ignore next */
232+
author: () => expect.fail('Should not be called'),
238233
}),
239234
},
240235
abortController.signal,
@@ -244,7 +239,7 @@ describe('Execute: Cancellation', () => {
244239
await resolveOnNextTick();
245240
await resolveOnNextTick();
246241

247-
abortController.abort('Aborted');
242+
abortController.abort(new Error('Aborted'));
248243

249244
const result = await resultPromise;
250245

@@ -264,6 +259,8 @@ describe('Execute: Cancellation', () => {
264259
errors: [
265260
{
266261
message: 'Aborted',
262+
path: ['todo', 'text'],
263+
locations: [{ line: 6, column: 13 }],
267264
},
268265
],
269266
id: '0',
@@ -294,7 +291,7 @@ describe('Execute: Cancellation', () => {
294291
},
295292
});
296293

297-
abortController.abort('Aborted');
294+
abortController.abort(new Error('Aborted'));
298295

299296
const result = await resultPromise;
300297

@@ -325,7 +322,9 @@ describe('Execute: Cancellation', () => {
325322
}
326323
}
327324
`);
328-
abortController.abort('Aborted');
325+
326+
abortController.abort(new Error('Aborted'));
327+
329328
const result = await execute({
330329
document,
331330
schema,

src/execution/execute.ts

Lines changed: 18 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -517,8 +517,10 @@ export function validateExecutionArgs(
517517
abortSignal,
518518
} = args;
519519

520-
if (abortSignal?.aborted) {
521-
return [new GraphQLError(abortSignal.reason)];
520+
try {
521+
abortSignal?.throwIfAborted();
522+
} catch (rawError: unknown) {
523+
return [locatedError(rawError, undefined)];
522524
}
523525

524526
// If the schema used for execution is invalid, throw an error.
@@ -665,10 +667,11 @@ function executeFieldsSerially(
665667
groupedFieldSet,
666668
(graphqlWrappedResult, [responseName, fieldDetailsList]) => {
667669
const fieldPath = addPath(path, responseName, parentType.name);
668-
const abortSignal = exeContext.validatedExecutionArgs.abortSignal;
669-
if (abortSignal?.aborted) {
670+
try {
671+
exeContext.validatedExecutionArgs.abortSignal?.throwIfAborted();
672+
} catch (rawError) {
670673
handleFieldError(
671-
new Error(abortSignal.reason),
674+
rawError,
672675
exeContext,
673676
parentType,
674677
fieldDetailsList,
@@ -728,12 +731,18 @@ function executeFields(
728731

729732
try {
730733
for (const [responseName, fieldDetailsList] of groupedFieldSet) {
731-
const abortSignal = exeContext.validatedExecutionArgs.abortSignal;
732-
if (abortSignal?.aborted) {
733-
throw new GraphQLError(abortSignal.reason);
734+
const fieldPath = addPath(path, responseName, parentType.name);
735+
736+
try {
737+
exeContext.validatedExecutionArgs.abortSignal?.throwIfAborted();
738+
} catch (rawError) {
739+
throw locatedError(
740+
rawError,
741+
toNodes(fieldDetailsList),
742+
pathToArray(fieldPath),
743+
);
734744
}
735745

736-
const fieldPath = addPath(path, responseName, parentType.name);
737746
const result = executeField(
738747
exeContext,
739748
parentType,

0 commit comments

Comments
 (0)