@apollo/gateway 0.42.0 → 0.43.0
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.
- package/CHANGELOG.md +26 -2
- package/dist/__generated__/graphqlTypes.d.ts +27 -21
- package/dist/__generated__/graphqlTypes.d.ts.map +1 -1
- package/dist/__generated__/graphqlTypes.js +6 -6
- package/dist/__generated__/graphqlTypes.js.map +1 -1
- package/dist/executeQueryPlan.d.ts +3 -2
- package/dist/executeQueryPlan.d.ts.map +1 -1
- package/dist/executeQueryPlan.js +26 -1
- package/dist/executeQueryPlan.js.map +1 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +3 -1
- package/dist/index.js.map +1 -1
- package/dist/utilities/graphql.d.ts +1 -2
- package/dist/utilities/graphql.d.ts.map +1 -1
- package/dist/utilities/graphql.js +1 -9
- package/dist/utilities/graphql.js.map +1 -1
- package/package.json +5 -5
- package/src/__generated__/graphqlTypes.ts +27 -22
- package/src/__tests__/buildQueryPlan.test.ts +277 -26
- package/src/__tests__/executeQueryPlan.test.ts +264 -7
- package/src/__tests__/execution-utils.ts +6 -3
- package/src/__tests__/gateway/endToEnd.test.ts +2 -2
- package/src/__tests__/gateway/opentelemetry.test.ts +1 -1
- package/src/__tests__/gateway/queryPlanCache.test.ts +1 -1
- package/src/__tests__/gateway/reporting.test.ts +1 -1
- package/src/__tests__/integration/aliases.test.ts +1 -1
- package/src/datasources/__tests__/LocalGraphQLDataSource.test.ts +1 -1
- package/src/executeQueryPlan.ts +41 -11
- package/src/index.ts +10 -1
- package/src/utilities/graphql.ts +0 -22
|
@@ -14,11 +14,11 @@ export type Scalars = {
|
|
|
14
14
|
};
|
|
15
15
|
|
|
16
16
|
export type ApiMonitoringReport = {
|
|
17
|
+
endedAt: Scalars['Timestamp'];
|
|
17
18
|
error: Error;
|
|
18
19
|
request: Request;
|
|
19
20
|
response?: Maybe<Response>;
|
|
20
21
|
startedAt: Scalars['Timestamp'];
|
|
21
|
-
endedAt: Scalars['Timestamp'];
|
|
22
22
|
/** Tags can include things like version and package name */
|
|
23
23
|
tags?: Maybe<Array<Scalars['String']>>;
|
|
24
24
|
};
|
|
@@ -29,11 +29,11 @@ export type Error = {
|
|
|
29
29
|
};
|
|
30
30
|
|
|
31
31
|
export enum ErrorCode {
|
|
32
|
-
InvalidBody = 'INVALID_BODY',
|
|
33
|
-
UnexpectedResponse = 'UNEXPECTED_RESPONSE',
|
|
34
32
|
ConnectionFailed = 'CONNECTION_FAILED',
|
|
33
|
+
InvalidBody = 'INVALID_BODY',
|
|
34
|
+
Other = 'OTHER',
|
|
35
35
|
Timeout = 'TIMEOUT',
|
|
36
|
-
|
|
36
|
+
UnexpectedResponse = 'UNEXPECTED_RESPONSE'
|
|
37
37
|
}
|
|
38
38
|
|
|
39
39
|
export type FetchError = {
|
|
@@ -43,14 +43,14 @@ export type FetchError = {
|
|
|
43
43
|
};
|
|
44
44
|
|
|
45
45
|
export enum FetchErrorCode {
|
|
46
|
-
/** This token provided is not a valid graph token. Do not retry */
|
|
47
|
-
AuthenticationFailed = 'AUTHENTICATION_FAILED',
|
|
48
46
|
/** This token does not have access to fetch the schema for this ref. Do not retry. */
|
|
49
47
|
AccessDenied = 'ACCESS_DENIED',
|
|
50
|
-
/**
|
|
51
|
-
|
|
48
|
+
/** This token provided is not a valid graph token. Do not retry */
|
|
49
|
+
AuthenticationFailed = 'AUTHENTICATION_FAILED',
|
|
52
50
|
/** An internal server error occurred. Please retry with some backoff */
|
|
53
|
-
RetryLater = 'RETRY_LATER'
|
|
51
|
+
RetryLater = 'RETRY_LATER',
|
|
52
|
+
/** The graphRef passed is not a valid ref or no configuration for that ref is found. Do not retry */
|
|
53
|
+
UnknownRef = 'UNKNOWN_REF'
|
|
54
54
|
}
|
|
55
55
|
|
|
56
56
|
export type HttpHeader = {
|
|
@@ -60,14 +60,14 @@ export type HttpHeader = {
|
|
|
60
60
|
|
|
61
61
|
export type Message = {
|
|
62
62
|
__typename?: 'Message';
|
|
63
|
-
level: MessageLevel;
|
|
64
63
|
body: Scalars['String'];
|
|
64
|
+
level: MessageLevel;
|
|
65
65
|
};
|
|
66
66
|
|
|
67
67
|
export enum MessageLevel {
|
|
68
68
|
Error = 'ERROR',
|
|
69
|
-
|
|
70
|
-
|
|
69
|
+
Info = 'INFO',
|
|
70
|
+
Warn = 'WARN'
|
|
71
71
|
}
|
|
72
72
|
|
|
73
73
|
export type Mutation = {
|
|
@@ -89,32 +89,37 @@ export type Query = {
|
|
|
89
89
|
|
|
90
90
|
|
|
91
91
|
export type QueryRouterConfigArgs = {
|
|
92
|
-
ref: Scalars['String'];
|
|
93
92
|
apiKey: Scalars['String'];
|
|
94
|
-
|
|
93
|
+
ref: Scalars['String'];
|
|
94
|
+
unlessIdIn?: Maybe<Array<Scalars['ID']>>;
|
|
95
95
|
};
|
|
96
96
|
|
|
97
97
|
export type Request = {
|
|
98
|
-
url: Scalars['String'];
|
|
99
|
-
headers?: Maybe<Array<HttpHeader>>;
|
|
100
98
|
body?: Maybe<Scalars['String']>;
|
|
99
|
+
headers?: Maybe<Array<HttpHeader>>;
|
|
100
|
+
url: Scalars['String'];
|
|
101
101
|
};
|
|
102
102
|
|
|
103
103
|
export type Response = {
|
|
104
|
-
httpStatusCode: Scalars['Int'];
|
|
105
|
-
headers?: Maybe<Array<HttpHeader>>;
|
|
106
104
|
body?: Maybe<Scalars['String']>;
|
|
105
|
+
headers?: Maybe<Array<HttpHeader>>;
|
|
106
|
+
httpStatusCode: Scalars['Int'];
|
|
107
107
|
};
|
|
108
108
|
|
|
109
|
-
export type RouterConfigResponse = RouterConfigResult |
|
|
109
|
+
export type RouterConfigResponse = FetchError | RouterConfigResult | Unchanged;
|
|
110
110
|
|
|
111
111
|
export type RouterConfigResult = {
|
|
112
112
|
__typename?: 'RouterConfigResult';
|
|
113
113
|
id: Scalars['ID'];
|
|
114
|
-
/** The configuration as core schema */
|
|
115
|
-
supergraphSDL: Scalars['String'];
|
|
116
114
|
/** Messages that should be reported back to the operators of this router, eg through logs and/or monitoring. */
|
|
117
115
|
messages: Array<Message>;
|
|
116
|
+
/** The configuration as core schema */
|
|
117
|
+
supergraphSDL: Scalars['String'];
|
|
118
|
+
};
|
|
119
|
+
|
|
120
|
+
export type Unchanged = {
|
|
121
|
+
__typename?: 'Unchanged';
|
|
122
|
+
id: Scalars['ID'];
|
|
118
123
|
};
|
|
119
124
|
|
|
120
125
|
export type SupergraphSdlQueryVariables = Exact<{
|
|
@@ -123,7 +128,7 @@ export type SupergraphSdlQueryVariables = Exact<{
|
|
|
123
128
|
}>;
|
|
124
129
|
|
|
125
130
|
|
|
126
|
-
export type SupergraphSdlQuery = { __typename?: 'Query', routerConfig: { __typename: '
|
|
131
|
+
export type SupergraphSdlQuery = { __typename?: 'Query', routerConfig: { __typename: 'FetchError', code: FetchErrorCode, message: string } | { __typename: 'RouterConfigResult', id: string, supergraphSdl: string } | { __typename: 'Unchanged' } };
|
|
127
132
|
|
|
128
133
|
export type OobReportMutationVariables = Exact<{
|
|
129
134
|
input?: Maybe<ApiMonitoringReport>;
|
|
@@ -1,9 +1,13 @@
|
|
|
1
1
|
import { GraphQLSchema } from 'graphql';
|
|
2
2
|
import gql from 'graphql-tag';
|
|
3
3
|
import { buildOperationContext } from '../operationContext';
|
|
4
|
-
import {
|
|
4
|
+
import {
|
|
5
|
+
astSerializer,
|
|
6
|
+
queryPlanSerializer,
|
|
7
|
+
fixturesWithUpdate,
|
|
8
|
+
} from 'apollo-federation-integration-testsuite';
|
|
5
9
|
import { getFederatedTestingSchema } from './execution-utils';
|
|
6
|
-
import { QueryPlanner } from '@apollo/query-planner';
|
|
10
|
+
import { QueryPlanner, FetchNode } from '@apollo/query-planner';
|
|
7
11
|
|
|
8
12
|
expect.addSnapshotSerializer(astSerializer);
|
|
9
13
|
expect.addSnapshotSerializer(queryPlanSerializer);
|
|
@@ -85,7 +89,7 @@ describe('buildQueryPlan', () => {
|
|
|
85
89
|
buildOperationContext({
|
|
86
90
|
schema,
|
|
87
91
|
operationDocument,
|
|
88
|
-
})
|
|
92
|
+
}),
|
|
89
93
|
);
|
|
90
94
|
|
|
91
95
|
expect(queryPlan).toMatchInlineSnapshot(`
|
|
@@ -119,7 +123,7 @@ describe('buildQueryPlan', () => {
|
|
|
119
123
|
buildOperationContext({
|
|
120
124
|
schema,
|
|
121
125
|
operationDocument,
|
|
122
|
-
})
|
|
126
|
+
}),
|
|
123
127
|
);
|
|
124
128
|
|
|
125
129
|
expect(queryPlan).toMatchInlineSnapshot(`
|
|
@@ -206,7 +210,7 @@ describe('buildQueryPlan', () => {
|
|
|
206
210
|
buildOperationContext({
|
|
207
211
|
schema,
|
|
208
212
|
operationDocument,
|
|
209
|
-
})
|
|
213
|
+
}),
|
|
210
214
|
);
|
|
211
215
|
|
|
212
216
|
expect(queryPlan).toMatchInlineSnapshot(`
|
|
@@ -337,7 +341,7 @@ describe('buildQueryPlan', () => {
|
|
|
337
341
|
buildOperationContext({
|
|
338
342
|
schema,
|
|
339
343
|
operationDocument,
|
|
340
|
-
})
|
|
344
|
+
}),
|
|
341
345
|
);
|
|
342
346
|
|
|
343
347
|
expect(queryPlan).toMatchInlineSnapshot(`
|
|
@@ -379,7 +383,7 @@ describe('buildQueryPlan', () => {
|
|
|
379
383
|
buildOperationContext({
|
|
380
384
|
schema,
|
|
381
385
|
operationDocument,
|
|
382
|
-
})
|
|
386
|
+
}),
|
|
383
387
|
);
|
|
384
388
|
|
|
385
389
|
expect(queryPlan).toMatchInlineSnapshot(`
|
|
@@ -420,7 +424,7 @@ describe('buildQueryPlan', () => {
|
|
|
420
424
|
buildOperationContext({
|
|
421
425
|
schema,
|
|
422
426
|
operationDocument,
|
|
423
|
-
})
|
|
427
|
+
}),
|
|
424
428
|
);
|
|
425
429
|
|
|
426
430
|
expect(queryPlan).toMatchInlineSnapshot(`
|
|
@@ -475,7 +479,7 @@ describe('buildQueryPlan', () => {
|
|
|
475
479
|
buildOperationContext({
|
|
476
480
|
schema,
|
|
477
481
|
operationDocument,
|
|
478
|
-
})
|
|
482
|
+
}),
|
|
479
483
|
);
|
|
480
484
|
|
|
481
485
|
expect(queryPlan).toMatchInlineSnapshot(`
|
|
@@ -531,7 +535,7 @@ describe('buildQueryPlan', () => {
|
|
|
531
535
|
buildOperationContext({
|
|
532
536
|
schema,
|
|
533
537
|
operationDocument,
|
|
534
|
-
})
|
|
538
|
+
}),
|
|
535
539
|
);
|
|
536
540
|
|
|
537
541
|
expect(queryPlan).toMatchInlineSnapshot(`
|
|
@@ -571,7 +575,7 @@ describe('buildQueryPlan', () => {
|
|
|
571
575
|
|
|
572
576
|
describe(`when requesting a composite field with subfields from another service`, () => {
|
|
573
577
|
it(`should add key fields to the parent selection set and use a dependent fetch`, () => {
|
|
574
|
-
|
|
578
|
+
const operationString = `#graphql
|
|
575
579
|
query {
|
|
576
580
|
topReviews {
|
|
577
581
|
body
|
|
@@ -588,7 +592,7 @@ describe('buildQueryPlan', () => {
|
|
|
588
592
|
buildOperationContext({
|
|
589
593
|
schema,
|
|
590
594
|
operationDocument,
|
|
591
|
-
})
|
|
595
|
+
}),
|
|
592
596
|
);
|
|
593
597
|
|
|
594
598
|
expect(queryPlan).toMatchInlineSnapshot(`
|
|
@@ -641,7 +645,7 @@ describe('buildQueryPlan', () => {
|
|
|
641
645
|
buildOperationContext({
|
|
642
646
|
schema,
|
|
643
647
|
operationDocument,
|
|
644
|
-
})
|
|
648
|
+
}),
|
|
645
649
|
);
|
|
646
650
|
|
|
647
651
|
expect(queryPlan).toMatchInlineSnapshot(`
|
|
@@ -696,7 +700,7 @@ describe('buildQueryPlan', () => {
|
|
|
696
700
|
buildOperationContext({
|
|
697
701
|
schema,
|
|
698
702
|
operationDocument,
|
|
699
|
-
})
|
|
703
|
+
}),
|
|
700
704
|
);
|
|
701
705
|
|
|
702
706
|
expect(queryPlan).toMatchInlineSnapshot(`
|
|
@@ -751,7 +755,7 @@ describe('buildQueryPlan', () => {
|
|
|
751
755
|
buildOperationContext({
|
|
752
756
|
schema,
|
|
753
757
|
operationDocument,
|
|
754
|
-
})
|
|
758
|
+
}),
|
|
755
759
|
);
|
|
756
760
|
|
|
757
761
|
expect(queryPlan).toMatchInlineSnapshot(`
|
|
@@ -807,7 +811,7 @@ describe('buildQueryPlan', () => {
|
|
|
807
811
|
buildOperationContext({
|
|
808
812
|
schema,
|
|
809
813
|
operationDocument,
|
|
810
|
-
})
|
|
814
|
+
}),
|
|
811
815
|
);
|
|
812
816
|
|
|
813
817
|
expect(queryPlan).toMatchInlineSnapshot(`
|
|
@@ -854,7 +858,7 @@ describe('buildQueryPlan', () => {
|
|
|
854
858
|
buildOperationContext({
|
|
855
859
|
schema,
|
|
856
860
|
operationDocument,
|
|
857
|
-
})
|
|
861
|
+
}),
|
|
858
862
|
);
|
|
859
863
|
|
|
860
864
|
expect(queryPlan).toMatchInlineSnapshot(`
|
|
@@ -901,7 +905,7 @@ describe('buildQueryPlan', () => {
|
|
|
901
905
|
buildOperationContext({
|
|
902
906
|
schema,
|
|
903
907
|
operationDocument,
|
|
904
|
-
})
|
|
908
|
+
}),
|
|
905
909
|
);
|
|
906
910
|
|
|
907
911
|
expect(queryPlan).toMatchInlineSnapshot(`
|
|
@@ -942,7 +946,7 @@ describe('buildQueryPlan', () => {
|
|
|
942
946
|
buildOperationContext({
|
|
943
947
|
schema,
|
|
944
948
|
operationDocument,
|
|
945
|
-
})
|
|
949
|
+
}),
|
|
946
950
|
);
|
|
947
951
|
|
|
948
952
|
expect(queryPlan).toMatchInlineSnapshot(`
|
|
@@ -982,7 +986,7 @@ describe('buildQueryPlan', () => {
|
|
|
982
986
|
buildOperationContext({
|
|
983
987
|
schema,
|
|
984
988
|
operationDocument,
|
|
985
|
-
})
|
|
989
|
+
}),
|
|
986
990
|
);
|
|
987
991
|
|
|
988
992
|
expect(queryPlan).toMatchInlineSnapshot(`
|
|
@@ -1025,7 +1029,7 @@ describe('buildQueryPlan', () => {
|
|
|
1025
1029
|
buildOperationContext({
|
|
1026
1030
|
schema,
|
|
1027
1031
|
operationDocument,
|
|
1028
|
-
})
|
|
1032
|
+
}),
|
|
1029
1033
|
);
|
|
1030
1034
|
|
|
1031
1035
|
expect(queryPlan).toMatchInlineSnapshot(`
|
|
@@ -1099,7 +1103,7 @@ describe('buildQueryPlan', () => {
|
|
|
1099
1103
|
buildOperationContext({
|
|
1100
1104
|
schema,
|
|
1101
1105
|
operationDocument,
|
|
1102
|
-
})
|
|
1106
|
+
}),
|
|
1103
1107
|
);
|
|
1104
1108
|
|
|
1105
1109
|
expect(queryPlan).toMatchInlineSnapshot(`
|
|
@@ -1154,7 +1158,7 @@ describe('buildQueryPlan', () => {
|
|
|
1154
1158
|
buildOperationContext({
|
|
1155
1159
|
schema,
|
|
1156
1160
|
operationDocument,
|
|
1157
|
-
})
|
|
1161
|
+
}),
|
|
1158
1162
|
);
|
|
1159
1163
|
|
|
1160
1164
|
expect(queryPlan).toMatchInlineSnapshot(`
|
|
@@ -1550,7 +1554,7 @@ describe('buildQueryPlan', () => {
|
|
|
1550
1554
|
buildOperationContext({
|
|
1551
1555
|
schema,
|
|
1552
1556
|
operationDocument,
|
|
1553
|
-
})
|
|
1557
|
+
}),
|
|
1554
1558
|
);
|
|
1555
1559
|
|
|
1556
1560
|
expect(queryPlan).toMatchInlineSnapshot(`
|
|
@@ -1612,7 +1616,7 @@ describe('buildQueryPlan', () => {
|
|
|
1612
1616
|
buildOperationContext({
|
|
1613
1617
|
schema,
|
|
1614
1618
|
operationDocument,
|
|
1615
|
-
})
|
|
1619
|
+
}),
|
|
1616
1620
|
);
|
|
1617
1621
|
|
|
1618
1622
|
expect(queryPlan).toMatchInlineSnapshot(`
|
|
@@ -1662,7 +1666,7 @@ describe('buildQueryPlan', () => {
|
|
|
1662
1666
|
buildOperationContext({
|
|
1663
1667
|
schema,
|
|
1664
1668
|
operationDocument,
|
|
1665
|
-
})
|
|
1669
|
+
}),
|
|
1666
1670
|
);
|
|
1667
1671
|
|
|
1668
1672
|
expect(queryPlan).toMatchInlineSnapshot(`
|
|
@@ -1684,4 +1688,251 @@ describe('buildQueryPlan', () => {
|
|
|
1684
1688
|
`);
|
|
1685
1689
|
});
|
|
1686
1690
|
});
|
|
1691
|
+
|
|
1692
|
+
describe('top-level @skip/@include behavior', () => {
|
|
1693
|
+
beforeEach(() => {
|
|
1694
|
+
({ schema, queryPlanner } =
|
|
1695
|
+
getFederatedTestingSchema(fixturesWithUpdate));
|
|
1696
|
+
});
|
|
1697
|
+
|
|
1698
|
+
function getQueryPlan(operation: string) {
|
|
1699
|
+
const operationDocument = gql(operation);
|
|
1700
|
+
|
|
1701
|
+
return queryPlanner.buildQueryPlan(
|
|
1702
|
+
buildOperationContext({
|
|
1703
|
+
schema,
|
|
1704
|
+
operationDocument,
|
|
1705
|
+
}),
|
|
1706
|
+
);
|
|
1707
|
+
}
|
|
1708
|
+
|
|
1709
|
+
it('simple skip', () => {
|
|
1710
|
+
const operation = `#graphql
|
|
1711
|
+
query {
|
|
1712
|
+
topReviews @skip(if: true) {
|
|
1713
|
+
body
|
|
1714
|
+
}
|
|
1715
|
+
}
|
|
1716
|
+
`;
|
|
1717
|
+
|
|
1718
|
+
expect(
|
|
1719
|
+
(getQueryPlan(operation).node as FetchNode).inclusionConditions,
|
|
1720
|
+
).toEqual([{ skip: true, include: null }]);
|
|
1721
|
+
});
|
|
1722
|
+
|
|
1723
|
+
it('simple include', () => {
|
|
1724
|
+
const operation = `#graphql
|
|
1725
|
+
query {
|
|
1726
|
+
topReviews @include(if: false) {
|
|
1727
|
+
body
|
|
1728
|
+
}
|
|
1729
|
+
}
|
|
1730
|
+
`;
|
|
1731
|
+
|
|
1732
|
+
expect(
|
|
1733
|
+
(getQueryPlan(operation).node as FetchNode).inclusionConditions,
|
|
1734
|
+
).toEqual([{ include: false, skip: null }]);
|
|
1735
|
+
});
|
|
1736
|
+
|
|
1737
|
+
it('simple include with variables', () => {
|
|
1738
|
+
const operation = `#graphql
|
|
1739
|
+
query {
|
|
1740
|
+
topReviews @include(if: $shouldInclude) {
|
|
1741
|
+
body
|
|
1742
|
+
}
|
|
1743
|
+
}
|
|
1744
|
+
`;
|
|
1745
|
+
|
|
1746
|
+
expect(
|
|
1747
|
+
(getQueryPlan(operation).node as FetchNode).inclusionConditions,
|
|
1748
|
+
).toEqual([{ include: 'shouldInclude', skip: null }]);
|
|
1749
|
+
});
|
|
1750
|
+
|
|
1751
|
+
it('simple skip with variables', () => {
|
|
1752
|
+
const operation = `#graphql
|
|
1753
|
+
query {
|
|
1754
|
+
topReviews @skip(if: $shouldSkip) {
|
|
1755
|
+
body
|
|
1756
|
+
}
|
|
1757
|
+
}
|
|
1758
|
+
`;
|
|
1759
|
+
|
|
1760
|
+
expect(
|
|
1761
|
+
(getQueryPlan(operation).node as FetchNode).inclusionConditions,
|
|
1762
|
+
).toEqual([{ skip: 'shouldSkip', include: null }]);
|
|
1763
|
+
});
|
|
1764
|
+
|
|
1765
|
+
it('not all top-levels have conditionals', () => {
|
|
1766
|
+
const operation = `#graphql
|
|
1767
|
+
query {
|
|
1768
|
+
topReviews @skip(if: $shouldSkip) {
|
|
1769
|
+
body
|
|
1770
|
+
}
|
|
1771
|
+
review(id: "1") {
|
|
1772
|
+
body
|
|
1773
|
+
}
|
|
1774
|
+
}
|
|
1775
|
+
`;
|
|
1776
|
+
|
|
1777
|
+
expect(
|
|
1778
|
+
(getQueryPlan(operation).node as FetchNode).inclusionConditions,
|
|
1779
|
+
).toBeUndefined();
|
|
1780
|
+
});
|
|
1781
|
+
|
|
1782
|
+
it('all top-levels have conditionals', () => {
|
|
1783
|
+
const operation = `#graphql
|
|
1784
|
+
query {
|
|
1785
|
+
topReviews @skip(if: $shouldSkip) {
|
|
1786
|
+
body
|
|
1787
|
+
}
|
|
1788
|
+
review(id: "1") @skip(if: true) {
|
|
1789
|
+
body
|
|
1790
|
+
}
|
|
1791
|
+
}
|
|
1792
|
+
`;
|
|
1793
|
+
|
|
1794
|
+
expect(
|
|
1795
|
+
(getQueryPlan(operation).node as FetchNode).inclusionConditions,
|
|
1796
|
+
).toEqual([
|
|
1797
|
+
{ skip: 'shouldSkip', include: null },
|
|
1798
|
+
{ skip: true, include: null },
|
|
1799
|
+
]);
|
|
1800
|
+
});
|
|
1801
|
+
|
|
1802
|
+
it('all top-levels use literals (include case)', () => {
|
|
1803
|
+
const operation = `#graphql
|
|
1804
|
+
query {
|
|
1805
|
+
topReviews @skip(if: false) {
|
|
1806
|
+
body
|
|
1807
|
+
}
|
|
1808
|
+
review(id: "1") @include(if: true) {
|
|
1809
|
+
body
|
|
1810
|
+
}
|
|
1811
|
+
}
|
|
1812
|
+
`;
|
|
1813
|
+
|
|
1814
|
+
expect(
|
|
1815
|
+
(getQueryPlan(operation).node as FetchNode).inclusionConditions,
|
|
1816
|
+
).toBeUndefined();
|
|
1817
|
+
});
|
|
1818
|
+
|
|
1819
|
+
it('all top-levels use literals (skip case)', () => {
|
|
1820
|
+
const operation = `#graphql
|
|
1821
|
+
query {
|
|
1822
|
+
topReviews @skip(if: true) {
|
|
1823
|
+
body
|
|
1824
|
+
}
|
|
1825
|
+
review(id: "1") @include(if: false) {
|
|
1826
|
+
body
|
|
1827
|
+
}
|
|
1828
|
+
}
|
|
1829
|
+
`;
|
|
1830
|
+
|
|
1831
|
+
expect(
|
|
1832
|
+
(getQueryPlan(operation).node as FetchNode).inclusionConditions,
|
|
1833
|
+
).toEqual([
|
|
1834
|
+
{ skip: true, include: null },
|
|
1835
|
+
{ include: false, skip: null },
|
|
1836
|
+
]);
|
|
1837
|
+
});
|
|
1838
|
+
|
|
1839
|
+
it('skip: false, include: false', () => {
|
|
1840
|
+
const operation = `#graphql
|
|
1841
|
+
query {
|
|
1842
|
+
topReviews @skip(if: false) @include(if: false) {
|
|
1843
|
+
body
|
|
1844
|
+
}
|
|
1845
|
+
}
|
|
1846
|
+
`;
|
|
1847
|
+
|
|
1848
|
+
expect(
|
|
1849
|
+
(getQueryPlan(operation).node as FetchNode).inclusionConditions,
|
|
1850
|
+
).toEqual([{ skip: false, include: false }]);
|
|
1851
|
+
});
|
|
1852
|
+
|
|
1853
|
+
it('skip: false, include: true', () => {
|
|
1854
|
+
const operation = `#graphql
|
|
1855
|
+
query {
|
|
1856
|
+
topReviews @skip(if: false) @include(if: true) {
|
|
1857
|
+
body
|
|
1858
|
+
}
|
|
1859
|
+
}
|
|
1860
|
+
`;
|
|
1861
|
+
|
|
1862
|
+
expect(
|
|
1863
|
+
(getQueryPlan(operation).node as FetchNode).inclusionConditions,
|
|
1864
|
+
).toBeUndefined();
|
|
1865
|
+
});
|
|
1866
|
+
|
|
1867
|
+
it('skip: true, include: false', () => {
|
|
1868
|
+
const operation = `#graphql
|
|
1869
|
+
query {
|
|
1870
|
+
topReviews @skip(if: true) @include(if: false) {
|
|
1871
|
+
body
|
|
1872
|
+
}
|
|
1873
|
+
}
|
|
1874
|
+
`;
|
|
1875
|
+
|
|
1876
|
+
expect(
|
|
1877
|
+
(getQueryPlan(operation).node as FetchNode).inclusionConditions,
|
|
1878
|
+
).toEqual([{ skip: true, include: false }]);
|
|
1879
|
+
});
|
|
1880
|
+
|
|
1881
|
+
it('skip: true, include: true', () => {
|
|
1882
|
+
const operation = `#graphql
|
|
1883
|
+
query {
|
|
1884
|
+
topReviews @skip(if: true) @include(if: true) {
|
|
1885
|
+
body
|
|
1886
|
+
}
|
|
1887
|
+
}
|
|
1888
|
+
`;
|
|
1889
|
+
|
|
1890
|
+
expect(
|
|
1891
|
+
(getQueryPlan(operation).node as FetchNode).inclusionConditions,
|
|
1892
|
+
).toEqual([{ skip: true, include: true }]);
|
|
1893
|
+
});
|
|
1894
|
+
|
|
1895
|
+
describe.skip('known limitations', () => {
|
|
1896
|
+
it('conditionals on top-level fragment spreads are captured', () => {
|
|
1897
|
+
const operation = `#graphql
|
|
1898
|
+
query {
|
|
1899
|
+
...TopReviews @skip(if: $shouldSkip)
|
|
1900
|
+
}
|
|
1901
|
+
|
|
1902
|
+
fragment TopReviews on Query {
|
|
1903
|
+
topReviews {
|
|
1904
|
+
body
|
|
1905
|
+
}
|
|
1906
|
+
}
|
|
1907
|
+
`;
|
|
1908
|
+
|
|
1909
|
+
expect(
|
|
1910
|
+
(getQueryPlan(operation).node as FetchNode).inclusionConditions,
|
|
1911
|
+
).toEqual([{ skip: 'shouldSkip', include: null }]);
|
|
1912
|
+
});
|
|
1913
|
+
|
|
1914
|
+
it('conditionals on top-level inline fragments are captured', () => {
|
|
1915
|
+
const operation = `#graphql
|
|
1916
|
+
query {
|
|
1917
|
+
... on Query @skip(if: $shouldSkip) {
|
|
1918
|
+
topReviews {
|
|
1919
|
+
body
|
|
1920
|
+
}
|
|
1921
|
+
}
|
|
1922
|
+
}
|
|
1923
|
+
`;
|
|
1924
|
+
|
|
1925
|
+
expect(
|
|
1926
|
+
(getQueryPlan(operation).node as FetchNode).inclusionConditions,
|
|
1927
|
+
).toEqual([{ skip: 'shouldSkip', include: null }]);
|
|
1928
|
+
});
|
|
1929
|
+
|
|
1930
|
+
it.todo(
|
|
1931
|
+
'deeply-nested conditionals within fragment spreads are captured',
|
|
1932
|
+
);
|
|
1933
|
+
it.todo(
|
|
1934
|
+
'deeply-nested conditionals within inline fragments are captured',
|
|
1935
|
+
);
|
|
1936
|
+
});
|
|
1937
|
+
});
|
|
1687
1938
|
});
|