@vertexvis/utils 0.24.5-canary.6 → 1.0.0-testing.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,27 +1,29 @@
1
1
  import { __awaiter, __generator, __asyncValues, __assign, __extends, __read, __spreadArray, __values } from 'tslib';
2
- import crypto from 'crypto';
2
+ import fastDeepEqual from 'fast-deep-equal';
3
+ import isSimpleObject from 'is-plain-object';
4
+ import { v4 } from 'uuid';
3
5
 
4
- /**
5
- * Adds a listener to the given `target`, and returns a promise that
6
- * resolves with the first event emitted of the given `type`.
7
- *
8
- * @param target The target to add an event listener to.
9
- * @param type The event type to listen for.
10
- * @param opts Options to pass to `addEventListener`.
11
- * @returns A promise that resolves with the first event emitted of `type`.
12
- */
13
- function once(target, type, opts) {
14
- return __awaiter(this, void 0, void 0, function () {
15
- return __generator(this, function (_a) {
16
- return [2 /*return*/, new Promise(function (resolve) {
17
- function handler(event) {
18
- target.removeEventListener(type, handler);
19
- resolve(event);
20
- }
21
- target.addEventListener(type, handler, opts);
22
- })];
23
- });
24
- });
6
+ /**
7
+ * Adds a listener to the given `target`, and returns a promise that
8
+ * resolves with the first event emitted of the given `type`.
9
+ *
10
+ * @param target The target to add an event listener to.
11
+ * @param type The event type to listen for.
12
+ * @param opts Options to pass to `addEventListener`.
13
+ * @returns A promise that resolves with the first event emitted of `type`.
14
+ */
15
+ function once(target, type, opts) {
16
+ return __awaiter(this, void 0, Promise, function () {
17
+ return __generator(this, function (_a) {
18
+ return [2 /*return*/, new Promise(function (resolve) {
19
+ function handler(event) {
20
+ target.removeEventListener(type, handler);
21
+ resolve(event);
22
+ }
23
+ target.addEventListener(type, handler, opts);
24
+ })];
25
+ });
26
+ });
25
27
  }
26
28
 
27
29
  var eventTargets = /*#__PURE__*/Object.freeze({
@@ -29,206 +31,210 @@ var eventTargets = /*#__PURE__*/Object.freeze({
29
31
  once: once
30
32
  });
31
33
 
32
- /**
33
- * Converts an async generator to an array of results.
34
- *
35
- * @param generator The generator to convert.
36
- * @returns A promise that resolves with an array of results yielded by the
37
- * generator.
38
- */
39
- function asArray(generator) {
40
- var generator_1, generator_1_1;
41
- var e_1, _a;
42
- return __awaiter(this, void 0, void 0, function () {
43
- var res, next, e_1_1;
44
- return __generator(this, function (_b) {
45
- switch (_b.label) {
46
- case 0:
47
- res = [];
48
- _b.label = 1;
49
- case 1:
50
- _b.trys.push([1, 6, 7, 12]);
51
- generator_1 = __asyncValues(generator);
52
- _b.label = 2;
53
- case 2: return [4 /*yield*/, generator_1.next()];
54
- case 3:
55
- if (!(generator_1_1 = _b.sent(), !generator_1_1.done)) return [3 /*break*/, 5];
56
- next = generator_1_1.value;
57
- res.push(next);
58
- _b.label = 4;
59
- case 4: return [3 /*break*/, 2];
60
- case 5: return [3 /*break*/, 12];
61
- case 6:
62
- e_1_1 = _b.sent();
63
- e_1 = { error: e_1_1 };
64
- return [3 /*break*/, 12];
65
- case 7:
66
- _b.trys.push([7, , 10, 11]);
67
- if (!(generator_1_1 && !generator_1_1.done && (_a = generator_1.return))) return [3 /*break*/, 9];
68
- return [4 /*yield*/, _a.call(generator_1)];
69
- case 8:
70
- _b.sent();
71
- _b.label = 9;
72
- case 9: return [3 /*break*/, 11];
73
- case 10:
74
- if (e_1) throw e_1.error;
75
- return [7 /*endfinally*/];
76
- case 11: return [7 /*endfinally*/];
77
- case 12: return [2 /*return*/, res];
78
- }
79
- });
80
- });
81
- }
82
- function delay() {
83
- var args = [];
84
- for (var _i = 0; _i < arguments.length; _i++) {
85
- args[_i] = arguments[_i];
86
- }
87
- return __awaiter(this, void 0, void 0, function () {
88
- var ms, promise, delay_1;
89
- return __generator(this, function (_a) {
90
- switch (_a.label) {
91
- case 0:
92
- ms = args[0];
93
- if (!(typeof ms === 'number')) return [3 /*break*/, 4];
94
- promise = args[1];
95
- delay_1 = new Promise(function (resolve) { return setTimeout(resolve, ms); });
96
- if (!(promise != null)) return [3 /*break*/, 2];
97
- return [4 /*yield*/, delay_1];
98
- case 1:
99
- _a.sent();
100
- return [2 /*return*/, promise];
101
- case 2: return [2 /*return*/, delay_1];
102
- case 3: return [3 /*break*/, 5];
103
- case 4: return [2 /*return*/, Promise.reject(new TypeError('First argument to `delay` must be a number'))];
104
- case 5: return [2 /*return*/];
105
- }
106
- });
107
- });
108
- }
109
- function timeout() {
110
- var args = [];
111
- for (var _i = 0; _i < arguments.length; _i++) {
112
- args[_i] = arguments[_i];
113
- }
114
- return __awaiter(this, void 0, void 0, function () {
115
- var ms, promise, timer_1, timeout_1, res;
116
- return __generator(this, function (_a) {
117
- switch (_a.label) {
118
- case 0:
119
- ms = args[0];
120
- if (!(typeof ms === 'number')) return [3 /*break*/, 4];
121
- promise = args[1];
122
- timeout_1 = new Promise(function (_, reject) {
123
- timer_1 = setTimeout(function () { return reject(new Error("Promise timed out after ".concat(ms, "ms"))); }, ms);
124
- });
125
- if (!(promise != null)) return [3 /*break*/, 2];
126
- return [4 /*yield*/, Promise.race([promise, timeout_1])];
127
- case 1:
128
- res = _a.sent();
129
- clearTimeout(timer_1);
130
- return [2 /*return*/, res];
131
- case 2: return [2 /*return*/, timeout_1];
132
- case 3: return [3 /*break*/, 5];
133
- case 4: return [2 /*return*/, Promise.reject('First argument to `timeout` must be a number')];
134
- case 5: return [2 /*return*/];
135
- }
136
- });
137
- });
138
- }
139
- /**
140
- * Executes and reattempts execution of an asynchronous function if it throws an
141
- * error. By default, this function will only retry once and reexecute
142
- * immediately after the previous execution throws. You can configure the number
143
- * of retry attempts and delays with the `maxRetries` and `delaysInMs` options.
144
- *
145
- * The `delaysInMs` is an array of delays in milliseconds for each retry
146
- * attempt. If there are more retry attempts than delays, the last delay will be
147
- * used.
148
- *
149
- * @param process The process to execute.
150
- * @param opts Options to configure retry behavior.
151
- * @returns A promise that resolves with a successful value, or the original
152
- * rejected value if the process fails.
153
- */
154
- function retry(process, opts) {
155
- if (opts === void 0) { opts = {}; }
156
- return __awaiter(this, void 0, void 0, function () {
157
- function execute(attempt, process, opts) {
158
- return __awaiter(this, void 0, void 0, function () {
159
- var _a, delaysInMs, _b, maxRetries, delayInMs, e_2;
160
- return __generator(this, function (_c) {
161
- switch (_c.label) {
162
- case 0:
163
- _a = opts.delaysInMs, delaysInMs = _a === void 0 ? [] : _a, _b = opts.maxRetries, maxRetries = _b === void 0 ? 1 : _b;
164
- _c.label = 1;
165
- case 1:
166
- _c.trys.push([1, 4, , 8]);
167
- delayInMs = attempt === 0 || delaysInMs.length === 0
168
- ? 0
169
- : delaysInMs[Math.min(attempt - 1, delaysInMs.length - 1)];
170
- return [4 /*yield*/, delay(delayInMs)];
171
- case 2:
172
- _c.sent();
173
- return [4 /*yield*/, process()];
174
- case 3: return [2 /*return*/, _c.sent()];
175
- case 4:
176
- e_2 = _c.sent();
177
- if (!(attempt < maxRetries)) return [3 /*break*/, 6];
178
- return [4 /*yield*/, execute(attempt + 1, process, opts)];
179
- case 5: return [2 /*return*/, _c.sent()];
180
- case 6: throw e_2;
181
- case 7: return [3 /*break*/, 8];
182
- case 8: return [2 /*return*/];
183
- }
184
- });
185
- });
186
- }
187
- return __generator(this, function (_a) {
188
- return [2 /*return*/, execute(0, process, opts)];
189
- });
190
- });
191
- }
192
- /**
193
- * Returns a promise that either resolves with the result of `promise`, or a
194
- * value that indicates the execution was aborted.
195
- *
196
- * **Note:** Because Promises in JS cannot be canceled, an abort signal will not
197
- * cancel the execution of the promise.
198
- *
199
- * @param signal A signal that communicates the process should be aborted.
200
- * @param promise A promise who's value will be returned if not aborted.
201
- * @returns A value indicating if the process was aborted, or the value of
202
- * `promise`.
203
- */
204
- function abort(signal, promise) {
205
- return __awaiter(this, void 0, void 0, function () {
206
- var controller, pendingAbort, result;
207
- return __generator(this, function (_a) {
208
- switch (_a.label) {
209
- case 0:
210
- controller = new AbortController();
211
- pendingAbort = once(signal, 'abort', { signal: controller.signal });
212
- return [4 /*yield*/, Promise.race([promise, pendingAbort])];
213
- case 1:
214
- result = _a.sent();
215
- if (isAbortEvent(result)) {
216
- return [2 /*return*/, { aborted: true }];
217
- }
218
- else {
219
- controller.abort();
220
- return [2 /*return*/, { aborted: false, result: result }];
221
- }
222
- }
223
- });
224
- });
225
- }
226
- function isAbortEvent(obj) {
227
- if (obj instanceof Event) {
228
- return obj.type === 'abort';
229
- }
230
- else
231
- return false;
34
+ /**
35
+ * Converts an async generator to an array of results.
36
+ *
37
+ * @param generator The generator to convert.
38
+ * @returns A promise that resolves with an array of results yielded by the
39
+ * generator.
40
+ */
41
+ function asArray(generator) {
42
+ return __awaiter(this, void 0, Promise, function () {
43
+ var res, next, e_1_1;
44
+ var _a, generator_1, generator_1_1;
45
+ var _b, e_1, _c, _d;
46
+ return __generator(this, function (_e) {
47
+ switch (_e.label) {
48
+ case 0:
49
+ res = [];
50
+ _e.label = 1;
51
+ case 1:
52
+ _e.trys.push([1, 6, 7, 12]);
53
+ _a = true, generator_1 = __asyncValues(generator);
54
+ _e.label = 2;
55
+ case 2: return [4 /*yield*/, generator_1.next()];
56
+ case 3:
57
+ if (!(generator_1_1 = _e.sent(), _b = generator_1_1.done, !_b)) return [3 /*break*/, 5];
58
+ _d = generator_1_1.value;
59
+ _a = false;
60
+ next = _d;
61
+ res.push(next);
62
+ _e.label = 4;
63
+ case 4:
64
+ _a = true;
65
+ return [3 /*break*/, 2];
66
+ case 5: return [3 /*break*/, 12];
67
+ case 6:
68
+ e_1_1 = _e.sent();
69
+ e_1 = { error: e_1_1 };
70
+ return [3 /*break*/, 12];
71
+ case 7:
72
+ _e.trys.push([7, , 10, 11]);
73
+ if (!(!_a && !_b && (_c = generator_1.return))) return [3 /*break*/, 9];
74
+ return [4 /*yield*/, _c.call(generator_1)];
75
+ case 8:
76
+ _e.sent();
77
+ _e.label = 9;
78
+ case 9: return [3 /*break*/, 11];
79
+ case 10:
80
+ if (e_1) throw e_1.error;
81
+ return [7 /*endfinally*/];
82
+ case 11: return [7 /*endfinally*/];
83
+ case 12: return [2 /*return*/, res];
84
+ }
85
+ });
86
+ });
87
+ }
88
+ function delay() {
89
+ var args = [];
90
+ for (var _i = 0; _i < arguments.length; _i++) {
91
+ args[_i] = arguments[_i];
92
+ }
93
+ return __awaiter(this, void 0, Promise, function () {
94
+ var ms, promise, delay_1;
95
+ return __generator(this, function (_a) {
96
+ switch (_a.label) {
97
+ case 0:
98
+ ms = args[0];
99
+ if (!(typeof ms === 'number')) return [3 /*break*/, 4];
100
+ promise = args[1];
101
+ delay_1 = new Promise(function (resolve) { return setTimeout(resolve, ms); });
102
+ if (!(promise != null)) return [3 /*break*/, 2];
103
+ return [4 /*yield*/, delay_1];
104
+ case 1:
105
+ _a.sent();
106
+ return [2 /*return*/, promise];
107
+ case 2: return [2 /*return*/, delay_1];
108
+ case 3: return [3 /*break*/, 5];
109
+ case 4: return [2 /*return*/, Promise.reject(new TypeError('First argument to `delay` must be a number'))];
110
+ case 5: return [2 /*return*/];
111
+ }
112
+ });
113
+ });
114
+ }
115
+ function timeout() {
116
+ var args = [];
117
+ for (var _i = 0; _i < arguments.length; _i++) {
118
+ args[_i] = arguments[_i];
119
+ }
120
+ return __awaiter(this, void 0, Promise, function () {
121
+ var ms, promise, timer_1, timeout_1, res;
122
+ return __generator(this, function (_a) {
123
+ switch (_a.label) {
124
+ case 0:
125
+ ms = args[0];
126
+ if (!(typeof ms === 'number')) return [3 /*break*/, 4];
127
+ promise = args[1];
128
+ timeout_1 = new Promise(function (_, reject) {
129
+ timer_1 = setTimeout(function () { return reject(new Error("Promise timed out after ".concat(ms, "ms"))); }, ms);
130
+ });
131
+ if (!(promise != null)) return [3 /*break*/, 2];
132
+ return [4 /*yield*/, Promise.race([promise, timeout_1])];
133
+ case 1:
134
+ res = _a.sent();
135
+ clearTimeout(timer_1);
136
+ return [2 /*return*/, res];
137
+ case 2: return [2 /*return*/, timeout_1];
138
+ case 3: return [3 /*break*/, 5];
139
+ case 4: return [2 /*return*/, Promise.reject('First argument to `timeout` must be a number')];
140
+ case 5: return [2 /*return*/];
141
+ }
142
+ });
143
+ });
144
+ }
145
+ /**
146
+ * Executes and reattempts execution of an asynchronous function if it throws an
147
+ * error. By default, this function will only retry once and reexecute
148
+ * immediately after the previous execution throws. You can configure the number
149
+ * of retry attempts and delays with the `maxRetries` and `delaysInMs` options.
150
+ *
151
+ * The `delaysInMs` is an array of delays in milliseconds for each retry
152
+ * attempt. If there are more retry attempts than delays, the last delay will be
153
+ * used.
154
+ *
155
+ * @param process The process to execute.
156
+ * @param opts Options to configure retry behavior.
157
+ * @returns A promise that resolves with a successful value, or the original
158
+ * rejected value if the process fails.
159
+ */
160
+ function retry(process_1) {
161
+ return __awaiter(this, arguments, Promise, function (process, opts) {
162
+ function execute(attempt, process, opts) {
163
+ return __awaiter(this, void 0, Promise, function () {
164
+ var _a, delaysInMs, _b, maxRetries, delayInMs, e_2;
165
+ return __generator(this, function (_c) {
166
+ switch (_c.label) {
167
+ case 0:
168
+ _a = opts.delaysInMs, delaysInMs = _a === void 0 ? [] : _a, _b = opts.maxRetries, maxRetries = _b === void 0 ? 1 : _b;
169
+ _c.label = 1;
170
+ case 1:
171
+ _c.trys.push([1, 4, , 8]);
172
+ delayInMs = attempt === 0 || delaysInMs.length === 0
173
+ ? 0
174
+ : delaysInMs[Math.min(attempt - 1, delaysInMs.length - 1)];
175
+ return [4 /*yield*/, delay(delayInMs)];
176
+ case 2:
177
+ _c.sent();
178
+ return [4 /*yield*/, process()];
179
+ case 3: return [2 /*return*/, _c.sent()];
180
+ case 4:
181
+ e_2 = _c.sent();
182
+ if (!(attempt < maxRetries)) return [3 /*break*/, 6];
183
+ return [4 /*yield*/, execute(attempt + 1, process, opts)];
184
+ case 5: return [2 /*return*/, _c.sent()];
185
+ case 6: throw e_2;
186
+ case 7: return [3 /*break*/, 8];
187
+ case 8: return [2 /*return*/];
188
+ }
189
+ });
190
+ });
191
+ }
192
+ if (opts === void 0) { opts = {}; }
193
+ return __generator(this, function (_a) {
194
+ return [2 /*return*/, execute(0, process, opts)];
195
+ });
196
+ });
197
+ }
198
+ /**
199
+ * Returns a promise that either resolves with the result of `promise`, or a
200
+ * value that indicates the execution was aborted.
201
+ *
202
+ * **Note:** Because Promises in JS cannot be canceled, an abort signal will not
203
+ * cancel the execution of the promise.
204
+ *
205
+ * @param signal A signal that communicates the process should be aborted.
206
+ * @param promise A promise who's value will be returned if not aborted.
207
+ * @returns A value indicating if the process was aborted, or the value of
208
+ * `promise`.
209
+ */
210
+ function abort(signal, promise) {
211
+ return __awaiter(this, void 0, Promise, function () {
212
+ var controller, pendingAbort, result;
213
+ return __generator(this, function (_a) {
214
+ switch (_a.label) {
215
+ case 0:
216
+ controller = new AbortController();
217
+ pendingAbort = once(signal, 'abort', { signal: controller.signal });
218
+ return [4 /*yield*/, Promise.race([promise, pendingAbort])];
219
+ case 1:
220
+ result = _a.sent();
221
+ if (isAbortEvent(result)) {
222
+ return [2 /*return*/, { aborted: true }];
223
+ }
224
+ else {
225
+ controller.abort();
226
+ return [2 /*return*/, { aborted: false, result: result }];
227
+ }
228
+ }
229
+ });
230
+ });
231
+ }
232
+ function isAbortEvent(obj) {
233
+ if (obj instanceof Event) {
234
+ return obj.type === 'abort';
235
+ }
236
+ else
237
+ return false;
232
238
  }
233
239
 
234
240
  var async = /*#__PURE__*/Object.freeze({
@@ -240,48 +246,48 @@ var async = /*#__PURE__*/Object.freeze({
240
246
  abort: abort
241
247
  });
242
248
 
243
- /**
244
- * Returns a new `BinaryReader` for an `ArrayBuffer`.
245
- */
246
- var fromArrayBuffer = function (buffer) {
247
- return { offset: 0, data: new DataView(buffer) };
248
- };
249
- /**
250
- * Returns a `BinaryReader` that contains the read Int32 value at the given
251
- * reader's offset. The returned reader will have its offset adjusted so it can
252
- * be passed to the next helper.
253
- */
254
- var readInt32 = function (reader) {
255
- var value = reader.data.getInt32(reader.offset);
256
- return __assign(__assign({}, reader), { offset: reader.offset + 4, value: value });
257
- };
258
- /**
259
- * Returns a `BinaryReader` that contains the read UTF-8 string at the given
260
- * reader's offset. The returned reader will have its offset adjusted so it can
261
- * be passed to the next helper.
262
- */
263
- var readUtf8String = function (length, reader) {
264
- var value = String.fromCharCode.apply(null, Array.from(new Uint8Array(reader.data.buffer, reader.offset, length)));
265
- return __assign(__assign({}, reader), { offset: reader.offset + length, value: value });
266
- };
267
- /**
268
- * Returns a `BinaryReader` that contains the a signed `Int8Array` start from
269
- * the given reader's offset to the given length. The returned reader will have
270
- * its offset adjusted so it can be passed to the next helper.
271
- */
272
- var readInt8Array = function (length, reader) {
273
- var value = new Int8Array(reader.data.buffer, reader.offset, length);
274
- return __assign(__assign({}, reader), { offset: reader.offset + length, value: value });
275
- };
276
- /**
277
- * Returns a `BinaryReader` that contains the a signed `Int8Array` sliced from
278
- * the start of the reader's offset to offset + length. The new reader value has
279
- * an offset of zero, so downstream operations will not bee effected by the
280
- * previous offset
281
- */
282
- var sliceInt8Array = function (length, reader) {
283
- var value = new Int8Array(reader.data.buffer.slice(reader.offset, length + reader.offset));
284
- return __assign(__assign({}, reader), { offset: 0, value: value });
249
+ /**
250
+ * Returns a new `BinaryReader` for an `ArrayBuffer`.
251
+ */
252
+ var fromArrayBuffer = function (buffer) {
253
+ return { offset: 0, data: new DataView(buffer) };
254
+ };
255
+ /**
256
+ * Returns a `BinaryReader` that contains the read Int32 value at the given
257
+ * reader's offset. The returned reader will have its offset adjusted so it can
258
+ * be passed to the next helper.
259
+ */
260
+ var readInt32 = function (reader) {
261
+ var value = reader.data.getInt32(reader.offset);
262
+ return __assign(__assign({}, reader), { offset: reader.offset + 4, value: value });
263
+ };
264
+ /**
265
+ * Returns a `BinaryReader` that contains the read UTF-8 string at the given
266
+ * reader's offset. The returned reader will have its offset adjusted so it can
267
+ * be passed to the next helper.
268
+ */
269
+ var readUtf8String = function (length, reader) {
270
+ var value = String.fromCharCode.apply(null, Array.from(new Uint8Array(reader.data.buffer, reader.offset, length)));
271
+ return __assign(__assign({}, reader), { offset: reader.offset + length, value: value });
272
+ };
273
+ /**
274
+ * Returns a `BinaryReader` that contains the a signed `Int8Array` start from
275
+ * the given reader's offset to the given length. The returned reader will have
276
+ * its offset adjusted so it can be passed to the next helper.
277
+ */
278
+ var readInt8Array = function (length, reader) {
279
+ var value = new Int8Array(reader.data.buffer, reader.offset, length);
280
+ return __assign(__assign({}, reader), { offset: reader.offset + length, value: value });
281
+ };
282
+ /**
283
+ * Returns a `BinaryReader` that contains the a signed `Int8Array` sliced from
284
+ * the start of the reader's offset to offset + length. The new reader value has
285
+ * an offset of zero, so downstream operations will not bee effected by the
286
+ * previous offset
287
+ */
288
+ var sliceInt8Array = function (length, reader) {
289
+ var value = new Int8Array(reader.data.buffer.slice(reader.offset, length + reader.offset));
290
+ return __assign(__assign({}, reader), { offset: 0, value: value });
285
291
  };
286
292
 
287
293
  var binaryReader = /*#__PURE__*/Object.freeze({
@@ -293,85 +299,85 @@ var binaryReader = /*#__PURE__*/Object.freeze({
293
299
  sliceInt8Array: sliceInt8Array
294
300
  });
295
301
 
296
- var rgbRegex = /rgb\(\s*(\d+)\s*,\s*(\d+)\s*,\s*(\d+)\s*\)/;
297
- var rgbaRegex = /rgba\(\s*(\d+)\s*,\s*(\d+)\s*,\s*(\d+)\s*,\s*(.+)\s*\)/;
298
- var hexRegex = /^(#|0x)?([A-Fa-f0-9]{6})$/;
299
- /**
300
- * Constructs a new color with the given red, green, blue and alpha values. If
301
- * alpha is undefined, defaults to 1.
302
- */
303
- var create$2 = function (r, g, b, a) {
304
- if (a === void 0) { a = 255; }
305
- return { r: r, g: g, b: b, a: a };
306
- };
307
- /**
308
- * Converts a numeric color value containing red, green and blue values to a
309
- * `Color`. The alpha channel will default to fully opaque.
310
- */
311
- var fromNumber = function (num) {
312
- // tslint:disable:no-bitwise
313
- var normalized = num & 0xffffff;
314
- return create$2((normalized >> 16) & 0xff, (normalized >> 8) & 0xff, normalized & 0xff);
315
- // tslint:enable:no-bitwise
316
- };
317
- /**
318
- * Returns a `Color` from a hex string, or undefined if the color string cannot
319
- * be parsed. Supports hex strings in the format of `"#00FF00"`, `"0x00FF00"` or
320
- * `"00FF00"`.
321
- */
322
- var fromHexString = function (str) {
323
- var match = hexRegex.exec(str);
324
- if (match != null) {
325
- return fromNumber(parseInt(match[2], 16));
326
- }
327
- };
328
- /**
329
- * Creates a `Color` from a CSS color value. This function currently only
330
- * supports `rgb(255, 255, 255)`, `rgba(255, 255, 255, 0.5)` or `"#FFFFFF"`.
331
- * Returns `undefined` if the color cannot be parsed.
332
- */
333
- var fromCss = function (css) {
334
- var rgbMatch = rgbRegex.exec(css);
335
- if (rgbMatch != null) {
336
- return create$2(parseInt(rgbMatch[1]), parseInt(rgbMatch[2]), parseInt(rgbMatch[3]));
337
- }
338
- var rgbaMatch = rgbaRegex.exec(css);
339
- if (rgbaMatch != null) {
340
- return create$2(parseInt(rgbaMatch[1]), parseInt(rgbaMatch[2]), parseInt(rgbaMatch[3]), Math.floor(parseFloat(rgbaMatch[4]) * 255));
341
- }
342
- if (hexRegex.test(css)) {
343
- return fromHexString(css);
344
- }
345
- };
346
- /**
347
- * Converts an array of four values to a `Color`. The sequence of the array is
348
- * expected to be `[r, g, b]` or `[r, g, b, a]`.
349
- */
350
- var fromArray = function (rgba) {
351
- return create$2(rgba[0], rgba[1], rgba[2], rgba[3]);
352
- };
353
- /**
354
- * Returns `true` if the color's alpha channel is 0.
355
- */
356
- var isInvisible = function (color) {
357
- return color.a === 0;
358
- };
359
- /**
360
- * Returns `true` if the alpha channel of this color is fully opaque (255).
361
- */
362
- var isOpaque = function (color) {
363
- return color.a === 255;
364
- };
365
- /**
366
- * Converts a `Color` to a hex string. The returned string will be prefixed with
367
- * `#`.
368
- */
369
- var toHexString = function (color) {
370
- return "#".concat(componentToHex(color.r)).concat(componentToHex(color.g)).concat(componentToHex(color.b));
371
- };
372
- var componentToHex = function (num) {
373
- var hex = num.toString(16);
374
- return hex.length === 1 ? '0' + hex : hex;
302
+ var rgbRegex = /rgb\(\s*(\d+)\s*,\s*(\d+)\s*,\s*(\d+)\s*\)/;
303
+ var rgbaRegex = /rgba\(\s*(\d+)\s*,\s*(\d+)\s*,\s*(\d+)\s*,\s*(.+)\s*\)/;
304
+ var hexRegex = /^(#|0x)?([A-Fa-f0-9]{6})$/;
305
+ /**
306
+ * Constructs a new color with the given red, green, blue and alpha values. If
307
+ * alpha is undefined, defaults to 1.
308
+ */
309
+ var create$2 = function (r, g, b, a) {
310
+ if (a === void 0) { a = 255; }
311
+ return { r: r, g: g, b: b, a: a };
312
+ };
313
+ /**
314
+ * Converts a numeric color value containing red, green and blue values to a
315
+ * `Color`. The alpha channel will default to fully opaque.
316
+ */
317
+ var fromNumber = function (num) {
318
+ // tslint:disable:no-bitwise
319
+ var normalized = num & 0xffffff;
320
+ return create$2((normalized >> 16) & 0xff, (normalized >> 8) & 0xff, normalized & 0xff);
321
+ // tslint:enable:no-bitwise
322
+ };
323
+ /**
324
+ * Returns a `Color` from a hex string, or undefined if the color string cannot
325
+ * be parsed. Supports hex strings in the format of `"#00FF00"`, `"0x00FF00"` or
326
+ * `"00FF00"`.
327
+ */
328
+ var fromHexString = function (str) {
329
+ var match = hexRegex.exec(str);
330
+ if (match != null) {
331
+ return fromNumber(parseInt(match[2], 16));
332
+ }
333
+ };
334
+ /**
335
+ * Creates a `Color` from a CSS color value. This function currently only
336
+ * supports `rgb(255, 255, 255)`, `rgba(255, 255, 255, 0.5)` or `"#FFFFFF"`.
337
+ * Returns `undefined` if the color cannot be parsed.
338
+ */
339
+ var fromCss = function (css) {
340
+ var rgbMatch = rgbRegex.exec(css);
341
+ if (rgbMatch != null) {
342
+ return create$2(parseInt(rgbMatch[1]), parseInt(rgbMatch[2]), parseInt(rgbMatch[3]));
343
+ }
344
+ var rgbaMatch = rgbaRegex.exec(css);
345
+ if (rgbaMatch != null) {
346
+ return create$2(parseInt(rgbaMatch[1]), parseInt(rgbaMatch[2]), parseInt(rgbaMatch[3]), Math.floor(parseFloat(rgbaMatch[4]) * 255));
347
+ }
348
+ if (hexRegex.test(css)) {
349
+ return fromHexString(css);
350
+ }
351
+ };
352
+ /**
353
+ * Converts an array of four values to a `Color`. The sequence of the array is
354
+ * expected to be `[r, g, b]` or `[r, g, b, a]`.
355
+ */
356
+ var fromArray = function (rgba) {
357
+ return create$2(rgba[0], rgba[1], rgba[2], rgba[3]);
358
+ };
359
+ /**
360
+ * Returns `true` if the color's alpha channel is 0.
361
+ */
362
+ var isInvisible = function (color) {
363
+ return color.a === 0;
364
+ };
365
+ /**
366
+ * Returns `true` if the alpha channel of this color is fully opaque (255).
367
+ */
368
+ var isOpaque = function (color) {
369
+ return color.a === 255;
370
+ };
371
+ /**
372
+ * Converts a `Color` to a hex string. The returned string will be prefixed with
373
+ * `#`.
374
+ */
375
+ var toHexString = function (color) {
376
+ return "#".concat(componentToHex(color.r)).concat(componentToHex(color.g)).concat(componentToHex(color.b));
377
+ };
378
+ var componentToHex = function (num) {
379
+ var hex = num.toString(16);
380
+ return hex.length === 1 ? '0' + hex : hex;
375
381
  };
376
382
 
377
383
  var color = /*#__PURE__*/Object.freeze({
@@ -386,359 +392,359 @@ var color = /*#__PURE__*/Object.freeze({
386
392
  toHexString: toHexString
387
393
  });
388
394
 
389
- /**
390
- * A module for defining functional schemas to map between different types. This
391
- * module is useful for parsing to or from JSON/protobufs to domain types.
392
- *
393
- * Mappers support greedy validation, so all validation errors are aggregated
394
- * and reported vs failing on the first invalid input.
395
- *
396
- * @example
397
- *
398
- * ```ts
399
- * import { Mapper as M } from '@vertexvis/utils';
400
- *
401
- * interface Address {
402
- * address: string;
403
- * city: string;
404
- * state: string;
405
- * zip: string;
406
- * }
407
- *
408
- * interface Person {
409
- * name: string;
410
- * addresses: Address[];
411
- * }
412
- *
413
- * type AddressJson = Partial<Address>;
414
- * type PersonJson = {
415
- * name?: string;
416
- * addresses?: AddressJson[];
417
- * }
418
- *
419
- * const mapAddress: M.Func<AddressJson, Address> = M.defineMapper(
420
- * M.read(
421
- * M.requireProp('address'),
422
- * M.requireProp('city'),
423
- * M.requireProp('state'),
424
- * M.requireProp('zip')
425
- * ),
426
- * ([address, city, state, zip]) => ({
427
- * address, city, state, zip
428
- * })
429
- * );
430
- *
431
- * const mapPerson: M.Func<PersonJson, Person> = M.defineMapper(
432
- * M.read(
433
- * M.requireProp('name'),
434
- * M.mapProp(
435
- * 'addresses',
436
- * M.compose(M.required('addresses'), M.mapArray(mapAddress))
437
- * )
438
- * ),
439
- * ([name, addresses]) => ({ name, addresses })
440
- * );
441
- *
442
- * const person = mapPerson({
443
- * name: 'John',
444
- * addresses: [{ address: '123', city: 'Ames', state: 'IA', zip: '50010' }]
445
- * });
446
- *
447
- * const invalidPerson = mapPerson({
448
- * addresses: [{ city: 'Ames', state: 'IA', zip: '50010' }]
449
- * });
450
- * ```
451
- * // {
452
- * // errors: ["Name is required.", "Address is required."]
453
- * // }
454
- *
455
- * @module
456
- */
457
- /**
458
- * An error that is thrown when validation of a schema fails.
459
- *
460
- * @see {@link ifInvalidThrow} - for throwing errors on invalid input.
461
- */
462
- var MapperValidationError = /** @class */ (function (_super) {
463
- __extends(MapperValidationError, _super);
464
- function MapperValidationError(errors) {
465
- var _this = _super.call(this, 'Validation error mapping object.') || this;
466
- _this.errors = errors;
467
- Object.setPrototypeOf(_this, MapperValidationError.prototype);
468
- return _this;
469
- }
470
- return MapperValidationError;
471
- }(Error));
472
- /**
473
- * Returns a mapper that asserts the input is not null or not undefined.
474
- *
475
- * @param name A name to report when invalid.
476
- */
477
- function required(name) {
478
- return function (input) {
479
- if (input != null) {
480
- return input;
481
- }
482
- else {
483
- return { errors: ["".concat(name, " is required.")] };
484
- }
485
- };
486
- }
487
- /**
488
- * Returns a mapper that asserts a property on the input is not null or not
489
- * defined.
490
- *
491
- * @param prop The prop to assert.
492
- * @returns A mapper that returns the property's value.
493
- */
494
- function requiredProp(prop) {
495
- return function (obj) {
496
- var value = obj[prop];
497
- if (value != null) {
498
- return value;
499
- }
500
- else {
501
- return { errors: ["".concat(String(prop), " is required")] };
502
- }
503
- };
504
- }
505
- /**
506
- * Returns a mapper that invokes a function if the input is not null or not
507
- * undefined.
508
- *
509
- * @param mapper A mapping function.
510
- */
511
- function ifDefined(mapper) {
512
- return function (input) {
513
- if (input != null) {
514
- return mapper(input);
515
- }
516
- else {
517
- return input;
518
- }
519
- };
520
- }
521
- /**
522
- * Returns a mapper that extracts a property's value.
523
- *
524
- * @param prop The property to extract.
525
- */
526
- function getProp(prop) {
527
- return function (input) {
528
- return input[prop];
529
- };
530
- }
531
- /**
532
- * Returns a mapper that will invoke a mapping function on an input's property.
533
- *
534
- * @param prop The name of the property to map over.
535
- * @param mapper A function that will be invoked with the property's value.
536
- */
537
- function mapProp(prop, mapper) {
538
- return function (input) {
539
- var value = input[prop];
540
- return mapper(value);
541
- };
542
- }
543
- /**
544
- * Returns a mapper that will check if the given property is defined, and if so
545
- * invoke the given mapping function.
546
- *
547
- * @param prop The name of the property to map over.
548
- * @param mapper A function that will be invoked with the property's value if
549
- * the property is defined.
550
- */
551
- function mapRequiredProp(prop, mapper) {
552
- return mapProp(prop, compose(required(prop.toString()), mapper));
553
- }
554
- /**
555
- * Returns a mapper that will invoke a mapper over each value in the input
556
- * array. Returns `Invalid` containing errors for all invalid values in the
557
- * array.
558
- *
559
- * @param mapper A function that will be invoked with each array value.
560
- * @returns
561
- */
562
- function mapArray(mapper) {
563
- return function (inputs) {
564
- if (inputs.length > 0) {
565
- var _a = __read(inputs), head = _a[0], tail = _a.slice(1);
566
- var first = mapper(head);
567
- return tail.reduce(function (res, input) {
568
- var value = mapper(input);
569
- if (isInvalid(value)) {
570
- return isInvalid(res)
571
- ? { errors: __spreadArray(__spreadArray([], __read(res.errors), false), __read(value.errors), false) }
572
- : value;
573
- }
574
- else if (isInvalid(res)) {
575
- return res;
576
- }
577
- else {
578
- return __spreadArray(__spreadArray([], __read(res), false), [value], false);
579
- }
580
- }, isInvalid(first) ? first : [first]);
581
- }
582
- else {
583
- return [];
584
- }
585
- };
586
- }
587
- /**
588
- * A type guard that checks if the object is an `Invalid` type.
589
- */
590
- function isInvalid(obj) {
591
- // eslint-disable-next-line @typescript-eslint/no-explicit-any
592
- return obj != null && obj.hasOwnProperty('errors');
593
- }
594
- /**
595
- * Returns a function that throws an error if the input is invalid. Otherwise,
596
- * returns the result.
597
- *
598
- * @param mapper A mapper that will be invoked with the input.
599
- * @throws {@link MapperValidationError} If the input is invalid.
600
- */
601
- function ifInvalidThrow(mapper) {
602
- return function (input) {
603
- var value = mapper(input);
604
- if (isInvalid(value)) {
605
- throw new MapperValidationError(value.errors);
606
- }
607
- else
608
- return value;
609
- };
610
- }
611
- function ifValidThen(obj, f) {
612
- if (isInvalid(obj)) {
613
- return obj;
614
- }
615
- else {
616
- return f(obj);
617
- }
618
- }
619
- function read() {
620
- var mappers = [];
621
- for (var _i = 0; _i < arguments.length; _i++) {
622
- mappers[_i] = arguments[_i];
623
- }
624
- return function (input) {
625
- return mappers.reduce(function (res, decoder) {
626
- var value = decoder(input);
627
- if (isInvalid(value)) {
628
- return isInvalid(res)
629
- ? { errors: __spreadArray(__spreadArray([], __read(res.errors), false), __read(value.errors), false) }
630
- : value;
631
- }
632
- else if (isInvalid(res)) {
633
- return res;
634
- }
635
- else {
636
- return __spreadArray(__spreadArray([], __read(res), false), [value], false);
637
- }
638
- }, []);
639
- };
640
- }
641
- /* eslint-enable padding-line-between-statements */
642
- /**
643
- * Defines a mapper that reads the values from an input and invokes a builder to
644
- * transform data from one schema to another.
645
- *
646
- * @example
647
- *
648
- * ```ts
649
- * import { Mapper as M } from '@vertexvis/utils';
650
- *
651
- * interface Address {
652
- * address: string;
653
- * city: string;
654
- * state: string;
655
- * zip: string;
656
- * }
657
- *
658
- * interface Person {
659
- * name: string;
660
- * addresses: Address[];
661
- * }
662
- *
663
- * type AddressJson = Partial<Address>;
664
- * type PersonJson = {
665
- * name?: string;
666
- * addresses?: AddressJson[];
667
- * }
668
- *
669
- * const mapAddress: M.Func<AddressJson, Address> = M.defineMapper(
670
- * M.read(
671
- * M.requireProp('address'),
672
- * M.requireProp('city'),
673
- * M.requireProp('state'),
674
- * M.requireProp('zip')
675
- * ),
676
- * ([address, city, state, zip]) => ({
677
- * address, city, state, zip
678
- * })
679
- * );
680
- *
681
- * const mapPerson: M.Func<PersonJson, Person> = M.defineMapper(
682
- * M.read(
683
- * M.requireProp('name'),
684
- * M.mapProp(
685
- * 'addresses',
686
- * M.compose(M.required('addresses'), M.mapArray(mapAddress))
687
- * )
688
- * ),
689
- * ([name, addresses]) => ({ name, addresses })
690
- * )
691
- *
692
- * const person = mapPerson({
693
- * name: 'John',
694
- * addresses: [{ address: '123', city: 'Ames', state: 'IA', zip: '50010' }]
695
- * })
696
- * ```
697
- *
698
- * @param reader The mapper that reads values from the input an creates an
699
- * intermediate format that will be passed to the `builder`.
700
- * @param builder A mapper that takes the output of `reader` and constructs the
701
- * output format.
702
- * @see {@link read} - a helper function to read and validate input values.
703
- */
704
- function defineMapper(reader, builder) {
705
- return function (input) {
706
- var values = reader(input);
707
- return ifValidThen(values, builder);
708
- };
709
- }
710
- function compose() {
711
- var decoders = [];
712
- for (var _i = 0; _i < arguments.length; _i++) {
713
- decoders[_i] = arguments[_i];
714
- }
715
- return function (input) {
716
- return decoders.reduce(function (last, decoder) {
717
- if (isInvalid(last)) {
718
- return last;
719
- }
720
- else {
721
- return decoder(last);
722
- }
723
- }, input);
724
- };
725
- }
726
- function pickFirst() {
727
- var decoders = [];
728
- for (var _i = 0; _i < arguments.length; _i++) {
729
- decoders[_i] = arguments[_i];
730
- }
731
- return function (input) {
732
- return decoders.reduce(function (value, decoder) {
733
- if (value === undefined) {
734
- return decoder(input);
735
- }
736
- else {
737
- return value;
738
- }
739
- }, undefined);
740
- };
741
- }
395
+ /**
396
+ * A module for defining functional schemas to map between different types. This
397
+ * module is useful for parsing to or from JSON/protobufs to domain types.
398
+ *
399
+ * Mappers support greedy validation, so all validation errors are aggregated
400
+ * and reported vs failing on the first invalid input.
401
+ *
402
+ * @example
403
+ *
404
+ * ```ts
405
+ * import { Mapper as M } from '@vertexvis/utils';
406
+ *
407
+ * interface Address {
408
+ * address: string;
409
+ * city: string;
410
+ * state: string;
411
+ * zip: string;
412
+ * }
413
+ *
414
+ * interface Person {
415
+ * name: string;
416
+ * addresses: Address[];
417
+ * }
418
+ *
419
+ * type AddressJson = Partial<Address>;
420
+ * type PersonJson = {
421
+ * name?: string;
422
+ * addresses?: AddressJson[];
423
+ * }
424
+ *
425
+ * const mapAddress: M.Func<AddressJson, Address> = M.defineMapper(
426
+ * M.read(
427
+ * M.requireProp('address'),
428
+ * M.requireProp('city'),
429
+ * M.requireProp('state'),
430
+ * M.requireProp('zip')
431
+ * ),
432
+ * ([address, city, state, zip]) => ({
433
+ * address, city, state, zip
434
+ * })
435
+ * );
436
+ *
437
+ * const mapPerson: M.Func<PersonJson, Person> = M.defineMapper(
438
+ * M.read(
439
+ * M.requireProp('name'),
440
+ * M.mapProp(
441
+ * 'addresses',
442
+ * M.compose(M.required('addresses'), M.mapArray(mapAddress))
443
+ * )
444
+ * ),
445
+ * ([name, addresses]) => ({ name, addresses })
446
+ * );
447
+ *
448
+ * const person = mapPerson({
449
+ * name: 'John',
450
+ * addresses: [{ address: '123', city: 'Ames', state: 'IA', zip: '50010' }]
451
+ * });
452
+ *
453
+ * const invalidPerson = mapPerson({
454
+ * addresses: [{ city: 'Ames', state: 'IA', zip: '50010' }]
455
+ * });
456
+ * ```
457
+ * // {
458
+ * // errors: ["Name is required.", "Address is required."]
459
+ * // }
460
+ *
461
+ * @module
462
+ */
463
+ /**
464
+ * An error that is thrown when validation of a schema fails.
465
+ *
466
+ * @see {@link ifInvalidThrow} - for throwing errors on invalid input.
467
+ */
468
+ var MapperValidationError = /** @class */ (function (_super) {
469
+ __extends(MapperValidationError, _super);
470
+ function MapperValidationError(errors) {
471
+ var _this = _super.call(this, 'Validation error mapping object.') || this;
472
+ _this.errors = errors;
473
+ Object.setPrototypeOf(_this, MapperValidationError.prototype);
474
+ return _this;
475
+ }
476
+ return MapperValidationError;
477
+ }(Error));
478
+ /**
479
+ * Returns a mapper that asserts the input is not null or not undefined.
480
+ *
481
+ * @param name A name to report when invalid.
482
+ */
483
+ function required(name) {
484
+ return function (input) {
485
+ if (input != null) {
486
+ return input;
487
+ }
488
+ else {
489
+ return { errors: ["".concat(name, " is required.")] };
490
+ }
491
+ };
492
+ }
493
+ /**
494
+ * Returns a mapper that asserts a property on the input is not null or not
495
+ * defined.
496
+ *
497
+ * @param prop The prop to assert.
498
+ * @returns A mapper that returns the property's value.
499
+ */
500
+ function requiredProp(prop) {
501
+ return function (obj) {
502
+ var value = obj[prop];
503
+ if (value != null) {
504
+ return value;
505
+ }
506
+ else {
507
+ return { errors: ["".concat(String(prop), " is required")] };
508
+ }
509
+ };
510
+ }
511
+ /**
512
+ * Returns a mapper that invokes a function if the input is not null or not
513
+ * undefined.
514
+ *
515
+ * @param mapper A mapping function.
516
+ */
517
+ function ifDefined(mapper) {
518
+ return function (input) {
519
+ if (input != null) {
520
+ return mapper(input);
521
+ }
522
+ else {
523
+ return input;
524
+ }
525
+ };
526
+ }
527
+ /**
528
+ * Returns a mapper that extracts a property's value.
529
+ *
530
+ * @param prop The property to extract.
531
+ */
532
+ function getProp(prop) {
533
+ return function (input) {
534
+ return input[prop];
535
+ };
536
+ }
537
+ /**
538
+ * Returns a mapper that will invoke a mapping function on an input's property.
539
+ *
540
+ * @param prop The name of the property to map over.
541
+ * @param mapper A function that will be invoked with the property's value.
542
+ */
543
+ function mapProp(prop, mapper) {
544
+ return function (input) {
545
+ var value = input[prop];
546
+ return mapper(value);
547
+ };
548
+ }
549
+ /**
550
+ * Returns a mapper that will check if the given property is defined, and if so
551
+ * invoke the given mapping function.
552
+ *
553
+ * @param prop The name of the property to map over.
554
+ * @param mapper A function that will be invoked with the property's value if
555
+ * the property is defined.
556
+ */
557
+ function mapRequiredProp(prop, mapper) {
558
+ return mapProp(prop, compose(required(prop.toString()), mapper));
559
+ }
560
+ /**
561
+ * Returns a mapper that will invoke a mapper over each value in the input
562
+ * array. Returns `Invalid` containing errors for all invalid values in the
563
+ * array.
564
+ *
565
+ * @param mapper A function that will be invoked with each array value.
566
+ * @returns
567
+ */
568
+ function mapArray(mapper) {
569
+ return function (inputs) {
570
+ if (inputs.length > 0) {
571
+ var _a = __read(inputs), head = _a[0], tail = _a.slice(1);
572
+ var first = mapper(head);
573
+ return tail.reduce(function (res, input) {
574
+ var value = mapper(input);
575
+ if (isInvalid(value)) {
576
+ return isInvalid(res)
577
+ ? { errors: __spreadArray(__spreadArray([], __read(res.errors), false), __read(value.errors), false) }
578
+ : value;
579
+ }
580
+ else if (isInvalid(res)) {
581
+ return res;
582
+ }
583
+ else {
584
+ return __spreadArray(__spreadArray([], __read(res), false), [value], false);
585
+ }
586
+ }, isInvalid(first) ? first : [first]);
587
+ }
588
+ else {
589
+ return [];
590
+ }
591
+ };
592
+ }
593
+ /**
594
+ * A type guard that checks if the object is an `Invalid` type.
595
+ */
596
+ function isInvalid(obj) {
597
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
598
+ return obj != null && obj.hasOwnProperty('errors');
599
+ }
600
+ /**
601
+ * Returns a function that throws an error if the input is invalid. Otherwise,
602
+ * returns the result.
603
+ *
604
+ * @param mapper A mapper that will be invoked with the input.
605
+ * @throws {@link MapperValidationError} If the input is invalid.
606
+ */
607
+ function ifInvalidThrow(mapper) {
608
+ return function (input) {
609
+ var value = mapper(input);
610
+ if (isInvalid(value)) {
611
+ throw new MapperValidationError(value.errors);
612
+ }
613
+ else
614
+ return value;
615
+ };
616
+ }
617
+ function ifValidThen(obj, f) {
618
+ if (isInvalid(obj)) {
619
+ return obj;
620
+ }
621
+ else {
622
+ return f(obj);
623
+ }
624
+ }
625
+ function read() {
626
+ var mappers = [];
627
+ for (var _i = 0; _i < arguments.length; _i++) {
628
+ mappers[_i] = arguments[_i];
629
+ }
630
+ return function (input) {
631
+ return mappers.reduce(function (res, decoder) {
632
+ var value = decoder(input);
633
+ if (isInvalid(value)) {
634
+ return isInvalid(res)
635
+ ? { errors: __spreadArray(__spreadArray([], __read(res.errors), false), __read(value.errors), false) }
636
+ : value;
637
+ }
638
+ else if (isInvalid(res)) {
639
+ return res;
640
+ }
641
+ else {
642
+ return __spreadArray(__spreadArray([], __read(res), false), [value], false);
643
+ }
644
+ }, []);
645
+ };
646
+ }
647
+ /* eslint-enable padding-line-between-statements */
648
+ /**
649
+ * Defines a mapper that reads the values from an input and invokes a builder to
650
+ * transform data from one schema to another.
651
+ *
652
+ * @example
653
+ *
654
+ * ```ts
655
+ * import { Mapper as M } from '@vertexvis/utils';
656
+ *
657
+ * interface Address {
658
+ * address: string;
659
+ * city: string;
660
+ * state: string;
661
+ * zip: string;
662
+ * }
663
+ *
664
+ * interface Person {
665
+ * name: string;
666
+ * addresses: Address[];
667
+ * }
668
+ *
669
+ * type AddressJson = Partial<Address>;
670
+ * type PersonJson = {
671
+ * name?: string;
672
+ * addresses?: AddressJson[];
673
+ * }
674
+ *
675
+ * const mapAddress: M.Func<AddressJson, Address> = M.defineMapper(
676
+ * M.read(
677
+ * M.requireProp('address'),
678
+ * M.requireProp('city'),
679
+ * M.requireProp('state'),
680
+ * M.requireProp('zip')
681
+ * ),
682
+ * ([address, city, state, zip]) => ({
683
+ * address, city, state, zip
684
+ * })
685
+ * );
686
+ *
687
+ * const mapPerson: M.Func<PersonJson, Person> = M.defineMapper(
688
+ * M.read(
689
+ * M.requireProp('name'),
690
+ * M.mapProp(
691
+ * 'addresses',
692
+ * M.compose(M.required('addresses'), M.mapArray(mapAddress))
693
+ * )
694
+ * ),
695
+ * ([name, addresses]) => ({ name, addresses })
696
+ * )
697
+ *
698
+ * const person = mapPerson({
699
+ * name: 'John',
700
+ * addresses: [{ address: '123', city: 'Ames', state: 'IA', zip: '50010' }]
701
+ * })
702
+ * ```
703
+ *
704
+ * @param reader The mapper that reads values from the input an creates an
705
+ * intermediate format that will be passed to the `builder`.
706
+ * @param builder A mapper that takes the output of `reader` and constructs the
707
+ * output format.
708
+ * @see {@link read} - a helper function to read and validate input values.
709
+ */
710
+ function defineMapper(reader, builder) {
711
+ return function (input) {
712
+ var values = reader(input);
713
+ return ifValidThen(values, builder);
714
+ };
715
+ }
716
+ function compose() {
717
+ var decoders = [];
718
+ for (var _i = 0; _i < arguments.length; _i++) {
719
+ decoders[_i] = arguments[_i];
720
+ }
721
+ return function (input) {
722
+ return decoders.reduce(function (last, decoder) {
723
+ if (isInvalid(last)) {
724
+ return last;
725
+ }
726
+ else {
727
+ return decoder(last);
728
+ }
729
+ }, input);
730
+ };
731
+ }
732
+ function pickFirst() {
733
+ var decoders = [];
734
+ for (var _i = 0; _i < arguments.length; _i++) {
735
+ decoders[_i] = arguments[_i];
736
+ }
737
+ return function (input) {
738
+ return decoders.reduce(function (value, decoder) {
739
+ if (value === undefined) {
740
+ return decoder(input);
741
+ }
742
+ else {
743
+ return value;
744
+ }
745
+ }, undefined);
746
+ };
747
+ }
742
748
  /* eslint-enable padding-line-between-statements */
743
749
 
744
750
  var mapper = /*#__PURE__*/Object.freeze({
@@ -759,186 +765,96 @@ var mapper = /*#__PURE__*/Object.freeze({
759
765
  pickFirst: pickFirst
760
766
  });
761
767
 
762
- // do not edit .js files directly - edit src/index.jst
763
-
764
-
765
-
766
- var fastDeepEqual = function equal(a, b) {
767
- if (a === b) return true;
768
-
769
- if (a && b && typeof a == 'object' && typeof b == 'object') {
770
- if (a.constructor !== b.constructor) return false;
771
-
772
- var length, i, keys;
773
- if (Array.isArray(a)) {
774
- length = a.length;
775
- if (length != b.length) return false;
776
- for (i = length; i-- !== 0;)
777
- if (!equal(a[i], b[i])) return false;
778
- return true;
768
+ function defaults() {
769
+ var objects = [];
770
+ for (var _i = 0; _i < arguments.length; _i++) {
771
+ objects[_i] = arguments[_i];
779
772
  }
780
-
781
-
782
-
783
- if (a.constructor === RegExp) return a.source === b.source && a.flags === b.flags;
784
- if (a.valueOf !== Object.prototype.valueOf) return a.valueOf() === b.valueOf();
785
- if (a.toString !== Object.prototype.toString) return a.toString() === b.toString();
786
-
787
- keys = Object.keys(a);
788
- length = keys.length;
789
- if (length !== Object.keys(b).length) return false;
790
-
791
- for (i = length; i-- !== 0;)
792
- if (!Object.prototype.hasOwnProperty.call(b, keys[i])) return false;
793
-
794
- for (i = length; i-- !== 0;) {
795
- var key = keys[i];
796
-
797
- if (!equal(a[key], b[key])) return false;
773
+ var _a = __read(objects), a = _a[0], other = _a.slice(1);
774
+ var result = __assign({}, a);
775
+ if (other.length === 0) {
776
+ return result;
798
777
  }
799
-
800
- return true;
801
- }
802
-
803
- // true if both NaN, false otherwise
804
- return a!==a && b!==b;
805
- };
806
-
807
- /*!
808
- * isobject <https://github.com/jonschlinkert/isobject>
778
+ else if (other.length === 1) {
779
+ var b = other[0];
780
+ for (var key in b) {
781
+ if (result[key] == null) {
782
+ result[key] = b[key];
783
+ }
784
+ else if (isPlainObject(result[key])) {
785
+ result[key] = defaults(result[key], b[key]);
786
+ }
787
+ }
788
+ return result;
789
+ }
790
+ else {
791
+ return other.reduce(function (result, next) { return defaults(result, next); }, a);
792
+ }
793
+ }
794
+ /* eslint-enable padding-line-between-statements */
795
+ /**
796
+ * Returns `true` if this is a plain object, which is defined by a type created
797
+ * by the `Object` constructor. Returns `false` otherwise.
809
798
  *
810
- * Copyright (c) 2014-2017, Jon Schlinkert.
811
- * Released under the MIT License.
799
+ * @example
800
+ * ```
801
+ * isPlainObject(Object.create({})); //=> true
802
+ * isPlainObject(Object.create(Object.prototype)); //=> true
803
+ * isPlainObject({foo: 'bar'}); //=> true
804
+ * isPlainObject({}); //=> true
805
+ *
806
+ * isPlainObject(1); //=> false
807
+ * isPlainObject(['foo', 'bar']); //=> false
808
+ * isPlainObject([]); //=> false
809
+ * isPlainObject(new Foo); //=> false
810
+ * isPlainObject(null); //=> false
811
+ * isPlainObject(Object.create(null)); //=> false
812
+ * ```
812
813
  */
813
-
814
- function isObject(val) {
815
- return val != null && typeof val === 'object' && Array.isArray(val) === false;
814
+ function isPlainObject(obj) {
815
+ return isSimpleObject(obj);
816
816
  }
817
-
818
- /*!
819
- * is-plain-object <https://github.com/jonschlinkert/is-plain-object>
817
+ /**
818
+ * Performs a deep comparison of two objects and returns `true` if they're
819
+ * equal.
820
+ *
821
+ * This method supports comparing arrays, array buffers, booleans, date objects,
822
+ * error objects, maps, numbers, Object objects, regexes, sets, strings,
823
+ * symbols, and typed arrays. Object objects are compared by their own, not
824
+ * inherited, enumerable properties. Functions and DOM nodes are compared by
825
+ * strict equality, i.e. ===.
820
826
  *
821
- * Copyright (c) 2014-2017, Jon Schlinkert.
822
- * Released under the MIT License.
827
+ * @param a The object to compare with `b`.
828
+ * @param b The object to compare with `a`.
829
+ * @returns `true` if the two objects are equal. Otherwise `false`.
823
830
  */
824
-
825
- function isObjectObject(o) {
826
- return isObject(o) === true
827
- && Object.prototype.toString.call(o) === '[object Object]';
831
+ function isEqual$1(a, b) {
832
+ return fastDeepEqual(a, b);
828
833
  }
829
-
830
- function isPlainObject$1(o) {
831
- var ctor,prot;
832
-
833
- if (isObjectObject(o) === false) return false;
834
-
835
- // If has modified constructor
836
- ctor = o.constructor;
837
- if (typeof ctor !== 'function') return false;
838
-
839
- // If has modified prototype
840
- prot = ctor.prototype;
841
- if (isObjectObject(prot) === false) return false;
842
-
843
- // If constructor does not have an Object-specific method
844
- if (prot.hasOwnProperty('isPrototypeOf') === false) {
845
- return false;
846
- }
847
-
848
- // Most likely a plain Object
849
- return true;
834
+ function toPairs(obj) {
835
+ if (obj != null) {
836
+ return Object.keys(obj).map(function (key) { return [key, obj[key]]; });
837
+ }
838
+ else {
839
+ return [];
840
+ }
841
+ }
842
+ function fromPairs(pairs) {
843
+ if (Array.isArray(pairs)) {
844
+ return pairs.reduce(function (result, pair) {
845
+ var _a;
846
+ if (pair != null) {
847
+ return __assign(__assign({}, result), (_a = {}, _a[pair[0]] = pair[1], _a));
848
+ }
849
+ else {
850
+ return result;
851
+ }
852
+ }, {});
853
+ }
854
+ else {
855
+ return {};
856
+ }
850
857
  }
851
-
852
- function defaults() {
853
- var objects = [];
854
- for (var _i = 0; _i < arguments.length; _i++) {
855
- objects[_i] = arguments[_i];
856
- }
857
- var _a = __read(objects), a = _a[0], other = _a.slice(1);
858
- var result = __assign({}, a);
859
- if (other.length === 0) {
860
- return result;
861
- }
862
- else if (other.length === 1) {
863
- var b = other[0];
864
- for (var key in b) {
865
- if (result[key] == null) {
866
- result[key] = b[key];
867
- }
868
- else if (isPlainObject(result[key])) {
869
- result[key] = defaults(result[key], b[key]);
870
- }
871
- }
872
- return result;
873
- }
874
- else {
875
- return other.reduce(function (result, next) { return defaults(result, next); }, a);
876
- }
877
- }
878
- /* eslint-enable padding-line-between-statements */
879
- /**
880
- * Returns `true` if this is a plain object, which is defined by a type created
881
- * by the `Object` constructor. Returns `false` otherwise.
882
- *
883
- * @example
884
- * ```
885
- * isPlainObject(Object.create({})); //=> true
886
- * isPlainObject(Object.create(Object.prototype)); //=> true
887
- * isPlainObject({foo: 'bar'}); //=> true
888
- * isPlainObject({}); //=> true
889
- *
890
- * isPlainObject(1); //=> false
891
- * isPlainObject(['foo', 'bar']); //=> false
892
- * isPlainObject([]); //=> false
893
- * isPlainObject(new Foo); //=> false
894
- * isPlainObject(null); //=> false
895
- * isPlainObject(Object.create(null)); //=> false
896
- * ```
897
- */
898
- function isPlainObject(obj) {
899
- return isPlainObject$1(obj);
900
- }
901
- /**
902
- * Performs a deep comparison of two objects and returns `true` if they're
903
- * equal.
904
- *
905
- * This method supports comparing arrays, array buffers, booleans, date objects,
906
- * error objects, maps, numbers, Object objects, regexes, sets, strings,
907
- * symbols, and typed arrays. Object objects are compared by their own, not
908
- * inherited, enumerable properties. Functions and DOM nodes are compared by
909
- * strict equality, i.e. ===.
910
- *
911
- * @param a The object to compare with `b`.
912
- * @param b The object to compare with `a`.
913
- * @returns `true` if the two objects are equal. Otherwise `false`.
914
- */
915
- function isEqual$1(a, b) {
916
- return fastDeepEqual(a, b);
917
- }
918
- function toPairs(obj) {
919
- if (obj != null) {
920
- return Object.keys(obj).map(function (key) { return [key, obj[key]]; });
921
- }
922
- else {
923
- return [];
924
- }
925
- }
926
- function fromPairs(pairs) {
927
- if (Array.isArray(pairs)) {
928
- return pairs.reduce(function (result, pair) {
929
- var _a;
930
- if (pair != null) {
931
- return __assign(__assign({}, result), (_a = {}, _a[pair[0]] = pair[1], _a));
932
- }
933
- else {
934
- return result;
935
- }
936
- }, {});
937
- }
938
- else {
939
- return {};
940
- }
941
- }
942
858
  /* eslint-enable padding-line-between-statements */
943
859
 
944
860
  var objects = /*#__PURE__*/Object.freeze({
@@ -950,136 +866,136 @@ var objects = /*#__PURE__*/Object.freeze({
950
866
  fromPairs: fromPairs
951
867
  });
952
868
 
953
- /**
954
- * Returns a new `Range` with the given start and end points.
955
- */
956
- var create$1 = function (start, end) { return ({ start: start, end: end }); };
957
- /**
958
- * Returns a new `Range` with the start and end points at the given position.
959
- */
960
- var at = function (position) { return ({
961
- start: position,
962
- end: position,
963
- }); };
964
- /**
965
- * Returns a new `Range` with the given start point and length.
966
- */
967
- var withLength = function (start, len) { return ({
968
- start: start,
969
- end: start + len - 1,
970
- }); };
971
- /**
972
- * Returns a range with the start and end points shifted by the given distance.
973
- */
974
- var add = function (distance, range) {
975
- return create$1(range.start + distance, range.end + distance);
976
- };
977
- /**
978
- * Returns a range such that `range` is constrained to the start and end points
979
- * of `to`. The function will try to maintain the length of the range, but will
980
- * shrink the range if its length is greater than `to`.
981
- */
982
- var constrain = function (range, to) {
983
- if (contains(range, to)) {
984
- return range;
985
- }
986
- else if (length(range) > length(to)) {
987
- return to;
988
- }
989
- else if (range.start < to.start) {
990
- return create$1(to.start, to.start + length(range) - 1);
991
- }
992
- else {
993
- return create$1(to.end - length(range) + 1, to.end);
994
- }
995
- };
996
- /**
997
- * Checks if the given number or range is contained within another range.
998
- */
999
- var contains = function (numOrRange, range) {
1000
- if (typeof numOrRange === 'number') {
1001
- return range.start <= numOrRange && numOrRange <= range.end;
1002
- }
1003
- else {
1004
- return contains(numOrRange.start, range) && contains(numOrRange.end, range);
1005
- }
1006
- };
1007
- /**
1008
- * Returns a range that represents the overlap between `other` and `range`. If
1009
- * the two ranges do not intersect, then `undefined` is returned.
1010
- * @param other
1011
- * @param range
1012
- */
1013
- var intersection = function (other, range) {
1014
- if (intersects(other, range)) {
1015
- return create$1(Math.max(other.start, range.start), Math.min(other.end, range.end));
1016
- }
1017
- };
1018
- /**
1019
- * Returns `true` if `other` intersects with `range`.
1020
- */
1021
- var intersects = function (other, range) {
1022
- return ((other.start <= range.end && other.end >= range.start) ||
1023
- (range.start <= other.end && range.end >= other.start));
1024
- };
1025
- /**
1026
- * Checks if a range has the same starting point as another range.
1027
- */
1028
- var isAt = function (other, range) {
1029
- return other.start === range.start;
1030
- };
1031
- /**
1032
- * Returns `true` if a range's start point is after the starting point of
1033
- * another range.
1034
- */
1035
- var isAfter = function (other, range) {
1036
- return other.start > range.start;
1037
- };
1038
- /**
1039
- * Returns `true` if a range start at or is after another range.
1040
- */
1041
- var isAtOrAfter = function (other, range) {
1042
- return isAt(other, range) || isAfter(other, range);
1043
- };
1044
- /**
1045
- * Returns `true` if a range's starting point is before another range's starting
1046
- * point.
1047
- */
1048
- var isBefore = function (other, range) {
1049
- return other.start < range.start;
1050
- };
1051
- /**
1052
- * Returns `true` if a range's starting point is at or before another range's
1053
- * starting point.
1054
- */
1055
- var isAtOrBefore = function (other, range) {
1056
- return isAt(other, range) || isBefore(other, range);
1057
- };
1058
- /**
1059
- * Returns the length of a range.
1060
- */
1061
- var length = function (range) {
1062
- return range.end - range.start + 1;
1063
- };
1064
- /**
1065
- * Returns a `Range` with its start and end points subtracted by the given
1066
- * distance.
1067
- */
1068
- var subtract = function (distance, range) {
1069
- return add(distance * -1, range);
1070
- };
1071
- /**
1072
- * Adjusts either the start or end position of a range so that its contained
1073
- * within another range. Unlike `constrain`, this will not attempt to retain
1074
- * the range's length.
1075
- *
1076
- * If `other` does not intersect with `to`, then the range cannot be truncated
1077
- * and `undefined` is returned.
1078
- */
1079
- var truncate = function (other, to) {
1080
- if (intersects(to, other)) {
1081
- return create$1(Math.max(other.start, to.start), Math.min(other.end, to.end));
1082
- }
869
+ /**
870
+ * Returns a new `Range` with the given start and end points.
871
+ */
872
+ var create$1 = function (start, end) { return ({ start: start, end: end }); };
873
+ /**
874
+ * Returns a new `Range` with the start and end points at the given position.
875
+ */
876
+ var at = function (position) { return ({
877
+ start: position,
878
+ end: position,
879
+ }); };
880
+ /**
881
+ * Returns a new `Range` with the given start point and length.
882
+ */
883
+ var withLength = function (start, len) { return ({
884
+ start: start,
885
+ end: start + len - 1,
886
+ }); };
887
+ /**
888
+ * Returns a range with the start and end points shifted by the given distance.
889
+ */
890
+ var add = function (distance, range) {
891
+ return create$1(range.start + distance, range.end + distance);
892
+ };
893
+ /**
894
+ * Returns a range such that `range` is constrained to the start and end points
895
+ * of `to`. The function will try to maintain the length of the range, but will
896
+ * shrink the range if its length is greater than `to`.
897
+ */
898
+ var constrain = function (range, to) {
899
+ if (contains(range, to)) {
900
+ return range;
901
+ }
902
+ else if (length(range) > length(to)) {
903
+ return to;
904
+ }
905
+ else if (range.start < to.start) {
906
+ return create$1(to.start, to.start + length(range) - 1);
907
+ }
908
+ else {
909
+ return create$1(to.end - length(range) + 1, to.end);
910
+ }
911
+ };
912
+ /**
913
+ * Checks if the given number or range is contained within another range.
914
+ */
915
+ var contains = function (numOrRange, range) {
916
+ if (typeof numOrRange === 'number') {
917
+ return range.start <= numOrRange && numOrRange <= range.end;
918
+ }
919
+ else {
920
+ return contains(numOrRange.start, range) && contains(numOrRange.end, range);
921
+ }
922
+ };
923
+ /**
924
+ * Returns a range that represents the overlap between `other` and `range`. If
925
+ * the two ranges do not intersect, then `undefined` is returned.
926
+ * @param other
927
+ * @param range
928
+ */
929
+ var intersection = function (other, range) {
930
+ if (intersects(other, range)) {
931
+ return create$1(Math.max(other.start, range.start), Math.min(other.end, range.end));
932
+ }
933
+ };
934
+ /**
935
+ * Returns `true` if `other` intersects with `range`.
936
+ */
937
+ var intersects = function (other, range) {
938
+ return ((other.start <= range.end && other.end >= range.start) ||
939
+ (range.start <= other.end && range.end >= other.start));
940
+ };
941
+ /**
942
+ * Checks if a range has the same starting point as another range.
943
+ */
944
+ var isAt = function (other, range) {
945
+ return other.start === range.start;
946
+ };
947
+ /**
948
+ * Returns `true` if a range's start point is after the starting point of
949
+ * another range.
950
+ */
951
+ var isAfter = function (other, range) {
952
+ return other.start > range.start;
953
+ };
954
+ /**
955
+ * Returns `true` if a range start at or is after another range.
956
+ */
957
+ var isAtOrAfter = function (other, range) {
958
+ return isAt(other, range) || isAfter(other, range);
959
+ };
960
+ /**
961
+ * Returns `true` if a range's starting point is before another range's starting
962
+ * point.
963
+ */
964
+ var isBefore = function (other, range) {
965
+ return other.start < range.start;
966
+ };
967
+ /**
968
+ * Returns `true` if a range's starting point is at or before another range's
969
+ * starting point.
970
+ */
971
+ var isAtOrBefore = function (other, range) {
972
+ return isAt(other, range) || isBefore(other, range);
973
+ };
974
+ /**
975
+ * Returns the length of a range.
976
+ */
977
+ var length = function (range) {
978
+ return range.end - range.start + 1;
979
+ };
980
+ /**
981
+ * Returns a `Range` with its start and end points subtracted by the given
982
+ * distance.
983
+ */
984
+ var subtract = function (distance, range) {
985
+ return add(distance * -1, range);
986
+ };
987
+ /**
988
+ * Adjusts either the start or end position of a range so that its contained
989
+ * within another range. Unlike `constrain`, this will not attempt to retain
990
+ * the range's length.
991
+ *
992
+ * If `other` does not intersect with `to`, then the range cannot be truncated
993
+ * and `undefined` is returned.
994
+ */
995
+ var truncate = function (other, to) {
996
+ if (intersects(to, other)) {
997
+ return create$1(Math.max(other.start, to.start), Math.min(other.end, to.end));
998
+ }
1083
999
  };
1084
1000
 
1085
1001
  var range = /*#__PURE__*/Object.freeze({
@@ -1102,25 +1018,25 @@ var range = /*#__PURE__*/Object.freeze({
1102
1018
  truncate: truncate
1103
1019
  });
1104
1020
 
1105
- function diffSet(a, b) {
1106
- var e_1, _a;
1107
- var res = new Set();
1108
- try {
1109
- for (var b_1 = __values(b), b_1_1 = b_1.next(); !b_1_1.done; b_1_1 = b_1.next()) {
1110
- var item = b_1_1.value;
1111
- if (!a.has(item)) {
1112
- res.add(item);
1113
- }
1114
- }
1115
- }
1116
- catch (e_1_1) { e_1 = { error: e_1_1 }; }
1117
- finally {
1118
- try {
1119
- if (b_1_1 && !b_1_1.done && (_a = b_1.return)) _a.call(b_1);
1120
- }
1121
- finally { if (e_1) throw e_1.error; }
1122
- }
1123
- return res;
1021
+ function diffSet(a, b) {
1022
+ var e_1, _a;
1023
+ var res = new Set();
1024
+ try {
1025
+ for (var b_1 = __values(b), b_1_1 = b_1.next(); !b_1_1.done; b_1_1 = b_1.next()) {
1026
+ var item = b_1_1.value;
1027
+ if (!a.has(item)) {
1028
+ res.add(item);
1029
+ }
1030
+ }
1031
+ }
1032
+ catch (e_1_1) { e_1 = { error: e_1_1 }; }
1033
+ finally {
1034
+ try {
1035
+ if (b_1_1 && !b_1_1.done && (_a = b_1.return)) _a.call(b_1);
1036
+ }
1037
+ finally { if (e_1) throw e_1.error; }
1038
+ }
1039
+ return res;
1124
1040
  }
1125
1041
 
1126
1042
  var sets = /*#__PURE__*/Object.freeze({
@@ -1128,17 +1044,17 @@ var sets = /*#__PURE__*/Object.freeze({
1128
1044
  diffSet: diffSet
1129
1045
  });
1130
1046
 
1131
- var trimStartRegex = /^\W+/;
1132
- var trimEndRegex = /\W+$/;
1133
- var trimStartAndEndRegex = /^\W+|\W+$/g;
1134
- function trimStart(str) {
1135
- return str.replace(trimStartRegex, '');
1136
- }
1137
- function trimEnd(str) {
1138
- return str.replace(trimEndRegex, '');
1139
- }
1140
- function trim(str) {
1141
- return str.replace(trimStartAndEndRegex, '');
1047
+ var trimStartRegex = /^\W+/;
1048
+ var trimEndRegex = /\W+$/;
1049
+ var trimStartAndEndRegex = /^\W+|\W+$/g;
1050
+ function trimStart(str) {
1051
+ return str.replace(trimStartRegex, '');
1052
+ }
1053
+ function trimEnd(str) {
1054
+ return str.replace(trimEndRegex, '');
1055
+ }
1056
+ function trim(str) {
1057
+ return str.replace(trimStartAndEndRegex, '');
1142
1058
  }
1143
1059
 
1144
1060
  var strings = /*#__PURE__*/Object.freeze({
@@ -1148,178 +1064,178 @@ var strings = /*#__PURE__*/Object.freeze({
1148
1064
  trim: trim
1149
1065
  });
1150
1066
 
1151
- /**
1152
- * A comparator that sorts a number or string in ascending order.
1153
- */
1154
- var asc = function (a, b) {
1155
- if (a < b) {
1156
- return -1;
1157
- }
1158
- else if (a > b) {
1159
- return 1;
1160
- }
1161
- else {
1162
- return 0;
1163
- }
1164
- };
1165
- /**
1166
- * A comparator that plucks the first element of an array and passes that value
1167
- * to the given comparator for sorting.
1168
- */
1169
- var head = function (comparator) {
1170
- return function (_a, _b) {
1171
- var _c = __read(_a, 1), a = _c[0];
1172
- var _d = __read(_b, 1), b = _d[0];
1173
- return comparator(a, b);
1174
- };
1067
+ /**
1068
+ * A comparator that sorts a number or string in ascending order.
1069
+ */
1070
+ var asc = function (a, b) {
1071
+ if (a < b) {
1072
+ return -1;
1073
+ }
1074
+ else if (a > b) {
1075
+ return 1;
1076
+ }
1077
+ else {
1078
+ return 0;
1079
+ }
1080
+ };
1081
+ /**
1082
+ * A comparator that plucks the first element of an array and passes that value
1083
+ * to the given comparator for sorting.
1084
+ */
1085
+ var head = function (comparator) {
1086
+ return function (_a, _b) {
1087
+ var _c = __read(_a, 1), a = _c[0];
1088
+ var _d = __read(_b, 1), b = _d[0];
1089
+ return comparator(a, b);
1090
+ };
1175
1091
  };
1176
1092
 
1177
- /**
1178
- * Parses a URI string according to RFC 3986. If the URI is an empty string,
1179
- * then an empty object is returned.
1180
- *
1181
- * See https://tools.ietf.org/html/rfc3986#appendix-B for parsing rules.
1182
- *
1183
- * @param uri The URI to parse.
1184
- */
1185
- var parse = function (uri) {
1186
- var regex = /^(([^:/?#]+):)?(\/\/([^/?#]*))?([^?#]*)(\?([^#]*))?(#(.*))?/;
1187
- var match = regex.exec(uri);
1188
- if (match != null) {
1189
- return {
1190
- scheme: match[2],
1191
- authority: match[4],
1192
- path: match[5],
1193
- query: match[7],
1194
- fragment: match[9],
1195
- };
1196
- }
1197
- else {
1198
- return {};
1199
- }
1200
- };
1201
- /**
1202
- * Convenience method to create a URI from a base string and add params if present
1203
- * @param base
1204
- * @param params
1205
- */
1206
- var parseAndAddParams = function (baseStr, params) {
1207
- var base = parse(baseStr);
1208
- return params ? addQueryParams(params, base) : base;
1209
- };
1210
- var isEqual = function (a, b) {
1211
- var queryA = JSON.stringify(sortByQueryName(queryAsArray(a)));
1212
- var queryB = JSON.stringify(sortByQueryName(queryAsArray(b)));
1213
- return (a.scheme === b.scheme &&
1214
- a.authority === b.authority &&
1215
- a.path === b.path &&
1216
- a.fragment === b.fragment &&
1217
- queryA === queryB);
1218
- };
1219
- var replacePath = function (path, uri) {
1220
- var pathWithForwardSlash = path[0] === '/' ? path : "/".concat(path);
1221
- return __assign(__assign({}, uri), { path: pathWithForwardSlash });
1222
- };
1223
- var pathAsArray = function (uri) {
1224
- return uri.path != null ? sanitizePath(uri.path.split('/')) : [];
1225
- };
1226
- var appendPath = function (path, uri) {
1227
- var beforeParts = pathAsArray(uri);
1228
- var afterParts = sanitizePath(path.split('/'));
1229
- return replacePath(beforeParts.concat(afterParts).join('/'), uri);
1230
- };
1231
- var addQueryString = function (query, uri) {
1232
- var queryArray = stringAsQueryArray(query);
1233
- return addQueryEntries(queryArray, uri);
1234
- };
1235
- var addQueryEntry = function (query, uri) {
1236
- if (query[1] != null) {
1237
- var newQuery = __spreadArray(__spreadArray([], __read(queryAsArray(uri)), false), [query], false);
1238
- return __assign(__assign({}, uri), { query: newQuery
1239
- .map(function (entry) { return entry.map(encodeURIComponent).join('='); })
1240
- .join('&') });
1241
- }
1242
- else {
1243
- return uri;
1244
- }
1245
- };
1246
- var addQueryEntries = function (entries, uri) {
1247
- return entries.reduce(function (result, entry) { return addQueryEntry(entry, result); }, uri);
1248
- };
1249
- var addQueryParams = function (params, uri) {
1250
- return mapAsEntries(params).reduce(function (result, entry) { return addQueryEntry(entry, result); }, uri);
1251
- };
1252
- var replaceFragment = function (fragment, uri) {
1253
- return __assign(__assign({}, uri), { fragment: fragment });
1254
- };
1255
- /**
1256
- * Return an array of name/value pairs representing the query string of a URI.
1257
- * The returned names and values will be URI decoded. If the query string is
1258
- * empty, then an empty array is returned.
1259
- *
1260
- * @param uri A URI to return the query string for.
1261
- */
1262
- var queryAsArray = function (uri) {
1263
- if (uri.query != null) {
1264
- return stringAsQueryArray(uri.query);
1265
- }
1266
- else {
1267
- return [];
1268
- }
1269
- };
1270
- var stringAsQueryArray = function (queryString) {
1271
- return queryString
1272
- .split('&')
1273
- .map(function (param) {
1274
- return param.split('=').map(function (value) { return decodeURIComponent(value); });
1275
- });
1276
- };
1277
- /**
1278
- * Return a map containing a URI's query string names and their values. The
1279
- * returned names and values will be URI decoded. If the query string contains
1280
- * multiple instances of the same name, then the last occurrence will be used.
1281
- *
1282
- * If the query string is empty, an empty map is returned.
1283
- *
1284
- * @param uri A URI to return the query string for.
1285
- */
1286
- var queryAsMap = function (uri) {
1287
- return queryAsArray(uri).reduce(function (map, _a) {
1288
- var _b;
1289
- var _c = __read(_a, 2), name = _c[0], value = _c[1];
1290
- return __assign(__assign({}, map), (_b = {}, _b[name] = value, _b));
1291
- }, {});
1292
- };
1293
- var toString = function (uri) {
1294
- var result = '';
1295
- if (uri.scheme != null && uri.scheme.length > 0) {
1296
- result = "".concat(uri.scheme, ":");
1297
- }
1298
- if (uri.authority != null && uri.authority.length > 0) {
1299
- result += "//".concat(uri.authority);
1300
- }
1301
- result += uri.path;
1302
- if (uri.query != null && uri.query.length > 0) {
1303
- result += "?".concat(uri.query);
1304
- }
1305
- if (uri.fragment != null && uri.fragment.length > 0) {
1306
- result += "#".concat(uri.fragment);
1307
- }
1308
- return result;
1309
- };
1310
- var sanitizePath = function (path) {
1311
- return path.filter(function (segment) { return segment.length > 0; });
1312
- };
1313
- var mapAsEntries = function (map) {
1314
- var entries = [];
1315
- for (var key in map) {
1316
- entries.push([key, map[key]]);
1317
- }
1318
- return entries;
1319
- };
1320
- var sortByQueryName = function (entries) {
1321
- return entries.concat().sort(head(asc));
1322
- };
1093
+ /**
1094
+ * Parses a URI string according to RFC 3986. If the URI is an empty string,
1095
+ * then an empty object is returned.
1096
+ *
1097
+ * See https://tools.ietf.org/html/rfc3986#appendix-B for parsing rules.
1098
+ *
1099
+ * @param uri The URI to parse.
1100
+ */
1101
+ var parse = function (uri) {
1102
+ var regex = /^(([^:/?#]+):)?(\/\/([^/?#]*))?([^?#]*)(\?([^#]*))?(#(.*))?/;
1103
+ var match = regex.exec(uri);
1104
+ if (match != null) {
1105
+ return {
1106
+ scheme: match[2],
1107
+ authority: match[4],
1108
+ path: match[5],
1109
+ query: match[7],
1110
+ fragment: match[9],
1111
+ };
1112
+ }
1113
+ else {
1114
+ return {};
1115
+ }
1116
+ };
1117
+ /**
1118
+ * Convenience method to create a URI from a base string and add params if present
1119
+ * @param base
1120
+ * @param params
1121
+ */
1122
+ var parseAndAddParams = function (baseStr, params) {
1123
+ var base = parse(baseStr);
1124
+ return params ? addQueryParams(params, base) : base;
1125
+ };
1126
+ var isEqual = function (a, b) {
1127
+ var queryA = JSON.stringify(sortByQueryName(queryAsArray(a)));
1128
+ var queryB = JSON.stringify(sortByQueryName(queryAsArray(b)));
1129
+ return (a.scheme === b.scheme &&
1130
+ a.authority === b.authority &&
1131
+ a.path === b.path &&
1132
+ a.fragment === b.fragment &&
1133
+ queryA === queryB);
1134
+ };
1135
+ var replacePath = function (path, uri) {
1136
+ var pathWithForwardSlash = path[0] === '/' ? path : "/".concat(path);
1137
+ return __assign(__assign({}, uri), { path: pathWithForwardSlash });
1138
+ };
1139
+ var pathAsArray = function (uri) {
1140
+ return uri.path != null ? sanitizePath(uri.path.split('/')) : [];
1141
+ };
1142
+ var appendPath = function (path, uri) {
1143
+ var beforeParts = pathAsArray(uri);
1144
+ var afterParts = sanitizePath(path.split('/'));
1145
+ return replacePath(beforeParts.concat(afterParts).join('/'), uri);
1146
+ };
1147
+ var addQueryString = function (query, uri) {
1148
+ var queryArray = stringAsQueryArray(query);
1149
+ return addQueryEntries(queryArray, uri);
1150
+ };
1151
+ var addQueryEntry = function (query, uri) {
1152
+ if (query[1] != null) {
1153
+ var newQuery = __spreadArray(__spreadArray([], __read(queryAsArray(uri)), false), [query], false);
1154
+ return __assign(__assign({}, uri), { query: newQuery
1155
+ .map(function (entry) { return entry.map(encodeURIComponent).join('='); })
1156
+ .join('&') });
1157
+ }
1158
+ else {
1159
+ return uri;
1160
+ }
1161
+ };
1162
+ var addQueryEntries = function (entries, uri) {
1163
+ return entries.reduce(function (result, entry) { return addQueryEntry(entry, result); }, uri);
1164
+ };
1165
+ var addQueryParams = function (params, uri) {
1166
+ return mapAsEntries(params).reduce(function (result, entry) { return addQueryEntry(entry, result); }, uri);
1167
+ };
1168
+ var replaceFragment = function (fragment, uri) {
1169
+ return __assign(__assign({}, uri), { fragment: fragment });
1170
+ };
1171
+ /**
1172
+ * Return an array of name/value pairs representing the query string of a URI.
1173
+ * The returned names and values will be URI decoded. If the query string is
1174
+ * empty, then an empty array is returned.
1175
+ *
1176
+ * @param uri A URI to return the query string for.
1177
+ */
1178
+ var queryAsArray = function (uri) {
1179
+ if (uri.query != null) {
1180
+ return stringAsQueryArray(uri.query);
1181
+ }
1182
+ else {
1183
+ return [];
1184
+ }
1185
+ };
1186
+ var stringAsQueryArray = function (queryString) {
1187
+ return queryString
1188
+ .split('&')
1189
+ .map(function (param) {
1190
+ return param.split('=').map(function (value) { return decodeURIComponent(value); });
1191
+ });
1192
+ };
1193
+ /**
1194
+ * Return a map containing a URI's query string names and their values. The
1195
+ * returned names and values will be URI decoded. If the query string contains
1196
+ * multiple instances of the same name, then the last occurrence will be used.
1197
+ *
1198
+ * If the query string is empty, an empty map is returned.
1199
+ *
1200
+ * @param uri A URI to return the query string for.
1201
+ */
1202
+ var queryAsMap = function (uri) {
1203
+ return queryAsArray(uri).reduce(function (map, _a) {
1204
+ var _b;
1205
+ var _c = __read(_a, 2), name = _c[0], value = _c[1];
1206
+ return __assign(__assign({}, map), (_b = {}, _b[name] = value, _b));
1207
+ }, {});
1208
+ };
1209
+ var toString = function (uri) {
1210
+ var result = '';
1211
+ if (uri.scheme != null && uri.scheme.length > 0) {
1212
+ result = "".concat(uri.scheme, ":");
1213
+ }
1214
+ if (uri.authority != null && uri.authority.length > 0) {
1215
+ result += "//".concat(uri.authority);
1216
+ }
1217
+ result += uri.path;
1218
+ if (uri.query != null && uri.query.length > 0) {
1219
+ result += "?".concat(uri.query);
1220
+ }
1221
+ if (uri.fragment != null && uri.fragment.length > 0) {
1222
+ result += "#".concat(uri.fragment);
1223
+ }
1224
+ return result;
1225
+ };
1226
+ var sanitizePath = function (path) {
1227
+ return path.filter(function (segment) { return segment.length > 0; });
1228
+ };
1229
+ var mapAsEntries = function (map) {
1230
+ var entries = [];
1231
+ for (var key in map) {
1232
+ entries.push([key, map[key]]);
1233
+ }
1234
+ return entries;
1235
+ };
1236
+ var sortByQueryName = function (entries) {
1237
+ return entries.concat().sort(head(asc));
1238
+ };
1323
1239
  /* eslint-enable @typescript-eslint/no-explicit-any */
1324
1240
 
1325
1241
  var uri = /*#__PURE__*/Object.freeze({
@@ -1340,96 +1256,31 @@ var uri = /*#__PURE__*/Object.freeze({
1340
1256
  toString: toString
1341
1257
  });
1342
1258
 
1343
- const rnds8Pool = new Uint8Array(256); // # of random values to pre-allocate
1344
-
1345
- let poolPtr = rnds8Pool.length;
1346
- function rng() {
1347
- if (poolPtr > rnds8Pool.length - 16) {
1348
- crypto.randomFillSync(rnds8Pool);
1349
- poolPtr = 0;
1350
- }
1351
-
1352
- return rnds8Pool.slice(poolPtr, poolPtr += 16);
1353
- }
1354
-
1355
- var REGEX = /^(?:[0-9a-f]{8}-[0-9a-f]{4}-[1-5][0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}|00000000-0000-0000-0000-000000000000)$/i;
1356
-
1357
- function validate(uuid) {
1358
- return typeof uuid === 'string' && REGEX.test(uuid);
1259
+ function create() {
1260
+ return v4();
1359
1261
  }
1360
-
1361
- /**
1362
- * Convert array of 16 byte values to UUID string format of the form:
1363
- * XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX
1364
- */
1365
-
1366
- const byteToHex = [];
1367
-
1368
- for (let i = 0; i < 256; ++i) {
1369
- byteToHex.push((i + 0x100).toString(16).substr(1));
1370
- }
1371
-
1372
- function stringify(arr, offset = 0) {
1373
- // Note: Be careful editing this code! It's been tuned for performance
1374
- // and works in ways you may not expect. See https://github.com/uuidjs/uuid/pull/434
1375
- const uuid = (byteToHex[arr[offset + 0]] + byteToHex[arr[offset + 1]] + byteToHex[arr[offset + 2]] + byteToHex[arr[offset + 3]] + '-' + byteToHex[arr[offset + 4]] + byteToHex[arr[offset + 5]] + '-' + byteToHex[arr[offset + 6]] + byteToHex[arr[offset + 7]] + '-' + byteToHex[arr[offset + 8]] + byteToHex[arr[offset + 9]] + '-' + byteToHex[arr[offset + 10]] + byteToHex[arr[offset + 11]] + byteToHex[arr[offset + 12]] + byteToHex[arr[offset + 13]] + byteToHex[arr[offset + 14]] + byteToHex[arr[offset + 15]]).toLowerCase(); // Consistency check for valid UUID. If this throws, it's likely due to one
1376
- // of the following:
1377
- // - One or more input array values don't map to a hex octet (leading to
1378
- // "undefined" in the uuid)
1379
- // - Invalid input values for the RFC `version` or `variant` fields
1380
-
1381
- if (!validate(uuid)) {
1382
- throw TypeError('Stringified UUID is invalid');
1383
- }
1384
-
1385
- return uuid;
1386
- }
1387
-
1388
- function v4(options, buf, offset) {
1389
- options = options || {};
1390
- const rnds = options.random || (options.rng || rng)(); // Per 4.4, set bits for version and `clock_seq_hi_and_reserved`
1391
-
1392
- rnds[6] = rnds[6] & 0x0f | 0x40;
1393
- rnds[8] = rnds[8] & 0x3f | 0x80; // Copy bytes to buffer, if provided
1394
-
1395
- if (buf) {
1396
- offset = offset || 0;
1397
-
1398
- for (let i = 0; i < 16; ++i) {
1399
- buf[offset + i] = rnds[i];
1262
+ function fromMsbLsb(msb, lsb) {
1263
+ function digits(val, ds) {
1264
+ var hi = BigInt(1) << (ds * BigInt(4));
1265
+ return (hi | (val & (hi - BigInt(1)))).toString(16).substring(1);
1400
1266
  }
1401
-
1402
- return buf;
1403
- }
1404
-
1405
- return stringify(rnds);
1267
+ var msbB = typeof msb === 'string' ? BigInt(msb) : msb;
1268
+ var lsbB = typeof lsb === 'string' ? BigInt(lsb) : lsb;
1269
+ var sec1 = digits(msbB >> BigInt(32), BigInt(8));
1270
+ var sec2 = digits(msbB >> BigInt(16), BigInt(4));
1271
+ var sec3 = digits(msbB, BigInt(4));
1272
+ var sec4 = digits(lsbB >> BigInt(48), BigInt(4));
1273
+ var sec5 = digits(lsbB, BigInt(12));
1274
+ return "".concat(sec1, "-").concat(sec2, "-").concat(sec3, "-").concat(sec4, "-").concat(sec5);
1406
1275
  }
1407
-
1408
- function create() {
1409
- return v4();
1410
- }
1411
- function fromMsbLsb(msb, lsb) {
1412
- function digits(val, ds) {
1413
- var hi = BigInt(1) << (ds * BigInt(4));
1414
- return (hi | (val & (hi - BigInt(1)))).toString(16).substring(1);
1415
- }
1416
- var msbB = typeof msb === 'string' ? BigInt(msb) : msb;
1417
- var lsbB = typeof lsb === 'string' ? BigInt(lsb) : lsb;
1418
- var sec1 = digits(msbB >> BigInt(32), BigInt(8));
1419
- var sec2 = digits(msbB >> BigInt(16), BigInt(4));
1420
- var sec3 = digits(msbB, BigInt(4));
1421
- var sec4 = digits(lsbB >> BigInt(48), BigInt(4));
1422
- var sec5 = digits(lsbB, BigInt(12));
1423
- return "".concat(sec1, "-").concat(sec2, "-").concat(sec3, "-").concat(sec4, "-").concat(sec5);
1424
- }
1425
- function toMsbLsb(id) {
1426
- var _a = __read(id.split('-'), 5), c1 = _a[0], c2 = _a[1], c3 = _a[2], c4 = _a[3], c5 = _a[4];
1427
- if (c1 == null || c2 == null || c3 == null || c4 == null || c5 == null) {
1428
- throw new Error("Invalid UUID string ".concat(id));
1429
- }
1430
- var msb = BigInt.asIntN(64, BigInt("0x".concat(c1 + c2 + c3)));
1431
- var lsb = BigInt.asIntN(64, BigInt("0x".concat(c4 + c5)));
1432
- return { msb: msb.toString(), lsb: lsb.toString() };
1276
+ function toMsbLsb(id) {
1277
+ var _a = __read(id.split('-'), 5), c1 = _a[0], c2 = _a[1], c3 = _a[2], c4 = _a[3], c5 = _a[4];
1278
+ if (c1 == null || c2 == null || c3 == null || c4 == null || c5 == null) {
1279
+ throw new Error("Invalid UUID string ".concat(id));
1280
+ }
1281
+ var msb = BigInt.asIntN(64, BigInt("0x".concat(c1 + c2 + c3)));
1282
+ var lsb = BigInt.asIntN(64, BigInt("0x".concat(c4 + c5)));
1283
+ return { msb: msb.toString(), lsb: lsb.toString() };
1433
1284
  }
1434
1285
 
1435
1286
  var uuid = /*#__PURE__*/Object.freeze({
@@ -1439,65 +1290,68 @@ var uuid = /*#__PURE__*/Object.freeze({
1439
1290
  toMsbLsb: toMsbLsb
1440
1291
  });
1441
1292
 
1442
- var EventDispatcher = /** @class */ (function () {
1443
- function EventDispatcher() {
1444
- this.listeners = [];
1445
- }
1446
- EventDispatcher.prototype.on = function (listener, opts) {
1447
- var _this = this;
1448
- var _a;
1449
- if (opts === void 0) { opts = {}; }
1450
- this.listeners.push(listener);
1451
- var controller = new AbortController();
1452
- controller.signal.addEventListener('abort', function () { return _this.off(listener); });
1453
- (_a = opts.abort) === null || _a === void 0 ? void 0 : _a.addEventListener('abort', function () { return controller.abort(); });
1454
- return { dispose: function () { return controller.abort(); } };
1455
- };
1456
- EventDispatcher.prototype.once = function (opts) {
1457
- var _this = this;
1458
- if (opts === void 0) { opts = {}; }
1459
- return new Promise(function (resolve) {
1460
- _this.on(function (event) { return resolve(event); }, opts);
1461
- });
1462
- };
1463
- EventDispatcher.prototype.onceWhen = function (predicate, opts) {
1464
- var _a;
1465
- if (opts === void 0) { opts = {}; }
1466
- return __awaiter(this, void 0, void 0, function () {
1467
- var controller;
1468
- var _this = this;
1469
- return __generator(this, function (_b) {
1470
- controller = new AbortController();
1471
- (_a = opts.abort) === null || _a === void 0 ? void 0 : _a.addEventListener('abort', function () { return controller.abort(); });
1472
- return [2 /*return*/, new Promise(function (resolve) {
1473
- _this.when(predicate, function (event) {
1474
- if (predicate(event)) {
1475
- controller.abort();
1476
- resolve(event);
1477
- }
1478
- }, __assign(__assign({}, opts), { abort: controller.signal }));
1479
- })];
1480
- });
1481
- });
1482
- };
1483
- EventDispatcher.prototype.when = function (predicate, listener, opts) {
1484
- if (opts === void 0) { opts = {}; }
1485
- return this.on(function (event) {
1486
- if (predicate(event)) {
1487
- listener(event);
1488
- }
1489
- }, opts);
1490
- };
1491
- EventDispatcher.prototype.off = function (listener) {
1492
- var index = this.listeners.indexOf(listener);
1493
- if (index !== -1) {
1494
- this.listeners.splice(index, 1);
1495
- }
1496
- };
1497
- EventDispatcher.prototype.emit = function (event) {
1498
- this.listeners.forEach(function (listener) { return listener(event); });
1499
- };
1500
- return EventDispatcher;
1293
+ var EventDispatcher = /** @class */ (function () {
1294
+ function EventDispatcher() {
1295
+ this.listeners = [];
1296
+ }
1297
+ EventDispatcher.prototype.on = function (listener, opts) {
1298
+ var _this = this;
1299
+ var _a;
1300
+ if (opts === void 0) { opts = {}; }
1301
+ this.listeners.push(listener);
1302
+ var controller = new AbortController();
1303
+ controller.signal.addEventListener('abort', function () { return _this.off(listener); });
1304
+ (_a = opts.abort) === null || _a === void 0 ? void 0 : _a.addEventListener('abort', function () { return controller.abort(); });
1305
+ return { dispose: function () { return controller.abort(); } };
1306
+ };
1307
+ EventDispatcher.prototype.once = function (opts) {
1308
+ var _this = this;
1309
+ if (opts === void 0) { opts = {}; }
1310
+ return new Promise(function (resolve) {
1311
+ var subscription = _this.on(function (event) {
1312
+ subscription.dispose();
1313
+ resolve(event);
1314
+ }, opts);
1315
+ });
1316
+ };
1317
+ EventDispatcher.prototype.onceWhen = function (predicate_1) {
1318
+ return __awaiter(this, arguments, Promise, function (predicate, opts) {
1319
+ var controller;
1320
+ var _this = this;
1321
+ var _a;
1322
+ if (opts === void 0) { opts = {}; }
1323
+ return __generator(this, function (_b) {
1324
+ controller = new AbortController();
1325
+ (_a = opts.abort) === null || _a === void 0 ? void 0 : _a.addEventListener('abort', function () { return controller.abort(); });
1326
+ return [2 /*return*/, new Promise(function (resolve) {
1327
+ _this.when(predicate, function (event) {
1328
+ if (predicate(event)) {
1329
+ controller.abort();
1330
+ resolve(event);
1331
+ }
1332
+ }, __assign(__assign({}, opts), { abort: controller.signal }));
1333
+ })];
1334
+ });
1335
+ });
1336
+ };
1337
+ EventDispatcher.prototype.when = function (predicate, listener, opts) {
1338
+ if (opts === void 0) { opts = {}; }
1339
+ return this.on(function (event) {
1340
+ if (predicate(event)) {
1341
+ listener(event);
1342
+ }
1343
+ }, opts);
1344
+ };
1345
+ EventDispatcher.prototype.off = function (listener) {
1346
+ var index = this.listeners.indexOf(listener);
1347
+ if (index !== -1) {
1348
+ this.listeners.splice(index, 1);
1349
+ }
1350
+ };
1351
+ EventDispatcher.prototype.emit = function (event) {
1352
+ this.listeners.forEach(function (listener) { return listener(event); });
1353
+ };
1354
+ return EventDispatcher;
1501
1355
  }());
1502
1356
 
1503
1357
  export { async as Async, binaryReader as BinaryReader, color as Color, EventDispatcher, eventTargets as EventTargets, mapper as Mapper, objects as Objects, range as Range, sets as Sets, strings as Strings, uuid as UUID, uri as Uri };