tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

reselect.js (9986B)


      1 (function (global, factory) {
      2  typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports) :
      3  typeof define === 'function' && define.amd ? define(['exports'], factory) :
      4  (global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.Reselect = {}));
      5 })(this, (function (exports) { 'use strict';
      6 
      7  // Cache implementation based on Erik Rasmussen's `lru-memoize`:
      8  // https://github.com/erikras/lru-memoize
      9  var NOT_FOUND = 'NOT_FOUND';
     10 
     11  function createSingletonCache(equals) {
     12    var entry;
     13    return {
     14      get: function get(key) {
     15        if (entry && equals(entry.key, key)) {
     16          return entry.value;
     17        }
     18 
     19        return NOT_FOUND;
     20      },
     21      put: function put(key, value) {
     22        entry = {
     23          key: key,
     24          value: value
     25        };
     26      },
     27      getEntries: function getEntries() {
     28        return entry ? [entry] : [];
     29      },
     30      clear: function clear() {
     31        entry = undefined;
     32      }
     33    };
     34  }
     35 
     36  function createLruCache(maxSize, equals) {
     37    var entries = [];
     38 
     39    function get(key) {
     40      var cacheIndex = entries.findIndex(function (entry) {
     41        return equals(key, entry.key);
     42      }); // We found a cached entry
     43 
     44      if (cacheIndex > -1) {
     45        var entry = entries[cacheIndex]; // Cached entry not at top of cache, move it to the top
     46 
     47        if (cacheIndex > 0) {
     48          entries.splice(cacheIndex, 1);
     49          entries.unshift(entry);
     50        }
     51 
     52        return entry.value;
     53      } // No entry found in cache, return sentinel
     54 
     55 
     56      return NOT_FOUND;
     57    }
     58 
     59    function put(key, value) {
     60      if (get(key) === NOT_FOUND) {
     61        // TODO Is unshift slow?
     62        entries.unshift({
     63          key: key,
     64          value: value
     65        });
     66 
     67        if (entries.length > maxSize) {
     68          entries.pop();
     69        }
     70      }
     71    }
     72 
     73    function getEntries() {
     74      return entries;
     75    }
     76 
     77    function clear() {
     78      entries = [];
     79    }
     80 
     81    return {
     82      get: get,
     83      put: put,
     84      getEntries: getEntries,
     85      clear: clear
     86    };
     87  }
     88 
     89  var defaultEqualityCheck = function defaultEqualityCheck(a, b) {
     90    return a === b;
     91  };
     92  function createCacheKeyComparator(equalityCheck) {
     93    return function areArgumentsShallowlyEqual(prev, next) {
     94      if (prev === null || next === null || prev.length !== next.length) {
     95        return false;
     96      } // Do this in a for loop (and not a `forEach` or an `every`) so we can determine equality as fast as possible.
     97 
     98 
     99      var length = prev.length;
    100 
    101      for (var i = 0; i < length; i++) {
    102        if (!equalityCheck(prev[i], next[i])) {
    103          return false;
    104        }
    105      }
    106 
    107      return true;
    108    };
    109  }
    110  // defaultMemoize now supports a configurable cache size with LRU behavior,
    111  // and optional comparison of the result value with existing values
    112  function defaultMemoize(func, equalityCheckOrOptions) {
    113    var providedOptions = typeof equalityCheckOrOptions === 'object' ? equalityCheckOrOptions : {
    114      equalityCheck: equalityCheckOrOptions
    115    };
    116    var _providedOptions$equa = providedOptions.equalityCheck,
    117        equalityCheck = _providedOptions$equa === void 0 ? defaultEqualityCheck : _providedOptions$equa,
    118        _providedOptions$maxS = providedOptions.maxSize,
    119        maxSize = _providedOptions$maxS === void 0 ? 1 : _providedOptions$maxS,
    120        resultEqualityCheck = providedOptions.resultEqualityCheck;
    121    var comparator = createCacheKeyComparator(equalityCheck);
    122    var cache = maxSize === 1 ? createSingletonCache(comparator) : createLruCache(maxSize, comparator); // we reference arguments instead of spreading them for performance reasons
    123 
    124    function memoized() {
    125      var value = cache.get(arguments);
    126 
    127      if (value === NOT_FOUND) {
    128        // @ts-ignore
    129        value = func.apply(null, arguments);
    130 
    131        if (resultEqualityCheck) {
    132          var entries = cache.getEntries();
    133          var matchingEntry = entries.find(function (entry) {
    134            return resultEqualityCheck(entry.value, value);
    135          });
    136 
    137          if (matchingEntry) {
    138            value = matchingEntry.value;
    139          }
    140        }
    141 
    142        cache.put(arguments, value);
    143      }
    144 
    145      return value;
    146    }
    147 
    148    memoized.clearCache = function () {
    149      return cache.clear();
    150    };
    151 
    152    return memoized;
    153  }
    154 
    155  function getDependencies(funcs) {
    156    var dependencies = Array.isArray(funcs[0]) ? funcs[0] : funcs;
    157 
    158    if (!dependencies.every(function (dep) {
    159      return typeof dep === 'function';
    160    })) {
    161      var dependencyTypes = dependencies.map(function (dep) {
    162        return typeof dep === 'function' ? "function " + (dep.name || 'unnamed') + "()" : typeof dep;
    163      }).join(', ');
    164      throw new Error("createSelector expects all input-selectors to be functions, but received the following types: [" + dependencyTypes + "]");
    165    }
    166 
    167    return dependencies;
    168  }
    169 
    170  function createSelectorCreator(memoize) {
    171    for (var _len = arguments.length, memoizeOptionsFromArgs = new Array(_len > 1 ? _len - 1 : 0), _key = 1; _key < _len; _key++) {
    172      memoizeOptionsFromArgs[_key - 1] = arguments[_key];
    173    }
    174 
    175    var createSelector = function createSelector() {
    176      for (var _len2 = arguments.length, funcs = new Array(_len2), _key2 = 0; _key2 < _len2; _key2++) {
    177        funcs[_key2] = arguments[_key2];
    178      }
    179 
    180      var _recomputations = 0;
    181 
    182      var _lastResult; // Due to the intricacies of rest params, we can't do an optional arg after `...funcs`.
    183      // So, start by declaring the default value here.
    184      // (And yes, the words 'memoize' and 'options' appear too many times in this next sequence.)
    185 
    186 
    187      var directlyPassedOptions = {
    188        memoizeOptions: undefined
    189      }; // Normally, the result func or "output selector" is the last arg
    190 
    191      var resultFunc = funcs.pop(); // If the result func is actually an _object_, assume it's our options object
    192 
    193      if (typeof resultFunc === 'object') {
    194        directlyPassedOptions = resultFunc; // and pop the real result func off
    195 
    196        resultFunc = funcs.pop();
    197      }
    198 
    199      if (typeof resultFunc !== 'function') {
    200        throw new Error("createSelector expects an output function after the inputs, but received: [" + typeof resultFunc + "]");
    201      } // Determine which set of options we're using. Prefer options passed directly,
    202      // but fall back to options given to createSelectorCreator.
    203 
    204 
    205      var _directlyPassedOption = directlyPassedOptions,
    206          _directlyPassedOption2 = _directlyPassedOption.memoizeOptions,
    207          memoizeOptions = _directlyPassedOption2 === void 0 ? memoizeOptionsFromArgs : _directlyPassedOption2; // Simplifying assumption: it's unlikely that the first options arg of the provided memoizer
    208      // is an array. In most libs I've looked at, it's an equality function or options object.
    209      // Based on that, if `memoizeOptions` _is_ an array, we assume it's a full
    210      // user-provided array of options. Otherwise, it must be just the _first_ arg, and so
    211      // we wrap it in an array so we can apply it.
    212 
    213      var finalMemoizeOptions = Array.isArray(memoizeOptions) ? memoizeOptions : [memoizeOptions];
    214      var dependencies = getDependencies(funcs);
    215      var memoizedResultFunc = memoize.apply(void 0, [function () {
    216        _recomputations++; // apply arguments instead of spreading for performance.
    217 
    218        return resultFunc.apply(null, arguments);
    219      }].concat(finalMemoizeOptions)); // If a selector is called with the exact same arguments we don't need to traverse our dependencies again.
    220 
    221      var selector = memoize(function () {
    222        var params = [];
    223        var length = dependencies.length;
    224 
    225        for (var i = 0; i < length; i++) {
    226          // apply arguments instead of spreading and mutate a local list of params for performance.
    227          // @ts-ignore
    228          params.push(dependencies[i].apply(null, arguments));
    229        } // apply arguments instead of spreading for performance.
    230 
    231 
    232        _lastResult = memoizedResultFunc.apply(null, params);
    233        return _lastResult;
    234      });
    235      Object.assign(selector, {
    236        resultFunc: resultFunc,
    237        memoizedResultFunc: memoizedResultFunc,
    238        dependencies: dependencies,
    239        lastResult: function lastResult() {
    240          return _lastResult;
    241        },
    242        recomputations: function recomputations() {
    243          return _recomputations;
    244        },
    245        resetRecomputations: function resetRecomputations() {
    246          return _recomputations = 0;
    247        }
    248      });
    249      return selector;
    250    }; // @ts-ignore
    251 
    252 
    253    return createSelector;
    254  }
    255  var createSelector = /* #__PURE__ */createSelectorCreator(defaultMemoize);
    256  // Manual definition of state and output arguments
    257  var createStructuredSelector = function createStructuredSelector(selectors, selectorCreator) {
    258    if (selectorCreator === void 0) {
    259      selectorCreator = createSelector;
    260    }
    261 
    262    if (typeof selectors !== 'object') {
    263      throw new Error('createStructuredSelector expects first argument to be an object ' + ("where each property is a selector, instead received a " + typeof selectors));
    264    }
    265 
    266    var objectKeys = Object.keys(selectors);
    267    var resultSelector = selectorCreator( // @ts-ignore
    268    objectKeys.map(function (key) {
    269      return selectors[key];
    270    }), function () {
    271      for (var _len3 = arguments.length, values = new Array(_len3), _key3 = 0; _key3 < _len3; _key3++) {
    272        values[_key3] = arguments[_key3];
    273      }
    274 
    275      return values.reduce(function (composition, value, index) {
    276        composition[objectKeys[index]] = value;
    277        return composition;
    278      }, {});
    279    });
    280    return resultSelector;
    281  };
    282 
    283  exports.createSelector = createSelector;
    284  exports.createSelectorCreator = createSelectorCreator;
    285  exports.createStructuredSelector = createStructuredSelector;
    286  exports.defaultEqualityCheck = defaultEqualityCheck;
    287  exports.defaultMemoize = defaultMemoize;
    288 
    289  Object.defineProperty(exports, '__esModule', { value: true });
    290 
    291 }));