react-native-onyx 1.0.55 → 1.0.56
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/dist/web.development.js +77 -8
- package/dist/web.development.js.map +1 -1
- package/dist/web.min.js +1 -1
- package/dist/web.min.js.map +1 -1
- package/lib/Onyx.js +41 -0
- package/lib/withOnyx.js +35 -7
- package/package.json +1 -1
package/dist/web.development.js
CHANGED
|
@@ -268,6 +268,46 @@ function isSafeEvictionKey(testKey) {
|
|
|
268
268
|
return underscore__WEBPACK_IMPORTED_MODULE_2___default().some(evictionAllowList, (key) => isKeyMatch(key, testKey));
|
|
269
269
|
}
|
|
270
270
|
|
|
271
|
+
/**
|
|
272
|
+
* Tries to get a value from the cache. If the value is not present in cache it will return the default value or undefined.
|
|
273
|
+
* If the requested key is a collection, it will return an object with all the collection members.
|
|
274
|
+
*
|
|
275
|
+
* @param {String} key
|
|
276
|
+
* @param {Object} mapping
|
|
277
|
+
* @returns {Mixed}
|
|
278
|
+
*/
|
|
279
|
+
function tryGetCachedValue(key) {let mapping = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {};
|
|
280
|
+
let val = _OnyxCache__WEBPACK_IMPORTED_MODULE_4__["default"].getValue(key);
|
|
281
|
+
|
|
282
|
+
if (isCollectionKey(key)) {
|
|
283
|
+
const allKeys = _OnyxCache__WEBPACK_IMPORTED_MODULE_4__["default"].getAllKeys();
|
|
284
|
+
const matchingKeys = underscore__WEBPACK_IMPORTED_MODULE_2___default().filter(allKeys, (k) => k.startsWith(key));
|
|
285
|
+
const values = underscore__WEBPACK_IMPORTED_MODULE_2___default().reduce(matchingKeys, (finalObject, matchedKey) => {
|
|
286
|
+
const cachedValue = _OnyxCache__WEBPACK_IMPORTED_MODULE_4__["default"].getValue(matchedKey);
|
|
287
|
+
if (cachedValue) {
|
|
288
|
+
// This is permissible because we're in the process of constructing the final object in a reduce function.
|
|
289
|
+
// eslint-disable-next-line no-param-reassign
|
|
290
|
+
finalObject[matchedKey] = cachedValue;
|
|
291
|
+
}
|
|
292
|
+
return finalObject;
|
|
293
|
+
}, {});
|
|
294
|
+
if (underscore__WEBPACK_IMPORTED_MODULE_2___default().isEmpty(values)) {
|
|
295
|
+
return;
|
|
296
|
+
}
|
|
297
|
+
val = values;
|
|
298
|
+
}
|
|
299
|
+
|
|
300
|
+
if (mapping.selector) {
|
|
301
|
+
const state = mapping.withOnyxInstance ? mapping.withOnyxInstance.state : undefined;
|
|
302
|
+
if (isCollectionKey(key)) {
|
|
303
|
+
return reduceCollectionWithSelector(val, mapping.selector, state);
|
|
304
|
+
}
|
|
305
|
+
return getSubsetOfData(val, mapping.selector, state);
|
|
306
|
+
}
|
|
307
|
+
|
|
308
|
+
return val;
|
|
309
|
+
}
|
|
310
|
+
|
|
271
311
|
/**
|
|
272
312
|
* Remove a key from the recently accessed key list.
|
|
273
313
|
*
|
|
@@ -1436,7 +1476,8 @@ const Onyx = {
|
|
|
1436
1476
|
removeFromEvictionBlockList,
|
|
1437
1477
|
isSafeEvictionKey,
|
|
1438
1478
|
METHOD,
|
|
1439
|
-
setMemoryOnlyKeys
|
|
1479
|
+
setMemoryOnlyKeys,
|
|
1480
|
+
tryGetCachedValue
|
|
1440
1481
|
};
|
|
1441
1482
|
|
|
1442
1483
|
/**
|
|
@@ -2402,13 +2443,25 @@ function getDisplayName(component) {
|
|
|
2402
2443
|
// disconnected. It is a key value store with the format {[mapping.key]: connectionID}.
|
|
2403
2444
|
this.activeConnectionIDs = {};
|
|
2404
2445
|
|
|
2446
|
+
const cachedState = underscore__WEBPACK_IMPORTED_MODULE_2___default().reduce(mapOnyxToState, (resultObj, mapping, propertyName) => {
|
|
2447
|
+
const key = _Str__WEBPACK_IMPORTED_MODULE_3__.result(mapping.key, props);
|
|
2448
|
+
const value = _Onyx__WEBPACK_IMPORTED_MODULE_4__["default"].tryGetCachedValue(key, mapping);
|
|
2449
|
+
|
|
2450
|
+
if (value !== undefined) {
|
|
2451
|
+
// eslint-disable-next-line no-param-reassign
|
|
2452
|
+
resultObj[propertyName] = value;
|
|
2453
|
+
}
|
|
2454
|
+
|
|
2455
|
+
return resultObj;
|
|
2456
|
+
}, {});
|
|
2457
|
+
|
|
2458
|
+
// If we have all the data we need, then we can render the component immediately
|
|
2459
|
+
cachedState.loading = underscore__WEBPACK_IMPORTED_MODULE_2___default().size(cachedState) < requiredKeysForInit.length;
|
|
2460
|
+
|
|
2405
2461
|
// Object holding the temporary initial state for the component while we load the various Onyx keys
|
|
2406
|
-
this.tempState =
|
|
2462
|
+
this.tempState = cachedState;
|
|
2407
2463
|
|
|
2408
|
-
this.state =
|
|
2409
|
-
// If there are no required keys for init then we can render the wrapped component immediately
|
|
2410
|
-
loading: requiredKeysForInit.length > 0
|
|
2411
|
-
};
|
|
2464
|
+
this.state = cachedState;
|
|
2412
2465
|
}
|
|
2413
2466
|
|
|
2414
2467
|
componentDidMount() {
|
|
@@ -2425,7 +2478,6 @@ function getDisplayName(component) {
|
|
|
2425
2478
|
underscore__WEBPACK_IMPORTED_MODULE_2___default().each(mapOnyxToState, (mapping, propertyName) => {
|
|
2426
2479
|
const previousKey = _Str__WEBPACK_IMPORTED_MODULE_3__.result(mapping.key, prevProps);
|
|
2427
2480
|
const newKey = _Str__WEBPACK_IMPORTED_MODULE_3__.result(mapping.key, this.props);
|
|
2428
|
-
|
|
2429
2481
|
if (previousKey !== newKey) {
|
|
2430
2482
|
_Onyx__WEBPACK_IMPORTED_MODULE_4__["default"].disconnect(this.activeConnectionIDs[previousKey], previousKey);
|
|
2431
2483
|
delete this.activeConnectionIDs[previousKey];
|
|
@@ -2453,6 +2505,16 @@ function getDisplayName(component) {
|
|
|
2453
2505
|
* @param {*} val
|
|
2454
2506
|
*/
|
|
2455
2507
|
setWithOnyxState(statePropertyName, val) {
|
|
2508
|
+
// We might have loaded the values for the onyx keys/mappings already from the cache.
|
|
2509
|
+
// In case we were able to load all the values upfront, the loading state will be false.
|
|
2510
|
+
// However, Onyx.js will always call setWithOnyxState, as it doesn't know that this implementation
|
|
2511
|
+
// already loaded the values from cache. Thus we have to check whether the value has changed
|
|
2512
|
+
// before we set the state to prevent unnecessary renders.
|
|
2513
|
+
const prevValue = this.state[statePropertyName];
|
|
2514
|
+
if (!this.state.loading && prevValue === val) {
|
|
2515
|
+
return;
|
|
2516
|
+
}
|
|
2517
|
+
|
|
2456
2518
|
if (!this.state.loading) {
|
|
2457
2519
|
this.setState({ [statePropertyName]: val });
|
|
2458
2520
|
return;
|
|
@@ -2465,7 +2527,14 @@ function getDisplayName(component) {
|
|
|
2465
2527
|
return;
|
|
2466
2528
|
}
|
|
2467
2529
|
|
|
2468
|
-
|
|
2530
|
+
const stateUpdate = { ...this.tempState, loading: false };
|
|
2531
|
+
|
|
2532
|
+
// The state is set here manually, instead of using setState because setState is an async operation, meaning it might execute on the next tick,
|
|
2533
|
+
// or at a later point in the microtask queue. That can lead to a race condition where
|
|
2534
|
+
// setWithOnyxState is called before the state is actually set. This results in unreliable behavior when checking the loading state and has been mainly observed on fabric.
|
|
2535
|
+
this.state = stateUpdate;
|
|
2536
|
+
|
|
2537
|
+
this.setState(stateUpdate); // Trigger a render
|
|
2469
2538
|
delete this.tempState;
|
|
2470
2539
|
}
|
|
2471
2540
|
|