react-relay 13.1.1 → 14.1.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (178) hide show
  1. package/ReactRelayContainerUtils.js.flow +0 -2
  2. package/ReactRelayContext.js +1 -1
  3. package/ReactRelayContext.js.flow +0 -2
  4. package/ReactRelayFragmentContainer.js.flow +7 -6
  5. package/ReactRelayFragmentMockRenderer.js.flow +0 -2
  6. package/ReactRelayLocalQueryRenderer.js.flow +1 -3
  7. package/ReactRelayPaginationContainer.js.flow +13 -10
  8. package/ReactRelayQueryFetcher.js.flow +10 -11
  9. package/ReactRelayQueryRenderer.js.flow +15 -16
  10. package/ReactRelayQueryRendererContext.js.flow +1 -3
  11. package/ReactRelayRefetchContainer.js.flow +10 -7
  12. package/ReactRelayTestMocker.js.flow +0 -2
  13. package/ReactRelayTypes.js.flow +6 -8
  14. package/RelayContext.js.flow +0 -2
  15. package/__flowtests__/ReactRelayFragmentContainer-flowtest.js.flow +2 -4
  16. package/__flowtests__/ReactRelayPaginationContainer-flowtest.js.flow +3 -5
  17. package/__flowtests__/ReactRelayRefetchContainer-flowtest.js.flow +3 -5
  18. package/__flowtests__/RelayModern-flowtest.js.flow +2 -4
  19. package/__flowtests__/RelayModernFlowtest_badref.graphql.js.flow +2 -4
  20. package/__flowtests__/RelayModernFlowtest_notref.graphql.js.flow +2 -4
  21. package/__flowtests__/RelayModernFlowtest_user.graphql.js.flow +2 -4
  22. package/__flowtests__/RelayModernFlowtest_users.graphql.js.flow +2 -4
  23. package/__flowtests__/__generated__/ReactRelayFragmentContainerFlowtest_viewer.graphql.js.flow +2 -2
  24. package/__flowtests__/__generated__/ReactRelayFragmentContainerFlowtest_viewer2.graphql.js.flow +2 -2
  25. package/__flowtests__/__generated__/ReactRelayPaginationContainerFlowtestQuery.graphql.js.flow +3 -3
  26. package/__flowtests__/__generated__/ReactRelayPaginationContainerFlowtest_viewer.graphql.js.flow +3 -3
  27. package/__flowtests__/__generated__/ReactRelayRefetchContainerFlowtestQuery.graphql.js.flow +3 -3
  28. package/__flowtests__/__generated__/ReactRelayRefetchContainerFlowtest_viewer.graphql.js.flow +3 -3
  29. package/__flowtests__/__generated__/RelayModernFlowtest_badref.graphql.js.flow +2 -2
  30. package/__flowtests__/__generated__/RelayModernFlowtest_notref.graphql.js.flow +2 -2
  31. package/__flowtests__/__generated__/RelayModernFlowtest_user.graphql.js.flow +2 -2
  32. package/__flowtests__/__generated__/RelayModernFlowtest_users.graphql.js.flow +2 -2
  33. package/assertFragmentMap.js.flow +0 -2
  34. package/buildReactRelayContainer.js.flow +2 -4
  35. package/getRootVariablesForFragments.js.flow +0 -2
  36. package/hooks.js +1 -1
  37. package/hooks.js.flow +0 -2
  38. package/index.js +1 -1
  39. package/index.js.flow +2 -2
  40. package/isRelayEnvironment.js.flow +0 -2
  41. package/jest-react/internalAct.js.flow +25 -9
  42. package/legacy.js +1 -1
  43. package/legacy.js.flow +0 -2
  44. package/lib/ReactRelayContainerUtils.js +0 -1
  45. package/lib/ReactRelayContext.js +0 -1
  46. package/lib/ReactRelayFragmentContainer.js +10 -9
  47. package/lib/ReactRelayFragmentMockRenderer.js +0 -1
  48. package/lib/ReactRelayLocalQueryRenderer.js +0 -1
  49. package/lib/ReactRelayPaginationContainer.js +14 -11
  50. package/lib/ReactRelayQueryFetcher.js +2 -2
  51. package/lib/ReactRelayQueryRenderer.js +2 -4
  52. package/lib/ReactRelayQueryRendererContext.js +0 -1
  53. package/lib/ReactRelayRefetchContainer.js +11 -14
  54. package/lib/ReactRelayTestMocker.js +1 -2
  55. package/lib/ReactRelayTypes.js +0 -1
  56. package/lib/RelayContext.js +0 -1
  57. package/lib/assertFragmentMap.js +0 -1
  58. package/lib/buildReactRelayContainer.js +1 -2
  59. package/lib/getRootVariablesForFragments.js +1 -2
  60. package/lib/hooks.js +0 -1
  61. package/lib/index.js +3 -1
  62. package/lib/isRelayEnvironment.js +0 -1
  63. package/lib/jest-react/internalAct.js +24 -4
  64. package/lib/legacy.js +0 -1
  65. package/lib/multi-actor/useRelayActorEnvironment.js +0 -1
  66. package/lib/readContext.js +2 -2
  67. package/lib/relay-hooks/EntryPointContainer.react.js +0 -1
  68. package/lib/relay-hooks/EntryPointTypes.flow.js +0 -1
  69. package/lib/relay-hooks/FragmentResource.js +68 -29
  70. package/lib/relay-hooks/HooksImplementation.js +29 -0
  71. package/lib/relay-hooks/InternalLogger.js +0 -1
  72. package/lib/relay-hooks/LRUCache.js +0 -1
  73. package/lib/relay-hooks/LazyLoadEntryPointContainer_DEPRECATED.react.js +0 -1
  74. package/lib/relay-hooks/MatchContainer.js +2 -2
  75. package/lib/relay-hooks/ProfilerContext.js +0 -1
  76. package/lib/relay-hooks/QueryResource.js +5 -168
  77. package/lib/relay-hooks/RelayEnvironmentProvider.js +0 -1
  78. package/lib/relay-hooks/SuspenseResource.js +1 -2
  79. package/lib/relay-hooks/loadQuery.js +1 -1
  80. package/lib/relay-hooks/preloadQuery_DEPRECATED.js +8 -13
  81. package/lib/relay-hooks/prepareEntryPoint_DEPRECATED.js +0 -1
  82. package/lib/relay-hooks/react-cache/RelayReactCache.js +36 -0
  83. package/lib/relay-hooks/react-cache/getQueryResultOrFetchQuery_REACT_CACHE.js +344 -0
  84. package/lib/relay-hooks/react-cache/readFragmentInternal_REACT_CACHE.js +239 -0
  85. package/lib/relay-hooks/react-cache/useFragmentInternal_REACT_CACHE.js +598 -0
  86. package/lib/relay-hooks/react-cache/useFragment_REACT_CACHE.js +50 -0
  87. package/lib/relay-hooks/react-cache/useLazyLoadQuery_REACT_CACHE.js +55 -0
  88. package/lib/relay-hooks/react-cache/usePaginationFragment_REACT_CACHE.js +150 -0
  89. package/lib/relay-hooks/react-cache/usePreloadedQuery_REACT_CACHE.js +124 -0
  90. package/lib/relay-hooks/react-cache/useRefetchableFragmentInternal_REACT_CACHE.js +367 -0
  91. package/lib/relay-hooks/react-cache/useRefetchableFragment_REACT_CACHE.js +45 -0
  92. package/lib/relay-hooks/useBlockingPaginationFragment.js +4 -3
  93. package/lib/relay-hooks/useClientQuery.js +33 -0
  94. package/lib/relay-hooks/useEntryPointLoader.js +1 -2
  95. package/lib/relay-hooks/useFetchTrackingRef.js +0 -1
  96. package/lib/relay-hooks/useFragment.js +15 -2
  97. package/lib/relay-hooks/useFragmentNode.js +0 -1
  98. package/lib/relay-hooks/useIsMountedRef.js +0 -1
  99. package/lib/relay-hooks/useLazyLoadQuery.js +4 -2
  100. package/lib/relay-hooks/useLazyLoadQueryNode.js +0 -1
  101. package/lib/relay-hooks/useLoadMoreFunction.js +1 -2
  102. package/lib/relay-hooks/useMemoOperationDescriptor.js +0 -1
  103. package/lib/relay-hooks/useMemoVariables.js +0 -1
  104. package/lib/relay-hooks/useMutation.js +5 -7
  105. package/lib/relay-hooks/usePaginationFragment.js +15 -3
  106. package/lib/relay-hooks/usePreloadedQuery.js +4 -2
  107. package/lib/relay-hooks/useQueryLoader.js +1 -2
  108. package/lib/relay-hooks/useRefetchableFragment.js +14 -2
  109. package/lib/relay-hooks/useRefetchableFragmentNode.js +1 -2
  110. package/lib/relay-hooks/useRelayEnvironment.js +0 -1
  111. package/lib/relay-hooks/useStaticFragmentNodeWarning.js +0 -1
  112. package/lib/relay-hooks/useSubscribeToInvalidationState.js +0 -1
  113. package/lib/relay-hooks/useSubscription.js +0 -1
  114. package/multi-actor/useRelayActorEnvironment.js.flow +0 -2
  115. package/package.json +3 -3
  116. package/react-relay-hooks.js +2 -2
  117. package/react-relay-hooks.min.js +2 -2
  118. package/react-relay-legacy.js +2 -2
  119. package/react-relay-legacy.min.js +2 -2
  120. package/react-relay.js +2 -2
  121. package/react-relay.min.js +2 -2
  122. package/readContext.js.flow +1 -2
  123. package/relay-hooks/EntryPointContainer.react.js.flow +2 -4
  124. package/relay-hooks/EntryPointTypes.flow.js.flow +30 -32
  125. package/relay-hooks/FragmentResource.js.flow +80 -37
  126. package/relay-hooks/HooksImplementation.js.flow +43 -0
  127. package/relay-hooks/InternalLogger.js.flow +0 -2
  128. package/relay-hooks/LRUCache.js.flow +0 -2
  129. package/relay-hooks/LazyLoadEntryPointContainer_DEPRECATED.react.js.flow +4 -6
  130. package/relay-hooks/MatchContainer.js.flow +11 -6
  131. package/relay-hooks/ProfilerContext.js.flow +0 -2
  132. package/relay-hooks/QueryResource.js.flow +12 -209
  133. package/relay-hooks/RelayEnvironmentProvider.js.flow +2 -4
  134. package/relay-hooks/SuspenseResource.js.flow +0 -2
  135. package/relay-hooks/__flowtests__/EntryPointTypes/EntryPointElementConfig-flowtest.js.flow +3 -3
  136. package/relay-hooks/__flowtests__/EntryPointTypes/NestedEntrypoints-flowtest.js.flow +2 -2
  137. package/relay-hooks/__flowtests__/__generated__/useFragmentFlowtest_user.graphql.js.flow +2 -2
  138. package/relay-hooks/__flowtests__/__generated__/useFragmentFlowtest_users.graphql.js.flow +2 -2
  139. package/relay-hooks/__flowtests__/useBlockingPaginationFragment-flowtest.js.flow +4 -6
  140. package/relay-hooks/__flowtests__/useFragment-flowtest.js.flow +0 -2
  141. package/relay-hooks/__flowtests__/usePaginationFragment-flowtest.js.flow +4 -6
  142. package/relay-hooks/__flowtests__/useRefetchableFragment-flowtest.js.flow +0 -2
  143. package/relay-hooks/__flowtests__/utils.js.flow +8 -10
  144. package/relay-hooks/loadQuery.js.flow +2 -1
  145. package/relay-hooks/preloadQuery_DEPRECATED.js.flow +11 -20
  146. package/relay-hooks/prepareEntryPoint_DEPRECATED.js.flow +0 -2
  147. package/relay-hooks/react-cache/RelayReactCache.js.flow +40 -0
  148. package/relay-hooks/react-cache/getQueryResultOrFetchQuery_REACT_CACHE.js.flow +430 -0
  149. package/relay-hooks/react-cache/readFragmentInternal_REACT_CACHE.js.flow +297 -0
  150. package/relay-hooks/react-cache/useFragmentInternal_REACT_CACHE.js.flow +599 -0
  151. package/relay-hooks/react-cache/useFragment_REACT_CACHE.js.flow +72 -0
  152. package/relay-hooks/react-cache/useLazyLoadQuery_REACT_CACHE.js.flow +70 -0
  153. package/relay-hooks/react-cache/usePaginationFragment_REACT_CACHE.js.flow +171 -0
  154. package/relay-hooks/react-cache/usePreloadedQuery_REACT_CACHE.js.flow +151 -0
  155. package/relay-hooks/react-cache/useRefetchableFragmentInternal_REACT_CACHE.js.flow +595 -0
  156. package/relay-hooks/react-cache/useRefetchableFragment_REACT_CACHE.js.flow +65 -0
  157. package/relay-hooks/useBlockingPaginationFragment.js.flow +4 -6
  158. package/relay-hooks/useClientQuery.js.flow +39 -0
  159. package/relay-hooks/useEntryPointLoader.js.flow +6 -8
  160. package/relay-hooks/useFetchTrackingRef.js.flow +2 -4
  161. package/relay-hooks/useFragment.js.flow +17 -12
  162. package/relay-hooks/useFragmentNode.js.flow +2 -4
  163. package/relay-hooks/useIsMountedRef.js.flow +1 -3
  164. package/relay-hooks/useLazyLoadQuery.js.flow +17 -5
  165. package/relay-hooks/useLazyLoadQueryNode.js.flow +2 -4
  166. package/relay-hooks/useLoadMoreFunction.js.flow +6 -8
  167. package/relay-hooks/useMemoOperationDescriptor.js.flow +0 -2
  168. package/relay-hooks/useMemoVariables.js.flow +0 -2
  169. package/relay-hooks/useMutation.js.flow +5 -7
  170. package/relay-hooks/usePaginationFragment.js.flow +44 -19
  171. package/relay-hooks/usePreloadedQuery.js.flow +14 -5
  172. package/relay-hooks/useQueryLoader.js.flow +4 -6
  173. package/relay-hooks/useRefetchableFragment.js.flow +32 -3
  174. package/relay-hooks/useRefetchableFragmentNode.js.flow +38 -25
  175. package/relay-hooks/useRelayEnvironment.js.flow +0 -2
  176. package/relay-hooks/useStaticFragmentNodeWarning.js.flow +0 -2
  177. package/relay-hooks/useSubscribeToInvalidationState.js.flow +0 -2
  178. package/relay-hooks/useSubscription.js.flow +14 -10
@@ -9,8 +9,6 @@
9
9
  * @format
10
10
  */
11
11
 
12
- // flowlint ambiguous-object-type:error
13
-
14
12
  'use strict';
15
13
 
16
14
  import type {Cache} from './LRUCache';
@@ -24,6 +22,7 @@ import type {
24
22
  RequestDescriptor,
25
23
  Snapshot,
26
24
  } from 'relay-runtime';
25
+ import type {MissingLiveResolverField} from 'relay-runtime/store/RelayStoreTypes';
27
26
 
28
27
  const LRUCache = require('./LRUCache');
29
28
  const {getQueryResourceForEnvironment} = require('./QueryResource');
@@ -37,21 +36,21 @@ const {
37
36
  getPendingOperationsForFragment,
38
37
  getSelector,
39
38
  getVariablesFromFragment,
39
+ handlePotentialSnapshotErrors,
40
40
  isPromise,
41
41
  recycleNodesInto,
42
- reportMissingRequiredFields,
43
42
  } = require('relay-runtime');
44
43
 
45
44
  export type FragmentResource = FragmentResourceImpl;
46
45
 
47
46
  type FragmentResourceCache = Cache<
48
- | {|
47
+ | {
49
48
  kind: 'pending',
50
49
  pendingOperations: $ReadOnlyArray<RequestDescriptor>,
51
50
  promise: Promise<mixed>,
52
51
  result: FragmentResult,
53
- |}
54
- | {|kind: 'done', result: FragmentResult|},
52
+ }
53
+ | {kind: 'done', result: FragmentResult},
55
54
  >;
56
55
 
57
56
  const WEAKMAP_SUPPORTED = typeof WeakMap === 'function';
@@ -62,13 +61,13 @@ interface IMap<K, V> {
62
61
 
63
62
  type SingularOrPluralSnapshot = Snapshot | $ReadOnlyArray<Snapshot>;
64
63
 
65
- opaque type FragmentResult: {data: mixed, ...} = {|
64
+ opaque type FragmentResult: {data: mixed, ...} = {
66
65
  cacheKey: string,
67
66
  data: mixed,
68
67
  isMissingData: boolean,
69
68
  snapshot: SingularOrPluralSnapshot | null,
70
69
  storeEpoch: number,
71
- |};
70
+ };
72
71
 
73
72
  // TODO: Fix to not rely on LRU. If the number of active fragments exceeds this
74
73
  // capacity, readSpec() will fail to find cached entries and break object
@@ -92,6 +91,18 @@ function hasMissingClientEdges(snapshot: SingularOrPluralSnapshot): boolean {
92
91
  return (snapshot.missingClientEdges?.length ?? 0) > 0;
93
92
  }
94
93
 
94
+ function missingLiveResolverFields(
95
+ snapshot: SingularOrPluralSnapshot,
96
+ ): ?$ReadOnlyArray<MissingLiveResolverField> {
97
+ if (Array.isArray(snapshot)) {
98
+ return snapshot
99
+ .map(s => s.missingLiveResolverFields)
100
+ .filter(Boolean)
101
+ .flat();
102
+ }
103
+ return snapshot.missingLiveResolverFields;
104
+ }
105
+
95
106
  function singularOrPluralForEach(
96
107
  snapshot: SingularOrPluralSnapshot,
97
108
  f: Snapshot => void,
@@ -165,7 +176,7 @@ class ClientEdgeQueryResultsCache {
165
176
  }
166
177
  }
167
178
 
168
- _retain(id) {
179
+ _retain(id: string): {dispose: () => void} {
169
180
  const retainCount = (this._retainCounts.get(id) ?? 0) + 1;
170
181
  this._retainCounts.set(id, retainCount);
171
182
  return {
@@ -288,8 +299,12 @@ class FragmentResourceImpl {
288
299
  throw cachedValue.promise;
289
300
  }
290
301
 
291
- if (cachedValue.kind === 'done' && cachedValue.result.snapshot) {
292
- this._reportMissingRequiredFieldsInSnapshot(
302
+ if (
303
+ cachedValue.kind === 'done' &&
304
+ cachedValue.result.snapshot &&
305
+ !missingLiveResolverFields(cachedValue.result.snapshot)?.length
306
+ ) {
307
+ this._handlePotentialSnapshotErrorsInSnapshot(
293
308
  cachedValue.result.snapshot,
294
309
  );
295
310
  return cachedValue.result;
@@ -330,7 +345,7 @@ class FragmentResourceImpl {
330
345
  storeEpoch,
331
346
  );
332
347
  if (!fragmentResult.isMissingData) {
333
- this._reportMissingRequiredFieldsInSnapshot(snapshot);
348
+ this._handlePotentialSnapshotErrorsInSnapshot(snapshot);
334
349
 
335
350
  this._cache.set(fragmentIdentifier, {
336
351
  kind: 'done',
@@ -352,6 +367,7 @@ class FragmentResourceImpl {
352
367
  let clientEdgeRequests: ?Array<RequestDescriptor> = null;
353
368
  if (
354
369
  RelayFeatureFlags.ENABLE_CLIENT_EDGES &&
370
+ fragmentNode.metadata?.hasClientEdges === true &&
355
371
  hasMissingClientEdges(snapshot)
356
372
  ) {
357
373
  clientEdgeRequests = [];
@@ -384,11 +400,11 @@ class FragmentResourceImpl {
384
400
  queryResults,
385
401
  );
386
402
  }
387
- let clientEdgePromises = null;
403
+ let clientEdgePromises: Array<Promise<void>> = [];
388
404
  if (RelayFeatureFlags.ENABLE_CLIENT_EDGES && clientEdgeRequests) {
389
405
  clientEdgePromises = clientEdgeRequests
390
406
  .map(request => getPromiseForActiveRequest(this._environment, request))
391
- .filter(p => p != null);
407
+ .filter(Boolean);
392
408
  }
393
409
 
394
410
  // Finally look for operations in flight for our parent query:
@@ -404,9 +420,17 @@ class FragmentResourceImpl {
404
420
  fragmentResult,
405
421
  );
406
422
  const parentQueryPromiseResultPromise = parentQueryPromiseResult?.promise; // for refinement
423
+ const missingResolverFieldPromises =
424
+ missingLiveResolverFields(snapshot)?.map(({liveStateID}) => {
425
+ const store = environment.getStore();
426
+
427
+ // $FlowFixMe[prop-missing] This is expected to be a LiveResolverStore
428
+ return store.getLiveResolverPromise(liveStateID);
429
+ }) ?? [];
407
430
 
408
431
  if (
409
- clientEdgePromises?.length ||
432
+ clientEdgePromises.length ||
433
+ missingResolverFieldPromises.length ||
410
434
  isPromise(parentQueryPromiseResultPromise)
411
435
  ) {
412
436
  environment.__log({
@@ -416,17 +440,36 @@ class FragmentResourceImpl {
416
440
  isRelayHooks: true,
417
441
  isPromiseCached: false,
418
442
  isMissingData: fragmentResult.isMissingData,
443
+ // TODO! Attach information here about missing live resolver fields
419
444
  pendingOperations: [
420
445
  ...(parentQueryPromiseResult?.pendingOperations ?? []),
421
446
  ...(clientEdgeRequests ?? []),
422
447
  ],
423
448
  });
424
- throw clientEdgePromises?.length
425
- ? Promise.all([parentQueryPromiseResultPromise, ...clientEdgePromises])
426
- : parentQueryPromiseResultPromise;
449
+ let promises = [];
450
+ if (clientEdgePromises.length > 0) {
451
+ promises = promises.concat(clientEdgePromises);
452
+ }
453
+ if (missingResolverFieldPromises.length > 0) {
454
+ promises = promises.concat(missingResolverFieldPromises);
455
+ }
456
+
457
+ if (promises.length > 0) {
458
+ if (parentQueryPromiseResultPromise) {
459
+ promises.push(parentQueryPromiseResultPromise);
460
+ }
461
+ throw Promise.all(promises);
462
+ }
463
+
464
+ // Note: we are re-throwing the `parentQueryPromiseResultPromise` here,
465
+ // because some of our suspense-related code is relying on the instance equality
466
+ // of thrown promises. See FragmentResource-test.js
467
+ if (parentQueryPromiseResultPromise) {
468
+ throw parentQueryPromiseResultPromise;
469
+ }
427
470
  }
428
471
 
429
- this._reportMissingRequiredFieldsInSnapshot(snapshot);
472
+ this._handlePotentialSnapshotErrorsInSnapshot(snapshot);
430
473
  return getFragmentResult(fragmentIdentifier, snapshot, storeEpoch);
431
474
  }
432
475
 
@@ -436,7 +479,7 @@ class FragmentResourceImpl {
436
479
  fragmentRef: mixed,
437
480
  request: ConcreteRequest,
438
481
  clientEdgeDestinationID: DataID,
439
- ) {
482
+ ): {queryResult: QueryResult, requestDescriptor: RequestDescriptor} {
440
483
  const originalVariables = getVariablesFromFragment(
441
484
  fragmentNode,
442
485
  fragmentRef,
@@ -462,23 +505,21 @@ class FragmentResourceImpl {
462
505
  };
463
506
  }
464
507
 
465
- _reportMissingRequiredFieldsInSnapshot(snapshot: SingularOrPluralSnapshot) {
508
+ _handlePotentialSnapshotErrorsInSnapshot(snapshot: SingularOrPluralSnapshot) {
466
509
  if (Array.isArray(snapshot)) {
467
510
  snapshot.forEach(s => {
468
- if (s.missingRequiredFields != null) {
469
- reportMissingRequiredFields(
470
- this._environment,
471
- s.missingRequiredFields,
472
- );
473
- }
474
- });
475
- } else {
476
- if (snapshot.missingRequiredFields != null) {
477
- reportMissingRequiredFields(
511
+ handlePotentialSnapshotErrors(
478
512
  this._environment,
479
- snapshot.missingRequiredFields,
513
+ s.missingRequiredFields,
514
+ s.relayResolverErrors,
480
515
  );
481
- }
516
+ });
517
+ } else {
518
+ handlePotentialSnapshotErrors(
519
+ this._environment,
520
+ snapshot.missingRequiredFields,
521
+ snapshot.relayResolverErrors,
522
+ );
482
523
  }
483
524
  }
484
525
 
@@ -487,7 +528,7 @@ class FragmentResourceImpl {
487
528
  fragmentRefs: {[string]: mixed, ...},
488
529
  componentDisplayName: string,
489
530
  ): {[string]: FragmentResult, ...} {
490
- const result = {};
531
+ const result: {[string]: FragmentResult} = {};
491
532
  for (const key in fragmentNodes) {
492
533
  result[key] = this.read(
493
534
  fragmentNodes[key],
@@ -596,7 +637,7 @@ class FragmentResourceImpl {
596
637
 
597
638
  checkMissedUpdates(
598
639
  fragmentResult: FragmentResult,
599
- ): [boolean, SingularOrPluralSnapshot | null] {
640
+ ): [boolean /* were updates missed? */, SingularOrPluralSnapshot | null] {
600
641
  const environment = this._environment;
601
642
  const renderedSnapshot = fragmentResult.snapshot;
602
643
  if (!renderedSnapshot) {
@@ -644,9 +685,11 @@ class FragmentResourceImpl {
644
685
  data: updatedData,
645
686
  isMissingData: currentSnapshot.isMissingData,
646
687
  missingClientEdges: currentSnapshot.missingClientEdges,
688
+ missingLiveResolverFields: currentSnapshot.missingLiveResolverFields,
647
689
  seenRecords: currentSnapshot.seenRecords,
648
690
  selector: currentSnapshot.selector,
649
691
  missingRequiredFields: currentSnapshot.missingRequiredFields,
692
+ relayResolverErrors: currentSnapshot.relayResolverErrors,
650
693
  };
651
694
  if (updatedData !== renderData) {
652
695
  this._cache.set(cacheKey, {
@@ -671,10 +714,10 @@ class FragmentResourceImpl {
671
714
  fragmentNode: ReaderFragment,
672
715
  fragmentOwner: RequestDescriptor,
673
716
  fragmentResult: FragmentResult,
674
- ): {|
717
+ ): {
675
718
  promise: Promise<void>,
676
719
  pendingOperations: $ReadOnlyArray<RequestDescriptor>,
677
- |} | null {
720
+ } | null {
678
721
  const pendingOperationsResult = getPendingOperationsForFragment(
679
722
  this._environment,
680
723
  fragmentNode,
@@ -0,0 +1,43 @@
1
+ /**
2
+ * Copyright (c) Meta Platforms, Inc. and affiliates.
3
+ *
4
+ * This source code is licensed under the MIT license found in the
5
+ * LICENSE file in the root directory of this source tree.
6
+ *
7
+ * @emails oncall+relay
8
+ * @flow strict-local
9
+ * @format
10
+ */
11
+
12
+ 'use strict';
13
+
14
+ import typeof useFragment from './useFragment';
15
+ import type {UsePaginationFragmentType} from './usePaginationFragment';
16
+ import type {UseRefetchableFragmentType} from './useRefetchableFragment';
17
+
18
+ const warning = require('warning');
19
+
20
+ type HooksImplementation = {
21
+ useFragment: useFragment,
22
+ usePaginationFragment: UsePaginationFragmentType,
23
+ useRefetchableFragment: UseRefetchableFragmentType,
24
+ };
25
+
26
+ let implementation: HooksImplementation | null = null;
27
+
28
+ function inject(impl: HooksImplementation): void {
29
+ warning(
30
+ implementation !== null,
31
+ 'Relay HooksImplementation was injected twice.',
32
+ );
33
+ implementation = impl;
34
+ }
35
+
36
+ function get(): HooksImplementation | null {
37
+ return implementation;
38
+ }
39
+
40
+ module.exports = {
41
+ inject,
42
+ get,
43
+ };
@@ -9,8 +9,6 @@
9
9
  * @format
10
10
  */
11
11
 
12
- // flowlint ambiguous-object-type:error
13
-
14
12
  'use strict';
15
13
 
16
14
  type LogEvent = (eventData: string) => void;
@@ -9,8 +9,6 @@
9
9
  * @format
10
10
  */
11
11
 
12
- // flowlint ambiguous-object-type:error
13
-
14
12
  'use strict';
15
13
 
16
14
  const invariant = require('invariant');
@@ -9,8 +9,6 @@
9
9
  * @format
10
10
  */
11
11
 
12
- // flowlint ambiguous-object-type:error
13
-
14
12
  'use strict';
15
13
 
16
14
  import type {
@@ -27,13 +25,13 @@ const React = require('react');
27
25
  const {useContext, useEffect, useMemo} = require('react');
28
26
  const {stableCopy} = require('relay-runtime');
29
27
 
30
- type PreloadedEntryPoint<TEntryPointComponent> = $ReadOnly<{|
28
+ type PreloadedEntryPoint<TEntryPointComponent> = $ReadOnly<{
31
29
  entryPoints: React.ElementConfig<TEntryPointComponent>['entryPoints'],
32
30
  extraProps: React.ElementConfig<TEntryPointComponent>['extraProps'],
33
31
  getComponent: () => TEntryPointComponent,
34
32
  queries: React.ElementConfig<TEntryPointComponent>['queries'],
35
33
  rootModuleID: string,
36
- |}>;
34
+ }>;
37
35
 
38
36
  type EntryPointContainerProps<
39
37
  TEntryPointParams,
@@ -42,7 +40,7 @@ type EntryPointContainerProps<
42
40
  TRuntimeProps,
43
41
  TExtraProps,
44
42
  > = $ReadOnly<
45
- $ReadOnly<{|
43
+ $ReadOnly<{
46
44
  entryPoint: EntryPoint<
47
45
  TEntryPointParams,
48
46
  EntryPointComponent<
@@ -55,7 +53,7 @@ type EntryPointContainerProps<
55
53
  entryPointParams: TEntryPointParams,
56
54
  environmentProvider?: IEnvironmentProvider<EnvironmentProviderOptions>,
57
55
  props: TRuntimeProps,
58
- |}>,
56
+ }>,
59
57
  >;
60
58
 
61
59
  function stableStringify(value: mixed): string {
@@ -9,8 +9,6 @@
9
9
  * @format
10
10
  */
11
11
 
12
- // flowlint ambiguous-object-type:error
13
-
14
12
  'use strict';
15
13
 
16
14
  const React = require('react');
@@ -87,7 +85,7 @@ const {useMemo} = React;
87
85
 
88
86
  // Note: this type is intentionally non-exact, it is expected that the
89
87
  // object may contain sibling fields.
90
- type TypenameOnlyPointer = {|+__typename: string|};
88
+ type TypenameOnlyPointer = {+__typename: string};
91
89
  export type MatchPointer = {
92
90
  +__fragmentPropName?: ?string,
93
91
  +__module_component?: mixed,
@@ -95,12 +93,12 @@ export type MatchPointer = {
95
93
  ...
96
94
  };
97
95
 
98
- export type MatchContainerProps<TProps: {...}, TFallback: React.Node> = {|
96
+ export type MatchContainerProps<TProps: {...}, TFallback: React.Node> = {
99
97
  +fallback?: ?TFallback,
100
98
  +loader: (module: mixed) => React.AbstractComponent<TProps>,
101
99
  +match: ?MatchPointer | ?TypenameOnlyPointer,
102
100
  +props?: TProps,
103
- |};
101
+ };
104
102
 
105
103
  function MatchContainer<TProps: {...}, TFallback: React.Node | null>({
106
104
  fallback,
@@ -149,7 +147,13 @@ function MatchContainer<TProps: {...}, TFallback: React.Node | null>({
149
147
  // TODO: Perform this transformation in RelayReader so that unchanged
150
148
  // output of subscriptions already has a stable identity.
151
149
  if (__fragmentPropName != null && __id != null && __fragments != null) {
152
- const fragProps = {};
150
+ const fragProps: {
151
+ [string]: {
152
+ __fragmentOwner: $FlowFixMe,
153
+ __fragments: $FlowFixMe,
154
+ __id: string,
155
+ },
156
+ } = {};
153
157
  fragProps[__fragmentPropName] = {__id, __fragments, __fragmentOwner};
154
158
  return fragProps;
155
159
  }
@@ -158,6 +162,7 @@ function MatchContainer<TProps: {...}, TFallback: React.Node | null>({
158
162
 
159
163
  if (LoadedContainer != null && fragmentProps != null) {
160
164
  // $FlowFixMe[incompatible-type]
165
+ // $FlowFixMe[cannot-spread-indexer]
161
166
  return <LoadedContainer {...props} {...fragmentProps} />;
162
167
  } else {
163
168
  return fallback ?? null;
@@ -9,8 +9,6 @@
9
9
  * @format
10
10
  */
11
11
 
12
- // flowlint ambiguous-object-type:error
13
-
14
12
  // This contextual profiler can be used to wrap a react sub-tree. It will bind
15
13
  // the RelayProfiler during the render phase of these components. Allows
16
14
  // collecting metrics for a specific part of your application.