123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138 |
- /* @flow */
-
- import _ from 'lodash';
-
- /**
- * Sets specific properties of a specific state to specific values and prevents
- * unnecessary state changes.
- *
- * @param {Object} target - The state on which the specified properties are to
- * be set.
- * @param {Object} source - The map of properties to values which are to be set
- * on the specified target.
- * @returns {Object} The specified target if the values of the specified
- * properties equal the specified values; otherwise, a new state constructed
- * from the specified target by setting the specified properties to the
- * specified values.
- */
- export function assign(target: Object, source: Object) {
- let t = target;
-
- for (const property in source) { // eslint-disable-line guard-for-in
- t = set(t, property, source[property], t === target);
- }
-
- return t;
- }
-
- /**
- * Determines whether {@code a} equals {@code b} according to deep comparison
- * (which makes sense for Redux and its state definition).
- *
- * @param {*} a - The value to compare to {@code b}.
- * @param {*} b - The value to compare to {@code a}.
- * @returns {boolean} True if {@code a} equals {@code b} (according to deep
- * comparison); false, otherwise.
- */
- export function equals(a: any, b: any) {
- return _.isEqual(a, b);
- }
-
- /**
- * Sets a specific property of a specific state to a specific value. Prevents
- * unnecessary state changes (when the specified {@code value} is equal to the
- * value of the specified {@code property} of the specified {@code state}).
- *
- * @param {Object} state - The (Redux) state from which a new state is to be
- * constructed by setting the specified {@code property} to the specified
- * {@code value}.
- * @param {string} property - The property of {@code state} which is to be
- * assigned the specified {@code value} (in the new state).
- * @param {*} value - The value to assign to the specified {@code property}.
- * @returns {Object} The specified {@code state} if the value of the specified
- * {@code property} equals the specified <tt>value/tt>; otherwise, a new state
- * constructed from the specified {@code state} by setting the specified
- * {@code property} to the specified {@code value}.
- */
- export function set(state: Object, property: string, value: any) {
- return _set(state, property, value, /* copyOnWrite */ true);
- }
-
- /* eslint-disable max-params */
-
- /**
- * Sets a specific property of a specific state to a specific value. Prevents
- * unnecessary state changes (when the specified {@code value} is equal to the
- * value of the specified {@code property} of the specified {@code state}).
- *
- * @param {Object} state - The (Redux) state from which a state is to be
- * constructed by setting the specified {@code property} to the specified
- * {@code value}.
- * @param {string} property - The property of {@code state} which is to be
- * assigned the specified {@code value}.
- * @param {*} value - The value to assign to the specified {@code property}.
- * @param {boolean} copyOnWrite - If the specified {@code state} is to not be
- * modified, {@code true}; otherwise, {@code false}.
- * @returns {Object} The specified {@code state} if the value of the specified
- * {@code property} equals the specified <tt>value/tt> or {@code copyOnWrite}
- * is truthy; otherwise, a new state constructed from the specified
- * {@code state} by setting the specified {@code property} to the specified
- * {@code value}.
- */
- function _set(
- state: Object,
- property: string,
- value: any,
- copyOnWrite: boolean) {
- // Delete state properties that are to be set to undefined. (It is a matter
- // of personal preference, mostly.)
- if (typeof value === 'undefined'
- && Object.prototype.hasOwnProperty.call(state, property)) {
- const newState = copyOnWrite ? { ...state } : state;
-
- if (delete newState[property]) {
- return newState;
- }
- }
-
- if (state[property] !== value) {
- if (copyOnWrite) {
- return {
- ...state,
- [property]: value
- };
- }
-
- state[property] = value;
- }
-
- return state;
- }
-
- /* eslint-enable max-params */
-
- /**
- * Returns redux state from the specified {@code stateful} which is presumed to
- * be related to the redux state (e.g. the redux store, the redux
- * {@code getState} function).
- *
- * @param {Function|Object} stateful - The entity such as the redux store or the
- * redux {@code getState} function from which the redux state is to be
- * returned.
- * @returns {Object} The redux state.
- */
- export function toState(stateful: Function | Object) {
- if (stateful) {
- if (typeof stateful === 'function') {
- return stateful();
- }
-
- const { getState } = stateful;
-
- if (typeof getState === 'function') {
- return getState();
- }
- }
-
- return stateful;
- }
|