Skip to content
Merged
Show file tree
Hide file tree
Changes from 3 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
21 changes: 18 additions & 3 deletions assets/js/googlesitekit/data/create-snapshot-store.js
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@
* External dependencies
*/
import invariant from 'invariant';
import { pick } from 'lodash';

/**
* Internal dependencies
Expand All @@ -38,12 +39,15 @@ const SET_STATE_FROM_SNAPSHOT = 'SET_STATE_FROM_SNAPSHOT';
* Creates a store object that includes actions and controls for restoring/creating state snapshots.
*
* @since 1.9.0
* @since n.e.x.t Added the ability to pick specific parts of the state to save in the snapshot.
* @private
*
* @param {string} storeName The name of the store to snapshot in the cache.
* @param {string} storeName The name of the store to snapshot in the cache.
* @param {Object} [options] Optional configuration object.
* @param {string|string[]} [options.pick] Property path(s) to pick from state when creating snapshots.
* @return {Object} The snapshot store object.
*/
export function createSnapshotStore( storeName ) {
export function createSnapshotStore( storeName, { pick: pickPaths } = {} ) {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Rather than using pick/pickPaths, can we have a more descriptive name for this argument? Calling it pick seems like the implementation detail of using lodash's pick() is bubbling up.

I'd call this keysToSnapshot or onlySnapshotKeys, etc. so it's a bit more clear to someone reading it.

invariant( storeName, 'storeName is required to create a snapshot store.' );

const initialState = {};
Expand Down Expand Up @@ -123,9 +127,13 @@ export function createSnapshotStore( storeName ) {
return deleteItem( `datastore::cache::${ storeName }` );
},
[ CREATE_SNAPSHOT ]: createRegistryControl( ( registry ) => () => {
const state = registry.stores[ storeName ].store.getState();
const stateToSnapshot =
pickPaths?.length > 0 ? pick( state, pickPaths ) : state;

return setItem(
`datastore::cache::${ storeName }`,
registry.stores[ storeName ].store.getState()
stateToSnapshot
);
} ),
[ RESTORE_SNAPSHOT ]: () => {
Expand All @@ -146,6 +154,13 @@ export function createSnapshotStore( storeName ) {
// eslint-disable-next-line no-unused-vars
const { error, ...newState } = snapshot;

// If only a part of the state has been added to the snapshot, then
// we should update the initial state with partial data restored
// from the snapshot.
if ( pickPaths?.length > 0 ) {
return { ...state, ...newState };
}

return newState;
}

Expand Down
6 changes: 4 additions & 2 deletions assets/js/googlesitekit/datastore/site/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,8 @@
* Internal dependencies
*/
import { combineStores, commonStore } from 'googlesitekit-data';
import { createErrorStore } from '@/js/googlesitekit/data/create-error-store';
import { createSnapshotStore } from '@/js/googlesitekit/data/create-snapshot-store';
import { CORE_SITE } from './constants';
import cache from './cache';
import connection from './connection';
Expand All @@ -35,7 +37,6 @@ import settings from './settings';
import urls from './urls';
import developerPlugin from './developer-plugin';
import notifications from './notifications';
import { createErrorStore } from '@/js/googlesitekit/data/create-error-store';

const store = combineStores(
commonStore,
Expand All @@ -53,7 +54,8 @@ const store = combineStores(
urls,
notifications,
cache,
createErrorStore( CORE_SITE )
createErrorStore( CORE_SITE ),
createSnapshotStore( CORE_SITE, { pick: [ 'conversionTracking' ] } )
);

export const initialState = store.initialState;
Expand Down
Loading