@apollo/client 4.3.0-alpha.2 → 4.3.0-alpha.4

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.
Files changed (142) hide show
  1. package/CHANGELOG.md +169 -0
  2. package/__cjs/cache/core/types/Cache.d.cts +25 -0
  3. package/__cjs/cache/index.cjs.map +1 -1
  4. package/__cjs/cache/index.d.cts +2 -2
  5. package/__cjs/cache/inmemory/entityStore.cjs +12 -6
  6. package/__cjs/cache/inmemory/entityStore.cjs.map +1 -1
  7. package/__cjs/cache/inmemory/entityStore.d.cts +1 -0
  8. package/__cjs/cache/inmemory/inMemoryCache.cjs +4 -0
  9. package/__cjs/cache/inmemory/inMemoryCache.cjs.map +1 -1
  10. package/__cjs/cache/inmemory/inMemoryCache.d.cts +7 -3
  11. package/__cjs/cache/inmemory/readFromStore.cjs +453 -43
  12. package/__cjs/cache/inmemory/readFromStore.cjs.map +1 -1
  13. package/__cjs/cache/inmemory/readFromStore.d.cts +11 -2
  14. package/__cjs/cache/inmemory/types.d.cts +11 -1
  15. package/__cjs/cache/inmemory/writeToStore.cjs +2 -2
  16. package/__cjs/cache/inmemory/writeToStore.cjs.map +1 -1
  17. package/__cjs/core/ObservableQuery.cjs +1 -3
  18. package/__cjs/core/ObservableQuery.cjs.map +1 -1
  19. package/__cjs/core/QueryInfo.cjs +94 -16
  20. package/__cjs/core/QueryInfo.cjs.map +1 -1
  21. package/__cjs/core/QueryInfo.d.cts +12 -3
  22. package/__cjs/core/QueryManager.cjs +13 -18
  23. package/__cjs/core/QueryManager.cjs.map +1 -1
  24. package/__cjs/core/QueryManager.d.cts +0 -2
  25. package/__cjs/incremental/handlers/defer20220824.cjs.map +1 -1
  26. package/__cjs/incremental/handlers/defer20220824.d.cts +2 -4
  27. package/__cjs/incremental/handlers/graphql17Alpha9.cjs +20 -12
  28. package/__cjs/incremental/handlers/graphql17Alpha9.cjs.map +1 -1
  29. package/__cjs/incremental/handlers/graphql17Alpha9.d.cts +5 -5
  30. package/__cjs/incremental/types.d.cts +16 -3
  31. package/__cjs/utilities/caching/sizes.cjs.map +1 -1
  32. package/__cjs/utilities/caching/sizes.d.cts +39 -1
  33. package/__cjs/utilities/index.cjs.map +1 -1
  34. package/__cjs/utilities/index.d.cts +1 -0
  35. package/__cjs/utilities/internal/StreamArrayState.cjs +27 -0
  36. package/__cjs/utilities/internal/StreamArrayState.cjs.map +1 -0
  37. package/__cjs/utilities/internal/StreamArrayState.d.cts +12 -0
  38. package/__cjs/utilities/internal/constants.cjs +20 -1
  39. package/__cjs/utilities/internal/constants.cjs.map +1 -1
  40. package/__cjs/utilities/internal/constants.d.cts +19 -0
  41. package/__cjs/utilities/internal/getFragmentFromSelection.cjs +1 -1
  42. package/__cjs/utilities/internal/getFragmentFromSelection.cjs.map +1 -1
  43. package/__cjs/utilities/internal/getMemoryInternals.cjs +6 -0
  44. package/__cjs/utilities/internal/getMemoryInternals.cjs.map +1 -1
  45. package/__cjs/utilities/internal/getMemoryInternals.d.cts +4 -0
  46. package/__cjs/utilities/internal/index.cjs +13 -2
  47. package/__cjs/utilities/internal/index.cjs.map +1 -1
  48. package/__cjs/utilities/internal/index.d.cts +7 -1
  49. package/__cjs/utilities/internal/isDeferredFragment.cjs +38 -0
  50. package/__cjs/utilities/internal/isDeferredFragment.cjs.map +1 -0
  51. package/__cjs/utilities/internal/isDeferredFragment.d.cts +9 -0
  52. package/__cjs/utilities/internal/isStreamField.cjs +37 -0
  53. package/__cjs/utilities/internal/isStreamField.cjs.map +1 -0
  54. package/__cjs/utilities/internal/isStreamField.d.cts +9 -0
  55. package/__cjs/utilities/internal/isTypenameField.cjs +7 -0
  56. package/__cjs/utilities/internal/isTypenameField.cjs.map +1 -0
  57. package/__cjs/utilities/internal/isTypenameField.d.cts +3 -0
  58. package/__cjs/utilities/internal/makeStreamInfoTrie.cjs +17 -0
  59. package/__cjs/utilities/internal/makeStreamInfoTrie.cjs.map +1 -0
  60. package/__cjs/utilities/internal/makeStreamInfoTrie.d.cts +8 -0
  61. package/__cjs/utilities/internal/types/DeferInfo.cjs +3 -0
  62. package/__cjs/utilities/internal/types/DeferInfo.cjs.map +1 -0
  63. package/__cjs/utilities/internal/types/DeferInfo.d.cts +10 -0
  64. package/__cjs/utilities/internal/types/StreamInfoTrie.d.cts +2 -0
  65. package/__cjs/utilities/policies/pagination.cjs.map +1 -1
  66. package/__cjs/utilities/policies/pagination.d.cts +1 -1
  67. package/__cjs/utilities/subscriptions/relay/index.cjs +1 -0
  68. package/__cjs/utilities/subscriptions/relay/index.cjs.map +1 -1
  69. package/__cjs/version.cjs +1 -1
  70. package/cache/core/types/Cache.d.ts +25 -0
  71. package/cache/core/types/Cache.js.map +1 -1
  72. package/cache/index.d.ts +2 -2
  73. package/cache/index.js.map +1 -1
  74. package/cache/inmemory/entityStore.d.ts +1 -0
  75. package/cache/inmemory/entityStore.js +12 -6
  76. package/cache/inmemory/entityStore.js.map +1 -1
  77. package/cache/inmemory/inMemoryCache.d.ts +7 -3
  78. package/cache/inmemory/inMemoryCache.js +5 -1
  79. package/cache/inmemory/inMemoryCache.js.map +1 -1
  80. package/cache/inmemory/readFromStore.d.ts +11 -2
  81. package/cache/inmemory/readFromStore.js +454 -44
  82. package/cache/inmemory/readFromStore.js.map +1 -1
  83. package/cache/inmemory/types.d.ts +12 -2
  84. package/cache/inmemory/types.js.map +1 -1
  85. package/cache/inmemory/writeToStore.js +3 -3
  86. package/cache/inmemory/writeToStore.js.map +1 -1
  87. package/core/ObservableQuery.js +1 -3
  88. package/core/ObservableQuery.js.map +1 -1
  89. package/core/QueryInfo.d.ts +12 -3
  90. package/core/QueryInfo.js +95 -17
  91. package/core/QueryInfo.js.map +1 -1
  92. package/core/QueryManager.d.ts +0 -2
  93. package/core/QueryManager.js +13 -18
  94. package/core/QueryManager.js.map +1 -1
  95. package/incremental/handlers/defer20220824.d.ts +2 -4
  96. package/incremental/handlers/defer20220824.js.map +1 -1
  97. package/incremental/handlers/graphql17Alpha9.d.ts +5 -5
  98. package/incremental/handlers/graphql17Alpha9.js +21 -13
  99. package/incremental/handlers/graphql17Alpha9.js.map +1 -1
  100. package/incremental/types.d.ts +16 -3
  101. package/incremental/types.js.map +1 -1
  102. package/package.json +1 -1
  103. package/utilities/caching/sizes.d.ts +39 -1
  104. package/utilities/caching/sizes.js.map +1 -1
  105. package/utilities/index.d.ts +1 -0
  106. package/utilities/index.js.map +1 -1
  107. package/utilities/internal/StreamArrayState.d.ts +12 -0
  108. package/utilities/internal/StreamArrayState.js +23 -0
  109. package/utilities/internal/StreamArrayState.js.map +1 -0
  110. package/utilities/internal/constants.d.ts +19 -0
  111. package/utilities/internal/constants.js +19 -0
  112. package/utilities/internal/constants.js.map +1 -1
  113. package/utilities/internal/getFragmentFromSelection.js +1 -1
  114. package/utilities/internal/getFragmentFromSelection.js.map +1 -1
  115. package/utilities/internal/getMemoryInternals.d.ts +4 -0
  116. package/utilities/internal/getMemoryInternals.js +6 -0
  117. package/utilities/internal/getMemoryInternals.js.map +1 -1
  118. package/utilities/internal/index.d.ts +7 -1
  119. package/utilities/internal/index.js +6 -1
  120. package/utilities/internal/index.js.map +1 -1
  121. package/utilities/internal/isDeferredFragment.d.ts +9 -0
  122. package/utilities/internal/isDeferredFragment.js +35 -0
  123. package/utilities/internal/isDeferredFragment.js.map +1 -0
  124. package/utilities/internal/isStreamField.d.ts +9 -0
  125. package/utilities/internal/isStreamField.js +34 -0
  126. package/utilities/internal/isStreamField.js.map +1 -0
  127. package/utilities/internal/isTypenameField.d.ts +3 -0
  128. package/utilities/internal/isTypenameField.js +4 -0
  129. package/utilities/internal/isTypenameField.js.map +1 -0
  130. package/utilities/internal/makeStreamInfoTrie.d.ts +8 -0
  131. package/utilities/internal/makeStreamInfoTrie.js +14 -0
  132. package/utilities/internal/makeStreamInfoTrie.js.map +1 -0
  133. package/utilities/internal/types/DeferInfo.d.ts +10 -0
  134. package/utilities/internal/types/DeferInfo.js +2 -0
  135. package/utilities/internal/types/DeferInfo.js.map +1 -0
  136. package/utilities/internal/types/StreamInfoTrie.d.ts +2 -0
  137. package/utilities/internal/types/StreamInfoTrie.js.map +1 -1
  138. package/utilities/policies/pagination.d.ts +1 -1
  139. package/utilities/policies/pagination.js.map +1 -1
  140. package/utilities/subscriptions/relay/index.js +1 -0
  141. package/utilities/subscriptions/relay/index.js.map +1 -1
  142. package/version.js +1 -1
@@ -4,10 +4,11 @@ import type { ApolloLink } from "@apollo/client/link";
4
4
  import type { Unmasked } from "@apollo/client/masking";
5
5
  import type { ExtensionsWithStreamInfo } from "@apollo/client/utilities/internal";
6
6
  import type { ApolloClient } from "./ApolloClient.js";
7
+ import { NetworkStatus } from "./networkStatus.js";
7
8
  import type { ObservableQuery } from "./ObservableQuery.js";
8
9
  import type { QueryManager } from "./QueryManager.js";
9
10
  import type { DataValue, DefaultContext, InternalRefetchQueriesInclude, MutationUpdaterFunction, NormalizedExecutionResult, OnQueryUpdated, OperationVariables, TypedDocumentNode } from "./types.js";
10
- import type { ErrorPolicy } from "./watchQueryOptions.js";
11
+ import type { ErrorPolicy, WatchQueryFetchPolicy } from "./watchQueryOptions.js";
11
12
  type UpdateQueries<TData> = ApolloClient.MutateOptions<TData, any, any>["updateQueries"];
12
13
  export declare const enum CacheWriteBehavior {
13
14
  FORBID = 0,
@@ -24,9 +25,12 @@ interface OperationInfo<TData, TVariables extends OperationVariables, AllowedCac
24
25
  variables: TVariables;
25
26
  errorPolicy: ErrorPolicy;
26
27
  cacheWriteBehavior: AllowedCacheWriteBehavior;
28
+ returnPartialData?: boolean | undefined;
29
+ }
30
+ interface MarkQueryResult<TData, TExtensions> extends FormattedExecutionResult<TData, TExtensions> {
31
+ dataState: "empty" | "partial" | "streaming" | "complete";
27
32
  }
28
33
  export declare class QueryInfo<TData, TVariables extends OperationVariables = OperationVariables, TCache extends Cache.Implementation = Cache.Implementation> {
29
- lastRequestId: number;
30
34
  private cache;
31
35
  private queryManager;
32
36
  readonly id: string;
@@ -47,7 +51,12 @@ export declare class QueryInfo<TData, TVariables extends OperationVariables = Op
47
51
  private shouldWrite;
48
52
  get hasNext(): boolean;
49
53
  private maybeHandleIncrementalResult;
50
- markQueryResult(incoming: ApolloLink.Result<TData>, { document: query, variables, errorPolicy, cacheWriteBehavior, }: OperationInfo<TData, TVariables>): FormattedExecutionResult<DataValue.Complete<TData> | DataValue.Streaming<TData>, ExtensionsWithStreamInfo>;
54
+ markQueryResult(incoming: ApolloLink.Result<TData>, { document: query, variables, errorPolicy, cacheWriteBehavior, returnPartialData, fetchPolicy, networkStatus, }: OperationInfo<TData, TVariables> & {
55
+ fetchPolicy: WatchQueryFetchPolicy;
56
+ networkStatus: NetworkStatus;
57
+ }): MarkQueryResult<DataValue.Complete<TData> | DataValue.Streaming<TData>, ExtensionsWithStreamInfo>;
58
+ private getIncrementalInfo;
59
+ private getDiff;
51
60
  markMutationResult(incoming: ApolloLink.Result<TData>, mutation: OperationInfo<TData, TVariables, CacheWriteBehavior.FORBID | CacheWriteBehavior.MERGE> & {
52
61
  context?: DefaultContext;
53
62
  updateQueries: UpdateQueries<TData>;
package/core/QueryInfo.js CHANGED
@@ -1,6 +1,8 @@
1
1
  import { equal } from "@wry/equality";
2
- import { getOperationName, graphQLResultHasError, streamInfoSymbol, } from "@apollo/client/utilities/internal";
2
+ import { Trie } from "@wry/trie";
3
+ import { getOperationName, graphQLResultHasError, handleIncrementalSymbol, hasDirectives, streamInfoSymbol, } from "@apollo/client/utilities/internal";
3
4
  import { invariant } from "@apollo/client/utilities/invariant";
5
+ import { NetworkStatus } from "./networkStatus.js";
4
6
  const IGNORE = {};
5
7
  const destructiveMethodCounts = new WeakMap();
6
8
  function wrapDestructiveCacheMethod(cache, methodName) {
@@ -26,8 +28,6 @@ const queryInfoIds = new WeakMap();
26
28
  // It is responsible for reporting results to the cache, merging and in a no-cache
27
29
  // scenario accumulating the response.
28
30
  export class QueryInfo {
29
- // TODO remove soon - this should be able to be handled by cancelling old operations before starting new ones
30
- lastRequestId = 1;
31
31
  cache;
32
32
  queryManager;
33
33
  id;
@@ -97,20 +97,49 @@ export class QueryInfo {
97
97
  }
98
98
  return incoming;
99
99
  }
100
- markQueryResult(incoming, { document: query, variables, errorPolicy, cacheWriteBehavior, }) {
100
+ markQueryResult(incoming, { document: query, variables, errorPolicy, cacheWriteBehavior, returnPartialData, fetchPolicy, networkStatus, }) {
101
101
  const diffOptions = {
102
102
  query,
103
103
  variables,
104
- returnPartialData: true,
105
104
  optimistic: true,
106
105
  };
107
106
  // Cancel the pending notify timeout (if it exists) to prevent extraneous network
108
107
  // requests. To allow future notify timeouts, diff and dirty are reset as well.
109
108
  this.observableQuery?.["resetNotifications"]();
110
109
  const skipCache = cacheWriteBehavior === 0 /* CacheWriteBehavior.FORBID */;
111
- const lastDiff = skipCache ? undefined : this.cache.diff(diffOptions);
112
- let result = this.maybeHandleIncrementalResult(lastDiff?.result, incoming, query);
110
+ const lastDiff = skipCache ? undefined : (this.getDiff({
111
+ ...diffOptions,
112
+ // Always request partial data to ensure the network incremental
113
+ // result is merged with all existing data (especially true to
114
+ // maintain @stream arrays with partial list items in the right order)
115
+ returnPartialData: true,
116
+ }));
117
+ const incrementalResult = this.maybeHandleIncrementalResult(lastDiff?.result, incoming, query);
118
+ let result = {
119
+ ...incrementalResult,
120
+ dataState: incrementalResult.data == null ? "empty" : "complete",
121
+ };
113
122
  if (skipCache) {
123
+ const hasPendingDefer = this.incremental?.pending?.some((pending) => this.incremental?.getPendingType?.(pending.id) === "defer");
124
+ if (hasPendingDefer ||
125
+ // The Defer20220824Handler cannot track pending/completed incremental
126
+ // chunks due to its data format so we naively set dataState to
127
+ // streaming if we are still processing chunks. The only case where
128
+ // streaming is incorrect and should actually be complete is when
129
+ // both a @defer and @stream boundary is present and the @defer chunk
130
+ // has completed before the `@stream` array.
131
+ //
132
+ // Assigning the naive "streaming" value avoids a much more expensive
133
+ // pass over `result.data` that would otherwise need to traverse the
134
+ // selection sets and evaluate the data object at each defer boundary
135
+ // to see if it fulfills the selection set. For such a narrow case where
136
+ // its incorrect on a format that is now outdated is not worth the
137
+ // fix so we are ok with reporting a `streaming` here.
138
+ (!this.incremental?.pending &&
139
+ this.hasNext &&
140
+ hasDirectives(["defer"], query))) {
141
+ result.dataState = "streaming";
142
+ }
114
143
  return result;
115
144
  }
116
145
  if (shouldWriteResult(result, errorPolicy)) {
@@ -129,7 +158,8 @@ export class QueryInfo {
129
158
  }
130
159
  },
131
160
  update: (cache) => {
132
- if (this.shouldWrite(result, variables)) {
161
+ const shouldWrite = this.shouldWrite(result, variables);
162
+ if (shouldWrite) {
133
163
  cache.writeQuery({
134
164
  query,
135
165
  data: result.data,
@@ -179,20 +209,27 @@ export class QueryInfo {
179
209
  if (lastDiff && lastDiff.complete) {
180
210
  // Reuse data from the last good (complete) diff that we
181
211
  // received, when possible.
182
- result = { ...result, data: lastDiff.result };
212
+ result = {
213
+ ...result,
214
+ data: lastDiff.result,
215
+ dataState: "complete",
216
+ };
183
217
  return;
184
218
  }
185
219
  // If the previous this.diff was incomplete, fall through to
186
220
  // re-reading the latest data with cache.diff, below.
187
221
  }
188
- const diff = cache.diff(diffOptions);
189
- // If we're allowed to write to the cache, and we can read a
190
- // complete result from the cache, update result.data to be the
191
- // result from the cache, rather than the raw network result.
192
- // Set without setDiff to avoid triggering a notify call, since
193
- // we have other ways of notifying for this result.
194
- if (diff.complete) {
195
- result = { ...result, data: diff.result };
222
+ const isNetworkOnly = fetchPolicy === "network-only" &&
223
+ networkStatus !== NetworkStatus.refetch;
224
+ const { dataState, result: diffResult } = this.getDiff({
225
+ ...diffOptions,
226
+ // Never deliver partial data for network-only requests
227
+ returnPartialData: returnPartialData && !isNetworkOnly,
228
+ }, this.getIncrementalInfo(result, { isNetworkOnly }));
229
+ if (dataState === "complete" ||
230
+ (returnPartialData && dataState === "partial" && shouldWrite) ||
231
+ (this.hasNext && dataState === "streaming")) {
232
+ result = { ...result, data: diffResult, dataState };
196
233
  }
197
234
  },
198
235
  });
@@ -202,6 +239,47 @@ export class QueryInfo {
202
239
  }
203
240
  return result;
204
241
  }
242
+ getIncrementalInfo(result, { isNetworkOnly }) {
243
+ const pending = this.incremental?.pending ?? [];
244
+ const streamInfo = result.extensions?.[streamInfoSymbol]?.deref();
245
+ const incrementalInfo = { streamInfo };
246
+ // We don't want to deliver stream items or complete defer boundaries
247
+ // for a network-only request if they haven't yet streamed from the
248
+ // network. We record all the still-pending paths so that cache.diff
249
+ // can prune complete defer/stream boundaries at those paths.
250
+ if (isNetworkOnly) {
251
+ for (const item of pending) {
252
+ const type = this.incremental?.getPendingType?.(item.id);
253
+ if (type === "defer") {
254
+ incrementalInfo.deferInfo ||= new Trie(true, () => true);
255
+ incrementalInfo.deferInfo.lookupArray(item.path);
256
+ }
257
+ else if (streamInfo && type === "stream") {
258
+ streamInfo.lookupArray(item.path).state.truncate = true;
259
+ }
260
+ }
261
+ }
262
+ return incrementalInfo;
263
+ }
264
+ getDiff(options, incrementalInfo) {
265
+ if (this.cache[handleIncrementalSymbol]) {
266
+ return this.cache.diff({
267
+ ...options,
268
+ [handleIncrementalSymbol]: incrementalInfo || true,
269
+ });
270
+ }
271
+ // returnPartialData is overridden for backwards compatibility with caches
272
+ // that don't handle incremental results. Without this, in-flight
273
+ // incremental cache data would come back null when returnPartialData is
274
+ // false due to the partial result.
275
+ const diff = this.cache.diff({ ...options, returnPartialData: true });
276
+ return {
277
+ ...diff,
278
+ dataState: diff.complete ? "complete"
279
+ : diff.result === null ? "empty"
280
+ : "partial",
281
+ };
282
+ }
205
283
  markMutationResult(incoming, mutation, cache = this.cache) {
206
284
  const cacheWrites = [];
207
285
  const skipCache = mutation.cacheWriteBehavior === 0 /* CacheWriteBehavior.FORBID */;