UNPKG

redux-devtools-instrument

Version:
823 lines (699 loc) 102 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.liftAction = liftAction; exports.liftReducerWith = liftReducerWith; exports.unliftState = unliftState; exports.unliftStore = unliftStore; exports["default"] = instrument; exports.INIT_ACTION = exports.ActionCreators = exports.ActionTypes = void 0; var _difference = _interopRequireDefault(require("lodash/difference")); var _union = _interopRequireDefault(require("lodash/union")); var _isPlainObject = _interopRequireDefault(require("lodash/isPlainObject")); var _symbolObservable = _interopRequireDefault(require("symbol-observable")); function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { "default": obj }; } function _toConsumableArray(arr) { return _arrayWithoutHoles(arr) || _iterableToArray(arr) || _unsupportedIterableToArray(arr) || _nonIterableSpread(); } function _nonIterableSpread() { throw new TypeError("Invalid attempt to spread non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); } function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); } function _iterableToArray(iter) { if (typeof Symbol !== "undefined" && Symbol.iterator in Object(iter)) return Array.from(iter); } function _arrayWithoutHoles(arr) { if (Array.isArray(arr)) return _arrayLikeToArray(arr); } function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) { arr2[i] = arr[i]; } return arr2; } function ownKeys(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); if (enumerableOnly) symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; }); keys.push.apply(keys, symbols); } return keys; } function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i] != null ? arguments[i] : {}; if (i % 2) { ownKeys(Object(source), true).forEach(function (key) { _defineProperty(target, key, source[key]); }); } else if (Object.getOwnPropertyDescriptors) { Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)); } else { ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } } return target; } function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; } function _typeof(obj) { "@babel/helpers - typeof"; if (typeof Symbol === "function" && typeof Symbol.iterator === "symbol") { _typeof = function _typeof(obj) { return typeof obj; }; } else { _typeof = function _typeof(obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; }; } return _typeof(obj); } var ActionTypes = { PERFORM_ACTION: 'PERFORM_ACTION', RESET: 'RESET', ROLLBACK: 'ROLLBACK', COMMIT: 'COMMIT', SWEEP: 'SWEEP', TOGGLE_ACTION: 'TOGGLE_ACTION', SET_ACTIONS_ACTIVE: 'SET_ACTIONS_ACTIVE', JUMP_TO_STATE: 'JUMP_TO_STATE', JUMP_TO_ACTION: 'JUMP_TO_ACTION', REORDER_ACTION: 'REORDER_ACTION', IMPORT_STATE: 'IMPORT_STATE', LOCK_CHANGES: 'LOCK_CHANGES', PAUSE_RECORDING: 'PAUSE_RECORDING' }; exports.ActionTypes = ActionTypes; var isChrome = (typeof window === "undefined" ? "undefined" : _typeof(window)) === 'object' && (typeof window.chrome !== 'undefined' || typeof window.process !== 'undefined' && window.process.type === 'renderer'); var isChromeOrNode = isChrome || typeof process !== 'undefined' && process.release && process.release.name === 'node'; /** * Action creators to change the History state. */ var ActionCreators = { performAction: function performAction(action, trace, traceLimit, // eslint-disable-next-line @typescript-eslint/ban-types toExcludeFromTrace) { if (!(0, _isPlainObject["default"])(action)) { throw new Error('Actions must be plain objects. ' + 'Use custom middleware for async actions.'); } if (typeof action.type === 'undefined') { throw new Error('Actions may not have an undefined "type" property. ' + 'Have you misspelled a constant?'); } var stack; if (trace) { var extraFrames = 0; if (typeof trace === 'function') { stack = trace(action); } else { var error = Error(); var prevStackTraceLimit; if (Error.captureStackTrace && isChromeOrNode) { // avoid error-polyfill if (traceLimit && Error.stackTraceLimit < traceLimit) { prevStackTraceLimit = Error.stackTraceLimit; Error.stackTraceLimit = traceLimit; } Error.captureStackTrace(error, toExcludeFromTrace); } else { extraFrames = 3; } stack = error.stack; if (prevStackTraceLimit) Error.stackTraceLimit = prevStackTraceLimit; if (extraFrames || typeof Error.stackTraceLimit !== 'number' || traceLimit && Error.stackTraceLimit > traceLimit) { if (stack != null) { var frames = stack.split('\n'); if (traceLimit && frames.length > traceLimit) { stack = frames.slice(0, traceLimit + extraFrames + (frames[0].startsWith('Error') ? 1 : 0)).join('\n'); } } } } } return { type: ActionTypes.PERFORM_ACTION, action: action, timestamp: Date.now(), stack: stack }; }, reset: function reset() { return { type: ActionTypes.RESET, timestamp: Date.now() }; }, rollback: function rollback() { return { type: ActionTypes.ROLLBACK, timestamp: Date.now() }; }, commit: function commit() { return { type: ActionTypes.COMMIT, timestamp: Date.now() }; }, sweep: function sweep() { return { type: ActionTypes.SWEEP }; }, toggleAction: function toggleAction(id) { return { type: ActionTypes.TOGGLE_ACTION, id: id }; }, setActionsActive: function setActionsActive(start, end) { var active = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : true; return { type: ActionTypes.SET_ACTIONS_ACTIVE, start: start, end: end, active: active }; }, reorderAction: function reorderAction(actionId, beforeActionId) { return { type: ActionTypes.REORDER_ACTION, actionId: actionId, beforeActionId: beforeActionId }; }, jumpToState: function jumpToState(index) { return { type: ActionTypes.JUMP_TO_STATE, index: index }; }, jumpToAction: function jumpToAction(actionId) { return { type: ActionTypes.JUMP_TO_ACTION, actionId: actionId }; }, importState: function importState(nextLiftedState, noRecompute) { return { type: ActionTypes.IMPORT_STATE, nextLiftedState: nextLiftedState, noRecompute: noRecompute }; }, lockChanges: function lockChanges(status) { return { type: ActionTypes.LOCK_CHANGES, status: status }; }, pauseRecording: function pauseRecording(status) { return { type: ActionTypes.PAUSE_RECORDING, status: status }; } }; exports.ActionCreators = ActionCreators; var INIT_ACTION = { type: '@@INIT' }; /** * Computes the next entry with exceptions catching. */ exports.INIT_ACTION = INIT_ACTION; function computeWithTryCatch(reducer, action, state) { var nextState = state; var nextError; try { nextState = reducer(state, action); } catch (err) { nextError = err.toString(); if (isChrome) { // In Chrome, rethrowing provides better source map support setTimeout(function () { throw err; }); } else { console.error(err); // eslint-disable-line no-console } } return { state: nextState, error: nextError }; } /** * Computes the next entry in the log by applying an action. */ function computeNextEntry(reducer, action, state, shouldCatchErrors) { if (!shouldCatchErrors) { return { state: reducer(state, action) }; } return computeWithTryCatch(reducer, action, state); } /** * Runs the reducer on invalidated actions to get a fresh computation log. */ function recomputeStates(computedStates, minInvalidatedStateIndex, reducer, committedState, actionsById, stagedActionIds, skippedActionIds, shouldCatchErrors) { // Optimization: exit early and return the same reference // if we know nothing could have changed. if (!computedStates || minInvalidatedStateIndex === -1 || minInvalidatedStateIndex >= computedStates.length && computedStates.length === stagedActionIds.length) { return computedStates; } var nextComputedStates = computedStates.slice(0, minInvalidatedStateIndex); for (var i = minInvalidatedStateIndex; i < stagedActionIds.length; i++) { var _actionId = stagedActionIds[i]; var _action = actionsById[_actionId].action; var previousEntry = nextComputedStates[i - 1]; var previousState = previousEntry ? previousEntry.state : committedState; var shouldSkip = skippedActionIds.indexOf(_actionId) > -1; var entry = void 0; if (shouldSkip) { entry = previousEntry; } else { if (shouldCatchErrors && previousEntry && previousEntry.error) { entry = { state: previousState, error: 'Interrupted by an error up the chain' }; } else { entry = computeNextEntry(reducer, _action, previousState, shouldCatchErrors); } } nextComputedStates.push(entry); } return nextComputedStates; } /** * Lifts an app's action into an action on the lifted store. */ function liftAction(action, trace, traceLimit, // eslint-disable-next-line @typescript-eslint/ban-types toExcludeFromTrace) { return ActionCreators.performAction(action, trace, traceLimit, toExcludeFromTrace); } function isArray(nextLiftedState) { return Array.isArray(nextLiftedState); } /** * Creates a history state reducer from an app's reducer. */ function liftReducerWith(reducer, initialCommittedState, monitorReducer, options) { var initialLiftedState = { monitorState: monitorReducer(undefined, {}), nextActionId: 1, actionsById: { 0: liftAction(INIT_ACTION) }, stagedActionIds: [0], skippedActionIds: [], committedState: initialCommittedState, currentStateIndex: 0, computedStates: [], isLocked: options.shouldStartLocked === true, isPaused: options.shouldRecordChanges === false }; /** * Manages how the history actions modify the history state. */ return function (liftedState, liftedAction) { var _ref = liftedState || initialLiftedState, monitorState = _ref.monitorState, actionsById = _ref.actionsById, nextActionId = _ref.nextActionId, stagedActionIds = _ref.stagedActionIds, skippedActionIds = _ref.skippedActionIds, committedState = _ref.committedState, currentStateIndex = _ref.currentStateIndex, computedStates = _ref.computedStates, isLocked = _ref.isLocked, isPaused = _ref.isPaused; if (!liftedState) { // Prevent mutating initialLiftedState actionsById = _objectSpread({}, actionsById); } function commitExcessActions(n) { // Auto-commits n-number of excess actions. var excess = n; var idsToDelete = stagedActionIds.slice(1, excess + 1); for (var i = 0; i < idsToDelete.length; i++) { if (computedStates[i + 1].error) { // Stop if error is found. Commit actions up to error. excess = i; idsToDelete = stagedActionIds.slice(1, excess + 1); break; } else { delete actionsById[idsToDelete[i]]; } } skippedActionIds = skippedActionIds.filter(function (id) { return idsToDelete.indexOf(id) === -1; }); stagedActionIds = [0].concat(_toConsumableArray(stagedActionIds.slice(excess + 1))); committedState = computedStates[excess].state; computedStates = computedStates.slice(excess); currentStateIndex = currentStateIndex > excess ? currentStateIndex - excess : 0; } function computePausedAction(shouldInit) { var computedState; if (shouldInit) { computedState = computedStates[currentStateIndex]; monitorState = monitorReducer(monitorState, liftedAction); } else { computedState = computeNextEntry(reducer, liftedAction.action, computedStates[currentStateIndex].state, false); } if (!options.pauseActionType || nextActionId === 1) { return { monitorState: monitorState, actionsById: { 0: liftAction(INIT_ACTION) }, nextActionId: 1, stagedActionIds: [0], skippedActionIds: [], committedState: computedState.state, currentStateIndex: 0, computedStates: [computedState], isLocked: isLocked, isPaused: true }; } if (shouldInit) { if (currentStateIndex === stagedActionIds.length - 1) { currentStateIndex++; } stagedActionIds = [].concat(_toConsumableArray(stagedActionIds), [nextActionId]); nextActionId++; } return { monitorState: monitorState, actionsById: _objectSpread(_objectSpread({}, actionsById), {}, _defineProperty({}, nextActionId - 1, liftAction({ type: options.pauseActionType }))), nextActionId: nextActionId, stagedActionIds: stagedActionIds, skippedActionIds: skippedActionIds, committedState: committedState, currentStateIndex: currentStateIndex, computedStates: [].concat(_toConsumableArray(computedStates.slice(0, stagedActionIds.length - 1)), [computedState]), isLocked: isLocked, isPaused: true }; } // By default, aggressively recompute every state whatever happens. // This has O(n) performance, so we'll override this to a sensible // value whenever we feel like we don't have to recompute the states. var minInvalidatedStateIndex = 0; // maxAge number can be changed dynamically var maxAge = options.maxAge; if (typeof maxAge === 'function') maxAge = maxAge(liftedAction, liftedState); if (/^@@redux\/(INIT|REPLACE)/.test(liftedAction.type)) { if (options.shouldHotReload === false) { actionsById = { 0: liftAction(INIT_ACTION) }; nextActionId = 1; stagedActionIds = [0]; skippedActionIds = []; committedState = computedStates.length === 0 ? initialCommittedState : computedStates[currentStateIndex].state; currentStateIndex = 0; computedStates = []; } // Recompute states on hot reload and init. minInvalidatedStateIndex = 0; if (maxAge && stagedActionIds.length > maxAge) { // States must be recomputed before committing excess. computedStates = recomputeStates(computedStates, minInvalidatedStateIndex, reducer, committedState, actionsById, stagedActionIds, skippedActionIds, options.shouldCatchErrors); commitExcessActions(stagedActionIds.length - maxAge); // Avoid double computation. minInvalidatedStateIndex = Infinity; } } else { switch (liftedAction.type) { case ActionTypes.PERFORM_ACTION: { if (isLocked) return liftedState || initialLiftedState; if (isPaused) return computePausedAction(); // Auto-commit as new actions come in. if (maxAge && stagedActionIds.length >= maxAge) { commitExcessActions(stagedActionIds.length - maxAge + 1); } if (currentStateIndex === stagedActionIds.length - 1) { currentStateIndex++; } var _actionId2 = nextActionId++; // Mutation! This is the hottest path, and we optimize on purpose. // It is safe because we set a new key in a cache dictionary. actionsById[_actionId2] = liftedAction; stagedActionIds = [].concat(_toConsumableArray(stagedActionIds), [_actionId2]); // Optimization: we know that only the new action needs computing. minInvalidatedStateIndex = stagedActionIds.length - 1; break; } case ActionTypes.RESET: { // Get back to the state the store was created with. actionsById = { 0: liftAction(INIT_ACTION) }; nextActionId = 1; stagedActionIds = [0]; skippedActionIds = []; committedState = initialCommittedState; currentStateIndex = 0; computedStates = []; break; } case ActionTypes.COMMIT: { // Consider the last committed state the new starting point. // Squash any staged actions into a single committed state. actionsById = { 0: liftAction(INIT_ACTION) }; nextActionId = 1; stagedActionIds = [0]; skippedActionIds = []; committedState = computedStates[currentStateIndex].state; currentStateIndex = 0; computedStates = []; break; } case ActionTypes.ROLLBACK: { // Forget about any staged actions. // Start again from the last committed state. actionsById = { 0: liftAction(INIT_ACTION) }; nextActionId = 1; stagedActionIds = [0]; skippedActionIds = []; currentStateIndex = 0; computedStates = []; break; } case ActionTypes.TOGGLE_ACTION: { // Toggle whether an action with given ID is skipped. // Being skipped means it is a no-op during the computation. var _actionId3 = liftedAction.id; var index = skippedActionIds.indexOf(_actionId3); if (index === -1) { skippedActionIds = [_actionId3].concat(_toConsumableArray(skippedActionIds)); } else { skippedActionIds = skippedActionIds.filter(function (id) { return id !== _actionId3; }); } // Optimization: we know history before this action hasn't changed minInvalidatedStateIndex = stagedActionIds.indexOf(_actionId3); break; } case ActionTypes.SET_ACTIONS_ACTIVE: { // Toggle whether an action with given ID is skipped. // Being skipped means it is a no-op during the computation. var start = liftedAction.start, end = liftedAction.end, active = liftedAction.active; var actionIds = []; for (var i = start; i < end; i++) { actionIds.push(i); } if (active) { skippedActionIds = (0, _difference["default"])(skippedActionIds, actionIds); } else { skippedActionIds = (0, _union["default"])(skippedActionIds, actionIds); } // Optimization: we know history before this action hasn't changed minInvalidatedStateIndex = stagedActionIds.indexOf(start); break; } case ActionTypes.JUMP_TO_STATE: { // Without recomputing anything, move the pointer that tell us // which state is considered the current one. Useful for sliders. currentStateIndex = liftedAction.index; // Optimization: we know the history has not changed. minInvalidatedStateIndex = Infinity; break; } case ActionTypes.JUMP_TO_ACTION: { // Jumps to a corresponding state to a specific action. // Useful when filtering actions. var _index = stagedActionIds.indexOf(liftedAction.actionId); if (_index !== -1) currentStateIndex = _index; minInvalidatedStateIndex = Infinity; break; } case ActionTypes.SWEEP: { // Forget any actions that are currently being skipped. stagedActionIds = (0, _difference["default"])(stagedActionIds, skippedActionIds); skippedActionIds = []; currentStateIndex = Math.min(currentStateIndex, stagedActionIds.length - 1); break; } case ActionTypes.REORDER_ACTION: { // Recompute actions in a new order. var _actionId4 = liftedAction.actionId; var idx = stagedActionIds.indexOf(_actionId4); // do nothing in case the action is already removed or trying to move the first action if (idx < 1) break; var beforeActionId = liftedAction.beforeActionId; var newIdx = stagedActionIds.indexOf(beforeActionId); if (newIdx < 1) { // move to the beginning or to the end var count = stagedActionIds.length; newIdx = beforeActionId > stagedActionIds[count - 1] ? count : 1; } var diff = idx - newIdx; if (diff > 0) { // move left stagedActionIds = [].concat(_toConsumableArray(stagedActionIds.slice(0, newIdx)), [_actionId4], _toConsumableArray(stagedActionIds.slice(newIdx, idx)), _toConsumableArray(stagedActionIds.slice(idx + 1))); minInvalidatedStateIndex = newIdx; } else if (diff < 0) { // move right stagedActionIds = [].concat(_toConsumableArray(stagedActionIds.slice(0, idx)), _toConsumableArray(stagedActionIds.slice(idx + 1, newIdx)), [_actionId4], _toConsumableArray(stagedActionIds.slice(newIdx))); minInvalidatedStateIndex = idx; } break; } case ActionTypes.IMPORT_STATE: { if (isArray(liftedAction.nextLiftedState)) { // recompute array of actions actionsById = { 0: liftAction(INIT_ACTION) }; nextActionId = 1; stagedActionIds = [0]; skippedActionIds = []; currentStateIndex = liftedAction.nextLiftedState.length; computedStates = []; committedState = liftedAction.preloadedState; minInvalidatedStateIndex = 0; // iterate through actions liftedAction.nextLiftedState.forEach(function (action) { actionsById[nextActionId] = liftAction(action, options.trace || options.shouldIncludeCallstack); stagedActionIds.push(nextActionId); nextActionId++; }); } else { // Completely replace everything. var _liftedAction$nextLif = liftedAction.nextLiftedState; monitorState = _liftedAction$nextLif.monitorState; actionsById = _liftedAction$nextLif.actionsById; nextActionId = _liftedAction$nextLif.nextActionId; stagedActionIds = _liftedAction$nextLif.stagedActionIds; skippedActionIds = _liftedAction$nextLif.skippedActionIds; committedState = _liftedAction$nextLif.committedState; currentStateIndex = _liftedAction$nextLif.currentStateIndex; computedStates = _liftedAction$nextLif.computedStates; if (liftedAction.noRecompute) { minInvalidatedStateIndex = Infinity; } } break; } case ActionTypes.LOCK_CHANGES: { isLocked = liftedAction.status; minInvalidatedStateIndex = Infinity; break; } case ActionTypes.PAUSE_RECORDING: { isPaused = liftedAction.status; if (isPaused) { return computePausedAction(true); } // Commit when unpausing actionsById = { 0: liftAction(INIT_ACTION) }; nextActionId = 1; stagedActionIds = [0]; skippedActionIds = []; committedState = computedStates[currentStateIndex].state; currentStateIndex = 0; computedStates = []; break; } default: { // If the action is not recognized, it's a monitor action. // Optimization: a monitor action can't change history. minInvalidatedStateIndex = Infinity; break; } } } computedStates = recomputeStates(computedStates, minInvalidatedStateIndex, reducer, committedState, actionsById, stagedActionIds, skippedActionIds, options.shouldCatchErrors); monitorState = monitorReducer(monitorState, liftedAction); return { monitorState: monitorState, actionsById: actionsById, nextActionId: nextActionId, stagedActionIds: stagedActionIds, skippedActionIds: skippedActionIds, committedState: committedState, currentStateIndex: currentStateIndex, computedStates: computedStates, isLocked: isLocked, isPaused: isPaused }; }; } /** * Provides an app's view into the state of the lifted store. */ function unliftState(liftedState) { var computedStates = liftedState.computedStates, currentStateIndex = liftedState.currentStateIndex; var state = computedStates[currentStateIndex].state; return state; } /** * Provides an app's view into the lifted store. */ function unliftStore(liftedStore, liftReducer, options) { var lastDefinedState; var trace = options.trace || options.shouldIncludeCallstack; var traceLimit = options.traceLimit || 10; function getState() { var state = unliftState(liftedStore.getState()); if (state !== undefined) { lastDefinedState = state; } return lastDefinedState; } function dispatch(action) { liftedStore.dispatch(liftAction(action, trace, traceLimit, dispatch)); return action; } return _objectSpread(_objectSpread({}, liftedStore), {}, _defineProperty({ liftedStore: liftedStore, dispatch: dispatch, getState: getState, replaceReducer: function replaceReducer(nextReducer) { liftedStore.replaceReducer(liftReducer(nextReducer)); } }, _symbolObservable["default"], function () { return _objectSpread(_objectSpread({}, liftedStore[_symbolObservable["default"]]()), {}, _defineProperty({ subscribe: function subscribe(observer) { if (_typeof(observer) !== 'object') { throw new TypeError('Expected the observer to be an object.'); } function observeState() { if (observer.next) { observer.next(getState()); } } observeState(); var unsubscribe = liftedStore.subscribe(observeState); return { unsubscribe: unsubscribe }; } }, _symbolObservable["default"], function () { return this; })); })); } /** * Redux instrumentation store enhancer. */ function instrument() { var monitorReducer = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : function () { return null; }; var options = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {}; if (typeof options.maxAge === 'number' && options.maxAge < 2) { throw new Error('DevTools.instrument({ maxAge }) option, if specified, ' + 'may not be less than 2.'); } return function (createStore) { return function (reducer, initialState) { function liftReducer(r) { if (typeof r !== 'function') { if (r && typeof r["default"] === 'function') { throw new Error('Expected the reducer to be a function. ' + 'Instead got an object with a "default" field. ' + 'Did you pass a module instead of the default export? ' + 'Try passing require(...).default instead.'); } throw new Error('Expected the reducer to be a function.'); } return liftReducerWith(r, initialState, monitorReducer, options); } var liftedStore = createStore(liftReducer(reducer)); if (liftedStore.liftedStore) { throw new Error('DevTools instrumentation should not be applied more than once. ' + 'Check your store configuration.'); } return unliftStore(liftedStore, liftReducer, options); }; }; } //# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi4uL3NyYy9pbnN0cnVtZW50LnRzIl0sIm5hbWVzIjpbIkFjdGlvblR5cGVzIiwiUEVSRk9STV9BQ1RJT04iLCJSRVNFVCIsIlJPTExCQUNLIiwiQ09NTUlUIiwiU1dFRVAiLCJUT0dHTEVfQUNUSU9OIiwiU0VUX0FDVElPTlNfQUNUSVZFIiwiSlVNUF9UT19TVEFURSIsIkpVTVBfVE9fQUNUSU9OIiwiUkVPUkRFUl9BQ1RJT04iLCJJTVBPUlRfU1RBVEUiLCJMT0NLX0NIQU5HRVMiLCJQQVVTRV9SRUNPUkRJTkciLCJpc0Nocm9tZSIsIndpbmRvdyIsImNocm9tZSIsInByb2Nlc3MiLCJ0eXBlIiwiaXNDaHJvbWVPck5vZGUiLCJyZWxlYXNlIiwibmFtZSIsIkFjdGlvbkNyZWF0b3JzIiwicGVyZm9ybUFjdGlvbiIsImFjdGlvbiIsInRyYWNlIiwidHJhY2VMaW1pdCIsInRvRXhjbHVkZUZyb21UcmFjZSIsIkVycm9yIiwic3RhY2siLCJleHRyYUZyYW1lcyIsImVycm9yIiwicHJldlN0YWNrVHJhY2VMaW1pdCIsImNhcHR1cmVTdGFja1RyYWNlIiwic3RhY2tUcmFjZUxpbWl0IiwiZnJhbWVzIiwic3BsaXQiLCJsZW5ndGgiLCJzbGljZSIsInN0YXJ0c1dpdGgiLCJqb2luIiwidGltZXN0YW1wIiwiRGF0ZSIsIm5vdyIsInJlc2V0Iiwicm9sbGJhY2siLCJjb21taXQiLCJzd2VlcCIsInRvZ2dsZUFjdGlvbiIsImlkIiwic2V0QWN0aW9uc0FjdGl2ZSIsInN0YXJ0IiwiZW5kIiwiYWN0aXZlIiwicmVvcmRlckFjdGlvbiIsImFjdGlvbklkIiwiYmVmb3JlQWN0aW9uSWQiLCJqdW1wVG9TdGF0ZSIsImluZGV4IiwianVtcFRvQWN0aW9uIiwiaW1wb3J0U3RhdGUiLCJuZXh0TGlmdGVkU3RhdGUiLCJub1JlY29tcHV0ZSIsImxvY2tDaGFuZ2VzIiwic3RhdHVzIiwicGF1c2VSZWNvcmRpbmciLCJJTklUX0FDVElPTiIsImNvbXB1dGVXaXRoVHJ5Q2F0Y2giLCJyZWR1Y2VyIiwic3RhdGUiLCJuZXh0U3RhdGUiLCJuZXh0RXJyb3IiLCJlcnIiLCJ0b1N0cmluZyIsInNldFRpbWVvdXQiLCJjb25zb2xlIiwiY29tcHV0ZU5leHRFbnRyeSIsInNob3VsZENhdGNoRXJyb3JzIiwicmVjb21wdXRlU3RhdGVzIiwiY29tcHV0ZWRTdGF0ZXMiLCJtaW5JbnZhbGlkYXRlZFN0YXRlSW5kZXgiLCJjb21taXR0ZWRTdGF0ZSIsImFjdGlvbnNCeUlkIiwic3RhZ2VkQWN0aW9uSWRzIiwic2tpcHBlZEFjdGlvbklkcyIsIm5leHRDb21wdXRlZFN0YXRlcyIsImkiLCJwcmV2aW91c0VudHJ5IiwicHJldmlvdXNTdGF0ZSIsInNob3VsZFNraXAiLCJpbmRleE9mIiwiZW50cnkiLCJwdXNoIiwibGlmdEFjdGlvbiIsImlzQXJyYXkiLCJBcnJheSIsImxpZnRSZWR1Y2VyV2l0aCIsImluaXRpYWxDb21taXR0ZWRTdGF0ZSIsIm1vbml0b3JSZWR1Y2VyIiwib3B0aW9ucyIsImluaXRpYWxMaWZ0ZWRTdGF0ZSIsIm1vbml0b3JTdGF0ZSIsInVuZGVmaW5lZCIsIm5leHRBY3Rpb25JZCIsImN1cnJlbnRTdGF0ZUluZGV4IiwiaXNMb2NrZWQiLCJzaG91bGRTdGFydExvY2tlZCIsImlzUGF1c2VkIiwic2hvdWxkUmVjb3JkQ2hhbmdlcyIsImxpZnRlZFN0YXRlIiwibGlmdGVkQWN0aW9uIiwiY29tbWl0RXhjZXNzQWN0aW9ucyIsIm4iLCJleGNlc3MiLCJpZHNUb0RlbGV0ZSIsImZpbHRlciIsImNvbXB1dGVQYXVzZWRBY3Rpb24iLCJzaG91bGRJbml0IiwiY29tcHV0ZWRTdGF0ZSIsInBhdXNlQWN0aW9uVHlwZSIsIm1heEFnZSIsInRlc3QiLCJzaG91bGRIb3RSZWxvYWQiLCJJbmZpbml0eSIsImFjdGlvbklkcyIsIk1hdGgiLCJtaW4iLCJpZHgiLCJuZXdJZHgiLCJjb3VudCIsImRpZmYiLCJwcmVsb2FkZWRTdGF0ZSIsImZvckVhY2giLCJzaG91bGRJbmNsdWRlQ2FsbHN0YWNrIiwidW5saWZ0U3RhdGUiLCJ1bmxpZnRTdG9yZSIsImxpZnRlZFN0b3JlIiwibGlmdFJlZHVjZXIiLCJsYXN0RGVmaW5lZFN0YXRlIiwiZ2V0U3RhdGUiLCJkaXNwYXRjaCIsInJlcGxhY2VSZWR1Y2VyIiwibmV4dFJlZHVjZXIiLCIkJG9ic2VydmFibGUiLCJzdWJzY3JpYmUiLCJvYnNlcnZlciIsIlR5cGVFcnJvciIsIm9ic2VydmVTdGF0ZSIsIm5leHQiLCJ1bnN1YnNjcmliZSIsImluc3RydW1lbnQiLCJjcmVhdGVTdG9yZSIsImluaXRpYWxTdGF0ZSIsInIiXSwibWFwcGluZ3MiOiI7Ozs7Ozs7Ozs7OztBQUFBOztBQUNBOztBQUNBOztBQUNBOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7QUFXTyxJQUFNQSxXQUFXLEdBQUc7QUFDekJDLEVBQUFBLGNBQWMsRUFBRSxnQkFEUztBQUV6QkMsRUFBQUEsS0FBSyxFQUFFLE9BRmtCO0FBR3pCQyxFQUFBQSxRQUFRLEVBQUUsVUFIZTtBQUl6QkMsRUFBQUEsTUFBTSxFQUFFLFFBSmlCO0FBS3pCQyxFQUFBQSxLQUFLLEVBQUUsT0FMa0I7QUFNekJDLEVBQUFBLGFBQWEsRUFBRSxlQU5VO0FBT3pCQyxFQUFBQSxrQkFBa0IsRUFBRSxvQkFQSztBQVF6QkMsRUFBQUEsYUFBYSxFQUFFLGVBUlU7QUFTekJDLEVBQUFBLGNBQWMsRUFBRSxnQkFUUztBQVV6QkMsRUFBQUEsY0FBYyxFQUFFLGdCQVZTO0FBV3pCQyxFQUFBQSxZQUFZLEVBQUUsY0FYVztBQVl6QkMsRUFBQUEsWUFBWSxFQUFFLGNBWlc7QUFhekJDLEVBQUFBLGVBQWUsRUFBRTtBQWJRLENBQXBCOztBQWdCUCxJQUFNQyxRQUFRLEdBQ1osUUFBT0MsTUFBUCx5Q0FBT0EsTUFBUCxPQUFrQixRQUFsQixLQUNDLE9BQVFBLE1BQUQsQ0FBZ0RDLE1BQXZELEtBQ0MsV0FERCxJQUVFLE9BQU9ELE1BQU0sQ0FBQ0UsT0FBZCxLQUEwQixXQUExQixJQUNFRixNQUFNLENBQUNFLE9BQVIsQ0FBOERDLElB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