'use strict'; Object.defineProperty(exports, '__esModule', { value: true }); var proxyCompare = require('proxy-compare'); var isObject = function isObject(x) { return typeof x === 'object' && x !== null; }; var refSet = new WeakSet(); var VERSION = process.env.NODE_ENV !== "production" ? Symbol('VERSION') : Symbol(); var LISTENERS = process.env.NODE_ENV !== "production" ? Symbol('LISTENERS') : Symbol(); var SNAPSHOT = process.env.NODE_ENV !== "production" ? Symbol('SNAPSHOT') : Symbol(); var buildProxyFunction = function buildProxyFunction(objectIs, newProxy, canProxy, PROMISE_RESULT, PROMISE_ERROR, snapshotCache, createSnapshot, proxyCache, versionHolder, proxyFunction) { if (objectIs === void 0) { objectIs = Object.is; } if (newProxy === void 0) { newProxy = function newProxy(target, handler) { return new Proxy(target, handler); }; } if (canProxy === void 0) { canProxy = function canProxy(x) { return isObject(x) && !refSet.has(x) && (Array.isArray(x) || !(Symbol.iterator in x)) && !(x instanceof WeakMap) && !(x instanceof WeakSet) && !(x instanceof Error) && !(x instanceof Number) && !(x instanceof Date) && !(x instanceof String) && !(x instanceof RegExp) && !(x instanceof ArrayBuffer); }; } if (PROMISE_RESULT === void 0) { PROMISE_RESULT = process.env.NODE_ENV !== "production" ? Symbol('PROMISE_RESULT') : Symbol(); } if (PROMISE_ERROR === void 0) { PROMISE_ERROR = process.env.NODE_ENV !== "production" ? Symbol('PROMISE_ERROR') : Symbol(); } if (snapshotCache === void 0) { snapshotCache = new WeakMap(); } if (createSnapshot === void 0) { createSnapshot = function createSnapshot(version, target, receiver) { var cache = snapshotCache.get(receiver); if ((cache == null ? void 0 : cache[0]) === version) { return cache[1]; } var snapshot = Array.isArray(target) ? [] : Object.create(Object.getPrototypeOf(target)); proxyCompare.markToTrack(snapshot, true); snapshotCache.set(receiver, [version, snapshot]); Reflect.ownKeys(target).forEach(function (key) { var value = Reflect.get(target, key, receiver); if (refSet.has(value)) { proxyCompare.markToTrack(value, false); snapshot[key] = value; } else if (value instanceof Promise) { if (PROMISE_RESULT in value) { snapshot[key] = value[PROMISE_RESULT]; } else { var errorOrPromise = value[PROMISE_ERROR] || value; Object.defineProperty(snapshot, key, { get: function get() { if (PROMISE_RESULT in value) { return value[PROMISE_RESULT]; } throw errorOrPromise; } }); } } else if (value != null && value[LISTENERS]) { snapshot[key] = value[SNAPSHOT]; } else { snapshot[key] = value; } }); return Object.freeze(snapshot); }; } if (proxyCache === void 0) { proxyCache = new WeakMap(); } if (versionHolder === void 0) { versionHolder = [1]; } if (proxyFunction === void 0) { proxyFunction = function proxyFunction(initialObject) { if (!isObject(initialObject)) { throw new Error('object required'); } var found = proxyCache.get(initialObject); if (found) { return found; } var version = versionHolder[0]; var listeners = new Set(); var notifyUpdate = function notifyUpdate(op, nextVersion) { if (nextVersion === void 0) { nextVersion = ++versionHolder[0]; } if (version !== nextVersion) { version = nextVersion; listeners.forEach(function (listener) { return listener(op, nextVersion); }); } }; var propListeners = new Map(); var getPropListener = function getPropListener(prop) { var propListener = propListeners.get(prop); if (!propListener) { propListener = function propListener(op, nextVersion) { var newOp = [].concat(op); newOp[1] = [prop].concat(newOp[1]); notifyUpdate(newOp, nextVersion); }; propListeners.set(prop, propListener); } return propListener; }; var popPropListener = function popPropListener(prop) { var propListener = propListeners.get(prop); propListeners.delete(prop); return propListener; }; var baseObject = Array.isArray(initialObject) ? [] : Object.create(Object.getPrototypeOf(initialObject)); var handler = { get: function get(target, prop, receiver) { if (prop === VERSION) { return version; } if (prop === LISTENERS) { return listeners; } if (prop === SNAPSHOT) { return createSnapshot(version, target, receiver); } return Reflect.get(target, prop, receiver); }, deleteProperty: function deleteProperty(target, prop) { var prevValue = Reflect.get(target, prop); var childListeners = prevValue == null ? void 0 : prevValue[LISTENERS]; if (childListeners) { childListeners.delete(popPropListener(prop)); } var deleted = Reflect.deleteProperty(target, prop); if (deleted) { notifyUpdate(['delete', [prop], prevValue]); } return deleted; }, set: function set(target, prop, value, receiver) { var _Object$getOwnPropert, _value; var hasPrevValue = Reflect.has(target, prop); var prevValue = Reflect.get(target, prop, receiver); if (hasPrevValue && objectIs(prevValue, value)) { return true; } var childListeners = prevValue == null ? void 0 : prevValue[LISTENERS]; if (childListeners) { childListeners.delete(popPropListener(prop)); } if (isObject(value)) { value = proxyCompare.getUntracked(value) || value; } var nextValue; if ((_Object$getOwnPropert = Object.getOwnPropertyDescriptor(target, prop)) != null && _Object$getOwnPropert.set) { nextValue = value; } else if (value instanceof Promise) { nextValue = value.then(function (v) { nextValue[PROMISE_RESULT] = v; notifyUpdate(['resolve', [prop], v]); return v; }).catch(function (e) { nextValue[PROMISE_ERROR] = e; notifyUpdate(['reject', [prop], e]); }); } else if ((_value = value) != null && _value[LISTENERS]) { nextValue = value; nextValue[LISTENERS].add(getPropListener(prop)); } else if (canProxy(value)) { nextValue = proxy(value); nextValue[LISTENERS].add(getPropListener(prop)); } else { nextValue = value; } Reflect.set(target, prop, nextValue, receiver); notifyUpdate(['set', [prop], value, prevValue]); return true; } }; var proxyObject = newProxy(baseObject, handler); proxyCache.set(initialObject, proxyObject); Reflect.ownKeys(initialObject).forEach(function (key) { var desc = Object.getOwnPropertyDescriptor(initialObject, key); if (desc.get || desc.set) { Object.defineProperty(baseObject, key, desc); } else { proxyObject[key] = initialObject[key]; } }); return proxyObject; }; } return [proxyFunction, refSet, VERSION, LISTENERS, SNAPSHOT, objectIs, newProxy, canProxy, PROMISE_RESULT, PROMISE_ERROR, snapshotCache, createSnapshot, proxyCache, versionHolder]; }; var _buildProxyFunction = buildProxyFunction(), proxyFunction = _buildProxyFunction[0]; function proxy(initialObject) { if (initialObject === void 0) { initialObject = {}; } return proxyFunction(initialObject); } function getVersion(proxyObject) { return isObject(proxyObject) ? proxyObject[VERSION] : undefined; } function subscribe(proxyObject, callback, notifyInSync) { if (process.env.NODE_ENV !== "production" && !(proxyObject != null && proxyObject[LISTENERS])) { console.warn('Please use proxy object'); } var promise; var ops = []; var listener = function listener(op) { ops.push(op); if (notifyInSync) { callback(ops.splice(0)); return; } if (!promise) { promise = Promise.resolve().then(function () { promise = undefined; callback(ops.splice(0)); }); } }; proxyObject[LISTENERS].add(listener); return function () { proxyObject[LISTENERS].delete(listener); }; } function snapshot(proxyObject) { if (process.env.NODE_ENV !== "production" && !(proxyObject != null && proxyObject[SNAPSHOT])) { console.warn('Please use proxy object'); } return proxyObject[SNAPSHOT]; } function ref(obj) { refSet.add(obj); return obj; } var unstable_buildProxyFunction = buildProxyFunction; exports.getVersion = getVersion; exports.proxy = proxy; exports.ref = ref; exports.snapshot = snapshot; exports.subscribe = subscribe; exports.unstable_buildProxyFunction = unstable_buildProxyFunction;