react-relay 11.0.2 → 13.0.0-rc.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.
- package/README.md +47 -0
- package/ReactRelayContainerUtils.js.flow +1 -1
- package/ReactRelayContext.js +1 -1
- package/ReactRelayContext.js.flow +3 -4
- package/ReactRelayFragmentContainer.js.flow +25 -25
- package/ReactRelayFragmentMockRenderer.js.flow +2 -2
- package/ReactRelayLocalQueryRenderer.js.flow +7 -8
- package/ReactRelayPaginationContainer.js.flow +112 -59
- package/ReactRelayQueryFetcher.js.flow +10 -11
- package/ReactRelayQueryRenderer.js.flow +116 -82
- package/ReactRelayQueryRendererContext.js.flow +1 -1
- package/ReactRelayRefetchContainer.js.flow +42 -39
- package/ReactRelayTestMocker.js.flow +17 -15
- package/ReactRelayTypes.js.flow +11 -11
- package/RelayContext.js.flow +4 -4
- package/__flowtests__/ReactRelayFragmentContainer-flowtest.js.flow +2 -3
- package/__flowtests__/ReactRelayPaginationContainer-flowtest.js.flow +12 -8
- package/__flowtests__/ReactRelayRefetchContainer-flowtest.js.flow +11 -7
- package/__flowtests__/RelayModern-flowtest.js.flow +79 -47
- package/__flowtests__/RelayModernFlowtest_badref.graphql.js.flow +6 -5
- package/__flowtests__/RelayModernFlowtest_notref.graphql.js.flow +6 -5
- package/__flowtests__/RelayModernFlowtest_user.graphql.js.flow +5 -4
- package/__flowtests__/RelayModernFlowtest_users.graphql.js.flow +5 -4
- package/__flowtests__/__generated__/ReactRelayFragmentContainerFlowtest_viewer.graphql.js.flow +72 -0
- package/__flowtests__/__generated__/ReactRelayFragmentContainerFlowtest_viewer2.graphql.js.flow +72 -0
- package/__flowtests__/__generated__/ReactRelayPaginationContainerFlowtestQuery.graphql.js.flow +227 -0
- package/__flowtests__/__generated__/ReactRelayPaginationContainerFlowtest_viewer.graphql.js.flow +164 -0
- package/__flowtests__/__generated__/ReactRelayRefetchContainerFlowtestQuery.graphql.js.flow +227 -0
- package/__flowtests__/__generated__/ReactRelayRefetchContainerFlowtest_viewer.graphql.js.flow +164 -0
- package/__flowtests__/__generated__/RelayModernFlowtest_badref.graphql.js.flow +66 -0
- package/__flowtests__/__generated__/RelayModernFlowtest_notref.graphql.js.flow +66 -0
- package/__flowtests__/__generated__/RelayModernFlowtest_user.graphql.js.flow +59 -0
- package/__flowtests__/__generated__/RelayModernFlowtest_users.graphql.js.flow +61 -0
- package/assertFragmentMap.js.flow +3 -3
- package/buildReactRelayContainer.js.flow +12 -11
- package/getRootVariablesForFragments.js.flow +3 -5
- package/hooks.js +1 -1
- package/hooks.js.flow +6 -7
- package/index.js +1 -1
- package/index.js.flow +7 -8
- package/isRelayEnvironment.js.flow +1 -1
- package/jest-react/enqueueTask.js.flow +56 -0
- package/jest-react/index.js.flow +12 -0
- package/jest-react/internalAct.js.flow +138 -0
- package/legacy.js +1 -1
- package/legacy.js.flow +1 -1
- package/lib/ReactRelayContainerUtils.js +1 -1
- package/lib/ReactRelayContext.js +1 -1
- package/lib/ReactRelayFragmentContainer.js +22 -16
- package/lib/ReactRelayFragmentMockRenderer.js +3 -3
- package/lib/ReactRelayLocalQueryRenderer.js +8 -9
- package/lib/ReactRelayPaginationContainer.js +97 -39
- package/lib/ReactRelayQueryFetcher.js +3 -3
- package/lib/ReactRelayQueryRenderer.js +87 -54
- package/lib/ReactRelayQueryRendererContext.js +1 -1
- package/lib/ReactRelayRefetchContainer.js +39 -26
- package/lib/ReactRelayTestMocker.js +8 -9
- package/lib/ReactRelayTypes.js +1 -1
- package/lib/RelayContext.js +4 -3
- package/lib/assertFragmentMap.js +3 -2
- package/lib/buildReactRelayContainer.js +8 -8
- package/lib/getRootVariablesForFragments.js +2 -3
- package/lib/hooks.js +6 -6
- package/lib/index.js +8 -8
- package/lib/isRelayEnvironment.js +1 -1
- package/lib/jest-react/enqueueTask.js +53 -0
- package/lib/jest-react/index.js +13 -0
- package/lib/jest-react/internalAct.js +115 -0
- package/lib/legacy.js +1 -1
- package/lib/multi-actor/ActorChange.js +30 -0
- package/lib/multi-actor/index.js +11 -0
- package/lib/multi-actor/useRelayActorEnvironment.js +29 -0
- package/lib/readContext.js +1 -1
- package/lib/relay-hooks/EntryPointContainer.react.js +4 -4
- package/lib/relay-hooks/EntryPointTypes.flow.js +1 -1
- package/lib/relay-hooks/FragmentResource.js +342 -89
- package/lib/relay-hooks/InternalLogger.js +1 -1
- package/lib/relay-hooks/LRUCache.js +1 -1
- package/lib/relay-hooks/LazyLoadEntryPointContainer_DEPRECATED.react.js +5 -5
- package/lib/relay-hooks/MatchContainer.js +2 -2
- package/lib/relay-hooks/ProfilerContext.js +1 -1
- package/lib/relay-hooks/QueryResource.js +172 -29
- package/lib/relay-hooks/RelayEnvironmentProvider.js +6 -4
- package/lib/relay-hooks/SuspenseResource.js +130 -0
- package/lib/relay-hooks/loadEntryPoint.js +1 -1
- package/lib/relay-hooks/loadQuery.js +42 -20
- package/lib/relay-hooks/preloadQuery_DEPRECATED.js +25 -16
- package/lib/relay-hooks/prepareEntryPoint_DEPRECATED.js +1 -1
- package/lib/relay-hooks/useBlockingPaginationFragment.js +5 -6
- package/lib/relay-hooks/useEntryPointLoader.js +3 -3
- package/lib/relay-hooks/useFetchTrackingRef.js +3 -2
- package/lib/relay-hooks/useFragment.js +7 -7
- package/lib/relay-hooks/useFragmentNode.js +5 -5
- package/lib/relay-hooks/useIsMountedRef.js +1 -1
- package/lib/relay-hooks/useIsOperationNodeActive.js +3 -3
- package/lib/relay-hooks/useIsParentQueryActive.js +1 -1
- package/lib/relay-hooks/useLazyLoadQuery.js +4 -4
- package/lib/relay-hooks/useLazyLoadQueryNode.js +11 -5
- package/lib/relay-hooks/useLoadMoreFunction.js +9 -13
- package/lib/relay-hooks/useMemoOperationDescriptor.js +3 -3
- package/lib/relay-hooks/useMemoVariables.js +3 -3
- package/lib/relay-hooks/useMutation.js +18 -7
- package/lib/relay-hooks/usePaginationFragment.js +3 -4
- package/lib/relay-hooks/usePreloadedQuery.js +6 -6
- package/lib/relay-hooks/useQueryLoader.js +31 -11
- package/lib/relay-hooks/useRefetchableFragment.js +1 -1
- package/lib/relay-hooks/useRefetchableFragmentNode.js +14 -18
- package/lib/relay-hooks/useRelayEnvironment.js +3 -3
- package/lib/relay-hooks/useStaticFragmentNodeWarning.js +3 -3
- package/lib/relay-hooks/useSubscribeToInvalidationState.js +3 -2
- package/lib/relay-hooks/useSubscription.js +11 -8
- package/multi-actor/ActorChange.js.flow +58 -0
- package/multi-actor/index.js.flow +14 -0
- package/multi-actor/useRelayActorEnvironment.js.flow +49 -0
- package/package.json +3 -3
- package/react-relay-hooks.js +2 -2
- package/react-relay-hooks.min.js +2 -2
- package/react-relay-legacy.js +2 -2
- package/react-relay-legacy.min.js +2 -2
- package/react-relay.js +2 -2
- package/react-relay.min.js +2 -2
- package/readContext.js.flow +1 -1
- package/relay-hooks/EntryPointContainer.react.js.flow +9 -16
- package/relay-hooks/EntryPointTypes.flow.js.flow +25 -26
- package/relay-hooks/FragmentResource.js.flow +359 -93
- package/relay-hooks/InternalLogger.js.flow +1 -1
- package/relay-hooks/LRUCache.js.flow +1 -1
- package/relay-hooks/LazyLoadEntryPointContainer_DEPRECATED.react.js.flow +33 -47
- package/relay-hooks/MatchContainer.js.flow +4 -3
- package/relay-hooks/ProfilerContext.js.flow +1 -1
- package/relay-hooks/QueryResource.js.flow +217 -26
- package/relay-hooks/RelayEnvironmentProvider.js.flow +15 -5
- package/relay-hooks/SuspenseResource.js.flow +115 -0
- package/relay-hooks/__flowtests__/EntryPointTypes/EntryPointElementConfig-flowtest.js.flow +5 -4
- package/relay-hooks/__flowtests__/EntryPointTypes/NestedEntrypoints-flowtest.js.flow +2 -2
- package/relay-hooks/__flowtests__/__generated__/useFragmentFlowtest_user.graphql.js.flow +59 -0
- package/relay-hooks/__flowtests__/__generated__/useFragmentFlowtest_users.graphql.js.flow +61 -0
- package/relay-hooks/__flowtests__/useBlockingPaginationFragment-flowtest.js.flow +11 -10
- package/relay-hooks/__flowtests__/useFragment-flowtest.js.flow +55 -32
- package/relay-hooks/__flowtests__/usePaginationFragment-flowtest.js.flow +11 -10
- package/relay-hooks/__flowtests__/useRefetchableFragment-flowtest.js.flow +11 -10
- package/relay-hooks/__flowtests__/utils.js.flow +21 -32
- package/relay-hooks/loadEntryPoint.js.flow +7 -13
- package/relay-hooks/loadQuery.js.flow +50 -32
- package/relay-hooks/preloadQuery_DEPRECATED.js.flow +31 -22
- package/relay-hooks/prepareEntryPoint_DEPRECATED.js.flow +7 -13
- package/relay-hooks/useBlockingPaginationFragment.js.flow +14 -12
- package/relay-hooks/useEntryPointLoader.js.flow +8 -11
- package/relay-hooks/useFetchTrackingRef.js.flow +3 -3
- package/relay-hooks/useFragment.js.flow +31 -62
- package/relay-hooks/useFragmentNode.js.flow +6 -8
- package/relay-hooks/useIsMountedRef.js.flow +1 -1
- package/relay-hooks/useIsOperationNodeActive.js.flow +4 -6
- package/relay-hooks/useIsParentQueryActive.js.flow +4 -5
- package/relay-hooks/useLazyLoadQuery.js.flow +14 -16
- package/relay-hooks/useLazyLoadQueryNode.js.flow +20 -14
- package/relay-hooks/useLoadMoreFunction.js.flow +21 -30
- package/relay-hooks/useMemoOperationDescriptor.js.flow +6 -8
- package/relay-hooks/useMemoVariables.js.flow +7 -7
- package/relay-hooks/useMutation.js.flow +27 -27
- package/relay-hooks/usePaginationFragment.js.flow +39 -45
- package/relay-hooks/usePreloadedQuery.js.flow +14 -20
- package/relay-hooks/useQueryLoader.js.flow +42 -23
- package/relay-hooks/useRefetchableFragment.js.flow +8 -9
- package/relay-hooks/useRefetchableFragmentNode.js.flow +25 -33
- package/relay-hooks/useRelayEnvironment.js.flow +3 -5
- package/relay-hooks/useStaticFragmentNodeWarning.js.flow +3 -4
- package/relay-hooks/useSubscribeToInvalidationState.js.flow +4 -7
- package/relay-hooks/useSubscription.js.flow +21 -11
- package/lib/relay-hooks/getPaginationMetadata.js +0 -41
- package/lib/relay-hooks/getPaginationVariables.js +0 -67
- package/lib/relay-hooks/getRefetchMetadata.js +0 -36
- package/lib/relay-hooks/getValueAtPath.js +0 -51
- package/relay-hooks/getPaginationMetadata.js.flow +0 -74
- package/relay-hooks/getPaginationVariables.js.flow +0 -110
- package/relay-hooks/getRefetchMetadata.js.flow +0 -80
- package/relay-hooks/getValueAtPath.js.flow +0 -46
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* Copyright (c)
|
|
2
|
+
* Copyright (c) Meta Platforms, Inc. and affiliates.
|
|
3
3
|
*
|
|
4
4
|
* This source code is licensed under the MIT license found in the
|
|
5
5
|
* LICENSE file in the root directory of this source tree.
|
|
@@ -11,14 +11,14 @@
|
|
|
11
11
|
// flowlint ambiguous-object-type:error
|
|
12
12
|
'use strict';
|
|
13
13
|
|
|
14
|
-
var ProfilerContext = require('./ProfilerContext');
|
|
15
|
-
|
|
16
|
-
var React = require('react');
|
|
17
|
-
|
|
18
14
|
var preloadQuery_DEPRECATED = require('./preloadQuery_DEPRECATED');
|
|
19
15
|
|
|
16
|
+
var ProfilerContext = require('./ProfilerContext');
|
|
17
|
+
|
|
20
18
|
var useRelayEnvironment = require('./useRelayEnvironment');
|
|
21
19
|
|
|
20
|
+
var React = require('react');
|
|
21
|
+
|
|
22
22
|
var _require = require('react'),
|
|
23
23
|
useContext = _require.useContext,
|
|
24
24
|
useEffect = _require.useEffect,
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* Copyright (c)
|
|
2
|
+
* Copyright (c) Meta Platforms, Inc. and affiliates.
|
|
3
3
|
*
|
|
4
4
|
* This source code is licensed under the MIT license found in the
|
|
5
5
|
* LICENSE file in the root directory of this source tree.
|
|
@@ -98,7 +98,7 @@ function MatchContainer(_ref2) {
|
|
|
98
98
|
|
|
99
99
|
if (match != null && typeof match !== 'object') {
|
|
100
100
|
throw new Error('MatchContainer: Expected `match` value to be an object or null/undefined.');
|
|
101
|
-
} // NOTE: the MatchPointer type has a $
|
|
101
|
+
} // NOTE: the MatchPointer type has a $fragmentSpreads field to ensure that only
|
|
102
102
|
// an object that contains a FragmentSpread can be passed. If the fragment
|
|
103
103
|
// spread matches, then the metadata fields below (__id, __fragments, etc.)
|
|
104
104
|
// will be present. But they can be missing if all the fragment spreads use
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* Copyright (c)
|
|
2
|
+
* Copyright (c) Meta Platforms, Inc. and affiliates.
|
|
3
3
|
*
|
|
4
4
|
* This source code is licensed under the MIT license found in the
|
|
5
5
|
* LICENSE file in the root directory of this source tree.
|
|
@@ -19,16 +19,24 @@ var _defineProperty2 = _interopRequireDefault(require("@babel/runtime/helpers/de
|
|
|
19
19
|
|
|
20
20
|
var LRUCache = require('./LRUCache');
|
|
21
21
|
|
|
22
|
+
var SuspenseResource = require('./SuspenseResource');
|
|
23
|
+
|
|
22
24
|
var invariant = require('invariant');
|
|
23
25
|
|
|
24
26
|
var _require = require('relay-runtime'),
|
|
27
|
+
RelayFeatureFlags = _require.RelayFeatureFlags,
|
|
25
28
|
isPromise = _require.isPromise;
|
|
26
29
|
|
|
30
|
+
var warning = require("fbjs/lib/warning");
|
|
31
|
+
|
|
27
32
|
var CACHE_CAPACITY = 1000;
|
|
28
33
|
var DEFAULT_FETCH_POLICY = 'store-or-network';
|
|
29
|
-
var DATA_RETENTION_TIMEOUT = 5 * 60 * 1000;
|
|
30
34
|
var WEAKMAP_SUPPORTED = typeof WeakMap === 'function';
|
|
31
35
|
|
|
36
|
+
function operationIsLiveQuery(operation) {
|
|
37
|
+
return operation.request.node.params.metadata.live !== undefined;
|
|
38
|
+
}
|
|
39
|
+
|
|
32
40
|
function getQueryCacheIdentifier(environment, operation, maybeFetchPolicy, maybeRenderPolicy, cacheBreaker) {
|
|
33
41
|
var fetchPolicy = maybeFetchPolicy !== null && maybeFetchPolicy !== void 0 ? maybeFetchPolicy : DEFAULT_FETCH_POLICY;
|
|
34
42
|
var renderPolicy = maybeRenderPolicy !== null && maybeRenderPolicy !== void 0 ? maybeRenderPolicy : environment.UNSTABLE_getDefaultRenderPolicy();
|
|
@@ -57,11 +65,83 @@ function getQueryResult(operation, cacheIdentifier) {
|
|
|
57
65
|
|
|
58
66
|
var nextID = 200000;
|
|
59
67
|
|
|
60
|
-
function createCacheEntry(cacheIdentifier, operation, value, networkSubscription, onDispose) {
|
|
68
|
+
function createCacheEntry(cacheIdentifier, operation, operationAvailability, value, networkSubscription, onDispose) {
|
|
69
|
+
// There should be no behavior difference between createCacheEntry_new and
|
|
70
|
+
// createCacheEntry_old, and it doesn't directly relate to Client Edges.
|
|
71
|
+
// It was just a refactoring that was needed for Client Edges but that
|
|
72
|
+
// is behind the feature flag just in case there is any accidental breakage.
|
|
73
|
+
if (RelayFeatureFlags.REFACTOR_SUSPENSE_RESOURCE) {
|
|
74
|
+
return createCacheEntry_new(cacheIdentifier, operation, operationAvailability, value, networkSubscription, onDispose);
|
|
75
|
+
} else {
|
|
76
|
+
return createCacheEntry_old(cacheIdentifier, operation, operationAvailability, value, networkSubscription, onDispose);
|
|
77
|
+
}
|
|
78
|
+
}
|
|
79
|
+
|
|
80
|
+
function createCacheEntry_new(cacheIdentifier, operation, operationAvailability, value, networkSubscription, onDispose) {
|
|
81
|
+
var isLiveQuery = operationIsLiveQuery(operation);
|
|
82
|
+
var currentValue = value;
|
|
83
|
+
var currentNetworkSubscription = networkSubscription;
|
|
84
|
+
var suspenseResource = new SuspenseResource(function (environment) {
|
|
85
|
+
var retention = environment.retain(operation);
|
|
86
|
+
return {
|
|
87
|
+
dispose: function dispose() {
|
|
88
|
+
// Normally if this entry never commits, the request would've ended by the
|
|
89
|
+
// time this timeout expires and the temporary retain is released. However,
|
|
90
|
+
// we need to do this for live queries which remain open indefinitely.
|
|
91
|
+
if (isLiveQuery && currentNetworkSubscription != null) {
|
|
92
|
+
currentNetworkSubscription.unsubscribe();
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
retention.dispose();
|
|
96
|
+
onDispose(cacheEntry);
|
|
97
|
+
}
|
|
98
|
+
};
|
|
99
|
+
});
|
|
100
|
+
var cacheEntry = {
|
|
101
|
+
cacheIdentifier: cacheIdentifier,
|
|
102
|
+
id: nextID++,
|
|
103
|
+
processedPayloadsCount: 0,
|
|
104
|
+
operationAvailability: operationAvailability,
|
|
105
|
+
getValue: function getValue() {
|
|
106
|
+
return currentValue;
|
|
107
|
+
},
|
|
108
|
+
setValue: function setValue(val) {
|
|
109
|
+
currentValue = val;
|
|
110
|
+
},
|
|
111
|
+
getRetainCount: function getRetainCount() {
|
|
112
|
+
return suspenseResource.getRetainCount();
|
|
113
|
+
},
|
|
114
|
+
getNetworkSubscription: function getNetworkSubscription() {
|
|
115
|
+
return currentNetworkSubscription;
|
|
116
|
+
},
|
|
117
|
+
setNetworkSubscription: function setNetworkSubscription(subscription) {
|
|
118
|
+
if (isLiveQuery && currentNetworkSubscription != null) {
|
|
119
|
+
currentNetworkSubscription.unsubscribe();
|
|
120
|
+
}
|
|
121
|
+
|
|
122
|
+
currentNetworkSubscription = subscription;
|
|
123
|
+
},
|
|
124
|
+
temporaryRetain: function temporaryRetain(environment) {
|
|
125
|
+
return suspenseResource.temporaryRetain(environment);
|
|
126
|
+
},
|
|
127
|
+
permanentRetain: function permanentRetain(environment) {
|
|
128
|
+
return suspenseResource.permanentRetain(environment);
|
|
129
|
+
},
|
|
130
|
+
releaseTemporaryRetain: function releaseTemporaryRetain() {
|
|
131
|
+
suspenseResource.releaseTemporaryRetain();
|
|
132
|
+
}
|
|
133
|
+
};
|
|
134
|
+
return cacheEntry;
|
|
135
|
+
}
|
|
136
|
+
|
|
137
|
+
var DATA_RETENTION_TIMEOUT = 5 * 60 * 1000;
|
|
138
|
+
|
|
139
|
+
function createCacheEntry_old(cacheIdentifier, operation, operationAvailability, value, networkSubscription, onDispose) {
|
|
140
|
+
var isLiveQuery = operationIsLiveQuery(operation);
|
|
61
141
|
var currentValue = value;
|
|
62
142
|
var retainCount = 0;
|
|
63
143
|
var retainDisposable = null;
|
|
64
|
-
var
|
|
144
|
+
var _releaseTemporaryRetain = null;
|
|
65
145
|
var currentNetworkSubscription = networkSubscription;
|
|
66
146
|
|
|
67
147
|
var retain = function retain(environment) {
|
|
@@ -89,6 +169,8 @@ function createCacheEntry(cacheIdentifier, operation, value, networkSubscription
|
|
|
89
169
|
var cacheEntry = {
|
|
90
170
|
cacheIdentifier: cacheIdentifier,
|
|
91
171
|
id: nextID++,
|
|
172
|
+
processedPayloadsCount: 0,
|
|
173
|
+
operationAvailability: operationAvailability,
|
|
92
174
|
getValue: function getValue() {
|
|
93
175
|
return currentValue;
|
|
94
176
|
},
|
|
@@ -102,7 +184,7 @@ function createCacheEntry(cacheIdentifier, operation, value, networkSubscription
|
|
|
102
184
|
return currentNetworkSubscription;
|
|
103
185
|
},
|
|
104
186
|
setNetworkSubscription: function setNetworkSubscription(subscription) {
|
|
105
|
-
if (currentNetworkSubscription != null) {
|
|
187
|
+
if (isLiveQuery && currentNetworkSubscription != null) {
|
|
106
188
|
currentNetworkSubscription.unsubscribe();
|
|
107
189
|
}
|
|
108
190
|
|
|
@@ -129,12 +211,12 @@ function createCacheEntry(cacheIdentifier, operation, value, networkSubscription
|
|
|
129
211
|
var localReleaseTemporaryRetain = function localReleaseTemporaryRetain() {
|
|
130
212
|
clearTimeout(releaseQueryTimeout);
|
|
131
213
|
releaseQueryTimeout = null;
|
|
132
|
-
|
|
214
|
+
_releaseTemporaryRetain = null;
|
|
133
215
|
disposable.dispose(); // Normally if this entry never commits, the request would've ended by the
|
|
134
216
|
// time this timeout expires and the temporary retain is released. However,
|
|
135
217
|
// we need to do this for live queries which remain open indefinitely.
|
|
136
218
|
|
|
137
|
-
if (retainCount <= 0 && currentNetworkSubscription != null) {
|
|
219
|
+
if (isLiveQuery && retainCount <= 0 && currentNetworkSubscription != null) {
|
|
138
220
|
currentNetworkSubscription.unsubscribe();
|
|
139
221
|
}
|
|
140
222
|
};
|
|
@@ -147,34 +229,42 @@ function createCacheEntry(cacheIdentifier, operation, value, networkSubscription
|
|
|
147
229
|
// phase, as well as multiple times by other query components that are
|
|
148
230
|
// rendering the same query/variables.
|
|
149
231
|
|
|
150
|
-
if (
|
|
151
|
-
|
|
232
|
+
if (_releaseTemporaryRetain != null) {
|
|
233
|
+
_releaseTemporaryRetain();
|
|
152
234
|
}
|
|
153
235
|
|
|
154
|
-
|
|
236
|
+
_releaseTemporaryRetain = localReleaseTemporaryRetain;
|
|
155
237
|
return {
|
|
156
238
|
dispose: function dispose() {
|
|
157
|
-
|
|
239
|
+
_releaseTemporaryRetain && _releaseTemporaryRetain();
|
|
158
240
|
}
|
|
159
241
|
};
|
|
160
242
|
},
|
|
161
243
|
permanentRetain: function permanentRetain(environment) {
|
|
162
244
|
var disposable = retain(environment);
|
|
163
245
|
|
|
164
|
-
if (
|
|
165
|
-
|
|
166
|
-
|
|
246
|
+
if (_releaseTemporaryRetain != null) {
|
|
247
|
+
_releaseTemporaryRetain();
|
|
248
|
+
|
|
249
|
+
_releaseTemporaryRetain = null;
|
|
167
250
|
}
|
|
168
251
|
|
|
169
252
|
return {
|
|
170
253
|
dispose: function dispose() {
|
|
171
254
|
disposable.dispose();
|
|
172
255
|
|
|
173
|
-
if (retainCount <= 0 && currentNetworkSubscription != null) {
|
|
256
|
+
if (isLiveQuery && retainCount <= 0 && currentNetworkSubscription != null) {
|
|
174
257
|
currentNetworkSubscription.unsubscribe();
|
|
175
258
|
}
|
|
176
259
|
}
|
|
177
260
|
};
|
|
261
|
+
},
|
|
262
|
+
releaseTemporaryRetain: function releaseTemporaryRetain() {
|
|
263
|
+
if (_releaseTemporaryRetain != null) {
|
|
264
|
+
_releaseTemporaryRetain();
|
|
265
|
+
|
|
266
|
+
_releaseTemporaryRetain = null;
|
|
267
|
+
}
|
|
178
268
|
}
|
|
179
269
|
};
|
|
180
270
|
return cacheEntry;
|
|
@@ -185,8 +275,14 @@ var QueryResourceImpl = /*#__PURE__*/function () {
|
|
|
185
275
|
var _this = this;
|
|
186
276
|
|
|
187
277
|
(0, _defineProperty2["default"])(this, "_clearCacheEntry", function (cacheEntry) {
|
|
188
|
-
|
|
278
|
+
// The new code does this retainCount <= 0 check within SuspenseResource
|
|
279
|
+
// before calling _clearCacheEntry, whereas with the old code we do it here.
|
|
280
|
+
if (RelayFeatureFlags.REFACTOR_SUSPENSE_RESOURCE) {
|
|
189
281
|
_this._cache["delete"](cacheEntry.cacheIdentifier);
|
|
282
|
+
} else {
|
|
283
|
+
if (cacheEntry.getRetainCount() <= 0) {
|
|
284
|
+
_this._cache["delete"](cacheEntry.cacheIdentifier);
|
|
285
|
+
}
|
|
190
286
|
}
|
|
191
287
|
});
|
|
192
288
|
this._environment = environment;
|
|
@@ -215,6 +311,7 @@ var QueryResourceImpl = /*#__PURE__*/function () {
|
|
|
215
311
|
var cacheEntry = this._cache.get(cacheIdentifier);
|
|
216
312
|
|
|
217
313
|
var temporaryRetainDisposable = null;
|
|
314
|
+
var entryWasCached = cacheEntry != null;
|
|
218
315
|
|
|
219
316
|
if (cacheEntry == null) {
|
|
220
317
|
// 2. If a cached value isn't available, try fetching the operation.
|
|
@@ -245,7 +342,20 @@ var QueryResourceImpl = /*#__PURE__*/function () {
|
|
|
245
342
|
temporaryRetainDisposable = cacheEntry.temporaryRetain(environment);
|
|
246
343
|
var cachedValue = cacheEntry.getValue();
|
|
247
344
|
|
|
248
|
-
if (isPromise(cachedValue)
|
|
345
|
+
if (isPromise(cachedValue)) {
|
|
346
|
+
environment.__log({
|
|
347
|
+
name: 'suspense.query',
|
|
348
|
+
fetchPolicy: fetchPolicy,
|
|
349
|
+
isPromiseCached: entryWasCached,
|
|
350
|
+
operation: operation,
|
|
351
|
+
queryAvailability: cacheEntry.operationAvailability,
|
|
352
|
+
renderPolicy: renderPolicy
|
|
353
|
+
});
|
|
354
|
+
|
|
355
|
+
throw cachedValue;
|
|
356
|
+
}
|
|
357
|
+
|
|
358
|
+
if (cachedValue instanceof Error) {
|
|
249
359
|
throw cachedValue;
|
|
250
360
|
}
|
|
251
361
|
|
|
@@ -263,7 +373,7 @@ var QueryResourceImpl = /*#__PURE__*/function () {
|
|
|
263
373
|
var cacheIdentifier = queryResult.cacheIdentifier,
|
|
264
374
|
operation = queryResult.operation;
|
|
265
375
|
|
|
266
|
-
var cacheEntry = this._getOrCreateCacheEntry(cacheIdentifier, operation, queryResult, null);
|
|
376
|
+
var cacheEntry = this._getOrCreateCacheEntry(cacheIdentifier, operation, null, queryResult, null);
|
|
267
377
|
|
|
268
378
|
var disposable = cacheEntry.permanentRetain(environment);
|
|
269
379
|
|
|
@@ -280,17 +390,25 @@ var QueryResourceImpl = /*#__PURE__*/function () {
|
|
|
280
390
|
};
|
|
281
391
|
};
|
|
282
392
|
|
|
393
|
+
_proto.releaseTemporaryRetain = function releaseTemporaryRetain(queryResult) {
|
|
394
|
+
var cacheEntry = this._cache.get(queryResult.cacheIdentifier);
|
|
395
|
+
|
|
396
|
+
if (cacheEntry != null) {
|
|
397
|
+
cacheEntry.releaseTemporaryRetain();
|
|
398
|
+
}
|
|
399
|
+
};
|
|
400
|
+
|
|
283
401
|
_proto.TESTS_ONLY__getCacheEntry = function TESTS_ONLY__getCacheEntry(operation, maybeFetchPolicy, maybeRenderPolicy, cacheBreaker) {
|
|
284
402
|
var environment = this._environment;
|
|
285
403
|
var cacheIdentifier = getQueryCacheIdentifier(environment, operation, maybeFetchPolicy, maybeRenderPolicy, cacheBreaker);
|
|
286
404
|
return this._cache.get(cacheIdentifier);
|
|
287
405
|
};
|
|
288
406
|
|
|
289
|
-
_proto._getOrCreateCacheEntry = function _getOrCreateCacheEntry(cacheIdentifier, operation, value, networkSubscription) {
|
|
407
|
+
_proto._getOrCreateCacheEntry = function _getOrCreateCacheEntry(cacheIdentifier, operation, operationAvailability, value, networkSubscription) {
|
|
290
408
|
var cacheEntry = this._cache.get(cacheIdentifier);
|
|
291
409
|
|
|
292
410
|
if (cacheEntry == null) {
|
|
293
|
-
cacheEntry = createCacheEntry(cacheIdentifier, operation, value, networkSubscription, this._clearCacheEntry);
|
|
411
|
+
cacheEntry = createCacheEntry(cacheIdentifier, operation, operationAvailability, value, networkSubscription, this._clearCacheEntry);
|
|
294
412
|
|
|
295
413
|
this._cache.set(cacheIdentifier, cacheEntry);
|
|
296
414
|
}
|
|
@@ -353,7 +471,7 @@ var QueryResourceImpl = /*#__PURE__*/function () {
|
|
|
353
471
|
if (shouldAllowRender) {
|
|
354
472
|
var queryResult = getQueryResult(operation, cacheIdentifier);
|
|
355
473
|
|
|
356
|
-
var _cacheEntry = createCacheEntry(cacheIdentifier, operation, queryResult, null, this._clearCacheEntry);
|
|
474
|
+
var _cacheEntry = createCacheEntry(cacheIdentifier, operation, queryAvailability, queryResult, null, this._clearCacheEntry);
|
|
357
475
|
|
|
358
476
|
this._cache.set(cacheIdentifier, _cacheEntry);
|
|
359
477
|
}
|
|
@@ -373,22 +491,47 @@ var QueryResourceImpl = /*#__PURE__*/function () {
|
|
|
373
491
|
}
|
|
374
492
|
|
|
375
493
|
var observerStart = observer === null || observer === void 0 ? void 0 : observer.start;
|
|
376
|
-
|
|
494
|
+
|
|
495
|
+
if (observerStart) {
|
|
496
|
+
var subscriptionWithConditionalCancelation = (0, _objectSpread2["default"])((0, _objectSpread2["default"])({}, subscription), {}, {
|
|
497
|
+
unsubscribe: function unsubscribe() {
|
|
498
|
+
// Only live queries should have their network requests canceled.
|
|
499
|
+
if (operationIsLiveQuery(operation)) {
|
|
500
|
+
subscription.unsubscribe();
|
|
501
|
+
}
|
|
502
|
+
}
|
|
503
|
+
});
|
|
504
|
+
observerStart(subscriptionWithConditionalCancelation);
|
|
505
|
+
}
|
|
377
506
|
},
|
|
378
507
|
next: function next() {
|
|
379
|
-
var
|
|
380
|
-
|
|
381
|
-
var cacheEntry = _this2._getOrCreateCacheEntry(cacheIdentifier, operation, _queryResult, networkSubscription);
|
|
508
|
+
var cacheEntry = _this2._getOrCreateCacheEntry(cacheIdentifier, operation, queryAvailability, _queryResult, networkSubscription);
|
|
382
509
|
|
|
510
|
+
cacheEntry.processedPayloadsCount += 1;
|
|
383
511
|
cacheEntry.setValue(_queryResult);
|
|
384
512
|
resolveNetworkPromise();
|
|
385
513
|
var observerNext = observer === null || observer === void 0 ? void 0 : observer.next;
|
|
386
|
-
|
|
514
|
+
|
|
515
|
+
if (observerNext != null) {
|
|
516
|
+
var snapshot = environment.lookup(operation.fragment);
|
|
517
|
+
observerNext(snapshot);
|
|
518
|
+
}
|
|
387
519
|
},
|
|
388
520
|
error: function error(_error) {
|
|
389
|
-
var cacheEntry = _this2._getOrCreateCacheEntry(cacheIdentifier, operation, _error, networkSubscription);
|
|
521
|
+
var cacheEntry = _this2._getOrCreateCacheEntry(cacheIdentifier, operation, queryAvailability, _error, networkSubscription); // If, this is the first thing we receive for the query,
|
|
522
|
+
// before any other payload handled is error, we will cache and
|
|
523
|
+
// re-throw that error later.
|
|
524
|
+
// We will ignore errors for any incremental payloads we receive.
|
|
525
|
+
|
|
526
|
+
|
|
527
|
+
if (cacheEntry.processedPayloadsCount === 0) {
|
|
528
|
+
cacheEntry.setValue(_error);
|
|
529
|
+
} else {
|
|
530
|
+
// TODO:T92030819 Remove this warning and actually throw the network error
|
|
531
|
+
// To complete this task we need to have a way of precisely tracking suspendable points
|
|
532
|
+
process.env.NODE_ENV !== "production" ? warning(false, 'QueryResource: An incremental payload for query `%` returned an error: `%`:`%`.', operation.fragment.node.name, _error.message, _error.stack) : void 0;
|
|
533
|
+
}
|
|
390
534
|
|
|
391
|
-
cacheEntry.setValue(_error);
|
|
392
535
|
resolveNetworkPromise();
|
|
393
536
|
networkSubscription = null;
|
|
394
537
|
cacheEntry.setNetworkSubscription(null);
|
|
@@ -419,7 +562,7 @@ var QueryResourceImpl = /*#__PURE__*/function () {
|
|
|
419
562
|
}); // $FlowExpectedError[prop-missing] Expando to annotate Promises.
|
|
420
563
|
|
|
421
564
|
networkPromise.displayName = 'Relay(' + operation.fragment.node.name + ')';
|
|
422
|
-
_cacheEntry2 = createCacheEntry(cacheIdentifier, operation, networkPromise, networkSubscription, this._clearCacheEntry);
|
|
565
|
+
_cacheEntry2 = createCacheEntry(cacheIdentifier, operation, queryAvailability, networkPromise, networkSubscription, this._clearCacheEntry);
|
|
423
566
|
|
|
424
567
|
this._cache.set(cacheIdentifier, _cacheEntry2);
|
|
425
568
|
}
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* Copyright (c)
|
|
2
|
+
* Copyright (c) Meta Platforms, Inc. and affiliates.
|
|
3
3
|
*
|
|
4
4
|
* This source code is licensed under the MIT license found in the
|
|
5
5
|
* LICENSE file in the root directory of this source tree.
|
|
@@ -19,12 +19,14 @@ var useMemo = React.useMemo;
|
|
|
19
19
|
|
|
20
20
|
function RelayEnvironmentProvider(props) {
|
|
21
21
|
var children = props.children,
|
|
22
|
-
environment = props.environment
|
|
22
|
+
environment = props.environment,
|
|
23
|
+
getEnvironmentForActor = props.getEnvironmentForActor;
|
|
23
24
|
var context = useMemo(function () {
|
|
24
25
|
return {
|
|
25
|
-
environment: environment
|
|
26
|
+
environment: environment,
|
|
27
|
+
getEnvironmentForActor: getEnvironmentForActor
|
|
26
28
|
};
|
|
27
|
-
}, [environment]);
|
|
29
|
+
}, [environment, getEnvironmentForActor]);
|
|
28
30
|
return /*#__PURE__*/React.createElement(ReactRelayContext.Provider, {
|
|
29
31
|
value: context
|
|
30
32
|
}, children);
|
|
@@ -0,0 +1,130 @@
|
|
|
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
|
+
*
|
|
8
|
+
* @emails oncall+relay
|
|
9
|
+
* @format
|
|
10
|
+
*/
|
|
11
|
+
// flowlint ambiguous-object-type:error
|
|
12
|
+
'use strict';
|
|
13
|
+
|
|
14
|
+
var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
|
|
15
|
+
|
|
16
|
+
var _defineProperty2 = _interopRequireDefault(require("@babel/runtime/helpers/defineProperty"));
|
|
17
|
+
|
|
18
|
+
var invariant = require('invariant');
|
|
19
|
+
|
|
20
|
+
var TEMPORARY_RETAIN_DURATION_MS = 5 * 60 * 1000;
|
|
21
|
+
/**
|
|
22
|
+
* Allows you to retain a resource as part of a component lifecycle accounting
|
|
23
|
+
* for Suspense. You temporarily retain the resource during render, then
|
|
24
|
+
* permanently retain it during commit and release it during unmount.
|
|
25
|
+
*/
|
|
26
|
+
|
|
27
|
+
var SuspenseResource = /*#__PURE__*/function () {
|
|
28
|
+
function SuspenseResource(retain) {
|
|
29
|
+
var _this = this;
|
|
30
|
+
|
|
31
|
+
(0, _defineProperty2["default"])(this, "_retainCount", 0);
|
|
32
|
+
(0, _defineProperty2["default"])(this, "_retainDisposable", null);
|
|
33
|
+
(0, _defineProperty2["default"])(this, "_releaseTemporaryRetain", null);
|
|
34
|
+
|
|
35
|
+
this._retain = function (environment) {
|
|
36
|
+
_this._retainCount++;
|
|
37
|
+
|
|
38
|
+
if (_this._retainCount === 1) {
|
|
39
|
+
_this._retainDisposable = retain(environment);
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
return {
|
|
43
|
+
dispose: function dispose() {
|
|
44
|
+
_this._retainCount = Math.max(0, _this._retainCount - 1);
|
|
45
|
+
|
|
46
|
+
if (_this._retainCount === 0) {
|
|
47
|
+
!(_this._retainDisposable != null) ? process.env.NODE_ENV !== "production" ? invariant(false, 'Relay: Expected disposable to release query to be defined.' + "If you're seeing this, this is likely a bug in Relay.") : invariant(false) : void 0;
|
|
48
|
+
|
|
49
|
+
_this._retainDisposable.dispose();
|
|
50
|
+
|
|
51
|
+
_this._retainDisposable = null;
|
|
52
|
+
}
|
|
53
|
+
}
|
|
54
|
+
};
|
|
55
|
+
};
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
var _proto = SuspenseResource.prototype;
|
|
59
|
+
|
|
60
|
+
_proto.temporaryRetain = function temporaryRetain(environment) {
|
|
61
|
+
var _this2 = this;
|
|
62
|
+
|
|
63
|
+
var _this$_releaseTempora;
|
|
64
|
+
|
|
65
|
+
// If we're executing in a server environment, there's no need
|
|
66
|
+
// to create temporary retains, since the component will never commit.
|
|
67
|
+
if (environment.isServer()) {
|
|
68
|
+
return {
|
|
69
|
+
dispose: function dispose() {}
|
|
70
|
+
};
|
|
71
|
+
} // temporaryRetain is called during the render phase. However,
|
|
72
|
+
// given that we can't tell if this render will eventually commit or not,
|
|
73
|
+
// we create a timer to autodispose of this retain in case the associated
|
|
74
|
+
// component never commits.
|
|
75
|
+
// If the component /does/ commit, permanentRetain will clear this timeout
|
|
76
|
+
// and permanently retain the data.
|
|
77
|
+
|
|
78
|
+
|
|
79
|
+
var retention = this._retain(environment);
|
|
80
|
+
|
|
81
|
+
var releaseQueryTimeout = null;
|
|
82
|
+
|
|
83
|
+
var releaseTemporaryRetain = function releaseTemporaryRetain() {
|
|
84
|
+
clearTimeout(releaseQueryTimeout);
|
|
85
|
+
releaseQueryTimeout = null;
|
|
86
|
+
_this2._releaseTemporaryRetain = null;
|
|
87
|
+
retention.dispose();
|
|
88
|
+
};
|
|
89
|
+
|
|
90
|
+
releaseQueryTimeout = setTimeout(releaseTemporaryRetain, TEMPORARY_RETAIN_DURATION_MS); // NOTE: Since temporaryRetain can be called multiple times, we release
|
|
91
|
+
// the previous temporary retain after we re-establish a new one, since
|
|
92
|
+
// we only ever need a single temporary retain until the permanent retain is
|
|
93
|
+
// established.
|
|
94
|
+
// temporaryRetain may be called multiple times by React during the render
|
|
95
|
+
// phase, as well as multiple times by other query components that are
|
|
96
|
+
// rendering the same query/variables.
|
|
97
|
+
|
|
98
|
+
(_this$_releaseTempora = this._releaseTemporaryRetain) === null || _this$_releaseTempora === void 0 ? void 0 : _this$_releaseTempora.call(this);
|
|
99
|
+
this._releaseTemporaryRetain = releaseTemporaryRetain;
|
|
100
|
+
return {
|
|
101
|
+
dispose: function dispose() {
|
|
102
|
+
var _this$_releaseTempora2;
|
|
103
|
+
|
|
104
|
+
(_this$_releaseTempora2 = _this2._releaseTemporaryRetain) === null || _this$_releaseTempora2 === void 0 ? void 0 : _this$_releaseTempora2.call(_this2);
|
|
105
|
+
}
|
|
106
|
+
};
|
|
107
|
+
};
|
|
108
|
+
|
|
109
|
+
_proto.permanentRetain = function permanentRetain(environment) {
|
|
110
|
+
var disposable = this._retain(environment);
|
|
111
|
+
|
|
112
|
+
this.releaseTemporaryRetain();
|
|
113
|
+
return disposable;
|
|
114
|
+
};
|
|
115
|
+
|
|
116
|
+
_proto.releaseTemporaryRetain = function releaseTemporaryRetain() {
|
|
117
|
+
var _this$_releaseTempora3;
|
|
118
|
+
|
|
119
|
+
(_this$_releaseTempora3 = this._releaseTemporaryRetain) === null || _this$_releaseTempora3 === void 0 ? void 0 : _this$_releaseTempora3.call(this);
|
|
120
|
+
this._releaseTemporaryRetain = null;
|
|
121
|
+
};
|
|
122
|
+
|
|
123
|
+
_proto.getRetainCount = function getRetainCount() {
|
|
124
|
+
return this._retainCount;
|
|
125
|
+
};
|
|
126
|
+
|
|
127
|
+
return SuspenseResource;
|
|
128
|
+
}();
|
|
129
|
+
|
|
130
|
+
module.exports = SuspenseResource;
|