relay-runtime 10.1.3 → 11.0.2

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 (106) hide show
  1. package/handlers/connection/ConnectionHandler.js.flow +60 -0
  2. package/handlers/connection/MutationHandlers.js.flow +28 -0
  3. package/index.js +1 -1
  4. package/index.js.flow +9 -3
  5. package/lib/handlers/RelayDefaultHandlerProvider.js +1 -1
  6. package/lib/handlers/connection/ConnectionHandler.js +68 -6
  7. package/lib/handlers/connection/MutationHandlers.js +67 -8
  8. package/lib/index.js +3 -0
  9. package/lib/multi-actor-environment/ActorIdentifier.js +23 -0
  10. package/lib/multi-actor-environment/ActorSpecificEnvironment.js +108 -0
  11. package/lib/multi-actor-environment/MultiActorEnvironment.js +156 -0
  12. package/lib/multi-actor-environment/MultiActorEnvironmentTypes.js +11 -0
  13. package/lib/multi-actor-environment/index.js +17 -0
  14. package/lib/mutations/RelayRecordProxy.js +1 -1
  15. package/lib/mutations/RelayRecordSourceMutator.js +1 -1
  16. package/lib/mutations/RelayRecordSourceProxy.js +1 -1
  17. package/lib/mutations/RelayRecordSourceSelectorProxy.js +1 -1
  18. package/lib/mutations/applyOptimisticMutation.js +1 -1
  19. package/lib/mutations/commitMutation.js +1 -1
  20. package/lib/mutations/validateMutation.js +36 -15
  21. package/lib/network/RelayNetwork.js +1 -1
  22. package/lib/network/RelayQueryResponseCache.js +3 -2
  23. package/lib/query/GraphQLTag.js +1 -1
  24. package/lib/query/fetchQuery.js +129 -13
  25. package/lib/query/fetchQueryInternal.js +3 -4
  26. package/lib/query/fetchQuery_DEPRECATED.js +39 -0
  27. package/lib/store/DataChecker.js +26 -14
  28. package/lib/store/{RelayModernQueryExecutor.js → OperationExecutor.js} +117 -47
  29. package/lib/store/RelayConcreteVariables.js +8 -4
  30. package/lib/store/RelayModernEnvironment.js +105 -136
  31. package/lib/store/RelayModernFragmentSpecResolver.js +16 -9
  32. package/lib/store/RelayModernRecord.js +1 -1
  33. package/lib/store/RelayModernSelector.js +1 -1
  34. package/lib/store/RelayModernStore.js +19 -20
  35. package/lib/store/RelayOperationTracker.js +55 -49
  36. package/lib/store/RelayPublishQueue.js +9 -5
  37. package/lib/store/RelayReader.js +68 -14
  38. package/lib/store/RelayReferenceMarker.js +28 -14
  39. package/lib/store/RelayResponseNormalizer.js +109 -15
  40. package/lib/store/RelayStoreReactFlightUtils.js +6 -4
  41. package/lib/store/RelayStoreSubscriptions.js +18 -8
  42. package/lib/store/RelayStoreSubscriptionsUsingMapByID.js +90 -30
  43. package/lib/store/RelayStoreUtils.js +3 -2
  44. package/lib/store/ResolverFragments.js +57 -0
  45. package/lib/store/cloneRelayHandleSourceField.js +1 -1
  46. package/lib/store/cloneRelayScalarHandleSourceField.js +1 -1
  47. package/lib/store/createFragmentSpecResolver.js +2 -2
  48. package/lib/store/createRelayContext.js +1 -1
  49. package/lib/store/defaultGetDataID.js +3 -1
  50. package/lib/store/hasOverlappingIDs.js +11 -3
  51. package/lib/store/readInlineData.js +1 -1
  52. package/lib/subscription/requestSubscription.js +33 -5
  53. package/lib/util/RelayConcreteNode.js +2 -0
  54. package/lib/util/RelayFeatureFlags.js +8 -3
  55. package/lib/util/RelayProfiler.js +17 -187
  56. package/lib/util/RelayReplaySubject.js +1 -1
  57. package/lib/util/deepFreeze.js +1 -0
  58. package/lib/util/getRelayHandleKey.js +1 -1
  59. package/lib/util/getRequestIdentifier.js +1 -1
  60. package/multi-actor-environment/ActorIdentifier.js.flow +27 -0
  61. package/multi-actor-environment/ActorSpecificEnvironment.js.flow +189 -0
  62. package/multi-actor-environment/MultiActorEnvironment.js.flow +233 -0
  63. package/multi-actor-environment/MultiActorEnvironmentTypes.js.flow +196 -0
  64. package/multi-actor-environment/index.js.flow +24 -0
  65. package/mutations/RelayRecordSourceProxy.js.flow +3 -2
  66. package/mutations/commitMutation.js.flow +1 -1
  67. package/mutations/validateMutation.js.flow +40 -15
  68. package/network/RelayNetworkTypes.js.flow +31 -11
  69. package/network/RelayQueryResponseCache.js.flow +2 -1
  70. package/package.json +3 -2
  71. package/query/fetchQuery.js.flow +147 -20
  72. package/query/fetchQueryInternal.js.flow +2 -3
  73. package/query/fetchQuery_DEPRECATED.js.flow +47 -0
  74. package/relay-runtime.js +2 -2
  75. package/relay-runtime.min.js +2 -2
  76. package/store/DataChecker.js.flow +23 -15
  77. package/store/{RelayModernQueryExecutor.js.flow → OperationExecutor.js.flow} +128 -40
  78. package/store/RelayConcreteVariables.js.flow +5 -0
  79. package/store/RelayModernEnvironment.js.flow +100 -130
  80. package/store/RelayModernFragmentSpecResolver.js.flow +30 -8
  81. package/store/RelayModernStore.js.flow +28 -24
  82. package/store/RelayOperationTracker.js.flow +69 -56
  83. package/store/RelayPublishQueue.js.flow +7 -4
  84. package/store/RelayReader.js.flow +63 -11
  85. package/store/RelayRecordSource.js.flow +3 -3
  86. package/store/RelayRecordSourceMapImpl.js.flow +6 -2
  87. package/store/RelayReferenceMarker.js.flow +28 -18
  88. package/store/RelayResponseNormalizer.js.flow +134 -23
  89. package/store/RelayStoreReactFlightUtils.js.flow +9 -4
  90. package/store/RelayStoreSubscriptions.js.flow +22 -7
  91. package/store/RelayStoreSubscriptionsUsingMapByID.js.flow +36 -12
  92. package/store/RelayStoreTypes.js.flow +51 -22
  93. package/store/RelayStoreUtils.js.flow +2 -1
  94. package/store/ResolverFragments.js.flow +125 -0
  95. package/store/createFragmentSpecResolver.js.flow +2 -0
  96. package/store/defaultGetDataID.js.flow +3 -1
  97. package/store/hasOverlappingIDs.js.flow +11 -9
  98. package/subscription/requestSubscription.js.flow +25 -2
  99. package/util/NormalizationNode.js.flow +13 -0
  100. package/util/ReaderNode.js.flow +14 -1
  101. package/util/RelayConcreteNode.js.flow +2 -0
  102. package/util/RelayFeatureFlags.js.flow +12 -2
  103. package/util/RelayProfiler.js.flow +22 -194
  104. package/util/RelayRuntimeTypes.js.flow +4 -5
  105. package/util/deepFreeze.js.flow +2 -1
  106. package/util/isEmptyObject.js.flow +1 -1
@@ -18,6 +18,7 @@ import type {
18
18
  PayloadData,
19
19
  PayloadError,
20
20
  ReactFlightServerTree,
21
+ ReactFlightServerError,
21
22
  UploadableMap,
22
23
  } from '../network/RelayNetworkTypes';
23
24
  import type RelayObservable from '../network/RelayObservable';
@@ -55,7 +56,7 @@ export type Record = {[key: string]: mixed, ...};
55
56
  /**
56
57
  * A collection of records keyed by id.
57
58
  */
58
- export type RecordMap = {[dataID: DataID]: ?Record, ...};
59
+ export type RecordObjectMap = {[DataID]: ?Record};
59
60
 
60
61
  export type FragmentMap = {[key: string]: ReaderFragment, ...};
61
62
 
@@ -112,7 +113,7 @@ export type MissingRequiredFields =
112
113
  export type Snapshot = {|
113
114
  +data: ?SelectorData,
114
115
  +isMissingData: boolean,
115
- +seenRecords: RecordMap,
116
+ +seenRecords: DataIDSet,
116
117
  +selector: SingularReaderSelector,
117
118
  +missingRequiredFields: ?MissingRequiredFields,
118
119
  |};
@@ -268,7 +269,7 @@ export interface Store {
268
269
  * internal record source. Subscribers are not immediately notified - this
269
270
  * occurs when `notify()` is called.
270
271
  */
271
- publish(source: RecordSource, idsMarkedForInvalidation?: Set<DataID>): void;
272
+ publish(source: RecordSource, idsMarkedForInvalidation?: DataIDSet): void;
272
273
 
273
274
  /**
274
275
  * Ensure that all the records necessary to fulfill the given selector are
@@ -362,8 +363,9 @@ export interface StoreSubscriptions {
362
363
  */
363
364
  updateSubscriptions(
364
365
  source: RecordSource,
365
- updatedRecordIDs: UpdatedRecords,
366
+ updatedRecordIDs: DataIDSet,
366
367
  updatedOwners: Array<RequestDescriptor>,
368
+ sourceOperation?: OperationDescriptor,
367
369
  ): void;
368
370
  }
369
371
 
@@ -451,9 +453,9 @@ export type LogEvent =
451
453
  +operation: OperationDescriptor,
452
454
  // value from ProfilerContext
453
455
  +profilerContext: mixed,
454
- // FetchPolicy from relay-experimental
456
+ // FetchPolicy from Relay Hooks
455
457
  +fetchPolicy: string,
456
- // RenderPolicy from relay-experimental
458
+ // RenderPolicy from Relay Hooks
457
459
  +renderPolicy: string,
458
460
  +queryAvailability: OperationAvailability,
459
461
  +shouldFetch: boolean,
@@ -474,6 +476,7 @@ export type LogEvent =
474
476
  +transactionID: number,
475
477
  +params: RequestParameters,
476
478
  +variables: Variables,
479
+ +cacheConfig: CacheConfig,
477
480
  |}
478
481
  | {|
479
482
  +name: 'network.next',
@@ -506,15 +509,23 @@ export type LogEvent =
506
509
  |}
507
510
  | {|
508
511
  +name: 'store.gc',
509
- +references: Set<DataID>,
512
+ +references: DataIDSet,
510
513
  |}
511
514
  | {|
512
515
  +name: 'store.notify.start',
516
+ +sourceOperation: ?OperationDescriptor,
513
517
  |}
514
518
  | {|
515
519
  +name: 'store.notify.complete',
516
- +updatedRecordIDs: UpdatedRecords,
517
- +invalidatedRecordIDs: Set<DataID>,
520
+ +sourceOperation: ?OperationDescriptor,
521
+ +updatedRecordIDs: DataIDSet,
522
+ +invalidatedRecordIDs: DataIDSet,
523
+ |}
524
+ | {|
525
+ +name: 'store.notify.subscription',
526
+ +sourceOperation: ?OperationDescriptor,
527
+ +snapshot: Snapshot,
528
+ +nextSnapshot: Snapshot,
518
529
  |}
519
530
  | {|
520
531
  +name: 'entrypoint.root.consume',
@@ -647,13 +658,9 @@ export interface IEnvironment {
647
658
  * the result is subscribed to:
648
659
  * environment.executeMutation({...}).subscribe({...}).
649
660
  */
650
- executeMutation({|
651
- operation: OperationDescriptor,
652
- optimisticUpdater?: ?SelectorStoreUpdater,
653
- optimisticResponse?: ?Object,
654
- updater?: ?SelectorStoreUpdater,
655
- uploadables?: ?UploadableMap,
656
- |}): RelayObservable<GraphQLResponse>;
661
+ executeMutation(
662
+ config: ExecuteMutationConfig,
663
+ ): RelayObservable<GraphQLResponse>;
657
664
 
658
665
  /**
659
666
  * Returns an Observable of GraphQLResponse resulting from executing the
@@ -704,9 +711,10 @@ export type ModuleImportPointer = {
704
711
  };
705
712
 
706
713
  /**
707
- * A map of records affected by an update operation.
714
+ * A set of DataIDs used to track which IDs a read() operation observed and which IDs
715
+ * a publish operation updated.
708
716
  */
709
- export type UpdatedRecords = {[dataID: DataID]: boolean, ...};
717
+ export type DataIDSet = Set<DataID>;
710
718
 
711
719
  /**
712
720
  * A function that updates a store (via a proxy) given the results of a "handle"
@@ -924,7 +932,18 @@ export type RelayResponsePayload = {|
924
932
  |};
925
933
 
926
934
  /**
927
- * Public interface for Publish Queue
935
+ * Configuration on the executeMutation(...).
936
+ */
937
+ export type ExecuteMutationConfig = {|
938
+ operation: OperationDescriptor,
939
+ optimisticUpdater?: ?SelectorStoreUpdater,
940
+ optimisticResponse?: ?Object,
941
+ updater?: ?SelectorStoreUpdater,
942
+ uploadables?: ?UploadableMap,
943
+ |};
944
+
945
+ /**
946
+ * Public interface for Publish Queue.
928
947
  */
929
948
  export interface PublishQueue {
930
949
  /**
@@ -978,15 +997,25 @@ export interface PublishQueue {
978
997
  */
979
998
  export type ReactFlightClientResponse = {readRoot: () => mixed, ...};
980
999
 
981
- export type ReactFlightReachableQuery = {|
1000
+ export type ReactFlightReachableExecutableDefinitions = {|
982
1001
  +module: mixed,
983
1002
  +variables: Variables,
984
1003
  |};
985
1004
 
986
1005
  /**
987
- * A user-supplied function that takes a ReactFlightServerTree, and deserializes
988
- * it into a ReactFlightClientResponse object.
1006
+ * A user-supplied function that takes a ReactFlightServerTree
1007
+ * (after successful execution on the server), and deserializes it into a
1008
+ * ReactFlightClientResponse object.
989
1009
  */
990
1010
  export type ReactFlightPayloadDeserializer = (
991
1011
  tree: ReactFlightServerTree,
992
1012
  ) => ReactFlightClientResponse;
1013
+
1014
+ /**
1015
+ * An optionally user-supplied function that handles errors returned by the
1016
+ * server's JS runtime while executing a React Server Component.
1017
+ */
1018
+ export type ReactFlightServerErrorHandler = (
1019
+ status: string,
1020
+ errors: Array<ReactFlightServerError>,
1021
+ ) => void;
@@ -26,7 +26,7 @@ import type {
26
26
  import type {ReaderArgument, ReaderField} from '../util/ReaderNode';
27
27
  import type {Variables} from '../util/RelayRuntimeTypes';
28
28
 
29
- export type Arguments = {+[string]: mixed, ...};
29
+ export type Arguments = interface {+[string]: mixed};
30
30
 
31
31
  const {VARIABLE, LITERAL, OBJECT_VALUE, LIST_VALUE} = RelayConcreteNode;
32
32
 
@@ -178,6 +178,7 @@ function getStableVariableValue(name: string, variables: Variables): mixed {
178
178
  'getVariableValue(): Undefined variable `%s`.',
179
179
  name,
180
180
  );
181
+ // $FlowFixMe[cannot-write]
181
182
  return stableCopy(variables[name]);
182
183
  }
183
184
 
@@ -0,0 +1,125 @@
1
+ /**
2
+ * Copyright (c) Facebook, Inc. and its 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
+ * @flow strict-local
8
+ * @format
9
+ */
10
+
11
+ // flowlint ambiguous-object-type:error
12
+
13
+ 'use strict';
14
+
15
+ const invariant = require('invariant');
16
+
17
+ const {getFragment} = require('../query/GraphQLTag');
18
+ const {getSelector} = require('./RelayModernSelector');
19
+
20
+ import type {GraphQLTaggedNode} from '../query/GraphQLTag';
21
+ import type {
22
+ FragmentReference,
23
+ SingularReaderSelector,
24
+ } from './RelayStoreTypes';
25
+
26
+ // When we call the user-supplied resolver function, it will in turn call
27
+ // `readFragment`, but that's a global function -- it needs information
28
+ // about what resolver is being executed, which is supplied by putting the
29
+ // info on this stack before we call the resolver function.
30
+ type ResolverContext = {|
31
+ getDataForResolverFragment: SingularReaderSelector => mixed,
32
+ |};
33
+ const contextStack: Array<ResolverContext> = [];
34
+
35
+ function withResolverContext<T>(context: ResolverContext, cb: () => T): T {
36
+ contextStack.push(context);
37
+ try {
38
+ return cb();
39
+ } finally {
40
+ contextStack.pop();
41
+ }
42
+ }
43
+
44
+ // NOTE: these declarations are copied from 'useFragment'; it would be good
45
+ // to figure out how to share the same type signature between the two functions.
46
+ // The declarations ensure that the type of the returned data is:
47
+ // - non-nullable if the provided ref type is non-nullable
48
+ // - nullable if the provided ref type is nullable
49
+ // - array of non-nullable if the privoided ref type is an array of
50
+ // non-nullable refs
51
+ // - array of nullable if the privoided ref type is an array of nullable refs
52
+
53
+ declare function readFragment<
54
+ TKey: {+$data?: mixed, +$fragmentRefs: FragmentReference, ...},
55
+ >(
56
+ fragmentInput: GraphQLTaggedNode,
57
+ fragmentRef: TKey,
58
+ ): $Call<<TFragmentData>({+$data?: TFragmentData, ...}) => TFragmentData, TKey>;
59
+
60
+ declare function readFragment<
61
+ TKey: ?{+$data?: mixed, +$fragmentRefs: FragmentReference, ...},
62
+ >(
63
+ fragmentInput: GraphQLTaggedNode,
64
+ fragmentRef: TKey,
65
+ ): $Call<
66
+ <TFragmentData>(?{+$data?: TFragmentData, ...}) => ?TFragmentData,
67
+ TKey,
68
+ >;
69
+
70
+ declare function readFragment<
71
+ TKey: $ReadOnlyArray<{
72
+ +$data?: mixed,
73
+ +$fragmentRefs: FragmentReference,
74
+ ...
75
+ }>,
76
+ >(
77
+ fragmentInput: GraphQLTaggedNode,
78
+ fragmentRef: TKey,
79
+ ): $Call<
80
+ <TFragmentData>(
81
+ $ReadOnlyArray<{+$data?: TFragmentData, ...}>,
82
+ ) => TFragmentData,
83
+ TKey,
84
+ >;
85
+
86
+ declare function readFragment<
87
+ TKey: ?$ReadOnlyArray<{
88
+ +$data?: mixed,
89
+ +$fragmentRefs: FragmentReference,
90
+ ...
91
+ }>,
92
+ >(
93
+ fragmentInput: GraphQLTaggedNode,
94
+ fragmentRef: TKey,
95
+ ): $Call<
96
+ <TFragmentData>(
97
+ ?$ReadOnlyArray<{+$data?: TFragmentData, ...}>,
98
+ ) => ?TFragmentData,
99
+ TKey,
100
+ >;
101
+
102
+ function readFragment(
103
+ fragmentInput: GraphQLTaggedNode,
104
+ fragmentRef: mixed,
105
+ ): mixed {
106
+ if (!contextStack.length) {
107
+ throw new Error(
108
+ 'readFragment should be called only from within a Relay Resolver function.',
109
+ );
110
+ }
111
+ const context = contextStack[contextStack.length - 1];
112
+ const fragmentNode = getFragment(fragmentInput);
113
+ const fragmentSelector = getSelector(fragmentNode, fragmentRef);
114
+ invariant(
115
+ fragmentSelector != null,
116
+ `Expected a selector for the fragment of the resolver ${fragmentNode.name}, but got null.`,
117
+ );
118
+ invariant(
119
+ fragmentSelector.kind === 'SingularReaderSelector',
120
+ `Expected a singular reader selector for the fragment of the resolver ${fragmentNode.name}, but it was plural.`,
121
+ );
122
+ return context.getDataForResolverFragment(fragmentSelector);
123
+ }
124
+
125
+ module.exports = {readFragment, withResolverContext};
@@ -28,6 +28,7 @@ function createFragmentSpecResolver(
28
28
  containerName: string,
29
29
  fragments: FragmentMap,
30
30
  props: Props,
31
+ rootIsQueryRenderer: boolean,
31
32
  callback?: () => void,
32
33
  ): FragmentSpecResolver {
33
34
  if (__DEV__) {
@@ -49,6 +50,7 @@ function createFragmentSpecResolver(
49
50
  fragments,
50
51
  props,
51
52
  callback,
53
+ rootIsQueryRenderer,
52
54
  );
53
55
  }
54
56
 
@@ -15,12 +15,14 @@
15
15
  const {VIEWER_ID, VIEWER_TYPE} = require('./ViewerPattern');
16
16
 
17
17
  function defaultGetDataID(
18
- fieldValue: {[string]: mixed, ...},
18
+ fieldValue: interface {[string]: mixed},
19
19
  typeName: string,
20
20
  ): mixed {
21
21
  if (typeName === VIEWER_TYPE) {
22
+ // $FlowFixMe[prop-missing]
22
23
  return fieldValue.id == null ? VIEWER_ID : fieldValue.id;
23
24
  }
25
+ // $FlowFixMe[prop-missing]
24
26
  return fieldValue.id;
25
27
  }
26
28
 
@@ -12,21 +12,23 @@
12
12
 
13
13
  'use strict';
14
14
 
15
- import type {RecordMap, UpdatedRecords} from './RelayStoreTypes';
15
+ import type {DataIDSet} from './RelayStoreTypes';
16
16
 
17
- const hasOwnProperty = Object.prototype.hasOwnProperty;
17
+ const ITERATOR_KEY = Symbol.iterator;
18
18
 
19
19
  function hasOverlappingIDs(
20
- seenRecords: RecordMap,
21
- updatedRecordIDs: UpdatedRecords,
20
+ seenRecords: DataIDSet,
21
+ updatedRecordIDs: DataIDSet,
22
22
  ): boolean {
23
- for (const key in seenRecords) {
24
- if (
25
- hasOwnProperty.call(seenRecords, key) &&
26
- hasOwnProperty.call(updatedRecordIDs, key)
27
- ) {
23
+ // $FlowFixMe: Set is an iterable type, accessing its iterator is allowed.
24
+ const iterator = seenRecords[ITERATOR_KEY]();
25
+ let next = iterator.next();
26
+ while (!next.done) {
27
+ const key = next.value;
28
+ if (updatedRecordIDs.has(key)) {
28
29
  return true;
29
30
  }
31
+ next = iterator.next();
30
32
  }
31
33
  return false;
32
34
  }
@@ -13,13 +13,16 @@
13
13
  'use strict';
14
14
 
15
15
  const RelayDeclarativeMutationConfig = require('../mutations/RelayDeclarativeMutationConfig');
16
+ const RelayFeatureFlags = require('../util/RelayFeatureFlags');
16
17
 
17
18
  const warning = require('warning');
18
19
 
19
20
  const {getRequest} = require('../query/GraphQLTag');
21
+ const {generateUniqueClientID} = require('../store/ClientID');
20
22
  const {
21
23
  createOperationDescriptor,
22
24
  } = require('../store/RelayModernOperationDescriptor');
25
+ const {createReaderSelector} = require('../store/RelayModernSelector');
23
26
 
24
27
  import type {DeclarativeMutationConfig} from '../mutations/RelayDeclarativeMutationConfig';
25
28
  import type {GraphQLTaggedNode} from '../query/GraphQLTag';
@@ -64,6 +67,9 @@ function requestSubscription<TSubscriptionPayload>(
64
67
  subscription,
65
68
  variables,
66
69
  cacheConfig,
70
+ RelayFeatureFlags.ENABLE_UNIQUE_SUBSCRIPTION_ROOT
71
+ ? generateUniqueClientID()
72
+ : undefined,
67
73
  );
68
74
 
69
75
  warning(
@@ -85,8 +91,25 @@ function requestSubscription<TSubscriptionPayload>(
85
91
  operation,
86
92
  updater,
87
93
  })
88
- .map(() => {
89
- const data = environment.lookup(operation.fragment).data;
94
+ .map(responses => {
95
+ let selector = operation.fragment;
96
+ if (RelayFeatureFlags.ENABLE_UNIQUE_SUBSCRIPTION_ROOT) {
97
+ let nextID;
98
+ if (Array.isArray(responses)) {
99
+ nextID = responses[0]?.extensions?.__relay_subscription_root_id;
100
+ } else {
101
+ nextID = responses.extensions?.__relay_subscription_root_id;
102
+ }
103
+ if (typeof nextID === 'string') {
104
+ selector = createReaderSelector(
105
+ selector.node,
106
+ nextID,
107
+ selector.variables,
108
+ selector.owner,
109
+ );
110
+ }
111
+ }
112
+ const data = environment.lookup(selector).data;
90
113
  // $FlowFixMe[incompatible-cast]
91
114
  return (data: TSubscriptionPayload);
92
115
  })
@@ -85,6 +85,12 @@ export type NormalizationInlineFragment = {|
85
85
  +abstractKey: ?string,
86
86
  |};
87
87
 
88
+ export type NormalizationFragmentSpread = {|
89
+ +kind: 'FragmentSpread',
90
+ +fragment: NormalizationNode,
91
+ +args: ?$ReadOnlyArray<NormalizationArgument>,
92
+ |};
93
+
88
94
  export type NormalizationLinkedField = {|
89
95
  +kind: 'LinkedField',
90
96
  +alias: ?string,
@@ -148,6 +154,11 @@ export type NormalizationFlightField = {|
148
154
  +storageKey: ?string,
149
155
  |};
150
156
 
157
+ export type NormalizationClientComponent = {|
158
+ +kind: 'ClientComponent',
159
+ +fragment: NormalizationNode,
160
+ |};
161
+
151
162
  export type NormalizationTypeDiscriminator = {|
152
163
  +kind: 'TypeDiscriminator',
153
164
  +abstractKey: string,
@@ -155,10 +166,12 @@ export type NormalizationTypeDiscriminator = {|
155
166
 
156
167
  export type NormalizationSelection =
157
168
  | NormalizationCondition
169
+ | NormalizationClientComponent
158
170
  | NormalizationClientExtension
159
171
  | NormalizationDefer
160
172
  | NormalizationField
161
173
  | NormalizationFlightField
174
+ | NormalizationFragmentSpread
162
175
  | NormalizationHandle
163
176
  | NormalizationInlineFragment
164
177
  | NormalizationModuleImport
@@ -206,6 +206,18 @@ export type ReaderRequiredField = {|
206
206
  +path: string,
207
207
  |};
208
208
 
209
+ export type ReaderRelayResolver = {|
210
+ +kind: 'RelayResolver',
211
+ +alias: ?string,
212
+ +name: string,
213
+ +fragment: ReaderFragmentSpread,
214
+ +resolverModule: (rootKey: {
215
+ +$data?: any, // flowlint-line unclear-type:off
216
+ +$fragmentRefs: any, // flowlint-line unclear-type:off
217
+ ...
218
+ }) => mixed,
219
+ |};
220
+
209
221
  export type ReaderSelection =
210
222
  | ReaderCondition
211
223
  | ReaderClientExtension
@@ -217,7 +229,8 @@ export type ReaderSelection =
217
229
  | ReaderInlineFragment
218
230
  | ReaderModuleImport
219
231
  | ReaderStream
220
- | ReaderRequiredField;
232
+ | ReaderRequiredField
233
+ | ReaderRelayResolver;
221
234
 
222
235
  export type ReaderVariableArgument = {|
223
236
  +kind: 'Variable',
@@ -68,6 +68,7 @@ export type GeneratedNode =
68
68
 
69
69
  const RelayConcreteNode = {
70
70
  CONDITION: 'Condition',
71
+ CLIENT_COMPONENT: 'ClientComponent',
71
72
  CLIENT_EXTENSION: 'ClientExtension',
72
73
  DEFER: 'Defer',
73
74
  CONNECTION: 'Connection',
@@ -83,6 +84,7 @@ const RelayConcreteNode = {
83
84
  LIST_VALUE: 'ListValue',
84
85
  LOCAL_ARGUMENT: 'LocalArgument',
85
86
  MODULE_IMPORT: 'ModuleImport',
87
+ RELAY_RESOLVER: 'RelayResolver',
86
88
  REQUIRED_FIELD: 'RequiredField',
87
89
  OBJECT_VALUE: 'ObjectValue',
88
90
  OPERATION: 'Operation',
@@ -19,23 +19,33 @@ type FeatureFlags = {|
19
19
  ENABLE_PRECISE_TYPE_REFINEMENT: boolean,
20
20
  ENABLE_REACT_FLIGHT_COMPONENT_FIELD: boolean,
21
21
  ENABLE_REQUIRED_DIRECTIVES: boolean | string,
22
+ ENABLE_RELAY_RESOLVERS: boolean,
22
23
  ENABLE_GETFRAGMENTIDENTIFIER_OPTIMIZATION: boolean,
23
24
  ENABLE_FRIENDLY_QUERY_NAME_GQL_URL: boolean,
24
25
  ENABLE_STORE_SUBSCRIPTIONS_REFACTOR: boolean,
25
26
  ENABLE_LOAD_QUERY_REQUEST_DEDUPING: boolean,
27
+ ENABLE_DO_NOT_WRAP_LIVE_QUERY: boolean,
28
+ ENABLE_NOTIFY_SUBSCRIPTION: boolean,
29
+ ENABLE_UNIQUE_SUBSCRIPTION_ROOT: boolean,
30
+ ENABLE_BATCHED_STORE_UPDATES: boolean,
26
31
  |};
27
32
 
28
33
  const RelayFeatureFlags: FeatureFlags = {
29
34
  ENABLE_VARIABLE_CONNECTION_KEY: false,
30
- ENABLE_PARTIAL_RENDERING_DEFAULT: false,
31
- ENABLE_RELAY_CONTAINERS_SUSPENSE: false,
35
+ ENABLE_PARTIAL_RENDERING_DEFAULT: true,
36
+ ENABLE_RELAY_CONTAINERS_SUSPENSE: true,
32
37
  ENABLE_PRECISE_TYPE_REFINEMENT: false,
33
38
  ENABLE_REACT_FLIGHT_COMPONENT_FIELD: false,
34
39
  ENABLE_REQUIRED_DIRECTIVES: false,
40
+ ENABLE_RELAY_RESOLVERS: false,
35
41
  ENABLE_GETFRAGMENTIDENTIFIER_OPTIMIZATION: false,
36
42
  ENABLE_FRIENDLY_QUERY_NAME_GQL_URL: false,
37
43
  ENABLE_STORE_SUBSCRIPTIONS_REFACTOR: false,
38
44
  ENABLE_LOAD_QUERY_REQUEST_DEDUPING: true,
45
+ ENABLE_DO_NOT_WRAP_LIVE_QUERY: false,
46
+ ENABLE_NOTIFY_SUBSCRIPTION: false,
47
+ ENABLE_UNIQUE_SUBSCRIPTION_ROOT: false,
48
+ ENABLE_BATCHED_STORE_UPDATES: false,
39
49
  };
40
50
 
41
51
  module.exports = RelayFeatureFlags;