summaryrefslogtreecommitdiff
path: root/node_modules/ts-mixer/dist/cjs/util.js
diff options
context:
space:
mode:
authorsowgro <tpoke.ferrari@gmail.com>2023-09-02 19:12:47 -0400
committersowgro <tpoke.ferrari@gmail.com>2023-09-02 19:12:47 -0400
commite4450c8417624b71d779cb4f41692538f9165e10 (patch)
treeb70826542223ecdf8a7a259f61b0a1abb8a217d8 /node_modules/ts-mixer/dist/cjs/util.js
downloadsowbot3-e4450c8417624b71d779cb4f41692538f9165e10.tar.gz
sowbot3-e4450c8417624b71d779cb4f41692538f9165e10.tar.bz2
sowbot3-e4450c8417624b71d779cb4f41692538f9165e10.zip
first commit
Diffstat (limited to 'node_modules/ts-mixer/dist/cjs/util.js')
-rw-r--r--node_modules/ts-mixer/dist/cjs/util.js85
1 files changed, 85 insertions, 0 deletions
diff --git a/node_modules/ts-mixer/dist/cjs/util.js b/node_modules/ts-mixer/dist/cjs/util.js
new file mode 100644
index 0000000..5151696
--- /dev/null
+++ b/node_modules/ts-mixer/dist/cjs/util.js
@@ -0,0 +1,85 @@
+"use strict";
+Object.defineProperty(exports, "__esModule", { value: true });
+exports.flatten = exports.unique = exports.hardMixProtos = exports.nearestCommonProto = exports.protoChain = exports.copyProps = void 0;
+/**
+ * Utility function that works like `Object.apply`, but copies getters and setters properly as well. Additionally gives
+ * the option to exclude properties by name.
+ */
+const copyProps = (dest, src, exclude = []) => {
+ const props = Object.getOwnPropertyDescriptors(src);
+ for (let prop of exclude)
+ delete props[prop];
+ Object.defineProperties(dest, props);
+};
+exports.copyProps = copyProps;
+/**
+ * Returns the full chain of prototypes up until Object.prototype given a starting object. The order of prototypes will
+ * be closest to farthest in the chain.
+ */
+const protoChain = (obj, currentChain = [obj]) => {
+ const proto = Object.getPrototypeOf(obj);
+ if (proto === null)
+ return currentChain;
+ return (0, exports.protoChain)(proto, [...currentChain, proto]);
+};
+exports.protoChain = protoChain;
+/**
+ * Identifies the nearest ancestor common to all the given objects in their prototype chains. For most unrelated
+ * objects, this function should return Object.prototype.
+ */
+const nearestCommonProto = (...objs) => {
+ if (objs.length === 0)
+ return undefined;
+ let commonProto = undefined;
+ const protoChains = objs.map(obj => (0, exports.protoChain)(obj));
+ while (protoChains.every(protoChain => protoChain.length > 0)) {
+ const protos = protoChains.map(protoChain => protoChain.pop());
+ const potentialCommonProto = protos[0];
+ if (protos.every(proto => proto === potentialCommonProto))
+ commonProto = potentialCommonProto;
+ else
+ break;
+ }
+ return commonProto;
+};
+exports.nearestCommonProto = nearestCommonProto;
+/**
+ * Creates a new prototype object that is a mixture of the given prototypes. The mixing is achieved by first
+ * identifying the nearest common ancestor and using it as the prototype for a new object. Then all properties/methods
+ * downstream of this prototype (ONLY downstream) are copied into the new object.
+ *
+ * The resulting prototype is more performant than softMixProtos(...), as well as ES5 compatible. However, it's not as
+ * flexible as updates to the source prototypes aren't captured by the mixed result. See softMixProtos for why you may
+ * want to use that instead.
+ */
+const hardMixProtos = (ingredients, constructor, exclude = []) => {
+ var _a;
+ const base = (_a = (0, exports.nearestCommonProto)(...ingredients)) !== null && _a !== void 0 ? _a : Object.prototype;
+ const mixedProto = Object.create(base);
+ // Keeps track of prototypes we've already visited to avoid copying the same properties multiple times. We init the
+ // list with the proto chain below the nearest common ancestor because we don't want any of those methods mixed in
+ // when they will already be accessible via prototype access.
+ const visitedProtos = (0, exports.protoChain)(base);
+ for (let prototype of ingredients) {
+ let protos = (0, exports.protoChain)(prototype);
+ // Apply the prototype chain in reverse order so that old methods don't override newer ones.
+ for (let i = protos.length - 1; i >= 0; i--) {
+ let newProto = protos[i];
+ if (visitedProtos.indexOf(newProto) === -1) {
+ (0, exports.copyProps)(mixedProto, newProto, ['constructor', ...exclude]);
+ visitedProtos.push(newProto);
+ }
+ }
+ }
+ mixedProto.constructor = constructor;
+ return mixedProto;
+};
+exports.hardMixProtos = hardMixProtos;
+const unique = (arr) => arr.filter((e, i) => arr.indexOf(e) == i);
+exports.unique = unique;
+const flatten = (arr) => arr.length === 0
+ ? []
+ : arr.length === 1
+ ? arr[0]
+ : arr.reduce((a1, a2) => [...a1, ...a2]);
+exports.flatten = flatten;