UNPKG

962 kBJavaScriptView Raw
1(function (global, factory) {
2 typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports) :
3 typeof define === 'function' && define.amd ? define('leancloud-realtime', ['exports'], factory) :
4 (global = global || self, factory(global.AV = global.AV || {}));
5}(this, (function (exports) { 'use strict';
6
7 var define = undefined;
8 var require = require || function(id) {throw new Error('Unexpected required ' + id)};
9
10
11
12 var process = (typeof window !== 'undefined' && window.process) || {};
13 process.env = process.env || {};
14
15 var commonjsGlobal = typeof globalThis !== 'undefined' ? globalThis : typeof window !== 'undefined' ? window : typeof global !== 'undefined' ? global : typeof self !== 'undefined' ? self : {};
16
17 function unwrapExports (x) {
18 return x && x.__esModule && Object.prototype.hasOwnProperty.call(x, 'default') ? x['default'] : x;
19 }
20
21 function createCommonjsModule(fn, basedir, module) {
22 return module = {
23 path: basedir,
24 exports: {},
25 require: function (path, base) {
26 return commonjsRequire(path, (base === undefined || base === null) ? module.path : base);
27 }
28 }, fn(module, module.exports), module.exports;
29 }
30
31 function getCjsExportFromNamespace (n) {
32 return n && n['default'] || n;
33 }
34
35 function commonjsRequire () {
36 throw new Error('Dynamic requires are not currently supported by @rollup/plugin-commonjs');
37 }
38
39 var _typeof_1 = createCommonjsModule(function (module) {
40 function _typeof(obj) {
41 "@babel/helpers - typeof";
42
43 if (typeof Symbol === "function" && typeof Symbol.iterator === "symbol") {
44 module.exports = _typeof = function _typeof(obj) {
45 return typeof obj;
46 };
47 } else {
48 module.exports = _typeof = function _typeof(obj) {
49 return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj;
50 };
51 }
52
53 return _typeof(obj);
54 }
55
56 module.exports = _typeof;
57 });
58
59 var componentEmitter = createCommonjsModule(function (module) {
60 /**
61 * Expose `Emitter`.
62 */
63 {
64 module.exports = Emitter;
65 }
66 /**
67 * Initialize a new `Emitter`.
68 *
69 * @api public
70 */
71
72
73 function Emitter(obj) {
74 if (obj) return mixin(obj);
75 }
76 /**
77 * Mixin the emitter properties.
78 *
79 * @param {Object} obj
80 * @return {Object}
81 * @api private
82 */
83
84 function mixin(obj) {
85 for (var key in Emitter.prototype) {
86 obj[key] = Emitter.prototype[key];
87 }
88
89 return obj;
90 }
91 /**
92 * Listen on the given `event` with `fn`.
93 *
94 * @param {String} event
95 * @param {Function} fn
96 * @return {Emitter}
97 * @api public
98 */
99
100
101 Emitter.prototype.on = Emitter.prototype.addEventListener = function (event, fn) {
102 this._callbacks = this._callbacks || {};
103 (this._callbacks['$' + event] = this._callbacks['$' + event] || []).push(fn);
104 return this;
105 };
106 /**
107 * Adds an `event` listener that will be invoked a single
108 * time then automatically removed.
109 *
110 * @param {String} event
111 * @param {Function} fn
112 * @return {Emitter}
113 * @api public
114 */
115
116
117 Emitter.prototype.once = function (event, fn) {
118 function on() {
119 this.off(event, on);
120 fn.apply(this, arguments);
121 }
122
123 on.fn = fn;
124 this.on(event, on);
125 return this;
126 };
127 /**
128 * Remove the given callback for `event` or all
129 * registered callbacks.
130 *
131 * @param {String} event
132 * @param {Function} fn
133 * @return {Emitter}
134 * @api public
135 */
136
137
138 Emitter.prototype.off = Emitter.prototype.removeListener = Emitter.prototype.removeAllListeners = Emitter.prototype.removeEventListener = function (event, fn) {
139 this._callbacks = this._callbacks || {}; // all
140
141 if (0 == arguments.length) {
142 this._callbacks = {};
143 return this;
144 } // specific event
145
146
147 var callbacks = this._callbacks['$' + event];
148 if (!callbacks) return this; // remove all handlers
149
150 if (1 == arguments.length) {
151 delete this._callbacks['$' + event];
152 return this;
153 } // remove specific handler
154
155
156 var cb;
157
158 for (var i = 0; i < callbacks.length; i++) {
159 cb = callbacks[i];
160
161 if (cb === fn || cb.fn === fn) {
162 callbacks.splice(i, 1);
163 break;
164 }
165 } // Remove event specific arrays for event types that no
166 // one is subscribed for to avoid memory leak.
167
168
169 if (callbacks.length === 0) {
170 delete this._callbacks['$' + event];
171 }
172
173 return this;
174 };
175 /**
176 * Emit `event` with the given args.
177 *
178 * @param {String} event
179 * @param {Mixed} ...
180 * @return {Emitter}
181 */
182
183
184 Emitter.prototype.emit = function (event) {
185 this._callbacks = this._callbacks || {};
186 var args = new Array(arguments.length - 1),
187 callbacks = this._callbacks['$' + event];
188
189 for (var i = 1; i < arguments.length; i++) {
190 args[i - 1] = arguments[i];
191 }
192
193 if (callbacks) {
194 callbacks = callbacks.slice(0);
195
196 for (var i = 0, len = callbacks.length; i < len; ++i) {
197 callbacks[i].apply(this, args);
198 }
199 }
200
201 return this;
202 };
203 /**
204 * Return array of callbacks for `event`.
205 *
206 * @param {String} event
207 * @return {Array}
208 * @api public
209 */
210
211
212 Emitter.prototype.listeners = function (event) {
213 this._callbacks = this._callbacks || {};
214 return this._callbacks['$' + event] || [];
215 };
216 /**
217 * Check if this emitter has `event` handlers.
218 *
219 * @param {String} event
220 * @return {Boolean}
221 * @api public
222 */
223
224
225 Emitter.prototype.hasListeners = function (event) {
226 return !!this.listeners(event).length;
227 };
228 });
229
230 var fastSafeStringify = stringify;
231 stringify.default = stringify;
232 stringify.stable = deterministicStringify;
233 stringify.stableStringify = deterministicStringify;
234
235 var arr = [];
236 var replacerStack = [];
237
238 // Regular stringify
239 function stringify (obj, replacer, spacer) {
240 decirc(obj, '', [], undefined);
241 var res;
242 if (replacerStack.length === 0) {
243 res = JSON.stringify(obj, replacer, spacer);
244 } else {
245 res = JSON.stringify(obj, replaceGetterValues(replacer), spacer);
246 }
247 while (arr.length !== 0) {
248 var part = arr.pop();
249 if (part.length === 4) {
250 Object.defineProperty(part[0], part[1], part[3]);
251 } else {
252 part[0][part[1]] = part[2];
253 }
254 }
255 return res
256 }
257 function decirc (val, k, stack, parent) {
258 var i;
259 if (typeof val === 'object' && val !== null) {
260 for (i = 0; i < stack.length; i++) {
261 if (stack[i] === val) {
262 var propertyDescriptor = Object.getOwnPropertyDescriptor(parent, k);
263 if (propertyDescriptor.get !== undefined) {
264 if (propertyDescriptor.configurable) {
265 Object.defineProperty(parent, k, { value: '[Circular]' });
266 arr.push([parent, k, val, propertyDescriptor]);
267 } else {
268 replacerStack.push([val, k]);
269 }
270 } else {
271 parent[k] = '[Circular]';
272 arr.push([parent, k, val]);
273 }
274 return
275 }
276 }
277 stack.push(val);
278 // Optimize for Arrays. Big arrays could kill the performance otherwise!
279 if (Array.isArray(val)) {
280 for (i = 0; i < val.length; i++) {
281 decirc(val[i], i, stack, val);
282 }
283 } else {
284 var keys = Object.keys(val);
285 for (i = 0; i < keys.length; i++) {
286 var key = keys[i];
287 decirc(val[key], key, stack, val);
288 }
289 }
290 stack.pop();
291 }
292 }
293
294 // Stable-stringify
295 function compareFunction (a, b) {
296 if (a < b) {
297 return -1
298 }
299 if (a > b) {
300 return 1
301 }
302 return 0
303 }
304
305 function deterministicStringify (obj, replacer, spacer) {
306 var tmp = deterministicDecirc(obj, '', [], undefined) || obj;
307 var res;
308 if (replacerStack.length === 0) {
309 res = JSON.stringify(tmp, replacer, spacer);
310 } else {
311 res = JSON.stringify(tmp, replaceGetterValues(replacer), spacer);
312 }
313 while (arr.length !== 0) {
314 var part = arr.pop();
315 if (part.length === 4) {
316 Object.defineProperty(part[0], part[1], part[3]);
317 } else {
318 part[0][part[1]] = part[2];
319 }
320 }
321 return res
322 }
323
324 function deterministicDecirc (val, k, stack, parent) {
325 var i;
326 if (typeof val === 'object' && val !== null) {
327 for (i = 0; i < stack.length; i++) {
328 if (stack[i] === val) {
329 var propertyDescriptor = Object.getOwnPropertyDescriptor(parent, k);
330 if (propertyDescriptor.get !== undefined) {
331 if (propertyDescriptor.configurable) {
332 Object.defineProperty(parent, k, { value: '[Circular]' });
333 arr.push([parent, k, val, propertyDescriptor]);
334 } else {
335 replacerStack.push([val, k]);
336 }
337 } else {
338 parent[k] = '[Circular]';
339 arr.push([parent, k, val]);
340 }
341 return
342 }
343 }
344 if (typeof val.toJSON === 'function') {
345 return
346 }
347 stack.push(val);
348 // Optimize for Arrays. Big arrays could kill the performance otherwise!
349 if (Array.isArray(val)) {
350 for (i = 0; i < val.length; i++) {
351 deterministicDecirc(val[i], i, stack, val);
352 }
353 } else {
354 // Create a temporary object in the required way
355 var tmp = {};
356 var keys = Object.keys(val).sort(compareFunction);
357 for (i = 0; i < keys.length; i++) {
358 var key = keys[i];
359 deterministicDecirc(val[key], key, stack, val);
360 tmp[key] = val[key];
361 }
362 if (parent !== undefined) {
363 arr.push([parent, k, val]);
364 parent[k] = tmp;
365 } else {
366 return tmp
367 }
368 }
369 stack.pop();
370 }
371 }
372
373 // wraps replacer function to handle values we couldn't replace
374 // and mark them as [Circular]
375 function replaceGetterValues (replacer) {
376 replacer = replacer !== undefined ? replacer : function (k, v) { return v };
377 return function (key, val) {
378 if (replacerStack.length > 0) {
379 for (var i = 0; i < replacerStack.length; i++) {
380 var part = replacerStack[i];
381 if (part[1] === key && part[0] === val) {
382 val = '[Circular]';
383 replacerStack.splice(i, 1);
384 break
385 }
386 }
387 }
388 return replacer.call(this, key, val)
389 }
390 }
391
392 function _typeof(obj) {
393 if (typeof Symbol === "function" && _typeof_1(Symbol.iterator) === "symbol") {
394 _typeof = function _typeof(obj) {
395 return _typeof_1(obj);
396 };
397 } else {
398 _typeof = function _typeof(obj) {
399 return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : _typeof_1(obj);
400 };
401 }
402
403 return _typeof(obj);
404 }
405 /**
406 * Check if `obj` is an object.
407 *
408 * @param {Object} obj
409 * @return {Boolean}
410 * @api private
411 */
412
413
414 function isObject(obj) {
415 return obj !== null && _typeof(obj) === 'object';
416 }
417
418 var isObject_1 = isObject;
419
420 function _typeof$1(obj) {
421 if (typeof Symbol === "function" && _typeof_1(Symbol.iterator) === "symbol") {
422 _typeof$1 = function _typeof(obj) {
423 return _typeof_1(obj);
424 };
425 } else {
426 _typeof$1 = function _typeof(obj) {
427 return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : _typeof_1(obj);
428 };
429 }
430
431 return _typeof$1(obj);
432 }
433 /**
434 * Module of mixed-in functions shared between node and client code
435 */
436
437 /**
438 * Expose `RequestBase`.
439 */
440
441
442 var requestBase = RequestBase;
443 /**
444 * Initialize a new `RequestBase`.
445 *
446 * @api public
447 */
448
449 function RequestBase(obj) {
450 if (obj) return mixin(obj);
451 }
452 /**
453 * Mixin the prototype properties.
454 *
455 * @param {Object} obj
456 * @return {Object}
457 * @api private
458 */
459
460
461 function mixin(obj) {
462 for (var key in RequestBase.prototype) {
463 if (Object.prototype.hasOwnProperty.call(RequestBase.prototype, key)) obj[key] = RequestBase.prototype[key];
464 }
465
466 return obj;
467 }
468 /**
469 * Clear previous timeout.
470 *
471 * @return {Request} for chaining
472 * @api public
473 */
474
475
476 RequestBase.prototype.clearTimeout = function () {
477 clearTimeout(this._timer);
478 clearTimeout(this._responseTimeoutTimer);
479 clearTimeout(this._uploadTimeoutTimer);
480 delete this._timer;
481 delete this._responseTimeoutTimer;
482 delete this._uploadTimeoutTimer;
483 return this;
484 };
485 /**
486 * Override default response body parser
487 *
488 * This function will be called to convert incoming data into request.body
489 *
490 * @param {Function}
491 * @api public
492 */
493
494
495 RequestBase.prototype.parse = function (fn) {
496 this._parser = fn;
497 return this;
498 };
499 /**
500 * Set format of binary response body.
501 * In browser valid formats are 'blob' and 'arraybuffer',
502 * which return Blob and ArrayBuffer, respectively.
503 *
504 * In Node all values result in Buffer.
505 *
506 * Examples:
507 *
508 * req.get('/')
509 * .responseType('blob')
510 * .end(callback);
511 *
512 * @param {String} val
513 * @return {Request} for chaining
514 * @api public
515 */
516
517
518 RequestBase.prototype.responseType = function (val) {
519 this._responseType = val;
520 return this;
521 };
522 /**
523 * Override default request body serializer
524 *
525 * This function will be called to convert data set via .send or .attach into payload to send
526 *
527 * @param {Function}
528 * @api public
529 */
530
531
532 RequestBase.prototype.serialize = function (fn) {
533 this._serializer = fn;
534 return this;
535 };
536 /**
537 * Set timeouts.
538 *
539 * - response timeout is time between sending request and receiving the first byte of the response. Includes DNS and connection time.
540 * - deadline is the time from start of the request to receiving response body in full. If the deadline is too short large files may not load at all on slow connections.
541 * - upload is the time since last bit of data was sent or received. This timeout works only if deadline timeout is off
542 *
543 * Value of 0 or false means no timeout.
544 *
545 * @param {Number|Object} ms or {response, deadline}
546 * @return {Request} for chaining
547 * @api public
548 */
549
550
551 RequestBase.prototype.timeout = function (options) {
552 if (!options || _typeof$1(options) !== 'object') {
553 this._timeout = options;
554 this._responseTimeout = 0;
555 this._uploadTimeout = 0;
556 return this;
557 }
558
559 for (var option in options) {
560 if (Object.prototype.hasOwnProperty.call(options, option)) {
561 switch (option) {
562 case 'deadline':
563 this._timeout = options.deadline;
564 break;
565
566 case 'response':
567 this._responseTimeout = options.response;
568 break;
569
570 case 'upload':
571 this._uploadTimeout = options.upload;
572 break;
573
574 default:
575 console.warn('Unknown timeout option', option);
576 }
577 }
578 }
579
580 return this;
581 };
582 /**
583 * Set number of retry attempts on error.
584 *
585 * Failed requests will be retried 'count' times if timeout or err.code >= 500.
586 *
587 * @param {Number} count
588 * @param {Function} [fn]
589 * @return {Request} for chaining
590 * @api public
591 */
592
593
594 RequestBase.prototype.retry = function (count, fn) {
595 // Default to 1 if no count passed or true
596 if (arguments.length === 0 || count === true) count = 1;
597 if (count <= 0) count = 0;
598 this._maxRetries = count;
599 this._retries = 0;
600 this._retryCallback = fn;
601 return this;
602 };
603
604 var ERROR_CODES = ['ECONNRESET', 'ETIMEDOUT', 'EADDRINFO', 'ESOCKETTIMEDOUT'];
605 /**
606 * Determine if a request should be retried.
607 * (Borrowed from segmentio/superagent-retry)
608 *
609 * @param {Error} err an error
610 * @param {Response} [res] response
611 * @returns {Boolean} if segment should be retried
612 */
613
614 RequestBase.prototype._shouldRetry = function (err, res) {
615 if (!this._maxRetries || this._retries++ >= this._maxRetries) {
616 return false;
617 }
618
619 if (this._retryCallback) {
620 try {
621 var override = this._retryCallback(err, res);
622
623 if (override === true) return true;
624 if (override === false) return false; // undefined falls back to defaults
625 } catch (err_) {
626 console.error(err_);
627 }
628 }
629
630 if (res && res.status && res.status >= 500 && res.status !== 501) return true;
631
632 if (err) {
633 if (err.code && ERROR_CODES.includes(err.code)) return true; // Superagent timeout
634
635 if (err.timeout && err.code === 'ECONNABORTED') return true;
636 if (err.crossDomain) return true;
637 }
638
639 return false;
640 };
641 /**
642 * Retry request
643 *
644 * @return {Request} for chaining
645 * @api private
646 */
647
648
649 RequestBase.prototype._retry = function () {
650 this.clearTimeout(); // node
651
652 if (this.req) {
653 this.req = null;
654 this.req = this.request();
655 }
656
657 this._aborted = false;
658 this.timedout = false;
659 this.timedoutError = null;
660 return this._end();
661 };
662 /**
663 * Promise support
664 *
665 * @param {Function} resolve
666 * @param {Function} [reject]
667 * @return {Request}
668 */
669
670
671 RequestBase.prototype.then = function (resolve, reject) {
672 var _this = this;
673
674 if (!this._fullfilledPromise) {
675 var self = this;
676
677 if (this._endCalled) {
678 console.warn('Warning: superagent request was sent twice, because both .end() and .then() were called. Never call .end() if you use promises');
679 }
680
681 this._fullfilledPromise = new Promise(function (resolve, reject) {
682 self.on('abort', function () {
683 if (_this.timedout && _this.timedoutError) {
684 reject(_this.timedoutError);
685 return;
686 }
687
688 var err = new Error('Aborted');
689 err.code = 'ABORTED';
690 err.status = _this.status;
691 err.method = _this.method;
692 err.url = _this.url;
693 reject(err);
694 });
695 self.end(function (err, res) {
696 if (err) reject(err);else resolve(res);
697 });
698 });
699 }
700
701 return this._fullfilledPromise.then(resolve, reject);
702 };
703
704 RequestBase.prototype["catch"] = function (cb) {
705 return this.then(undefined, cb);
706 };
707 /**
708 * Allow for extension
709 */
710
711
712 RequestBase.prototype.use = function (fn) {
713 fn(this);
714 return this;
715 };
716
717 RequestBase.prototype.ok = function (cb) {
718 if (typeof cb !== 'function') throw new Error('Callback required');
719 this._okCallback = cb;
720 return this;
721 };
722
723 RequestBase.prototype._isResponseOK = function (res) {
724 if (!res) {
725 return false;
726 }
727
728 if (this._okCallback) {
729 return this._okCallback(res);
730 }
731
732 return res.status >= 200 && res.status < 300;
733 };
734 /**
735 * Get request header `field`.
736 * Case-insensitive.
737 *
738 * @param {String} field
739 * @return {String}
740 * @api public
741 */
742
743
744 RequestBase.prototype.get = function (field) {
745 return this._header[field.toLowerCase()];
746 };
747 /**
748 * Get case-insensitive header `field` value.
749 * This is a deprecated internal API. Use `.get(field)` instead.
750 *
751 * (getHeader is no longer used internally by the superagent code base)
752 *
753 * @param {String} field
754 * @return {String}
755 * @api private
756 * @deprecated
757 */
758
759
760 RequestBase.prototype.getHeader = RequestBase.prototype.get;
761 /**
762 * Set header `field` to `val`, or multiple fields with one object.
763 * Case-insensitive.
764 *
765 * Examples:
766 *
767 * req.get('/')
768 * .set('Accept', 'application/json')
769 * .set('X-API-Key', 'foobar')
770 * .end(callback);
771 *
772 * req.get('/')
773 * .set({ Accept: 'application/json', 'X-API-Key': 'foobar' })
774 * .end(callback);
775 *
776 * @param {String|Object} field
777 * @param {String} val
778 * @return {Request} for chaining
779 * @api public
780 */
781
782 RequestBase.prototype.set = function (field, val) {
783 if (isObject_1(field)) {
784 for (var key in field) {
785 if (Object.prototype.hasOwnProperty.call(field, key)) this.set(key, field[key]);
786 }
787
788 return this;
789 }
790
791 this._header[field.toLowerCase()] = val;
792 this.header[field] = val;
793 return this;
794 };
795 /**
796 * Remove header `field`.
797 * Case-insensitive.
798 *
799 * Example:
800 *
801 * req.get('/')
802 * .unset('User-Agent')
803 * .end(callback);
804 *
805 * @param {String} field field name
806 */
807
808
809 RequestBase.prototype.unset = function (field) {
810 delete this._header[field.toLowerCase()];
811 delete this.header[field];
812 return this;
813 };
814 /**
815 * Write the field `name` and `val`, or multiple fields with one object
816 * for "multipart/form-data" request bodies.
817 *
818 * ``` js
819 * request.post('/upload')
820 * .field('foo', 'bar')
821 * .end(callback);
822 *
823 * request.post('/upload')
824 * .field({ foo: 'bar', baz: 'qux' })
825 * .end(callback);
826 * ```
827 *
828 * @param {String|Object} name name of field
829 * @param {String|Blob|File|Buffer|fs.ReadStream} val value of field
830 * @return {Request} for chaining
831 * @api public
832 */
833
834
835 RequestBase.prototype.field = function (name, val) {
836 // name should be either a string or an object.
837 if (name === null || undefined === name) {
838 throw new Error('.field(name, val) name can not be empty');
839 }
840
841 if (this._data) {
842 throw new Error(".field() can't be used if .send() is used. Please use only .send() or only .field() & .attach()");
843 }
844
845 if (isObject_1(name)) {
846 for (var key in name) {
847 if (Object.prototype.hasOwnProperty.call(name, key)) this.field(key, name[key]);
848 }
849
850 return this;
851 }
852
853 if (Array.isArray(val)) {
854 for (var i in val) {
855 if (Object.prototype.hasOwnProperty.call(val, i)) this.field(name, val[i]);
856 }
857
858 return this;
859 } // val should be defined now
860
861
862 if (val === null || undefined === val) {
863 throw new Error('.field(name, val) val can not be empty');
864 }
865
866 if (typeof val === 'boolean') {
867 val = String(val);
868 }
869
870 this._getFormData().append(name, val);
871
872 return this;
873 };
874 /**
875 * Abort the request, and clear potential timeout.
876 *
877 * @return {Request} request
878 * @api public
879 */
880
881
882 RequestBase.prototype.abort = function () {
883 if (this._aborted) {
884 return this;
885 }
886
887 this._aborted = true;
888 if (this.xhr) this.xhr.abort(); // browser
889
890 if (this.req) this.req.abort(); // node
891
892 this.clearTimeout();
893 this.emit('abort');
894 return this;
895 };
896
897 RequestBase.prototype._auth = function (user, pass, options, base64Encoder) {
898 switch (options.type) {
899 case 'basic':
900 this.set('Authorization', "Basic ".concat(base64Encoder("".concat(user, ":").concat(pass))));
901 break;
902
903 case 'auto':
904 this.username = user;
905 this.password = pass;
906 break;
907
908 case 'bearer':
909 // usage would be .auth(accessToken, { type: 'bearer' })
910 this.set('Authorization', "Bearer ".concat(user));
911 break;
912 }
913
914 return this;
915 };
916 /**
917 * Enable transmission of cookies with x-domain requests.
918 *
919 * Note that for this to work the origin must not be
920 * using "Access-Control-Allow-Origin" with a wildcard,
921 * and also must set "Access-Control-Allow-Credentials"
922 * to "true".
923 *
924 * @api public
925 */
926
927
928 RequestBase.prototype.withCredentials = function (on) {
929 // This is browser-only functionality. Node side is no-op.
930 if (on === undefined) on = true;
931 this._withCredentials = on;
932 return this;
933 };
934 /**
935 * Set the max redirects to `n`. Does nothing in browser XHR implementation.
936 *
937 * @param {Number} n
938 * @return {Request} for chaining
939 * @api public
940 */
941
942
943 RequestBase.prototype.redirects = function (n) {
944 this._maxRedirects = n;
945 return this;
946 };
947 /**
948 * Maximum size of buffered response body, in bytes. Counts uncompressed size.
949 * Default 200MB.
950 *
951 * @param {Number} n number of bytes
952 * @return {Request} for chaining
953 */
954
955
956 RequestBase.prototype.maxResponseSize = function (n) {
957 if (typeof n !== 'number') {
958 throw new TypeError('Invalid argument');
959 }
960
961 this._maxResponseSize = n;
962 return this;
963 };
964 /**
965 * Convert to a plain javascript object (not JSON string) of scalar properties.
966 * Note as this method is designed to return a useful non-this value,
967 * it cannot be chained.
968 *
969 * @return {Object} describing method, url, and data of this request
970 * @api public
971 */
972
973
974 RequestBase.prototype.toJSON = function () {
975 return {
976 method: this.method,
977 url: this.url,
978 data: this._data,
979 headers: this._header
980 };
981 };
982 /**
983 * Send `data` as the request body, defaulting the `.type()` to "json" when
984 * an object is given.
985 *
986 * Examples:
987 *
988 * // manual json
989 * request.post('/user')
990 * .type('json')
991 * .send('{"name":"tj"}')
992 * .end(callback)
993 *
994 * // auto json
995 * request.post('/user')
996 * .send({ name: 'tj' })
997 * .end(callback)
998 *
999 * // manual x-www-form-urlencoded
1000 * request.post('/user')
1001 * .type('form')
1002 * .send('name=tj')
1003 * .end(callback)
1004 *
1005 * // auto x-www-form-urlencoded
1006 * request.post('/user')
1007 * .type('form')
1008 * .send({ name: 'tj' })
1009 * .end(callback)
1010 *
1011 * // defaults to x-www-form-urlencoded
1012 * request.post('/user')
1013 * .send('name=tobi')
1014 * .send('species=ferret')
1015 * .end(callback)
1016 *
1017 * @param {String|Object} data
1018 * @return {Request} for chaining
1019 * @api public
1020 */
1021 // eslint-disable-next-line complexity
1022
1023
1024 RequestBase.prototype.send = function (data) {
1025 var isObj = isObject_1(data);
1026 var type = this._header['content-type'];
1027
1028 if (this._formData) {
1029 throw new Error(".send() can't be used if .attach() or .field() is used. Please use only .send() or only .field() & .attach()");
1030 }
1031
1032 if (isObj && !this._data) {
1033 if (Array.isArray(data)) {
1034 this._data = [];
1035 } else if (!this._isHost(data)) {
1036 this._data = {};
1037 }
1038 } else if (data && this._data && this._isHost(this._data)) {
1039 throw new Error("Can't merge these send calls");
1040 } // merge
1041
1042
1043 if (isObj && isObject_1(this._data)) {
1044 for (var key in data) {
1045 if (Object.prototype.hasOwnProperty.call(data, key)) this._data[key] = data[key];
1046 }
1047 } else if (typeof data === 'string') {
1048 // default to x-www-form-urlencoded
1049 if (!type) this.type('form');
1050 type = this._header['content-type'];
1051
1052 if (type === 'application/x-www-form-urlencoded') {
1053 this._data = this._data ? "".concat(this._data, "&").concat(data) : data;
1054 } else {
1055 this._data = (this._data || '') + data;
1056 }
1057 } else {
1058 this._data = data;
1059 }
1060
1061 if (!isObj || this._isHost(data)) {
1062 return this;
1063 } // default to json
1064
1065
1066 if (!type) this.type('json');
1067 return this;
1068 };
1069 /**
1070 * Sort `querystring` by the sort function
1071 *
1072 *
1073 * Examples:
1074 *
1075 * // default order
1076 * request.get('/user')
1077 * .query('name=Nick')
1078 * .query('search=Manny')
1079 * .sortQuery()
1080 * .end(callback)
1081 *
1082 * // customized sort function
1083 * request.get('/user')
1084 * .query('name=Nick')
1085 * .query('search=Manny')
1086 * .sortQuery(function(a, b){
1087 * return a.length - b.length;
1088 * })
1089 * .end(callback)
1090 *
1091 *
1092 * @param {Function} sort
1093 * @return {Request} for chaining
1094 * @api public
1095 */
1096
1097
1098 RequestBase.prototype.sortQuery = function (sort) {
1099 // _sort default to true but otherwise can be a function or boolean
1100 this._sort = typeof sort === 'undefined' ? true : sort;
1101 return this;
1102 };
1103 /**
1104 * Compose querystring to append to req.url
1105 *
1106 * @api private
1107 */
1108
1109
1110 RequestBase.prototype._finalizeQueryString = function () {
1111 var query = this._query.join('&');
1112
1113 if (query) {
1114 this.url += (this.url.includes('?') ? '&' : '?') + query;
1115 }
1116
1117 this._query.length = 0; // Makes the call idempotent
1118
1119 if (this._sort) {
1120 var index = this.url.indexOf('?');
1121
1122 if (index >= 0) {
1123 var queryArr = this.url.slice(index + 1).split('&');
1124
1125 if (typeof this._sort === 'function') {
1126 queryArr.sort(this._sort);
1127 } else {
1128 queryArr.sort();
1129 }
1130
1131 this.url = this.url.slice(0, index) + '?' + queryArr.join('&');
1132 }
1133 }
1134 }; // For backwards compat only
1135
1136
1137 RequestBase.prototype._appendQueryString = function () {
1138 console.warn('Unsupported');
1139 };
1140 /**
1141 * Invoke callback with timeout error.
1142 *
1143 * @api private
1144 */
1145
1146
1147 RequestBase.prototype._timeoutError = function (reason, timeout, errno) {
1148 if (this._aborted) {
1149 return;
1150 }
1151
1152 var err = new Error("".concat(reason + timeout, "ms exceeded"));
1153 err.timeout = timeout;
1154 err.code = 'ECONNABORTED';
1155 err.errno = errno;
1156 this.timedout = true;
1157 this.timedoutError = err;
1158 this.abort();
1159 this.callback(err);
1160 };
1161
1162 RequestBase.prototype._setTimeouts = function () {
1163 var self = this; // deadline
1164
1165 if (this._timeout && !this._timer) {
1166 this._timer = setTimeout(function () {
1167 self._timeoutError('Timeout of ', self._timeout, 'ETIME');
1168 }, this._timeout);
1169 } // response timeout
1170
1171
1172 if (this._responseTimeout && !this._responseTimeoutTimer) {
1173 this._responseTimeoutTimer = setTimeout(function () {
1174 self._timeoutError('Response timeout of ', self._responseTimeout, 'ETIMEDOUT');
1175 }, this._responseTimeout);
1176 }
1177 };
1178
1179 /**
1180 * Return the mime type for the given `str`.
1181 *
1182 * @param {String} str
1183 * @return {String}
1184 * @api private
1185 */
1186
1187 var type = function type(str) {
1188 return str.split(/ *; */).shift();
1189 };
1190 /**
1191 * Return header field parameters.
1192 *
1193 * @param {String} str
1194 * @return {Object}
1195 * @api private
1196 */
1197
1198
1199 var params = function params(str) {
1200 return str.split(/ *; */).reduce(function (obj, str) {
1201 var parts = str.split(/ *= */);
1202 var key = parts.shift();
1203 var val = parts.shift();
1204 if (key && val) obj[key] = val;
1205 return obj;
1206 }, {});
1207 };
1208 /**
1209 * Parse Link header fields.
1210 *
1211 * @param {String} str
1212 * @return {Object}
1213 * @api private
1214 */
1215
1216
1217 var parseLinks = function parseLinks(str) {
1218 return str.split(/ *, */).reduce(function (obj, str) {
1219 var parts = str.split(/ *; */);
1220 var url = parts[0].slice(1, -1);
1221 var rel = parts[1].split(/ *= */)[1].slice(1, -1);
1222 obj[rel] = url;
1223 return obj;
1224 }, {});
1225 };
1226 /**
1227 * Strip content related fields from `header`.
1228 *
1229 * @param {Object} header
1230 * @return {Object} header
1231 * @api private
1232 */
1233
1234
1235 var cleanHeader = function cleanHeader(header, changesOrigin) {
1236 delete header['content-type'];
1237 delete header['content-length'];
1238 delete header['transfer-encoding'];
1239 delete header.host; // secuirty
1240
1241 if (changesOrigin) {
1242 delete header.authorization;
1243 delete header.cookie;
1244 }
1245
1246 return header;
1247 };
1248
1249 var utils = {
1250 type: type,
1251 params: params,
1252 parseLinks: parseLinks,
1253 cleanHeader: cleanHeader
1254 };
1255
1256 /**
1257 * Module dependencies.
1258 */
1259
1260 /**
1261 * Expose `ResponseBase`.
1262 */
1263
1264
1265 var responseBase = ResponseBase;
1266 /**
1267 * Initialize a new `ResponseBase`.
1268 *
1269 * @api public
1270 */
1271
1272 function ResponseBase(obj) {
1273 if (obj) return mixin$1(obj);
1274 }
1275 /**
1276 * Mixin the prototype properties.
1277 *
1278 * @param {Object} obj
1279 * @return {Object}
1280 * @api private
1281 */
1282
1283
1284 function mixin$1(obj) {
1285 for (var key in ResponseBase.prototype) {
1286 if (Object.prototype.hasOwnProperty.call(ResponseBase.prototype, key)) obj[key] = ResponseBase.prototype[key];
1287 }
1288
1289 return obj;
1290 }
1291 /**
1292 * Get case-insensitive `field` value.
1293 *
1294 * @param {String} field
1295 * @return {String}
1296 * @api public
1297 */
1298
1299
1300 ResponseBase.prototype.get = function (field) {
1301 return this.header[field.toLowerCase()];
1302 };
1303 /**
1304 * Set header related properties:
1305 *
1306 * - `.type` the content type without params
1307 *
1308 * A response of "Content-Type: text/plain; charset=utf-8"
1309 * will provide you with a `.type` of "text/plain".
1310 *
1311 * @param {Object} header
1312 * @api private
1313 */
1314
1315
1316 ResponseBase.prototype._setHeaderProperties = function (header) {
1317 // TODO: moar!
1318 // TODO: make this a util
1319 // content-type
1320 var ct = header['content-type'] || '';
1321 this.type = utils.type(ct); // params
1322
1323 var params = utils.params(ct);
1324
1325 for (var key in params) {
1326 if (Object.prototype.hasOwnProperty.call(params, key)) this[key] = params[key];
1327 }
1328
1329 this.links = {}; // links
1330
1331 try {
1332 if (header.link) {
1333 this.links = utils.parseLinks(header.link);
1334 }
1335 } catch (_unused) {// ignore
1336 }
1337 };
1338 /**
1339 * Set flags such as `.ok` based on `status`.
1340 *
1341 * For example a 2xx response will give you a `.ok` of __true__
1342 * whereas 5xx will be __false__ and `.error` will be __true__. The
1343 * `.clientError` and `.serverError` are also available to be more
1344 * specific, and `.statusType` is the class of error ranging from 1..5
1345 * sometimes useful for mapping respond colors etc.
1346 *
1347 * "sugar" properties are also defined for common cases. Currently providing:
1348 *
1349 * - .noContent
1350 * - .badRequest
1351 * - .unauthorized
1352 * - .notAcceptable
1353 * - .notFound
1354 *
1355 * @param {Number} status
1356 * @api private
1357 */
1358
1359
1360 ResponseBase.prototype._setStatusProperties = function (status) {
1361 var type = status / 100 | 0; // status / class
1362
1363 this.statusCode = status;
1364 this.status = this.statusCode;
1365 this.statusType = type; // basics
1366
1367 this.info = type === 1;
1368 this.ok = type === 2;
1369 this.redirect = type === 3;
1370 this.clientError = type === 4;
1371 this.serverError = type === 5;
1372 this.error = type === 4 || type === 5 ? this.toError() : false; // sugar
1373
1374 this.created = status === 201;
1375 this.accepted = status === 202;
1376 this.noContent = status === 204;
1377 this.badRequest = status === 400;
1378 this.unauthorized = status === 401;
1379 this.notAcceptable = status === 406;
1380 this.forbidden = status === 403;
1381 this.notFound = status === 404;
1382 this.unprocessableEntity = status === 422;
1383 };
1384
1385 function _toConsumableArray(arr) {
1386 return _arrayWithoutHoles(arr) || _iterableToArray(arr) || _nonIterableSpread();
1387 }
1388
1389 function _nonIterableSpread() {
1390 throw new TypeError("Invalid attempt to spread non-iterable instance");
1391 }
1392
1393 function _iterableToArray(iter) {
1394 if (Symbol.iterator in Object(iter) || Object.prototype.toString.call(iter) === "[object Arguments]") return Array.from(iter);
1395 }
1396
1397 function _arrayWithoutHoles(arr) {
1398 if (Array.isArray(arr)) {
1399 for (var i = 0, arr2 = new Array(arr.length); i < arr.length; i++) {
1400 arr2[i] = arr[i];
1401 }
1402
1403 return arr2;
1404 }
1405 }
1406
1407 function Agent() {
1408 this._defaults = [];
1409 }
1410
1411 ['use', 'on', 'once', 'set', 'query', 'type', 'accept', 'auth', 'withCredentials', 'sortQuery', 'retry', 'ok', 'redirects', 'timeout', 'buffer', 'serialize', 'parse', 'ca', 'key', 'pfx', 'cert', 'disableTLSCerts'].forEach(function (fn) {
1412 // Default setting for all requests from this agent
1413 Agent.prototype[fn] = function () {
1414 for (var _len = arguments.length, args = new Array(_len), _key = 0; _key < _len; _key++) {
1415 args[_key] = arguments[_key];
1416 }
1417
1418 this._defaults.push({
1419 fn: fn,
1420 args: args
1421 });
1422
1423 return this;
1424 };
1425 });
1426
1427 Agent.prototype._setDefaults = function (req) {
1428 this._defaults.forEach(function (def) {
1429 req[def.fn].apply(req, _toConsumableArray(def.args));
1430 });
1431 };
1432
1433 var agentBase = Agent;
1434
1435 var client = createCommonjsModule(function (module, exports) {
1436
1437 function _typeof(obj) {
1438 if (typeof Symbol === "function" && _typeof_1(Symbol.iterator) === "symbol") {
1439 _typeof = function _typeof(obj) {
1440 return _typeof_1(obj);
1441 };
1442 } else {
1443 _typeof = function _typeof(obj) {
1444 return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : _typeof_1(obj);
1445 };
1446 }
1447
1448 return _typeof(obj);
1449 }
1450 /**
1451 * Root reference for iframes.
1452 */
1453
1454
1455 var root;
1456
1457 if (typeof window !== 'undefined') {
1458 // Browser window
1459 root = window;
1460 } else if (typeof self === 'undefined') {
1461 // Other environments
1462 console.warn('Using browser-only version of superagent in non-browser environment');
1463 root = void 0;
1464 } else {
1465 // Web Worker
1466 root = self;
1467 }
1468 /**
1469 * Noop.
1470 */
1471
1472
1473 function noop() {}
1474 /**
1475 * Expose `request`.
1476 */
1477
1478
1479 module.exports = function (method, url) {
1480 // callback
1481 if (typeof url === 'function') {
1482 return new exports.Request('GET', method).end(url);
1483 } // url first
1484
1485
1486 if (arguments.length === 1) {
1487 return new exports.Request('GET', method);
1488 }
1489
1490 return new exports.Request(method, url);
1491 };
1492
1493 exports = module.exports;
1494 var request = exports;
1495 exports.Request = Request;
1496 /**
1497 * Determine XHR.
1498 */
1499
1500 request.getXHR = function () {
1501 if (root.XMLHttpRequest && (!root.location || root.location.protocol !== 'file:' || !root.ActiveXObject)) {
1502 return new XMLHttpRequest();
1503 }
1504
1505 try {
1506 return new ActiveXObject('Microsoft.XMLHTTP');
1507 } catch (_unused) {}
1508
1509 try {
1510 return new ActiveXObject('Msxml2.XMLHTTP.6.0');
1511 } catch (_unused2) {}
1512
1513 try {
1514 return new ActiveXObject('Msxml2.XMLHTTP.3.0');
1515 } catch (_unused3) {}
1516
1517 try {
1518 return new ActiveXObject('Msxml2.XMLHTTP');
1519 } catch (_unused4) {}
1520
1521 throw new Error('Browser-only version of superagent could not find XHR');
1522 };
1523 /**
1524 * Removes leading and trailing whitespace, added to support IE.
1525 *
1526 * @param {String} s
1527 * @return {String}
1528 * @api private
1529 */
1530
1531
1532 var trim = ''.trim ? function (s) {
1533 return s.trim();
1534 } : function (s) {
1535 return s.replace(/(^\s*|\s*$)/g, '');
1536 };
1537 /**
1538 * Serialize the given `obj`.
1539 *
1540 * @param {Object} obj
1541 * @return {String}
1542 * @api private
1543 */
1544
1545 function serialize(obj) {
1546 if (!isObject_1(obj)) return obj;
1547 var pairs = [];
1548
1549 for (var key in obj) {
1550 if (Object.prototype.hasOwnProperty.call(obj, key)) pushEncodedKeyValuePair(pairs, key, obj[key]);
1551 }
1552
1553 return pairs.join('&');
1554 }
1555 /**
1556 * Helps 'serialize' with serializing arrays.
1557 * Mutates the pairs array.
1558 *
1559 * @param {Array} pairs
1560 * @param {String} key
1561 * @param {Mixed} val
1562 */
1563
1564
1565 function pushEncodedKeyValuePair(pairs, key, val) {
1566 if (val === undefined) return;
1567
1568 if (val === null) {
1569 pairs.push(encodeURI(key));
1570 return;
1571 }
1572
1573 if (Array.isArray(val)) {
1574 val.forEach(function (v) {
1575 pushEncodedKeyValuePair(pairs, key, v);
1576 });
1577 } else if (isObject_1(val)) {
1578 for (var subkey in val) {
1579 if (Object.prototype.hasOwnProperty.call(val, subkey)) pushEncodedKeyValuePair(pairs, "".concat(key, "[").concat(subkey, "]"), val[subkey]);
1580 }
1581 } else {
1582 pairs.push(encodeURI(key) + '=' + encodeURIComponent(val));
1583 }
1584 }
1585 /**
1586 * Expose serialization method.
1587 */
1588
1589
1590 request.serializeObject = serialize;
1591 /**
1592 * Parse the given x-www-form-urlencoded `str`.
1593 *
1594 * @param {String} str
1595 * @return {Object}
1596 * @api private
1597 */
1598
1599 function parseString(str) {
1600 var obj = {};
1601 var pairs = str.split('&');
1602 var pair;
1603 var pos;
1604
1605 for (var i = 0, len = pairs.length; i < len; ++i) {
1606 pair = pairs[i];
1607 pos = pair.indexOf('=');
1608
1609 if (pos === -1) {
1610 obj[decodeURIComponent(pair)] = '';
1611 } else {
1612 obj[decodeURIComponent(pair.slice(0, pos))] = decodeURIComponent(pair.slice(pos + 1));
1613 }
1614 }
1615
1616 return obj;
1617 }
1618 /**
1619 * Expose parser.
1620 */
1621
1622
1623 request.parseString = parseString;
1624 /**
1625 * Default MIME type map.
1626 *
1627 * superagent.types.xml = 'application/xml';
1628 *
1629 */
1630
1631 request.types = {
1632 html: 'text/html',
1633 json: 'application/json',
1634 xml: 'text/xml',
1635 urlencoded: 'application/x-www-form-urlencoded',
1636 form: 'application/x-www-form-urlencoded',
1637 'form-data': 'application/x-www-form-urlencoded'
1638 };
1639 /**
1640 * Default serialization map.
1641 *
1642 * superagent.serialize['application/xml'] = function(obj){
1643 * return 'generated xml here';
1644 * };
1645 *
1646 */
1647
1648 request.serialize = {
1649 'application/x-www-form-urlencoded': serialize,
1650 'application/json': fastSafeStringify
1651 };
1652 /**
1653 * Default parsers.
1654 *
1655 * superagent.parse['application/xml'] = function(str){
1656 * return { object parsed from str };
1657 * };
1658 *
1659 */
1660
1661 request.parse = {
1662 'application/x-www-form-urlencoded': parseString,
1663 'application/json': JSON.parse
1664 };
1665 /**
1666 * Parse the given header `str` into
1667 * an object containing the mapped fields.
1668 *
1669 * @param {String} str
1670 * @return {Object}
1671 * @api private
1672 */
1673
1674 function parseHeader(str) {
1675 var lines = str.split(/\r?\n/);
1676 var fields = {};
1677 var index;
1678 var line;
1679 var field;
1680 var val;
1681
1682 for (var i = 0, len = lines.length; i < len; ++i) {
1683 line = lines[i];
1684 index = line.indexOf(':');
1685
1686 if (index === -1) {
1687 // could be empty line, just skip it
1688 continue;
1689 }
1690
1691 field = line.slice(0, index).toLowerCase();
1692 val = trim(line.slice(index + 1));
1693 fields[field] = val;
1694 }
1695
1696 return fields;
1697 }
1698 /**
1699 * Check if `mime` is json or has +json structured syntax suffix.
1700 *
1701 * @param {String} mime
1702 * @return {Boolean}
1703 * @api private
1704 */
1705
1706
1707 function isJSON(mime) {
1708 // should match /json or +json
1709 // but not /json-seq
1710 return /[/+]json($|[^-\w])/.test(mime);
1711 }
1712 /**
1713 * Initialize a new `Response` with the given `xhr`.
1714 *
1715 * - set flags (.ok, .error, etc)
1716 * - parse header
1717 *
1718 * Examples:
1719 *
1720 * Aliasing `superagent` as `request` is nice:
1721 *
1722 * request = superagent;
1723 *
1724 * We can use the promise-like API, or pass callbacks:
1725 *
1726 * request.get('/').end(function(res){});
1727 * request.get('/', function(res){});
1728 *
1729 * Sending data can be chained:
1730 *
1731 * request
1732 * .post('/user')
1733 * .send({ name: 'tj' })
1734 * .end(function(res){});
1735 *
1736 * Or passed to `.send()`:
1737 *
1738 * request
1739 * .post('/user')
1740 * .send({ name: 'tj' }, function(res){});
1741 *
1742 * Or passed to `.post()`:
1743 *
1744 * request
1745 * .post('/user', { name: 'tj' })
1746 * .end(function(res){});
1747 *
1748 * Or further reduced to a single call for simple cases:
1749 *
1750 * request
1751 * .post('/user', { name: 'tj' }, function(res){});
1752 *
1753 * @param {XMLHTTPRequest} xhr
1754 * @param {Object} options
1755 * @api private
1756 */
1757
1758
1759 function Response(req) {
1760 this.req = req;
1761 this.xhr = this.req.xhr; // responseText is accessible only if responseType is '' or 'text' and on older browsers
1762
1763 this.text = this.req.method !== 'HEAD' && (this.xhr.responseType === '' || this.xhr.responseType === 'text') || typeof this.xhr.responseType === 'undefined' ? this.xhr.responseText : null;
1764 this.statusText = this.req.xhr.statusText;
1765 var status = this.xhr.status; // handle IE9 bug: http://stackoverflow.com/questions/10046972/msie-returns-status-code-of-1223-for-ajax-request
1766
1767 if (status === 1223) {
1768 status = 204;
1769 }
1770
1771 this._setStatusProperties(status);
1772
1773 this.headers = parseHeader(this.xhr.getAllResponseHeaders());
1774 this.header = this.headers; // getAllResponseHeaders sometimes falsely returns "" for CORS requests, but
1775 // getResponseHeader still works. so we get content-type even if getting
1776 // other headers fails.
1777
1778 this.header['content-type'] = this.xhr.getResponseHeader('content-type');
1779
1780 this._setHeaderProperties(this.header);
1781
1782 if (this.text === null && req._responseType) {
1783 this.body = this.xhr.response;
1784 } else {
1785 this.body = this.req.method === 'HEAD' ? null : this._parseBody(this.text ? this.text : this.xhr.response);
1786 }
1787 } // eslint-disable-next-line new-cap
1788
1789
1790 responseBase(Response.prototype);
1791 /**
1792 * Parse the given body `str`.
1793 *
1794 * Used for auto-parsing of bodies. Parsers
1795 * are defined on the `superagent.parse` object.
1796 *
1797 * @param {String} str
1798 * @return {Mixed}
1799 * @api private
1800 */
1801
1802 Response.prototype._parseBody = function (str) {
1803 var parse = request.parse[this.type];
1804
1805 if (this.req._parser) {
1806 return this.req._parser(this, str);
1807 }
1808
1809 if (!parse && isJSON(this.type)) {
1810 parse = request.parse['application/json'];
1811 }
1812
1813 return parse && str && (str.length > 0 || str instanceof Object) ? parse(str) : null;
1814 };
1815 /**
1816 * Return an `Error` representative of this response.
1817 *
1818 * @return {Error}
1819 * @api public
1820 */
1821
1822
1823 Response.prototype.toError = function () {
1824 var req = this.req;
1825 var method = req.method;
1826 var url = req.url;
1827 var msg = "cannot ".concat(method, " ").concat(url, " (").concat(this.status, ")");
1828 var err = new Error(msg);
1829 err.status = this.status;
1830 err.method = method;
1831 err.url = url;
1832 return err;
1833 };
1834 /**
1835 * Expose `Response`.
1836 */
1837
1838
1839 request.Response = Response;
1840 /**
1841 * Initialize a new `Request` with the given `method` and `url`.
1842 *
1843 * @param {String} method
1844 * @param {String} url
1845 * @api public
1846 */
1847
1848 function Request(method, url) {
1849 var self = this;
1850 this._query = this._query || [];
1851 this.method = method;
1852 this.url = url;
1853 this.header = {}; // preserves header name case
1854
1855 this._header = {}; // coerces header names to lowercase
1856
1857 this.on('end', function () {
1858 var err = null;
1859 var res = null;
1860
1861 try {
1862 res = new Response(self);
1863 } catch (err_) {
1864 err = new Error('Parser is unable to parse the response');
1865 err.parse = true;
1866 err.original = err_; // issue #675: return the raw response if the response parsing fails
1867
1868 if (self.xhr) {
1869 // ie9 doesn't have 'response' property
1870 err.rawResponse = typeof self.xhr.responseType === 'undefined' ? self.xhr.responseText : self.xhr.response; // issue #876: return the http status code if the response parsing fails
1871
1872 err.status = self.xhr.status ? self.xhr.status : null;
1873 err.statusCode = err.status; // backwards-compat only
1874 } else {
1875 err.rawResponse = null;
1876 err.status = null;
1877 }
1878
1879 return self.callback(err);
1880 }
1881
1882 self.emit('response', res);
1883 var new_err;
1884
1885 try {
1886 if (!self._isResponseOK(res)) {
1887 new_err = new Error(res.statusText || res.text || 'Unsuccessful HTTP response');
1888 }
1889 } catch (err_) {
1890 new_err = err_; // ok() callback can throw
1891 } // #1000 don't catch errors from the callback to avoid double calling it
1892
1893
1894 if (new_err) {
1895 new_err.original = err;
1896 new_err.response = res;
1897 new_err.status = res.status;
1898 self.callback(new_err, res);
1899 } else {
1900 self.callback(null, res);
1901 }
1902 });
1903 }
1904 /**
1905 * Mixin `Emitter` and `RequestBase`.
1906 */
1907 // eslint-disable-next-line new-cap
1908
1909
1910 componentEmitter(Request.prototype); // eslint-disable-next-line new-cap
1911
1912 requestBase(Request.prototype);
1913 /**
1914 * Set Content-Type to `type`, mapping values from `request.types`.
1915 *
1916 * Examples:
1917 *
1918 * superagent.types.xml = 'application/xml';
1919 *
1920 * request.post('/')
1921 * .type('xml')
1922 * .send(xmlstring)
1923 * .end(callback);
1924 *
1925 * request.post('/')
1926 * .type('application/xml')
1927 * .send(xmlstring)
1928 * .end(callback);
1929 *
1930 * @param {String} type
1931 * @return {Request} for chaining
1932 * @api public
1933 */
1934
1935 Request.prototype.type = function (type) {
1936 this.set('Content-Type', request.types[type] || type);
1937 return this;
1938 };
1939 /**
1940 * Set Accept to `type`, mapping values from `request.types`.
1941 *
1942 * Examples:
1943 *
1944 * superagent.types.json = 'application/json';
1945 *
1946 * request.get('/agent')
1947 * .accept('json')
1948 * .end(callback);
1949 *
1950 * request.get('/agent')
1951 * .accept('application/json')
1952 * .end(callback);
1953 *
1954 * @param {String} accept
1955 * @return {Request} for chaining
1956 * @api public
1957 */
1958
1959
1960 Request.prototype.accept = function (type) {
1961 this.set('Accept', request.types[type] || type);
1962 return this;
1963 };
1964 /**
1965 * Set Authorization field value with `user` and `pass`.
1966 *
1967 * @param {String} user
1968 * @param {String} [pass] optional in case of using 'bearer' as type
1969 * @param {Object} options with 'type' property 'auto', 'basic' or 'bearer' (default 'basic')
1970 * @return {Request} for chaining
1971 * @api public
1972 */
1973
1974
1975 Request.prototype.auth = function (user, pass, options) {
1976 if (arguments.length === 1) pass = '';
1977
1978 if (_typeof(pass) === 'object' && pass !== null) {
1979 // pass is optional and can be replaced with options
1980 options = pass;
1981 pass = '';
1982 }
1983
1984 if (!options) {
1985 options = {
1986 type: typeof btoa === 'function' ? 'basic' : 'auto'
1987 };
1988 }
1989
1990 var encoder = function encoder(string) {
1991 if (typeof btoa === 'function') {
1992 return btoa(string);
1993 }
1994
1995 throw new Error('Cannot use basic auth, btoa is not a function');
1996 };
1997
1998 return this._auth(user, pass, options, encoder);
1999 };
2000 /**
2001 * Add query-string `val`.
2002 *
2003 * Examples:
2004 *
2005 * request.get('/shoes')
2006 * .query('size=10')
2007 * .query({ color: 'blue' })
2008 *
2009 * @param {Object|String} val
2010 * @return {Request} for chaining
2011 * @api public
2012 */
2013
2014
2015 Request.prototype.query = function (val) {
2016 if (typeof val !== 'string') val = serialize(val);
2017 if (val) this._query.push(val);
2018 return this;
2019 };
2020 /**
2021 * Queue the given `file` as an attachment to the specified `field`,
2022 * with optional `options` (or filename).
2023 *
2024 * ``` js
2025 * request.post('/upload')
2026 * .attach('content', new Blob(['<a id="a"><b id="b">hey!</b></a>'], { type: "text/html"}))
2027 * .end(callback);
2028 * ```
2029 *
2030 * @param {String} field
2031 * @param {Blob|File} file
2032 * @param {String|Object} options
2033 * @return {Request} for chaining
2034 * @api public
2035 */
2036
2037
2038 Request.prototype.attach = function (field, file, options) {
2039 if (file) {
2040 if (this._data) {
2041 throw new Error("superagent can't mix .send() and .attach()");
2042 }
2043
2044 this._getFormData().append(field, file, options || file.name);
2045 }
2046
2047 return this;
2048 };
2049
2050 Request.prototype._getFormData = function () {
2051 if (!this._formData) {
2052 this._formData = new root.FormData();
2053 }
2054
2055 return this._formData;
2056 };
2057 /**
2058 * Invoke the callback with `err` and `res`
2059 * and handle arity check.
2060 *
2061 * @param {Error} err
2062 * @param {Response} res
2063 * @api private
2064 */
2065
2066
2067 Request.prototype.callback = function (err, res) {
2068 if (this._shouldRetry(err, res)) {
2069 return this._retry();
2070 }
2071
2072 var fn = this._callback;
2073 this.clearTimeout();
2074
2075 if (err) {
2076 if (this._maxRetries) err.retries = this._retries - 1;
2077 this.emit('error', err);
2078 }
2079
2080 fn(err, res);
2081 };
2082 /**
2083 * Invoke callback with x-domain error.
2084 *
2085 * @api private
2086 */
2087
2088
2089 Request.prototype.crossDomainError = function () {
2090 var err = new Error('Request has been terminated\nPossible causes: the network is offline, Origin is not allowed by Access-Control-Allow-Origin, the page is being unloaded, etc.');
2091 err.crossDomain = true;
2092 err.status = this.status;
2093 err.method = this.method;
2094 err.url = this.url;
2095 this.callback(err);
2096 }; // This only warns, because the request is still likely to work
2097
2098
2099 Request.prototype.agent = function () {
2100 console.warn('This is not supported in browser version of superagent');
2101 return this;
2102 };
2103
2104 Request.prototype.ca = Request.prototype.agent;
2105 Request.prototype.buffer = Request.prototype.ca; // This throws, because it can't send/receive data as expected
2106
2107 Request.prototype.write = function () {
2108 throw new Error('Streaming is not supported in browser version of superagent');
2109 };
2110
2111 Request.prototype.pipe = Request.prototype.write;
2112 /**
2113 * Check if `obj` is a host object,
2114 * we don't want to serialize these :)
2115 *
2116 * @param {Object} obj host object
2117 * @return {Boolean} is a host object
2118 * @api private
2119 */
2120
2121 Request.prototype._isHost = function (obj) {
2122 // Native objects stringify to [object File], [object Blob], [object FormData], etc.
2123 return obj && _typeof(obj) === 'object' && !Array.isArray(obj) && Object.prototype.toString.call(obj) !== '[object Object]';
2124 };
2125 /**
2126 * Initiate request, invoking callback `fn(res)`
2127 * with an instanceof `Response`.
2128 *
2129 * @param {Function} fn
2130 * @return {Request} for chaining
2131 * @api public
2132 */
2133
2134
2135 Request.prototype.end = function (fn) {
2136 if (this._endCalled) {
2137 console.warn('Warning: .end() was called twice. This is not supported in superagent');
2138 }
2139
2140 this._endCalled = true; // store callback
2141
2142 this._callback = fn || noop; // querystring
2143
2144 this._finalizeQueryString();
2145
2146 this._end();
2147 };
2148
2149 Request.prototype._setUploadTimeout = function () {
2150 var self = this; // upload timeout it's wokrs only if deadline timeout is off
2151
2152 if (this._uploadTimeout && !this._uploadTimeoutTimer) {
2153 this._uploadTimeoutTimer = setTimeout(function () {
2154 self._timeoutError('Upload timeout of ', self._uploadTimeout, 'ETIMEDOUT');
2155 }, this._uploadTimeout);
2156 }
2157 }; // eslint-disable-next-line complexity
2158
2159
2160 Request.prototype._end = function () {
2161 if (this._aborted) return this.callback(new Error('The request has been aborted even before .end() was called'));
2162 var self = this;
2163 this.xhr = request.getXHR();
2164 var xhr = this.xhr;
2165 var data = this._formData || this._data;
2166
2167 this._setTimeouts(); // state change
2168
2169
2170 xhr.onreadystatechange = function () {
2171 var readyState = xhr.readyState;
2172
2173 if (readyState >= 2 && self._responseTimeoutTimer) {
2174 clearTimeout(self._responseTimeoutTimer);
2175 }
2176
2177 if (readyState !== 4) {
2178 return;
2179 } // In IE9, reads to any property (e.g. status) off of an aborted XHR will
2180 // result in the error "Could not complete the operation due to error c00c023f"
2181
2182
2183 var status;
2184
2185 try {
2186 status = xhr.status;
2187 } catch (_unused5) {
2188 status = 0;
2189 }
2190
2191 if (!status) {
2192 if (self.timedout || self._aborted) return;
2193 return self.crossDomainError();
2194 }
2195
2196 self.emit('end');
2197 }; // progress
2198
2199
2200 var handleProgress = function handleProgress(direction, e) {
2201 if (e.total > 0) {
2202 e.percent = e.loaded / e.total * 100;
2203
2204 if (e.percent === 100) {
2205 clearTimeout(self._uploadTimeoutTimer);
2206 }
2207 }
2208
2209 e.direction = direction;
2210 self.emit('progress', e);
2211 };
2212
2213 if (this.hasListeners('progress')) {
2214 try {
2215 xhr.addEventListener('progress', handleProgress.bind(null, 'download'));
2216
2217 if (xhr.upload) {
2218 xhr.upload.addEventListener('progress', handleProgress.bind(null, 'upload'));
2219 }
2220 } catch (_unused6) {// Accessing xhr.upload fails in IE from a web worker, so just pretend it doesn't exist.
2221 // Reported here:
2222 // https://connect.microsoft.com/IE/feedback/details/837245/xmlhttprequest-upload-throws-invalid-argument-when-used-from-web-worker-context
2223 }
2224 }
2225
2226 if (xhr.upload) {
2227 this._setUploadTimeout();
2228 } // initiate request
2229
2230
2231 try {
2232 if (this.username && this.password) {
2233 xhr.open(this.method, this.url, true, this.username, this.password);
2234 } else {
2235 xhr.open(this.method, this.url, true);
2236 }
2237 } catch (err) {
2238 // see #1149
2239 return this.callback(err);
2240 } // CORS
2241
2242
2243 if (this._withCredentials) xhr.withCredentials = true; // body
2244
2245 if (!this._formData && this.method !== 'GET' && this.method !== 'HEAD' && typeof data !== 'string' && !this._isHost(data)) {
2246 // serialize stuff
2247 var contentType = this._header['content-type'];
2248
2249 var _serialize = this._serializer || request.serialize[contentType ? contentType.split(';')[0] : ''];
2250
2251 if (!_serialize && isJSON(contentType)) {
2252 _serialize = request.serialize['application/json'];
2253 }
2254
2255 if (_serialize) data = _serialize(data);
2256 } // set header fields
2257
2258
2259 for (var field in this.header) {
2260 if (this.header[field] === null) continue;
2261 if (Object.prototype.hasOwnProperty.call(this.header, field)) xhr.setRequestHeader(field, this.header[field]);
2262 }
2263
2264 if (this._responseType) {
2265 xhr.responseType = this._responseType;
2266 } // send stuff
2267
2268
2269 this.emit('request', this); // IE11 xhr.send(undefined) sends 'undefined' string as POST payload (instead of nothing)
2270 // We need null here if data is undefined
2271
2272 xhr.send(typeof data === 'undefined' ? null : data);
2273 };
2274
2275 request.agent = function () {
2276 return new agentBase();
2277 };
2278
2279 ['GET', 'POST', 'OPTIONS', 'PATCH', 'PUT', 'DELETE'].forEach(function (method) {
2280 agentBase.prototype[method.toLowerCase()] = function (url, fn) {
2281 var req = new request.Request(method, url);
2282
2283 this._setDefaults(req);
2284
2285 if (fn) {
2286 req.end(fn);
2287 }
2288
2289 return req;
2290 };
2291 });
2292 agentBase.prototype.del = agentBase.prototype["delete"];
2293 /**
2294 * GET `url` with optional callback `fn(res)`.
2295 *
2296 * @param {String} url
2297 * @param {Mixed|Function} [data] or fn
2298 * @param {Function} [fn]
2299 * @return {Request}
2300 * @api public
2301 */
2302
2303 request.get = function (url, data, fn) {
2304 var req = request('GET', url);
2305
2306 if (typeof data === 'function') {
2307 fn = data;
2308 data = null;
2309 }
2310
2311 if (data) req.query(data);
2312 if (fn) req.end(fn);
2313 return req;
2314 };
2315 /**
2316 * HEAD `url` with optional callback `fn(res)`.
2317 *
2318 * @param {String} url
2319 * @param {Mixed|Function} [data] or fn
2320 * @param {Function} [fn]
2321 * @return {Request}
2322 * @api public
2323 */
2324
2325
2326 request.head = function (url, data, fn) {
2327 var req = request('HEAD', url);
2328
2329 if (typeof data === 'function') {
2330 fn = data;
2331 data = null;
2332 }
2333
2334 if (data) req.query(data);
2335 if (fn) req.end(fn);
2336 return req;
2337 };
2338 /**
2339 * OPTIONS query to `url` with optional callback `fn(res)`.
2340 *
2341 * @param {String} url
2342 * @param {Mixed|Function} [data] or fn
2343 * @param {Function} [fn]
2344 * @return {Request}
2345 * @api public
2346 */
2347
2348
2349 request.options = function (url, data, fn) {
2350 var req = request('OPTIONS', url);
2351
2352 if (typeof data === 'function') {
2353 fn = data;
2354 data = null;
2355 }
2356
2357 if (data) req.send(data);
2358 if (fn) req.end(fn);
2359 return req;
2360 };
2361 /**
2362 * DELETE `url` with optional `data` and callback `fn(res)`.
2363 *
2364 * @param {String} url
2365 * @param {Mixed} [data]
2366 * @param {Function} [fn]
2367 * @return {Request}
2368 * @api public
2369 */
2370
2371
2372 function del(url, data, fn) {
2373 var req = request('DELETE', url);
2374
2375 if (typeof data === 'function') {
2376 fn = data;
2377 data = null;
2378 }
2379
2380 if (data) req.send(data);
2381 if (fn) req.end(fn);
2382 return req;
2383 }
2384
2385 request.del = del;
2386 request["delete"] = del;
2387 /**
2388 * PATCH `url` with optional `data` and callback `fn(res)`.
2389 *
2390 * @param {String} url
2391 * @param {Mixed} [data]
2392 * @param {Function} [fn]
2393 * @return {Request}
2394 * @api public
2395 */
2396
2397 request.patch = function (url, data, fn) {
2398 var req = request('PATCH', url);
2399
2400 if (typeof data === 'function') {
2401 fn = data;
2402 data = null;
2403 }
2404
2405 if (data) req.send(data);
2406 if (fn) req.end(fn);
2407 return req;
2408 };
2409 /**
2410 * POST `url` with optional `data` and callback `fn(res)`.
2411 *
2412 * @param {String} url
2413 * @param {Mixed} [data]
2414 * @param {Function} [fn]
2415 * @return {Request}
2416 * @api public
2417 */
2418
2419
2420 request.post = function (url, data, fn) {
2421 var req = request('POST', url);
2422
2423 if (typeof data === 'function') {
2424 fn = data;
2425 data = null;
2426 }
2427
2428 if (data) req.send(data);
2429 if (fn) req.end(fn);
2430 return req;
2431 };
2432 /**
2433 * PUT `url` with optional `data` and callback `fn(res)`.
2434 *
2435 * @param {String} url
2436 * @param {Mixed|Function} [data] or fn
2437 * @param {Function} [fn]
2438 * @return {Request}
2439 * @api public
2440 */
2441
2442
2443 request.put = function (url, data, fn) {
2444 var req = request('PUT', url);
2445
2446 if (typeof data === 'function') {
2447 fn = data;
2448 data = null;
2449 }
2450
2451 if (data) req.send(data);
2452 if (fn) req.end(fn);
2453 return req;
2454 };
2455 });
2456 var client_1 = client.Request;
2457
2458 var lib = createCommonjsModule(function (module, exports) {
2459 Object.defineProperty(exports, "__esModule", { value: true });
2460
2461 exports.request = function (url, options) {
2462 if (options === void 0) { options = {}; }
2463 var _a = options.method, method = _a === void 0 ? "GET" : _a, data = options.data, headers = options.headers, onprogress = options.onprogress;
2464 var req = client(method, url);
2465 if (headers) {
2466 req.set(headers);
2467 }
2468 if (onprogress) {
2469 req.on("progress", onprogress);
2470 }
2471 return req
2472 .send(data)
2473 .catch(function (error) {
2474 if (error.response) {
2475 return error.response;
2476 }
2477 throw error;
2478 })
2479 .then(function (_a) {
2480 var status = _a.status, ok = _a.ok, header = _a.header, body = _a.body;
2481 return ({
2482 status: status,
2483 ok: ok,
2484 headers: header,
2485 data: body
2486 });
2487 });
2488 };
2489 exports.upload = function (url, file, options) {
2490 if (options === void 0) { options = {}; }
2491 var data = options.data, headers = options.headers, onprogress = options.onprogress;
2492 var req = client("POST", url).attach(file.field, file.data, file.name);
2493 if (data) {
2494 req.field(data);
2495 }
2496 if (headers) {
2497 req.set(headers);
2498 }
2499 if (onprogress) {
2500 req.on("progress", onprogress);
2501 }
2502 return req
2503 .catch(function (error) {
2504 if (error.response) {
2505 return error.response;
2506 }
2507 throw error;
2508 })
2509 .then(function (_a) {
2510 var status = _a.status, ok = _a.ok, header = _a.header, body = _a.body;
2511 return ({
2512 status: status,
2513 ok: ok,
2514 headers: header,
2515 data: body
2516 });
2517 });
2518 };
2519
2520 });
2521
2522 unwrapExports(lib);
2523 var lib_1 = lib.request;
2524 var lib_2 = lib.upload;
2525
2526 var lib$1 = createCommonjsModule(function (module, exports) {
2527
2528 Object.defineProperty(exports, "__esModule", {
2529 value: true
2530 });
2531 exports.request = lib.request;
2532 exports.upload = lib.upload;
2533 exports.storage = window.localStorage;
2534 exports.WebSocket = window.WebSocket;
2535 exports.platformInfo = {
2536 name: "Browser"
2537 };
2538 });
2539 unwrapExports(lib$1);
2540 var lib_1$1 = lib$1.request;
2541 var lib_2$1 = lib$1.upload;
2542 var lib_3 = lib$1.storage;
2543 var lib_4 = lib$1.WebSocket;
2544 var lib_5 = lib$1.platformInfo;
2545
2546 function _defineProperty(obj, key, value) {
2547 if (key in obj) {
2548 Object.defineProperty(obj, key, {
2549 value: value,
2550 enumerable: true,
2551 configurable: true,
2552 writable: true
2553 });
2554 } else {
2555 obj[key] = value;
2556 }
2557
2558 return obj;
2559 }
2560
2561 var defineProperty = _defineProperty;
2562
2563 var long_1 = createCommonjsModule(function (module) {
2564 /*
2565 Copyright 2013 Daniel Wirtz <dcode@dcode.io>
2566 Copyright 2009 The Closure Library Authors. All Rights Reserved.
2567
2568 Licensed under the Apache License, Version 2.0 (the "License");
2569 you may not use this file except in compliance with the License.
2570 You may obtain a copy of the License at
2571
2572 http://www.apache.org/licenses/LICENSE-2.0
2573
2574 Unless required by applicable law or agreed to in writing, software
2575 distributed under the License is distributed on an "AS-IS" BASIS,
2576 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
2577 See the License for the specific language governing permissions and
2578 limitations under the License.
2579 */
2580
2581 /**
2582 * @license long.js (c) 2013 Daniel Wirtz <dcode@dcode.io>
2583 * Released under the Apache License, Version 2.0
2584 * see: https://github.com/dcodeIO/long.js for details
2585 */
2586 (function(global, factory) {
2587
2588 /* AMD */ if (typeof commonjsRequire === 'function' && 'object' === "object" && module && module["exports"])
2589 module["exports"] = factory();
2590 /* Global */ else
2591 (global["dcodeIO"] = global["dcodeIO"] || {})["Long"] = factory();
2592
2593 })(commonjsGlobal, function() {
2594
2595 /**
2596 * Constructs a 64 bit two's-complement integer, given its low and high 32 bit values as *signed* integers.
2597 * See the from* functions below for more convenient ways of constructing Longs.
2598 * @exports Long
2599 * @class A Long class for representing a 64 bit two's-complement integer value.
2600 * @param {number} low The low (signed) 32 bits of the long
2601 * @param {number} high The high (signed) 32 bits of the long
2602 * @param {boolean=} unsigned Whether unsigned or not, defaults to `false` for signed
2603 * @constructor
2604 */
2605 function Long(low, high, unsigned) {
2606
2607 /**
2608 * The low 32 bits as a signed value.
2609 * @type {number}
2610 */
2611 this.low = low | 0;
2612
2613 /**
2614 * The high 32 bits as a signed value.
2615 * @type {number}
2616 */
2617 this.high = high | 0;
2618
2619 /**
2620 * Whether unsigned or not.
2621 * @type {boolean}
2622 */
2623 this.unsigned = !!unsigned;
2624 }
2625
2626 // The internal representation of a long is the two given signed, 32-bit values.
2627 // We use 32-bit pieces because these are the size of integers on which
2628 // Javascript performs bit-operations. For operations like addition and
2629 // multiplication, we split each number into 16 bit pieces, which can easily be
2630 // multiplied within Javascript's floating-point representation without overflow
2631 // or change in sign.
2632 //
2633 // In the algorithms below, we frequently reduce the negative case to the
2634 // positive case by negating the input(s) and then post-processing the result.
2635 // Note that we must ALWAYS check specially whether those values are MIN_VALUE
2636 // (-2^63) because -MIN_VALUE == MIN_VALUE (since 2^63 cannot be represented as
2637 // a positive number, it overflows back into a negative). Not handling this
2638 // case would often result in infinite recursion.
2639 //
2640 // Common constant values ZERO, ONE, NEG_ONE, etc. are defined below the from*
2641 // methods on which they depend.
2642
2643 /**
2644 * An indicator used to reliably determine if an object is a Long or not.
2645 * @type {boolean}
2646 * @const
2647 * @private
2648 */
2649 Long.prototype.__isLong__;
2650
2651 Object.defineProperty(Long.prototype, "__isLong__", {
2652 value: true,
2653 enumerable: false,
2654 configurable: false
2655 });
2656
2657 /**
2658 * @function
2659 * @param {*} obj Object
2660 * @returns {boolean}
2661 * @inner
2662 */
2663 function isLong(obj) {
2664 return (obj && obj["__isLong__"]) === true;
2665 }
2666
2667 /**
2668 * Tests if the specified object is a Long.
2669 * @function
2670 * @param {*} obj Object
2671 * @returns {boolean}
2672 */
2673 Long.isLong = isLong;
2674
2675 /**
2676 * A cache of the Long representations of small integer values.
2677 * @type {!Object}
2678 * @inner
2679 */
2680 var INT_CACHE = {};
2681
2682 /**
2683 * A cache of the Long representations of small unsigned integer values.
2684 * @type {!Object}
2685 * @inner
2686 */
2687 var UINT_CACHE = {};
2688
2689 /**
2690 * @param {number} value
2691 * @param {boolean=} unsigned
2692 * @returns {!Long}
2693 * @inner
2694 */
2695 function fromInt(value, unsigned) {
2696 var obj, cachedObj, cache;
2697 if (unsigned) {
2698 value >>>= 0;
2699 if (cache = (0 <= value && value < 256)) {
2700 cachedObj = UINT_CACHE[value];
2701 if (cachedObj)
2702 return cachedObj;
2703 }
2704 obj = fromBits(value, (value | 0) < 0 ? -1 : 0, true);
2705 if (cache)
2706 UINT_CACHE[value] = obj;
2707 return obj;
2708 } else {
2709 value |= 0;
2710 if (cache = (-128 <= value && value < 128)) {
2711 cachedObj = INT_CACHE[value];
2712 if (cachedObj)
2713 return cachedObj;
2714 }
2715 obj = fromBits(value, value < 0 ? -1 : 0, false);
2716 if (cache)
2717 INT_CACHE[value] = obj;
2718 return obj;
2719 }
2720 }
2721
2722 /**
2723 * Returns a Long representing the given 32 bit integer value.
2724 * @function
2725 * @param {number} value The 32 bit integer in question
2726 * @param {boolean=} unsigned Whether unsigned or not, defaults to `false` for signed
2727 * @returns {!Long} The corresponding Long value
2728 */
2729 Long.fromInt = fromInt;
2730
2731 /**
2732 * @param {number} value
2733 * @param {boolean=} unsigned
2734 * @returns {!Long}
2735 * @inner
2736 */
2737 function fromNumber(value, unsigned) {
2738 if (isNaN(value) || !isFinite(value))
2739 return unsigned ? UZERO : ZERO;
2740 if (unsigned) {
2741 if (value < 0)
2742 return UZERO;
2743 if (value >= TWO_PWR_64_DBL)
2744 return MAX_UNSIGNED_VALUE;
2745 } else {
2746 if (value <= -TWO_PWR_63_DBL)
2747 return MIN_VALUE;
2748 if (value + 1 >= TWO_PWR_63_DBL)
2749 return MAX_VALUE;
2750 }
2751 if (value < 0)
2752 return fromNumber(-value, unsigned).neg();
2753 return fromBits((value % TWO_PWR_32_DBL) | 0, (value / TWO_PWR_32_DBL) | 0, unsigned);
2754 }
2755
2756 /**
2757 * Returns a Long representing the given value, provided that it is a finite number. Otherwise, zero is returned.
2758 * @function
2759 * @param {number} value The number in question
2760 * @param {boolean=} unsigned Whether unsigned or not, defaults to `false` for signed
2761 * @returns {!Long} The corresponding Long value
2762 */
2763 Long.fromNumber = fromNumber;
2764
2765 /**
2766 * @param {number} lowBits
2767 * @param {number} highBits
2768 * @param {boolean=} unsigned
2769 * @returns {!Long}
2770 * @inner
2771 */
2772 function fromBits(lowBits, highBits, unsigned) {
2773 return new Long(lowBits, highBits, unsigned);
2774 }
2775
2776 /**
2777 * Returns a Long representing the 64 bit integer that comes by concatenating the given low and high bits. Each is
2778 * assumed to use 32 bits.
2779 * @function
2780 * @param {number} lowBits The low 32 bits
2781 * @param {number} highBits The high 32 bits
2782 * @param {boolean=} unsigned Whether unsigned or not, defaults to `false` for signed
2783 * @returns {!Long} The corresponding Long value
2784 */
2785 Long.fromBits = fromBits;
2786
2787 /**
2788 * @function
2789 * @param {number} base
2790 * @param {number} exponent
2791 * @returns {number}
2792 * @inner
2793 */
2794 var pow_dbl = Math.pow; // Used 4 times (4*8 to 15+4)
2795
2796 /**
2797 * @param {string} str
2798 * @param {(boolean|number)=} unsigned
2799 * @param {number=} radix
2800 * @returns {!Long}
2801 * @inner
2802 */
2803 function fromString(str, unsigned, radix) {
2804 if (str.length === 0)
2805 throw Error('empty string');
2806 if (str === "NaN" || str === "Infinity" || str === "+Infinity" || str === "-Infinity")
2807 return ZERO;
2808 if (typeof unsigned === 'number') {
2809 // For goog.math.long compatibility
2810 radix = unsigned,
2811 unsigned = false;
2812 } else {
2813 unsigned = !! unsigned;
2814 }
2815 radix = radix || 10;
2816 if (radix < 2 || 36 < radix)
2817 throw RangeError('radix');
2818
2819 var p;
2820 if ((p = str.indexOf('-')) > 0)
2821 throw Error('interior hyphen');
2822 else if (p === 0) {
2823 return fromString(str.substring(1), unsigned, radix).neg();
2824 }
2825
2826 // Do several (8) digits each time through the loop, so as to
2827 // minimize the calls to the very expensive emulated div.
2828 var radixToPower = fromNumber(pow_dbl(radix, 8));
2829
2830 var result = ZERO;
2831 for (var i = 0; i < str.length; i += 8) {
2832 var size = Math.min(8, str.length - i),
2833 value = parseInt(str.substring(i, i + size), radix);
2834 if (size < 8) {
2835 var power = fromNumber(pow_dbl(radix, size));
2836 result = result.mul(power).add(fromNumber(value));
2837 } else {
2838 result = result.mul(radixToPower);
2839 result = result.add(fromNumber(value));
2840 }
2841 }
2842 result.unsigned = unsigned;
2843 return result;
2844 }
2845
2846 /**
2847 * Returns a Long representation of the given string, written using the specified radix.
2848 * @function
2849 * @param {string} str The textual representation of the Long
2850 * @param {(boolean|number)=} unsigned Whether unsigned or not, defaults to `false` for signed
2851 * @param {number=} radix The radix in which the text is written (2-36), defaults to 10
2852 * @returns {!Long} The corresponding Long value
2853 */
2854 Long.fromString = fromString;
2855
2856 /**
2857 * @function
2858 * @param {!Long|number|string|!{low: number, high: number, unsigned: boolean}} val
2859 * @returns {!Long}
2860 * @inner
2861 */
2862 function fromValue(val) {
2863 if (val /* is compatible */ instanceof Long)
2864 return val;
2865 if (typeof val === 'number')
2866 return fromNumber(val);
2867 if (typeof val === 'string')
2868 return fromString(val);
2869 // Throws for non-objects, converts non-instanceof Long:
2870 return fromBits(val.low, val.high, val.unsigned);
2871 }
2872
2873 /**
2874 * Converts the specified value to a Long.
2875 * @function
2876 * @param {!Long|number|string|!{low: number, high: number, unsigned: boolean}} val Value
2877 * @returns {!Long}
2878 */
2879 Long.fromValue = fromValue;
2880
2881 // NOTE: the compiler should inline these constant values below and then remove these variables, so there should be
2882 // no runtime penalty for these.
2883
2884 /**
2885 * @type {number}
2886 * @const
2887 * @inner
2888 */
2889 var TWO_PWR_16_DBL = 1 << 16;
2890
2891 /**
2892 * @type {number}
2893 * @const
2894 * @inner
2895 */
2896 var TWO_PWR_24_DBL = 1 << 24;
2897
2898 /**
2899 * @type {number}
2900 * @const
2901 * @inner
2902 */
2903 var TWO_PWR_32_DBL = TWO_PWR_16_DBL * TWO_PWR_16_DBL;
2904
2905 /**
2906 * @type {number}
2907 * @const
2908 * @inner
2909 */
2910 var TWO_PWR_64_DBL = TWO_PWR_32_DBL * TWO_PWR_32_DBL;
2911
2912 /**
2913 * @type {number}
2914 * @const
2915 * @inner
2916 */
2917 var TWO_PWR_63_DBL = TWO_PWR_64_DBL / 2;
2918
2919 /**
2920 * @type {!Long}
2921 * @const
2922 * @inner
2923 */
2924 var TWO_PWR_24 = fromInt(TWO_PWR_24_DBL);
2925
2926 /**
2927 * @type {!Long}
2928 * @inner
2929 */
2930 var ZERO = fromInt(0);
2931
2932 /**
2933 * Signed zero.
2934 * @type {!Long}
2935 */
2936 Long.ZERO = ZERO;
2937
2938 /**
2939 * @type {!Long}
2940 * @inner
2941 */
2942 var UZERO = fromInt(0, true);
2943
2944 /**
2945 * Unsigned zero.
2946 * @type {!Long}
2947 */
2948 Long.UZERO = UZERO;
2949
2950 /**
2951 * @type {!Long}
2952 * @inner
2953 */
2954 var ONE = fromInt(1);
2955
2956 /**
2957 * Signed one.
2958 * @type {!Long}
2959 */
2960 Long.ONE = ONE;
2961
2962 /**
2963 * @type {!Long}
2964 * @inner
2965 */
2966 var UONE = fromInt(1, true);
2967
2968 /**
2969 * Unsigned one.
2970 * @type {!Long}
2971 */
2972 Long.UONE = UONE;
2973
2974 /**
2975 * @type {!Long}
2976 * @inner
2977 */
2978 var NEG_ONE = fromInt(-1);
2979
2980 /**
2981 * Signed negative one.
2982 * @type {!Long}
2983 */
2984 Long.NEG_ONE = NEG_ONE;
2985
2986 /**
2987 * @type {!Long}
2988 * @inner
2989 */
2990 var MAX_VALUE = fromBits(0xFFFFFFFF|0, 0x7FFFFFFF|0, false);
2991
2992 /**
2993 * Maximum signed value.
2994 * @type {!Long}
2995 */
2996 Long.MAX_VALUE = MAX_VALUE;
2997
2998 /**
2999 * @type {!Long}
3000 * @inner
3001 */
3002 var MAX_UNSIGNED_VALUE = fromBits(0xFFFFFFFF|0, 0xFFFFFFFF|0, true);
3003
3004 /**
3005 * Maximum unsigned value.
3006 * @type {!Long}
3007 */
3008 Long.MAX_UNSIGNED_VALUE = MAX_UNSIGNED_VALUE;
3009
3010 /**
3011 * @type {!Long}
3012 * @inner
3013 */
3014 var MIN_VALUE = fromBits(0, 0x80000000|0, false);
3015
3016 /**
3017 * Minimum signed value.
3018 * @type {!Long}
3019 */
3020 Long.MIN_VALUE = MIN_VALUE;
3021
3022 /**
3023 * @alias Long.prototype
3024 * @inner
3025 */
3026 var LongPrototype = Long.prototype;
3027
3028 /**
3029 * Converts the Long to a 32 bit integer, assuming it is a 32 bit integer.
3030 * @returns {number}
3031 */
3032 LongPrototype.toInt = function toInt() {
3033 return this.unsigned ? this.low >>> 0 : this.low;
3034 };
3035
3036 /**
3037 * Converts the Long to a the nearest floating-point representation of this value (double, 53 bit mantissa).
3038 * @returns {number}
3039 */
3040 LongPrototype.toNumber = function toNumber() {
3041 if (this.unsigned)
3042 return ((this.high >>> 0) * TWO_PWR_32_DBL) + (this.low >>> 0);
3043 return this.high * TWO_PWR_32_DBL + (this.low >>> 0);
3044 };
3045
3046 /**
3047 * Converts the Long to a string written in the specified radix.
3048 * @param {number=} radix Radix (2-36), defaults to 10
3049 * @returns {string}
3050 * @override
3051 * @throws {RangeError} If `radix` is out of range
3052 */
3053 LongPrototype.toString = function toString(radix) {
3054 radix = radix || 10;
3055 if (radix < 2 || 36 < radix)
3056 throw RangeError('radix');
3057 if (this.isZero())
3058 return '0';
3059 if (this.isNegative()) { // Unsigned Longs are never negative
3060 if (this.eq(MIN_VALUE)) {
3061 // We need to change the Long value before it can be negated, so we remove
3062 // the bottom-most digit in this base and then recurse to do the rest.
3063 var radixLong = fromNumber(radix),
3064 div = this.div(radixLong),
3065 rem1 = div.mul(radixLong).sub(this);
3066 return div.toString(radix) + rem1.toInt().toString(radix);
3067 } else
3068 return '-' + this.neg().toString(radix);
3069 }
3070
3071 // Do several (6) digits each time through the loop, so as to
3072 // minimize the calls to the very expensive emulated div.
3073 var radixToPower = fromNumber(pow_dbl(radix, 6), this.unsigned),
3074 rem = this;
3075 var result = '';
3076 while (true) {
3077 var remDiv = rem.div(radixToPower),
3078 intval = rem.sub(remDiv.mul(radixToPower)).toInt() >>> 0,
3079 digits = intval.toString(radix);
3080 rem = remDiv;
3081 if (rem.isZero())
3082 return digits + result;
3083 else {
3084 while (digits.length < 6)
3085 digits = '0' + digits;
3086 result = '' + digits + result;
3087 }
3088 }
3089 };
3090
3091 /**
3092 * Gets the high 32 bits as a signed integer.
3093 * @returns {number} Signed high bits
3094 */
3095 LongPrototype.getHighBits = function getHighBits() {
3096 return this.high;
3097 };
3098
3099 /**
3100 * Gets the high 32 bits as an unsigned integer.
3101 * @returns {number} Unsigned high bits
3102 */
3103 LongPrototype.getHighBitsUnsigned = function getHighBitsUnsigned() {
3104 return this.high >>> 0;
3105 };
3106
3107 /**
3108 * Gets the low 32 bits as a signed integer.
3109 * @returns {number} Signed low bits
3110 */
3111 LongPrototype.getLowBits = function getLowBits() {
3112 return this.low;
3113 };
3114
3115 /**
3116 * Gets the low 32 bits as an unsigned integer.
3117 * @returns {number} Unsigned low bits
3118 */
3119 LongPrototype.getLowBitsUnsigned = function getLowBitsUnsigned() {
3120 return this.low >>> 0;
3121 };
3122
3123 /**
3124 * Gets the number of bits needed to represent the absolute value of this Long.
3125 * @returns {number}
3126 */
3127 LongPrototype.getNumBitsAbs = function getNumBitsAbs() {
3128 if (this.isNegative()) // Unsigned Longs are never negative
3129 return this.eq(MIN_VALUE) ? 64 : this.neg().getNumBitsAbs();
3130 var val = this.high != 0 ? this.high : this.low;
3131 for (var bit = 31; bit > 0; bit--)
3132 if ((val & (1 << bit)) != 0)
3133 break;
3134 return this.high != 0 ? bit + 33 : bit + 1;
3135 };
3136
3137 /**
3138 * Tests if this Long's value equals zero.
3139 * @returns {boolean}
3140 */
3141 LongPrototype.isZero = function isZero() {
3142 return this.high === 0 && this.low === 0;
3143 };
3144
3145 /**
3146 * Tests if this Long's value is negative.
3147 * @returns {boolean}
3148 */
3149 LongPrototype.isNegative = function isNegative() {
3150 return !this.unsigned && this.high < 0;
3151 };
3152
3153 /**
3154 * Tests if this Long's value is positive.
3155 * @returns {boolean}
3156 */
3157 LongPrototype.isPositive = function isPositive() {
3158 return this.unsigned || this.high >= 0;
3159 };
3160
3161 /**
3162 * Tests if this Long's value is odd.
3163 * @returns {boolean}
3164 */
3165 LongPrototype.isOdd = function isOdd() {
3166 return (this.low & 1) === 1;
3167 };
3168
3169 /**
3170 * Tests if this Long's value is even.
3171 * @returns {boolean}
3172 */
3173 LongPrototype.isEven = function isEven() {
3174 return (this.low & 1) === 0;
3175 };
3176
3177 /**
3178 * Tests if this Long's value equals the specified's.
3179 * @param {!Long|number|string} other Other value
3180 * @returns {boolean}
3181 */
3182 LongPrototype.equals = function equals(other) {
3183 if (!isLong(other))
3184 other = fromValue(other);
3185 if (this.unsigned !== other.unsigned && (this.high >>> 31) === 1 && (other.high >>> 31) === 1)
3186 return false;
3187 return this.high === other.high && this.low === other.low;
3188 };
3189
3190 /**
3191 * Tests if this Long's value equals the specified's. This is an alias of {@link Long#equals}.
3192 * @function
3193 * @param {!Long|number|string} other Other value
3194 * @returns {boolean}
3195 */
3196 LongPrototype.eq = LongPrototype.equals;
3197
3198 /**
3199 * Tests if this Long's value differs from the specified's.
3200 * @param {!Long|number|string} other Other value
3201 * @returns {boolean}
3202 */
3203 LongPrototype.notEquals = function notEquals(other) {
3204 return !this.eq(/* validates */ other);
3205 };
3206
3207 /**
3208 * Tests if this Long's value differs from the specified's. This is an alias of {@link Long#notEquals}.
3209 * @function
3210 * @param {!Long|number|string} other Other value
3211 * @returns {boolean}
3212 */
3213 LongPrototype.neq = LongPrototype.notEquals;
3214
3215 /**
3216 * Tests if this Long's value is less than the specified's.
3217 * @param {!Long|number|string} other Other value
3218 * @returns {boolean}
3219 */
3220 LongPrototype.lessThan = function lessThan(other) {
3221 return this.comp(/* validates */ other) < 0;
3222 };
3223
3224 /**
3225 * Tests if this Long's value is less than the specified's. This is an alias of {@link Long#lessThan}.
3226 * @function
3227 * @param {!Long|number|string} other Other value
3228 * @returns {boolean}
3229 */
3230 LongPrototype.lt = LongPrototype.lessThan;
3231
3232 /**
3233 * Tests if this Long's value is less than or equal the specified's.
3234 * @param {!Long|number|string} other Other value
3235 * @returns {boolean}
3236 */
3237 LongPrototype.lessThanOrEqual = function lessThanOrEqual(other) {
3238 return this.comp(/* validates */ other) <= 0;
3239 };
3240
3241 /**
3242 * Tests if this Long's value is less than or equal the specified's. This is an alias of {@link Long#lessThanOrEqual}.
3243 * @function
3244 * @param {!Long|number|string} other Other value
3245 * @returns {boolean}
3246 */
3247 LongPrototype.lte = LongPrototype.lessThanOrEqual;
3248
3249 /**
3250 * Tests if this Long's value is greater than the specified's.
3251 * @param {!Long|number|string} other Other value
3252 * @returns {boolean}
3253 */
3254 LongPrototype.greaterThan = function greaterThan(other) {
3255 return this.comp(/* validates */ other) > 0;
3256 };
3257
3258 /**
3259 * Tests if this Long's value is greater than the specified's. This is an alias of {@link Long#greaterThan}.
3260 * @function
3261 * @param {!Long|number|string} other Other value
3262 * @returns {boolean}
3263 */
3264 LongPrototype.gt = LongPrototype.greaterThan;
3265
3266 /**
3267 * Tests if this Long's value is greater than or equal the specified's.
3268 * @param {!Long|number|string} other Other value
3269 * @returns {boolean}
3270 */
3271 LongPrototype.greaterThanOrEqual = function greaterThanOrEqual(other) {
3272 return this.comp(/* validates */ other) >= 0;
3273 };
3274
3275 /**
3276 * Tests if this Long's value is greater than or equal the specified's. This is an alias of {@link Long#greaterThanOrEqual}.
3277 * @function
3278 * @param {!Long|number|string} other Other value
3279 * @returns {boolean}
3280 */
3281 LongPrototype.gte = LongPrototype.greaterThanOrEqual;
3282
3283 /**
3284 * Compares this Long's value with the specified's.
3285 * @param {!Long|number|string} other Other value
3286 * @returns {number} 0 if they are the same, 1 if the this is greater and -1
3287 * if the given one is greater
3288 */
3289 LongPrototype.compare = function compare(other) {
3290 if (!isLong(other))
3291 other = fromValue(other);
3292 if (this.eq(other))
3293 return 0;
3294 var thisNeg = this.isNegative(),
3295 otherNeg = other.isNegative();
3296 if (thisNeg && !otherNeg)
3297 return -1;
3298 if (!thisNeg && otherNeg)
3299 return 1;
3300 // At this point the sign bits are the same
3301 if (!this.unsigned)
3302 return this.sub(other).isNegative() ? -1 : 1;
3303 // Both are positive if at least one is unsigned
3304 return (other.high >>> 0) > (this.high >>> 0) || (other.high === this.high && (other.low >>> 0) > (this.low >>> 0)) ? -1 : 1;
3305 };
3306
3307 /**
3308 * Compares this Long's value with the specified's. This is an alias of {@link Long#compare}.
3309 * @function
3310 * @param {!Long|number|string} other Other value
3311 * @returns {number} 0 if they are the same, 1 if the this is greater and -1
3312 * if the given one is greater
3313 */
3314 LongPrototype.comp = LongPrototype.compare;
3315
3316 /**
3317 * Negates this Long's value.
3318 * @returns {!Long} Negated Long
3319 */
3320 LongPrototype.negate = function negate() {
3321 if (!this.unsigned && this.eq(MIN_VALUE))
3322 return MIN_VALUE;
3323 return this.not().add(ONE);
3324 };
3325
3326 /**
3327 * Negates this Long's value. This is an alias of {@link Long#negate}.
3328 * @function
3329 * @returns {!Long} Negated Long
3330 */
3331 LongPrototype.neg = LongPrototype.negate;
3332
3333 /**
3334 * Returns the sum of this and the specified Long.
3335 * @param {!Long|number|string} addend Addend
3336 * @returns {!Long} Sum
3337 */
3338 LongPrototype.add = function add(addend) {
3339 if (!isLong(addend))
3340 addend = fromValue(addend);
3341
3342 // Divide each number into 4 chunks of 16 bits, and then sum the chunks.
3343
3344 var a48 = this.high >>> 16;
3345 var a32 = this.high & 0xFFFF;
3346 var a16 = this.low >>> 16;
3347 var a00 = this.low & 0xFFFF;
3348
3349 var b48 = addend.high >>> 16;
3350 var b32 = addend.high & 0xFFFF;
3351 var b16 = addend.low >>> 16;
3352 var b00 = addend.low & 0xFFFF;
3353
3354 var c48 = 0, c32 = 0, c16 = 0, c00 = 0;
3355 c00 += a00 + b00;
3356 c16 += c00 >>> 16;
3357 c00 &= 0xFFFF;
3358 c16 += a16 + b16;
3359 c32 += c16 >>> 16;
3360 c16 &= 0xFFFF;
3361 c32 += a32 + b32;
3362 c48 += c32 >>> 16;
3363 c32 &= 0xFFFF;
3364 c48 += a48 + b48;
3365 c48 &= 0xFFFF;
3366 return fromBits((c16 << 16) | c00, (c48 << 16) | c32, this.unsigned);
3367 };
3368
3369 /**
3370 * Returns the difference of this and the specified Long.
3371 * @param {!Long|number|string} subtrahend Subtrahend
3372 * @returns {!Long} Difference
3373 */
3374 LongPrototype.subtract = function subtract(subtrahend) {
3375 if (!isLong(subtrahend))
3376 subtrahend = fromValue(subtrahend);
3377 return this.add(subtrahend.neg());
3378 };
3379
3380 /**
3381 * Returns the difference of this and the specified Long. This is an alias of {@link Long#subtract}.
3382 * @function
3383 * @param {!Long|number|string} subtrahend Subtrahend
3384 * @returns {!Long} Difference
3385 */
3386 LongPrototype.sub = LongPrototype.subtract;
3387
3388 /**
3389 * Returns the product of this and the specified Long.
3390 * @param {!Long|number|string} multiplier Multiplier
3391 * @returns {!Long} Product
3392 */
3393 LongPrototype.multiply = function multiply(multiplier) {
3394 if (this.isZero())
3395 return ZERO;
3396 if (!isLong(multiplier))
3397 multiplier = fromValue(multiplier);
3398 if (multiplier.isZero())
3399 return ZERO;
3400 if (this.eq(MIN_VALUE))
3401 return multiplier.isOdd() ? MIN_VALUE : ZERO;
3402 if (multiplier.eq(MIN_VALUE))
3403 return this.isOdd() ? MIN_VALUE : ZERO;
3404
3405 if (this.isNegative()) {
3406 if (multiplier.isNegative())
3407 return this.neg().mul(multiplier.neg());
3408 else
3409 return this.neg().mul(multiplier).neg();
3410 } else if (multiplier.isNegative())
3411 return this.mul(multiplier.neg()).neg();
3412
3413 // If both longs are small, use float multiplication
3414 if (this.lt(TWO_PWR_24) && multiplier.lt(TWO_PWR_24))
3415 return fromNumber(this.toNumber() * multiplier.toNumber(), this.unsigned);
3416
3417 // Divide each long into 4 chunks of 16 bits, and then add up 4x4 products.
3418 // We can skip products that would overflow.
3419
3420 var a48 = this.high >>> 16;
3421 var a32 = this.high & 0xFFFF;
3422 var a16 = this.low >>> 16;
3423 var a00 = this.low & 0xFFFF;
3424
3425 var b48 = multiplier.high >>> 16;
3426 var b32 = multiplier.high & 0xFFFF;
3427 var b16 = multiplier.low >>> 16;
3428 var b00 = multiplier.low & 0xFFFF;
3429
3430 var c48 = 0, c32 = 0, c16 = 0, c00 = 0;
3431 c00 += a00 * b00;
3432 c16 += c00 >>> 16;
3433 c00 &= 0xFFFF;
3434 c16 += a16 * b00;
3435 c32 += c16 >>> 16;
3436 c16 &= 0xFFFF;
3437 c16 += a00 * b16;
3438 c32 += c16 >>> 16;
3439 c16 &= 0xFFFF;
3440 c32 += a32 * b00;
3441 c48 += c32 >>> 16;
3442 c32 &= 0xFFFF;
3443 c32 += a16 * b16;
3444 c48 += c32 >>> 16;
3445 c32 &= 0xFFFF;
3446 c32 += a00 * b32;
3447 c48 += c32 >>> 16;
3448 c32 &= 0xFFFF;
3449 c48 += a48 * b00 + a32 * b16 + a16 * b32 + a00 * b48;
3450 c48 &= 0xFFFF;
3451 return fromBits((c16 << 16) | c00, (c48 << 16) | c32, this.unsigned);
3452 };
3453
3454 /**
3455 * Returns the product of this and the specified Long. This is an alias of {@link Long#multiply}.
3456 * @function
3457 * @param {!Long|number|string} multiplier Multiplier
3458 * @returns {!Long} Product
3459 */
3460 LongPrototype.mul = LongPrototype.multiply;
3461
3462 /**
3463 * Returns this Long divided by the specified. The result is signed if this Long is signed or
3464 * unsigned if this Long is unsigned.
3465 * @param {!Long|number|string} divisor Divisor
3466 * @returns {!Long} Quotient
3467 */
3468 LongPrototype.divide = function divide(divisor) {
3469 if (!isLong(divisor))
3470 divisor = fromValue(divisor);
3471 if (divisor.isZero())
3472 throw Error('division by zero');
3473 if (this.isZero())
3474 return this.unsigned ? UZERO : ZERO;
3475 var approx, rem, res;
3476 if (!this.unsigned) {
3477 // This section is only relevant for signed longs and is derived from the
3478 // closure library as a whole.
3479 if (this.eq(MIN_VALUE)) {
3480 if (divisor.eq(ONE) || divisor.eq(NEG_ONE))
3481 return MIN_VALUE; // recall that -MIN_VALUE == MIN_VALUE
3482 else if (divisor.eq(MIN_VALUE))
3483 return ONE;
3484 else {
3485 // At this point, we have |other| >= 2, so |this/other| < |MIN_VALUE|.
3486 var halfThis = this.shr(1);
3487 approx = halfThis.div(divisor).shl(1);
3488 if (approx.eq(ZERO)) {
3489 return divisor.isNegative() ? ONE : NEG_ONE;
3490 } else {
3491 rem = this.sub(divisor.mul(approx));
3492 res = approx.add(rem.div(divisor));
3493 return res;
3494 }
3495 }
3496 } else if (divisor.eq(MIN_VALUE))
3497 return this.unsigned ? UZERO : ZERO;
3498 if (this.isNegative()) {
3499 if (divisor.isNegative())
3500 return this.neg().div(divisor.neg());
3501 return this.neg().div(divisor).neg();
3502 } else if (divisor.isNegative())
3503 return this.div(divisor.neg()).neg();
3504 res = ZERO;
3505 } else {
3506 // The algorithm below has not been made for unsigned longs. It's therefore
3507 // required to take special care of the MSB prior to running it.
3508 if (!divisor.unsigned)
3509 divisor = divisor.toUnsigned();
3510 if (divisor.gt(this))
3511 return UZERO;
3512 if (divisor.gt(this.shru(1))) // 15 >>> 1 = 7 ; with divisor = 8 ; true
3513 return UONE;
3514 res = UZERO;
3515 }
3516
3517 // Repeat the following until the remainder is less than other: find a
3518 // floating-point that approximates remainder / other *from below*, add this
3519 // into the result, and subtract it from the remainder. It is critical that
3520 // the approximate value is less than or equal to the real value so that the
3521 // remainder never becomes negative.
3522 rem = this;
3523 while (rem.gte(divisor)) {
3524 // Approximate the result of division. This may be a little greater or
3525 // smaller than the actual value.
3526 approx = Math.max(1, Math.floor(rem.toNumber() / divisor.toNumber()));
3527
3528 // We will tweak the approximate result by changing it in the 48-th digit or
3529 // the smallest non-fractional digit, whichever is larger.
3530 var log2 = Math.ceil(Math.log(approx) / Math.LN2),
3531 delta = (log2 <= 48) ? 1 : pow_dbl(2, log2 - 48),
3532
3533 // Decrease the approximation until it is smaller than the remainder. Note
3534 // that if it is too large, the product overflows and is negative.
3535 approxRes = fromNumber(approx),
3536 approxRem = approxRes.mul(divisor);
3537 while (approxRem.isNegative() || approxRem.gt(rem)) {
3538 approx -= delta;
3539 approxRes = fromNumber(approx, this.unsigned);
3540 approxRem = approxRes.mul(divisor);
3541 }
3542
3543 // We know the answer can't be zero... and actually, zero would cause
3544 // infinite recursion since we would make no progress.
3545 if (approxRes.isZero())
3546 approxRes = ONE;
3547
3548 res = res.add(approxRes);
3549 rem = rem.sub(approxRem);
3550 }
3551 return res;
3552 };
3553
3554 /**
3555 * Returns this Long divided by the specified. This is an alias of {@link Long#divide}.
3556 * @function
3557 * @param {!Long|number|string} divisor Divisor
3558 * @returns {!Long} Quotient
3559 */
3560 LongPrototype.div = LongPrototype.divide;
3561
3562 /**
3563 * Returns this Long modulo the specified.
3564 * @param {!Long|number|string} divisor Divisor
3565 * @returns {!Long} Remainder
3566 */
3567 LongPrototype.modulo = function modulo(divisor) {
3568 if (!isLong(divisor))
3569 divisor = fromValue(divisor);
3570 return this.sub(this.div(divisor).mul(divisor));
3571 };
3572
3573 /**
3574 * Returns this Long modulo the specified. This is an alias of {@link Long#modulo}.
3575 * @function
3576 * @param {!Long|number|string} divisor Divisor
3577 * @returns {!Long} Remainder
3578 */
3579 LongPrototype.mod = LongPrototype.modulo;
3580
3581 /**
3582 * Returns the bitwise NOT of this Long.
3583 * @returns {!Long}
3584 */
3585 LongPrototype.not = function not() {
3586 return fromBits(~this.low, ~this.high, this.unsigned);
3587 };
3588
3589 /**
3590 * Returns the bitwise AND of this Long and the specified.
3591 * @param {!Long|number|string} other Other Long
3592 * @returns {!Long}
3593 */
3594 LongPrototype.and = function and(other) {
3595 if (!isLong(other))
3596 other = fromValue(other);
3597 return fromBits(this.low & other.low, this.high & other.high, this.unsigned);
3598 };
3599
3600 /**
3601 * Returns the bitwise OR of this Long and the specified.
3602 * @param {!Long|number|string} other Other Long
3603 * @returns {!Long}
3604 */
3605 LongPrototype.or = function or(other) {
3606 if (!isLong(other))
3607 other = fromValue(other);
3608 return fromBits(this.low | other.low, this.high | other.high, this.unsigned);
3609 };
3610
3611 /**
3612 * Returns the bitwise XOR of this Long and the given one.
3613 * @param {!Long|number|string} other Other Long
3614 * @returns {!Long}
3615 */
3616 LongPrototype.xor = function xor(other) {
3617 if (!isLong(other))
3618 other = fromValue(other);
3619 return fromBits(this.low ^ other.low, this.high ^ other.high, this.unsigned);
3620 };
3621
3622 /**
3623 * Returns this Long with bits shifted to the left by the given amount.
3624 * @param {number|!Long} numBits Number of bits
3625 * @returns {!Long} Shifted Long
3626 */
3627 LongPrototype.shiftLeft = function shiftLeft(numBits) {
3628 if (isLong(numBits))
3629 numBits = numBits.toInt();
3630 if ((numBits &= 63) === 0)
3631 return this;
3632 else if (numBits < 32)
3633 return fromBits(this.low << numBits, (this.high << numBits) | (this.low >>> (32 - numBits)), this.unsigned);
3634 else
3635 return fromBits(0, this.low << (numBits - 32), this.unsigned);
3636 };
3637
3638 /**
3639 * Returns this Long with bits shifted to the left by the given amount. This is an alias of {@link Long#shiftLeft}.
3640 * @function
3641 * @param {number|!Long} numBits Number of bits
3642 * @returns {!Long} Shifted Long
3643 */
3644 LongPrototype.shl = LongPrototype.shiftLeft;
3645
3646 /**
3647 * Returns this Long with bits arithmetically shifted to the right by the given amount.
3648 * @param {number|!Long} numBits Number of bits
3649 * @returns {!Long} Shifted Long
3650 */
3651 LongPrototype.shiftRight = function shiftRight(numBits) {
3652 if (isLong(numBits))
3653 numBits = numBits.toInt();
3654 if ((numBits &= 63) === 0)
3655 return this;
3656 else if (numBits < 32)
3657 return fromBits((this.low >>> numBits) | (this.high << (32 - numBits)), this.high >> numBits, this.unsigned);
3658 else
3659 return fromBits(this.high >> (numBits - 32), this.high >= 0 ? 0 : -1, this.unsigned);
3660 };
3661
3662 /**
3663 * Returns this Long with bits arithmetically shifted to the right by the given amount. This is an alias of {@link Long#shiftRight}.
3664 * @function
3665 * @param {number|!Long} numBits Number of bits
3666 * @returns {!Long} Shifted Long
3667 */
3668 LongPrototype.shr = LongPrototype.shiftRight;
3669
3670 /**
3671 * Returns this Long with bits logically shifted to the right by the given amount.
3672 * @param {number|!Long} numBits Number of bits
3673 * @returns {!Long} Shifted Long
3674 */
3675 LongPrototype.shiftRightUnsigned = function shiftRightUnsigned(numBits) {
3676 if (isLong(numBits))
3677 numBits = numBits.toInt();
3678 numBits &= 63;
3679 if (numBits === 0)
3680 return this;
3681 else {
3682 var high = this.high;
3683 if (numBits < 32) {
3684 var low = this.low;
3685 return fromBits((low >>> numBits) | (high << (32 - numBits)), high >>> numBits, this.unsigned);
3686 } else if (numBits === 32)
3687 return fromBits(high, 0, this.unsigned);
3688 else
3689 return fromBits(high >>> (numBits - 32), 0, this.unsigned);
3690 }
3691 };
3692
3693 /**
3694 * Returns this Long with bits logically shifted to the right by the given amount. This is an alias of {@link Long#shiftRightUnsigned}.
3695 * @function
3696 * @param {number|!Long} numBits Number of bits
3697 * @returns {!Long} Shifted Long
3698 */
3699 LongPrototype.shru = LongPrototype.shiftRightUnsigned;
3700
3701 /**
3702 * Converts this Long to signed.
3703 * @returns {!Long} Signed long
3704 */
3705 LongPrototype.toSigned = function toSigned() {
3706 if (!this.unsigned)
3707 return this;
3708 return fromBits(this.low, this.high, false);
3709 };
3710
3711 /**
3712 * Converts this Long to unsigned.
3713 * @returns {!Long} Unsigned long
3714 */
3715 LongPrototype.toUnsigned = function toUnsigned() {
3716 if (this.unsigned)
3717 return this;
3718 return fromBits(this.low, this.high, true);
3719 };
3720
3721 /**
3722 * Converts this Long to its byte representation.
3723 * @param {boolean=} le Whether little or big endian, defaults to big endian
3724 * @returns {!Array.<number>} Byte representation
3725 */
3726 LongPrototype.toBytes = function(le) {
3727 return le ? this.toBytesLE() : this.toBytesBE();
3728 };
3729
3730 /**
3731 * Converts this Long to its little endian byte representation.
3732 * @returns {!Array.<number>} Little endian byte representation
3733 */
3734 LongPrototype.toBytesLE = function() {
3735 var hi = this.high,
3736 lo = this.low;
3737 return [
3738 lo & 0xff,
3739 (lo >>> 8) & 0xff,
3740 (lo >>> 16) & 0xff,
3741 (lo >>> 24) & 0xff,
3742 hi & 0xff,
3743 (hi >>> 8) & 0xff,
3744 (hi >>> 16) & 0xff,
3745 (hi >>> 24) & 0xff
3746 ];
3747 };
3748
3749 /**
3750 * Converts this Long to its big endian byte representation.
3751 * @returns {!Array.<number>} Big endian byte representation
3752 */
3753 LongPrototype.toBytesBE = function() {
3754 var hi = this.high,
3755 lo = this.low;
3756 return [
3757 (hi >>> 24) & 0xff,
3758 (hi >>> 16) & 0xff,
3759 (hi >>> 8) & 0xff,
3760 hi & 0xff,
3761 (lo >>> 24) & 0xff,
3762 (lo >>> 16) & 0xff,
3763 (lo >>> 8) & 0xff,
3764 lo & 0xff
3765 ];
3766 };
3767
3768 return Long;
3769 });
3770 });
3771
3772 var bytebuffer = createCommonjsModule(function (module) {
3773 /*
3774 Copyright 2013-2014 Daniel Wirtz <dcode@dcode.io>
3775
3776 Licensed under the Apache License, Version 2.0 (the "License");
3777 you may not use this file except in compliance with the License.
3778 You may obtain a copy of the License at
3779
3780 http://www.apache.org/licenses/LICENSE-2.0
3781
3782 Unless required by applicable law or agreed to in writing, software
3783 distributed under the License is distributed on an "AS IS" BASIS,
3784 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
3785 See the License for the specific language governing permissions and
3786 limitations under the License.
3787 */
3788
3789 /**
3790 * @license bytebuffer.js (c) 2015 Daniel Wirtz <dcode@dcode.io>
3791 * Backing buffer: ArrayBuffer, Accessor: Uint8Array
3792 * Released under the Apache License, Version 2.0
3793 * see: https://github.com/dcodeIO/bytebuffer.js for details
3794 */
3795 (function(global, factory) {
3796
3797 /* AMD */ if (typeof commonjsRequire === 'function' && 'object' === "object" && module && module["exports"])
3798 module['exports'] = (function() {
3799 var Long; try { Long = long_1; } catch (e) {}
3800 return factory(Long);
3801 })();
3802 /* Global */ else
3803 (global["dcodeIO"] = global["dcodeIO"] || {})["ByteBuffer"] = factory(global["dcodeIO"]["Long"]);
3804
3805 })(commonjsGlobal, function(Long) {
3806
3807 /**
3808 * Constructs a new ByteBuffer.
3809 * @class The swiss army knife for binary data in JavaScript.
3810 * @exports ByteBuffer
3811 * @constructor
3812 * @param {number=} capacity Initial capacity. Defaults to {@link ByteBuffer.DEFAULT_CAPACITY}.
3813 * @param {boolean=} littleEndian Whether to use little or big endian byte order. Defaults to
3814 * {@link ByteBuffer.DEFAULT_ENDIAN}.
3815 * @param {boolean=} noAssert Whether to skip assertions of offsets and values. Defaults to
3816 * {@link ByteBuffer.DEFAULT_NOASSERT}.
3817 * @expose
3818 */
3819 var ByteBuffer = function(capacity, littleEndian, noAssert) {
3820 if (typeof capacity === 'undefined')
3821 capacity = ByteBuffer.DEFAULT_CAPACITY;
3822 if (typeof littleEndian === 'undefined')
3823 littleEndian = ByteBuffer.DEFAULT_ENDIAN;
3824 if (typeof noAssert === 'undefined')
3825 noAssert = ByteBuffer.DEFAULT_NOASSERT;
3826 if (!noAssert) {
3827 capacity = capacity | 0;
3828 if (capacity < 0)
3829 throw RangeError("Illegal capacity");
3830 littleEndian = !!littleEndian;
3831 noAssert = !!noAssert;
3832 }
3833
3834 /**
3835 * Backing ArrayBuffer.
3836 * @type {!ArrayBuffer}
3837 * @expose
3838 */
3839 this.buffer = capacity === 0 ? EMPTY_BUFFER : new ArrayBuffer(capacity);
3840
3841 /**
3842 * Uint8Array utilized to manipulate the backing buffer. Becomes `null` if the backing buffer has a capacity of `0`.
3843 * @type {?Uint8Array}
3844 * @expose
3845 */
3846 this.view = capacity === 0 ? null : new Uint8Array(this.buffer);
3847
3848 /**
3849 * Absolute read/write offset.
3850 * @type {number}
3851 * @expose
3852 * @see ByteBuffer#flip
3853 * @see ByteBuffer#clear
3854 */
3855 this.offset = 0;
3856
3857 /**
3858 * Marked offset.
3859 * @type {number}
3860 * @expose
3861 * @see ByteBuffer#mark
3862 * @see ByteBuffer#reset
3863 */
3864 this.markedOffset = -1;
3865
3866 /**
3867 * Absolute limit of the contained data. Set to the backing buffer's capacity upon allocation.
3868 * @type {number}
3869 * @expose
3870 * @see ByteBuffer#flip
3871 * @see ByteBuffer#clear
3872 */
3873 this.limit = capacity;
3874
3875 /**
3876 * Whether to use little endian byte order, defaults to `false` for big endian.
3877 * @type {boolean}
3878 * @expose
3879 */
3880 this.littleEndian = littleEndian;
3881
3882 /**
3883 * Whether to skip assertions of offsets and values, defaults to `false`.
3884 * @type {boolean}
3885 * @expose
3886 */
3887 this.noAssert = noAssert;
3888 };
3889
3890 /**
3891 * ByteBuffer version.
3892 * @type {string}
3893 * @const
3894 * @expose
3895 */
3896 ByteBuffer.VERSION = "5.0.1";
3897
3898 /**
3899 * Little endian constant that can be used instead of its boolean value. Evaluates to `true`.
3900 * @type {boolean}
3901 * @const
3902 * @expose
3903 */
3904 ByteBuffer.LITTLE_ENDIAN = true;
3905
3906 /**
3907 * Big endian constant that can be used instead of its boolean value. Evaluates to `false`.
3908 * @type {boolean}
3909 * @const
3910 * @expose
3911 */
3912 ByteBuffer.BIG_ENDIAN = false;
3913
3914 /**
3915 * Default initial capacity of `16`.
3916 * @type {number}
3917 * @expose
3918 */
3919 ByteBuffer.DEFAULT_CAPACITY = 16;
3920
3921 /**
3922 * Default endianess of `false` for big endian.
3923 * @type {boolean}
3924 * @expose
3925 */
3926 ByteBuffer.DEFAULT_ENDIAN = ByteBuffer.BIG_ENDIAN;
3927
3928 /**
3929 * Default no assertions flag of `false`.
3930 * @type {boolean}
3931 * @expose
3932 */
3933 ByteBuffer.DEFAULT_NOASSERT = false;
3934
3935 /**
3936 * A `Long` class for representing a 64-bit two's-complement integer value. May be `null` if Long.js has not been loaded
3937 * and int64 support is not available.
3938 * @type {?Long}
3939 * @const
3940 * @see https://github.com/dcodeIO/long.js
3941 * @expose
3942 */
3943 ByteBuffer.Long = Long || null;
3944
3945 /**
3946 * @alias ByteBuffer.prototype
3947 * @inner
3948 */
3949 var ByteBufferPrototype = ByteBuffer.prototype;
3950
3951 /**
3952 * An indicator used to reliably determine if an object is a ByteBuffer or not.
3953 * @type {boolean}
3954 * @const
3955 * @expose
3956 * @private
3957 */
3958 ByteBufferPrototype.__isByteBuffer__;
3959
3960 Object.defineProperty(ByteBufferPrototype, "__isByteBuffer__", {
3961 value: true,
3962 enumerable: false,
3963 configurable: false
3964 });
3965
3966 // helpers
3967
3968 /**
3969 * @type {!ArrayBuffer}
3970 * @inner
3971 */
3972 var EMPTY_BUFFER = new ArrayBuffer(0);
3973
3974 /**
3975 * String.fromCharCode reference for compile-time renaming.
3976 * @type {function(...number):string}
3977 * @inner
3978 */
3979 var stringFromCharCode = String.fromCharCode;
3980
3981 /**
3982 * Creates a source function for a string.
3983 * @param {string} s String to read from
3984 * @returns {function():number|null} Source function returning the next char code respectively `null` if there are
3985 * no more characters left.
3986 * @throws {TypeError} If the argument is invalid
3987 * @inner
3988 */
3989 function stringSource(s) {
3990 var i=0; return function() {
3991 return i < s.length ? s.charCodeAt(i++) : null;
3992 };
3993 }
3994
3995 /**
3996 * Creates a destination function for a string.
3997 * @returns {function(number=):undefined|string} Destination function successively called with the next char code.
3998 * Returns the final string when called without arguments.
3999 * @inner
4000 */
4001 function stringDestination() {
4002 var cs = [], ps = []; return function() {
4003 if (arguments.length === 0)
4004 return ps.join('')+stringFromCharCode.apply(String, cs);
4005 if (cs.length + arguments.length > 1024)
4006 ps.push(stringFromCharCode.apply(String, cs)),
4007 cs.length = 0;
4008 Array.prototype.push.apply(cs, arguments);
4009 };
4010 }
4011
4012 /**
4013 * Gets the accessor type.
4014 * @returns {Function} `Buffer` under node.js, `Uint8Array` respectively `DataView` in the browser (classes)
4015 * @expose
4016 */
4017 ByteBuffer.accessor = function() {
4018 return Uint8Array;
4019 };
4020 /**
4021 * Allocates a new ByteBuffer backed by a buffer of the specified capacity.
4022 * @param {number=} capacity Initial capacity. Defaults to {@link ByteBuffer.DEFAULT_CAPACITY}.
4023 * @param {boolean=} littleEndian Whether to use little or big endian byte order. Defaults to
4024 * {@link ByteBuffer.DEFAULT_ENDIAN}.
4025 * @param {boolean=} noAssert Whether to skip assertions of offsets and values. Defaults to
4026 * {@link ByteBuffer.DEFAULT_NOASSERT}.
4027 * @returns {!ByteBuffer}
4028 * @expose
4029 */
4030 ByteBuffer.allocate = function(capacity, littleEndian, noAssert) {
4031 return new ByteBuffer(capacity, littleEndian, noAssert);
4032 };
4033
4034 /**
4035 * Concatenates multiple ByteBuffers into one.
4036 * @param {!Array.<!ByteBuffer|!ArrayBuffer|!Uint8Array|string>} buffers Buffers to concatenate
4037 * @param {(string|boolean)=} encoding String encoding if `buffers` contains a string ("base64", "hex", "binary",
4038 * defaults to "utf8")
4039 * @param {boolean=} littleEndian Whether to use little or big endian byte order for the resulting ByteBuffer. Defaults
4040 * to {@link ByteBuffer.DEFAULT_ENDIAN}.
4041 * @param {boolean=} noAssert Whether to skip assertions of offsets and values for the resulting ByteBuffer. Defaults to
4042 * {@link ByteBuffer.DEFAULT_NOASSERT}.
4043 * @returns {!ByteBuffer} Concatenated ByteBuffer
4044 * @expose
4045 */
4046 ByteBuffer.concat = function(buffers, encoding, littleEndian, noAssert) {
4047 if (typeof encoding === 'boolean' || typeof encoding !== 'string') {
4048 noAssert = littleEndian;
4049 littleEndian = encoding;
4050 encoding = undefined;
4051 }
4052 var capacity = 0;
4053 for (var i=0, k=buffers.length, length; i<k; ++i) {
4054 if (!ByteBuffer.isByteBuffer(buffers[i]))
4055 buffers[i] = ByteBuffer.wrap(buffers[i], encoding);
4056 length = buffers[i].limit - buffers[i].offset;
4057 if (length > 0) capacity += length;
4058 }
4059 if (capacity === 0)
4060 return new ByteBuffer(0, littleEndian, noAssert);
4061 var bb = new ByteBuffer(capacity, littleEndian, noAssert),
4062 bi;
4063 i=0; while (i<k) {
4064 bi = buffers[i++];
4065 length = bi.limit - bi.offset;
4066 if (length <= 0) continue;
4067 bb.view.set(bi.view.subarray(bi.offset, bi.limit), bb.offset);
4068 bb.offset += length;
4069 }
4070 bb.limit = bb.offset;
4071 bb.offset = 0;
4072 return bb;
4073 };
4074
4075 /**
4076 * Tests if the specified type is a ByteBuffer.
4077 * @param {*} bb ByteBuffer to test
4078 * @returns {boolean} `true` if it is a ByteBuffer, otherwise `false`
4079 * @expose
4080 */
4081 ByteBuffer.isByteBuffer = function(bb) {
4082 return (bb && bb["__isByteBuffer__"]) === true;
4083 };
4084 /**
4085 * Gets the backing buffer type.
4086 * @returns {Function} `Buffer` under node.js, `ArrayBuffer` in the browser (classes)
4087 * @expose
4088 */
4089 ByteBuffer.type = function() {
4090 return ArrayBuffer;
4091 };
4092 /**
4093 * Wraps a buffer or a string. Sets the allocated ByteBuffer's {@link ByteBuffer#offset} to `0` and its
4094 * {@link ByteBuffer#limit} to the length of the wrapped data.
4095 * @param {!ByteBuffer|!ArrayBuffer|!Uint8Array|string|!Array.<number>} buffer Anything that can be wrapped
4096 * @param {(string|boolean)=} encoding String encoding if `buffer` is a string ("base64", "hex", "binary", defaults to
4097 * "utf8")
4098 * @param {boolean=} littleEndian Whether to use little or big endian byte order. Defaults to
4099 * {@link ByteBuffer.DEFAULT_ENDIAN}.
4100 * @param {boolean=} noAssert Whether to skip assertions of offsets and values. Defaults to
4101 * {@link ByteBuffer.DEFAULT_NOASSERT}.
4102 * @returns {!ByteBuffer} A ByteBuffer wrapping `buffer`
4103 * @expose
4104 */
4105 ByteBuffer.wrap = function(buffer, encoding, littleEndian, noAssert) {
4106 if (typeof encoding !== 'string') {
4107 noAssert = littleEndian;
4108 littleEndian = encoding;
4109 encoding = undefined;
4110 }
4111 if (typeof buffer === 'string') {
4112 if (typeof encoding === 'undefined')
4113 encoding = "utf8";
4114 switch (encoding) {
4115 case "base64":
4116 return ByteBuffer.fromBase64(buffer, littleEndian);
4117 case "hex":
4118 return ByteBuffer.fromHex(buffer, littleEndian);
4119 case "binary":
4120 return ByteBuffer.fromBinary(buffer, littleEndian);
4121 case "utf8":
4122 return ByteBuffer.fromUTF8(buffer, littleEndian);
4123 case "debug":
4124 return ByteBuffer.fromDebug(buffer, littleEndian);
4125 default:
4126 throw Error("Unsupported encoding: "+encoding);
4127 }
4128 }
4129 if (buffer === null || typeof buffer !== 'object')
4130 throw TypeError("Illegal buffer");
4131 var bb;
4132 if (ByteBuffer.isByteBuffer(buffer)) {
4133 bb = ByteBufferPrototype.clone.call(buffer);
4134 bb.markedOffset = -1;
4135 return bb;
4136 }
4137 if (buffer instanceof Uint8Array) { // Extract ArrayBuffer from Uint8Array
4138 bb = new ByteBuffer(0, littleEndian, noAssert);
4139 if (buffer.length > 0) { // Avoid references to more than one EMPTY_BUFFER
4140 bb.buffer = buffer.buffer;
4141 bb.offset = buffer.byteOffset;
4142 bb.limit = buffer.byteOffset + buffer.byteLength;
4143 bb.view = new Uint8Array(buffer.buffer);
4144 }
4145 } else if (buffer instanceof ArrayBuffer) { // Reuse ArrayBuffer
4146 bb = new ByteBuffer(0, littleEndian, noAssert);
4147 if (buffer.byteLength > 0) {
4148 bb.buffer = buffer;
4149 bb.offset = 0;
4150 bb.limit = buffer.byteLength;
4151 bb.view = buffer.byteLength > 0 ? new Uint8Array(buffer) : null;
4152 }
4153 } else if (Object.prototype.toString.call(buffer) === "[object Array]") { // Create from octets
4154 bb = new ByteBuffer(buffer.length, littleEndian, noAssert);
4155 bb.limit = buffer.length;
4156 for (var i=0; i<buffer.length; ++i)
4157 bb.view[i] = buffer[i];
4158 } else
4159 throw TypeError("Illegal buffer"); // Otherwise fail
4160 return bb;
4161 };
4162
4163 /**
4164 * Writes the array as a bitset.
4165 * @param {Array<boolean>} value Array of booleans to write
4166 * @param {number=} offset Offset to read from. Will use and increase {@link ByteBuffer#offset} by `length` if omitted.
4167 * @returns {!ByteBuffer}
4168 * @expose
4169 */
4170 ByteBufferPrototype.writeBitSet = function(value, offset) {
4171 var relative = typeof offset === 'undefined';
4172 if (relative) offset = this.offset;
4173 if (!this.noAssert) {
4174 if (!(value instanceof Array))
4175 throw TypeError("Illegal BitSet: Not an array");
4176 if (typeof offset !== 'number' || offset % 1 !== 0)
4177 throw TypeError("Illegal offset: "+offset+" (not an integer)");
4178 offset >>>= 0;
4179 if (offset < 0 || offset + 0 > this.buffer.byteLength)
4180 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+0+") <= "+this.buffer.byteLength);
4181 }
4182
4183 var start = offset,
4184 bits = value.length,
4185 bytes = (bits >> 3),
4186 bit = 0,
4187 k;
4188
4189 offset += this.writeVarint32(bits,offset);
4190
4191 while(bytes--) {
4192 k = (!!value[bit++] & 1) |
4193 ((!!value[bit++] & 1) << 1) |
4194 ((!!value[bit++] & 1) << 2) |
4195 ((!!value[bit++] & 1) << 3) |
4196 ((!!value[bit++] & 1) << 4) |
4197 ((!!value[bit++] & 1) << 5) |
4198 ((!!value[bit++] & 1) << 6) |
4199 ((!!value[bit++] & 1) << 7);
4200 this.writeByte(k,offset++);
4201 }
4202
4203 if(bit < bits) {
4204 var m = 0; k = 0;
4205 while(bit < bits) k = k | ((!!value[bit++] & 1) << (m++));
4206 this.writeByte(k,offset++);
4207 }
4208
4209 if (relative) {
4210 this.offset = offset;
4211 return this;
4212 }
4213 return offset - start;
4214 };
4215
4216 /**
4217 * Reads a BitSet as an array of booleans.
4218 * @param {number=} offset Offset to read from. Will use and increase {@link ByteBuffer#offset} by `length` if omitted.
4219 * @returns {Array<boolean>
4220 * @expose
4221 */
4222 ByteBufferPrototype.readBitSet = function(offset) {
4223 var relative = typeof offset === 'undefined';
4224 if (relative) offset = this.offset;
4225
4226 var ret = this.readVarint32(offset),
4227 bits = ret.value,
4228 bytes = (bits >> 3),
4229 bit = 0,
4230 value = [],
4231 k;
4232
4233 offset += ret.length;
4234
4235 while(bytes--) {
4236 k = this.readByte(offset++);
4237 value[bit++] = !!(k & 0x01);
4238 value[bit++] = !!(k & 0x02);
4239 value[bit++] = !!(k & 0x04);
4240 value[bit++] = !!(k & 0x08);
4241 value[bit++] = !!(k & 0x10);
4242 value[bit++] = !!(k & 0x20);
4243 value[bit++] = !!(k & 0x40);
4244 value[bit++] = !!(k & 0x80);
4245 }
4246
4247 if(bit < bits) {
4248 var m = 0;
4249 k = this.readByte(offset++);
4250 while(bit < bits) value[bit++] = !!((k >> (m++)) & 1);
4251 }
4252
4253 if (relative) {
4254 this.offset = offset;
4255 }
4256 return value;
4257 };
4258 /**
4259 * Reads the specified number of bytes.
4260 * @param {number} length Number of bytes to read
4261 * @param {number=} offset Offset to read from. Will use and increase {@link ByteBuffer#offset} by `length` if omitted.
4262 * @returns {!ByteBuffer}
4263 * @expose
4264 */
4265 ByteBufferPrototype.readBytes = function(length, offset) {
4266 var relative = typeof offset === 'undefined';
4267 if (relative) offset = this.offset;
4268 if (!this.noAssert) {
4269 if (typeof offset !== 'number' || offset % 1 !== 0)
4270 throw TypeError("Illegal offset: "+offset+" (not an integer)");
4271 offset >>>= 0;
4272 if (offset < 0 || offset + length > this.buffer.byteLength)
4273 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+length+") <= "+this.buffer.byteLength);
4274 }
4275 var slice = this.slice(offset, offset + length);
4276 if (relative) this.offset += length;
4277 return slice;
4278 };
4279
4280 /**
4281 * Writes a payload of bytes. This is an alias of {@link ByteBuffer#append}.
4282 * @function
4283 * @param {!ByteBuffer|!ArrayBuffer|!Uint8Array|string} source Data to write. If `source` is a ByteBuffer, its offsets
4284 * will be modified according to the performed read operation.
4285 * @param {(string|number)=} encoding Encoding if `data` is a string ("base64", "hex", "binary", defaults to "utf8")
4286 * @param {number=} offset Offset to write to. Will use and increase {@link ByteBuffer#offset} by the number of bytes
4287 * written if omitted.
4288 * @returns {!ByteBuffer} this
4289 * @expose
4290 */
4291 ByteBufferPrototype.writeBytes = ByteBufferPrototype.append;
4292
4293 // types/ints/int8
4294
4295 /**
4296 * Writes an 8bit signed integer.
4297 * @param {number} value Value to write
4298 * @param {number=} offset Offset to write to. Will use and advance {@link ByteBuffer#offset} by `1` if omitted.
4299 * @returns {!ByteBuffer} this
4300 * @expose
4301 */
4302 ByteBufferPrototype.writeInt8 = function(value, offset) {
4303 var relative = typeof offset === 'undefined';
4304 if (relative) offset = this.offset;
4305 if (!this.noAssert) {
4306 if (typeof value !== 'number' || value % 1 !== 0)
4307 throw TypeError("Illegal value: "+value+" (not an integer)");
4308 value |= 0;
4309 if (typeof offset !== 'number' || offset % 1 !== 0)
4310 throw TypeError("Illegal offset: "+offset+" (not an integer)");
4311 offset >>>= 0;
4312 if (offset < 0 || offset + 0 > this.buffer.byteLength)
4313 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+0+") <= "+this.buffer.byteLength);
4314 }
4315 offset += 1;
4316 var capacity0 = this.buffer.byteLength;
4317 if (offset > capacity0)
4318 this.resize((capacity0 *= 2) > offset ? capacity0 : offset);
4319 offset -= 1;
4320 this.view[offset] = value;
4321 if (relative) this.offset += 1;
4322 return this;
4323 };
4324
4325 /**
4326 * Writes an 8bit signed integer. This is an alias of {@link ByteBuffer#writeInt8}.
4327 * @function
4328 * @param {number} value Value to write
4329 * @param {number=} offset Offset to write to. Will use and advance {@link ByteBuffer#offset} by `1` if omitted.
4330 * @returns {!ByteBuffer} this
4331 * @expose
4332 */
4333 ByteBufferPrototype.writeByte = ByteBufferPrototype.writeInt8;
4334
4335 /**
4336 * Reads an 8bit signed integer.
4337 * @param {number=} offset Offset to read from. Will use and advance {@link ByteBuffer#offset} by `1` if omitted.
4338 * @returns {number} Value read
4339 * @expose
4340 */
4341 ByteBufferPrototype.readInt8 = function(offset) {
4342 var relative = typeof offset === 'undefined';
4343 if (relative) offset = this.offset;
4344 if (!this.noAssert) {
4345 if (typeof offset !== 'number' || offset % 1 !== 0)
4346 throw TypeError("Illegal offset: "+offset+" (not an integer)");
4347 offset >>>= 0;
4348 if (offset < 0 || offset + 1 > this.buffer.byteLength)
4349 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+1+") <= "+this.buffer.byteLength);
4350 }
4351 var value = this.view[offset];
4352 if ((value & 0x80) === 0x80) value = -(0xFF - value + 1); // Cast to signed
4353 if (relative) this.offset += 1;
4354 return value;
4355 };
4356
4357 /**
4358 * Reads an 8bit signed integer. This is an alias of {@link ByteBuffer#readInt8}.
4359 * @function
4360 * @param {number=} offset Offset to read from. Will use and advance {@link ByteBuffer#offset} by `1` if omitted.
4361 * @returns {number} Value read
4362 * @expose
4363 */
4364 ByteBufferPrototype.readByte = ByteBufferPrototype.readInt8;
4365
4366 /**
4367 * Writes an 8bit unsigned integer.
4368 * @param {number} value Value to write
4369 * @param {number=} offset Offset to write to. Will use and advance {@link ByteBuffer#offset} by `1` if omitted.
4370 * @returns {!ByteBuffer} this
4371 * @expose
4372 */
4373 ByteBufferPrototype.writeUint8 = function(value, offset) {
4374 var relative = typeof offset === 'undefined';
4375 if (relative) offset = this.offset;
4376 if (!this.noAssert) {
4377 if (typeof value !== 'number' || value % 1 !== 0)
4378 throw TypeError("Illegal value: "+value+" (not an integer)");
4379 value >>>= 0;
4380 if (typeof offset !== 'number' || offset % 1 !== 0)
4381 throw TypeError("Illegal offset: "+offset+" (not an integer)");
4382 offset >>>= 0;
4383 if (offset < 0 || offset + 0 > this.buffer.byteLength)
4384 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+0+") <= "+this.buffer.byteLength);
4385 }
4386 offset += 1;
4387 var capacity1 = this.buffer.byteLength;
4388 if (offset > capacity1)
4389 this.resize((capacity1 *= 2) > offset ? capacity1 : offset);
4390 offset -= 1;
4391 this.view[offset] = value;
4392 if (relative) this.offset += 1;
4393 return this;
4394 };
4395
4396 /**
4397 * Writes an 8bit unsigned integer. This is an alias of {@link ByteBuffer#writeUint8}.
4398 * @function
4399 * @param {number} value Value to write
4400 * @param {number=} offset Offset to write to. Will use and advance {@link ByteBuffer#offset} by `1` if omitted.
4401 * @returns {!ByteBuffer} this
4402 * @expose
4403 */
4404 ByteBufferPrototype.writeUInt8 = ByteBufferPrototype.writeUint8;
4405
4406 /**
4407 * Reads an 8bit unsigned integer.
4408 * @param {number=} offset Offset to read from. Will use and advance {@link ByteBuffer#offset} by `1` if omitted.
4409 * @returns {number} Value read
4410 * @expose
4411 */
4412 ByteBufferPrototype.readUint8 = function(offset) {
4413 var relative = typeof offset === 'undefined';
4414 if (relative) offset = this.offset;
4415 if (!this.noAssert) {
4416 if (typeof offset !== 'number' || offset % 1 !== 0)
4417 throw TypeError("Illegal offset: "+offset+" (not an integer)");
4418 offset >>>= 0;
4419 if (offset < 0 || offset + 1 > this.buffer.byteLength)
4420 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+1+") <= "+this.buffer.byteLength);
4421 }
4422 var value = this.view[offset];
4423 if (relative) this.offset += 1;
4424 return value;
4425 };
4426
4427 /**
4428 * Reads an 8bit unsigned integer. This is an alias of {@link ByteBuffer#readUint8}.
4429 * @function
4430 * @param {number=} offset Offset to read from. Will use and advance {@link ByteBuffer#offset} by `1` if omitted.
4431 * @returns {number} Value read
4432 * @expose
4433 */
4434 ByteBufferPrototype.readUInt8 = ByteBufferPrototype.readUint8;
4435
4436 // types/ints/int16
4437
4438 /**
4439 * Writes a 16bit signed integer.
4440 * @param {number} value Value to write
4441 * @param {number=} offset Offset to write to. Will use and advance {@link ByteBuffer#offset} by `2` if omitted.
4442 * @throws {TypeError} If `offset` or `value` is not a valid number
4443 * @throws {RangeError} If `offset` is out of bounds
4444 * @expose
4445 */
4446 ByteBufferPrototype.writeInt16 = function(value, offset) {
4447 var relative = typeof offset === 'undefined';
4448 if (relative) offset = this.offset;
4449 if (!this.noAssert) {
4450 if (typeof value !== 'number' || value % 1 !== 0)
4451 throw TypeError("Illegal value: "+value+" (not an integer)");
4452 value |= 0;
4453 if (typeof offset !== 'number' || offset % 1 !== 0)
4454 throw TypeError("Illegal offset: "+offset+" (not an integer)");
4455 offset >>>= 0;
4456 if (offset < 0 || offset + 0 > this.buffer.byteLength)
4457 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+0+") <= "+this.buffer.byteLength);
4458 }
4459 offset += 2;
4460 var capacity2 = this.buffer.byteLength;
4461 if (offset > capacity2)
4462 this.resize((capacity2 *= 2) > offset ? capacity2 : offset);
4463 offset -= 2;
4464 if (this.littleEndian) {
4465 this.view[offset+1] = (value & 0xFF00) >>> 8;
4466 this.view[offset ] = value & 0x00FF;
4467 } else {
4468 this.view[offset] = (value & 0xFF00) >>> 8;
4469 this.view[offset+1] = value & 0x00FF;
4470 }
4471 if (relative) this.offset += 2;
4472 return this;
4473 };
4474
4475 /**
4476 * Writes a 16bit signed integer. This is an alias of {@link ByteBuffer#writeInt16}.
4477 * @function
4478 * @param {number} value Value to write
4479 * @param {number=} offset Offset to write to. Will use and advance {@link ByteBuffer#offset} by `2` if omitted.
4480 * @throws {TypeError} If `offset` or `value` is not a valid number
4481 * @throws {RangeError} If `offset` is out of bounds
4482 * @expose
4483 */
4484 ByteBufferPrototype.writeShort = ByteBufferPrototype.writeInt16;
4485
4486 /**
4487 * Reads a 16bit signed integer.
4488 * @param {number=} offset Offset to read from. Will use and advance {@link ByteBuffer#offset} by `2` if omitted.
4489 * @returns {number} Value read
4490 * @throws {TypeError} If `offset` is not a valid number
4491 * @throws {RangeError} If `offset` is out of bounds
4492 * @expose
4493 */
4494 ByteBufferPrototype.readInt16 = function(offset) {
4495 var relative = typeof offset === 'undefined';
4496 if (relative) offset = this.offset;
4497 if (!this.noAssert) {
4498 if (typeof offset !== 'number' || offset % 1 !== 0)
4499 throw TypeError("Illegal offset: "+offset+" (not an integer)");
4500 offset >>>= 0;
4501 if (offset < 0 || offset + 2 > this.buffer.byteLength)
4502 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+2+") <= "+this.buffer.byteLength);
4503 }
4504 var value = 0;
4505 if (this.littleEndian) {
4506 value = this.view[offset ];
4507 value |= this.view[offset+1] << 8;
4508 } else {
4509 value = this.view[offset ] << 8;
4510 value |= this.view[offset+1];
4511 }
4512 if ((value & 0x8000) === 0x8000) value = -(0xFFFF - value + 1); // Cast to signed
4513 if (relative) this.offset += 2;
4514 return value;
4515 };
4516
4517 /**
4518 * Reads a 16bit signed integer. This is an alias of {@link ByteBuffer#readInt16}.
4519 * @function
4520 * @param {number=} offset Offset to read from. Will use and advance {@link ByteBuffer#offset} by `2` if omitted.
4521 * @returns {number} Value read
4522 * @throws {TypeError} If `offset` is not a valid number
4523 * @throws {RangeError} If `offset` is out of bounds
4524 * @expose
4525 */
4526 ByteBufferPrototype.readShort = ByteBufferPrototype.readInt16;
4527
4528 /**
4529 * Writes a 16bit unsigned integer.
4530 * @param {number} value Value to write
4531 * @param {number=} offset Offset to write to. Will use and advance {@link ByteBuffer#offset} by `2` if omitted.
4532 * @throws {TypeError} If `offset` or `value` is not a valid number
4533 * @throws {RangeError} If `offset` is out of bounds
4534 * @expose
4535 */
4536 ByteBufferPrototype.writeUint16 = function(value, offset) {
4537 var relative = typeof offset === 'undefined';
4538 if (relative) offset = this.offset;
4539 if (!this.noAssert) {
4540 if (typeof value !== 'number' || value % 1 !== 0)
4541 throw TypeError("Illegal value: "+value+" (not an integer)");
4542 value >>>= 0;
4543 if (typeof offset !== 'number' || offset % 1 !== 0)
4544 throw TypeError("Illegal offset: "+offset+" (not an integer)");
4545 offset >>>= 0;
4546 if (offset < 0 || offset + 0 > this.buffer.byteLength)
4547 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+0+") <= "+this.buffer.byteLength);
4548 }
4549 offset += 2;
4550 var capacity3 = this.buffer.byteLength;
4551 if (offset > capacity3)
4552 this.resize((capacity3 *= 2) > offset ? capacity3 : offset);
4553 offset -= 2;
4554 if (this.littleEndian) {
4555 this.view[offset+1] = (value & 0xFF00) >>> 8;
4556 this.view[offset ] = value & 0x00FF;
4557 } else {
4558 this.view[offset] = (value & 0xFF00) >>> 8;
4559 this.view[offset+1] = value & 0x00FF;
4560 }
4561 if (relative) this.offset += 2;
4562 return this;
4563 };
4564
4565 /**
4566 * Writes a 16bit unsigned integer. This is an alias of {@link ByteBuffer#writeUint16}.
4567 * @function
4568 * @param {number} value Value to write
4569 * @param {number=} offset Offset to write to. Will use and advance {@link ByteBuffer#offset} by `2` if omitted.
4570 * @throws {TypeError} If `offset` or `value` is not a valid number
4571 * @throws {RangeError} If `offset` is out of bounds
4572 * @expose
4573 */
4574 ByteBufferPrototype.writeUInt16 = ByteBufferPrototype.writeUint16;
4575
4576 /**
4577 * Reads a 16bit unsigned integer.
4578 * @param {number=} offset Offset to read from. Will use and advance {@link ByteBuffer#offset} by `2` if omitted.
4579 * @returns {number} Value read
4580 * @throws {TypeError} If `offset` is not a valid number
4581 * @throws {RangeError} If `offset` is out of bounds
4582 * @expose
4583 */
4584 ByteBufferPrototype.readUint16 = function(offset) {
4585 var relative = typeof offset === 'undefined';
4586 if (relative) offset = this.offset;
4587 if (!this.noAssert) {
4588 if (typeof offset !== 'number' || offset % 1 !== 0)
4589 throw TypeError("Illegal offset: "+offset+" (not an integer)");
4590 offset >>>= 0;
4591 if (offset < 0 || offset + 2 > this.buffer.byteLength)
4592 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+2+") <= "+this.buffer.byteLength);
4593 }
4594 var value = 0;
4595 if (this.littleEndian) {
4596 value = this.view[offset ];
4597 value |= this.view[offset+1] << 8;
4598 } else {
4599 value = this.view[offset ] << 8;
4600 value |= this.view[offset+1];
4601 }
4602 if (relative) this.offset += 2;
4603 return value;
4604 };
4605
4606 /**
4607 * Reads a 16bit unsigned integer. This is an alias of {@link ByteBuffer#readUint16}.
4608 * @function
4609 * @param {number=} offset Offset to read from. Will use and advance {@link ByteBuffer#offset} by `2` if omitted.
4610 * @returns {number} Value read
4611 * @throws {TypeError} If `offset` is not a valid number
4612 * @throws {RangeError} If `offset` is out of bounds
4613 * @expose
4614 */
4615 ByteBufferPrototype.readUInt16 = ByteBufferPrototype.readUint16;
4616
4617 // types/ints/int32
4618
4619 /**
4620 * Writes a 32bit signed integer.
4621 * @param {number} value Value to write
4622 * @param {number=} offset Offset to write to. Will use and increase {@link ByteBuffer#offset} by `4` if omitted.
4623 * @expose
4624 */
4625 ByteBufferPrototype.writeInt32 = function(value, offset) {
4626 var relative = typeof offset === 'undefined';
4627 if (relative) offset = this.offset;
4628 if (!this.noAssert) {
4629 if (typeof value !== 'number' || value % 1 !== 0)
4630 throw TypeError("Illegal value: "+value+" (not an integer)");
4631 value |= 0;
4632 if (typeof offset !== 'number' || offset % 1 !== 0)
4633 throw TypeError("Illegal offset: "+offset+" (not an integer)");
4634 offset >>>= 0;
4635 if (offset < 0 || offset + 0 > this.buffer.byteLength)
4636 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+0+") <= "+this.buffer.byteLength);
4637 }
4638 offset += 4;
4639 var capacity4 = this.buffer.byteLength;
4640 if (offset > capacity4)
4641 this.resize((capacity4 *= 2) > offset ? capacity4 : offset);
4642 offset -= 4;
4643 if (this.littleEndian) {
4644 this.view[offset+3] = (value >>> 24) & 0xFF;
4645 this.view[offset+2] = (value >>> 16) & 0xFF;
4646 this.view[offset+1] = (value >>> 8) & 0xFF;
4647 this.view[offset ] = value & 0xFF;
4648 } else {
4649 this.view[offset ] = (value >>> 24) & 0xFF;
4650 this.view[offset+1] = (value >>> 16) & 0xFF;
4651 this.view[offset+2] = (value >>> 8) & 0xFF;
4652 this.view[offset+3] = value & 0xFF;
4653 }
4654 if (relative) this.offset += 4;
4655 return this;
4656 };
4657
4658 /**
4659 * Writes a 32bit signed integer. This is an alias of {@link ByteBuffer#writeInt32}.
4660 * @param {number} value Value to write
4661 * @param {number=} offset Offset to write to. Will use and increase {@link ByteBuffer#offset} by `4` if omitted.
4662 * @expose
4663 */
4664 ByteBufferPrototype.writeInt = ByteBufferPrototype.writeInt32;
4665
4666 /**
4667 * Reads a 32bit signed integer.
4668 * @param {number=} offset Offset to read from. Will use and increase {@link ByteBuffer#offset} by `4` if omitted.
4669 * @returns {number} Value read
4670 * @expose
4671 */
4672 ByteBufferPrototype.readInt32 = function(offset) {
4673 var relative = typeof offset === 'undefined';
4674 if (relative) offset = this.offset;
4675 if (!this.noAssert) {
4676 if (typeof offset !== 'number' || offset % 1 !== 0)
4677 throw TypeError("Illegal offset: "+offset+" (not an integer)");
4678 offset >>>= 0;
4679 if (offset < 0 || offset + 4 > this.buffer.byteLength)
4680 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+4+") <= "+this.buffer.byteLength);
4681 }
4682 var value = 0;
4683 if (this.littleEndian) {
4684 value = this.view[offset+2] << 16;
4685 value |= this.view[offset+1] << 8;
4686 value |= this.view[offset ];
4687 value += this.view[offset+3] << 24 >>> 0;
4688 } else {
4689 value = this.view[offset+1] << 16;
4690 value |= this.view[offset+2] << 8;
4691 value |= this.view[offset+3];
4692 value += this.view[offset ] << 24 >>> 0;
4693 }
4694 value |= 0; // Cast to signed
4695 if (relative) this.offset += 4;
4696 return value;
4697 };
4698
4699 /**
4700 * Reads a 32bit signed integer. This is an alias of {@link ByteBuffer#readInt32}.
4701 * @param {number=} offset Offset to read from. Will use and advance {@link ByteBuffer#offset} by `4` if omitted.
4702 * @returns {number} Value read
4703 * @expose
4704 */
4705 ByteBufferPrototype.readInt = ByteBufferPrototype.readInt32;
4706
4707 /**
4708 * Writes a 32bit unsigned integer.
4709 * @param {number} value Value to write
4710 * @param {number=} offset Offset to write to. Will use and increase {@link ByteBuffer#offset} by `4` if omitted.
4711 * @expose
4712 */
4713 ByteBufferPrototype.writeUint32 = function(value, offset) {
4714 var relative = typeof offset === 'undefined';
4715 if (relative) offset = this.offset;
4716 if (!this.noAssert) {
4717 if (typeof value !== 'number' || value % 1 !== 0)
4718 throw TypeError("Illegal value: "+value+" (not an integer)");
4719 value >>>= 0;
4720 if (typeof offset !== 'number' || offset % 1 !== 0)
4721 throw TypeError("Illegal offset: "+offset+" (not an integer)");
4722 offset >>>= 0;
4723 if (offset < 0 || offset + 0 > this.buffer.byteLength)
4724 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+0+") <= "+this.buffer.byteLength);
4725 }
4726 offset += 4;
4727 var capacity5 = this.buffer.byteLength;
4728 if (offset > capacity5)
4729 this.resize((capacity5 *= 2) > offset ? capacity5 : offset);
4730 offset -= 4;
4731 if (this.littleEndian) {
4732 this.view[offset+3] = (value >>> 24) & 0xFF;
4733 this.view[offset+2] = (value >>> 16) & 0xFF;
4734 this.view[offset+1] = (value >>> 8) & 0xFF;
4735 this.view[offset ] = value & 0xFF;
4736 } else {
4737 this.view[offset ] = (value >>> 24) & 0xFF;
4738 this.view[offset+1] = (value >>> 16) & 0xFF;
4739 this.view[offset+2] = (value >>> 8) & 0xFF;
4740 this.view[offset+3] = value & 0xFF;
4741 }
4742 if (relative) this.offset += 4;
4743 return this;
4744 };
4745
4746 /**
4747 * Writes a 32bit unsigned integer. This is an alias of {@link ByteBuffer#writeUint32}.
4748 * @function
4749 * @param {number} value Value to write
4750 * @param {number=} offset Offset to write to. Will use and increase {@link ByteBuffer#offset} by `4` if omitted.
4751 * @expose
4752 */
4753 ByteBufferPrototype.writeUInt32 = ByteBufferPrototype.writeUint32;
4754
4755 /**
4756 * Reads a 32bit unsigned integer.
4757 * @param {number=} offset Offset to read from. Will use and increase {@link ByteBuffer#offset} by `4` if omitted.
4758 * @returns {number} Value read
4759 * @expose
4760 */
4761 ByteBufferPrototype.readUint32 = function(offset) {
4762 var relative = typeof offset === 'undefined';
4763 if (relative) offset = this.offset;
4764 if (!this.noAssert) {
4765 if (typeof offset !== 'number' || offset % 1 !== 0)
4766 throw TypeError("Illegal offset: "+offset+" (not an integer)");
4767 offset >>>= 0;
4768 if (offset < 0 || offset + 4 > this.buffer.byteLength)
4769 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+4+") <= "+this.buffer.byteLength);
4770 }
4771 var value = 0;
4772 if (this.littleEndian) {
4773 value = this.view[offset+2] << 16;
4774 value |= this.view[offset+1] << 8;
4775 value |= this.view[offset ];
4776 value += this.view[offset+3] << 24 >>> 0;
4777 } else {
4778 value = this.view[offset+1] << 16;
4779 value |= this.view[offset+2] << 8;
4780 value |= this.view[offset+3];
4781 value += this.view[offset ] << 24 >>> 0;
4782 }
4783 if (relative) this.offset += 4;
4784 return value;
4785 };
4786
4787 /**
4788 * Reads a 32bit unsigned integer. This is an alias of {@link ByteBuffer#readUint32}.
4789 * @function
4790 * @param {number=} offset Offset to read from. Will use and increase {@link ByteBuffer#offset} by `4` if omitted.
4791 * @returns {number} Value read
4792 * @expose
4793 */
4794 ByteBufferPrototype.readUInt32 = ByteBufferPrototype.readUint32;
4795
4796 // types/ints/int64
4797
4798 if (Long) {
4799
4800 /**
4801 * Writes a 64bit signed integer.
4802 * @param {number|!Long} value Value to write
4803 * @param {number=} offset Offset to write to. Will use and increase {@link ByteBuffer#offset} by `8` if omitted.
4804 * @returns {!ByteBuffer} this
4805 * @expose
4806 */
4807 ByteBufferPrototype.writeInt64 = function(value, offset) {
4808 var relative = typeof offset === 'undefined';
4809 if (relative) offset = this.offset;
4810 if (!this.noAssert) {
4811 if (typeof value === 'number')
4812 value = Long.fromNumber(value);
4813 else if (typeof value === 'string')
4814 value = Long.fromString(value);
4815 else if (!(value && value instanceof Long))
4816 throw TypeError("Illegal value: "+value+" (not an integer or Long)");
4817 if (typeof offset !== 'number' || offset % 1 !== 0)
4818 throw TypeError("Illegal offset: "+offset+" (not an integer)");
4819 offset >>>= 0;
4820 if (offset < 0 || offset + 0 > this.buffer.byteLength)
4821 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+0+") <= "+this.buffer.byteLength);
4822 }
4823 if (typeof value === 'number')
4824 value = Long.fromNumber(value);
4825 else if (typeof value === 'string')
4826 value = Long.fromString(value);
4827 offset += 8;
4828 var capacity6 = this.buffer.byteLength;
4829 if (offset > capacity6)
4830 this.resize((capacity6 *= 2) > offset ? capacity6 : offset);
4831 offset -= 8;
4832 var lo = value.low,
4833 hi = value.high;
4834 if (this.littleEndian) {
4835 this.view[offset+3] = (lo >>> 24) & 0xFF;
4836 this.view[offset+2] = (lo >>> 16) & 0xFF;
4837 this.view[offset+1] = (lo >>> 8) & 0xFF;
4838 this.view[offset ] = lo & 0xFF;
4839 offset += 4;
4840 this.view[offset+3] = (hi >>> 24) & 0xFF;
4841 this.view[offset+2] = (hi >>> 16) & 0xFF;
4842 this.view[offset+1] = (hi >>> 8) & 0xFF;
4843 this.view[offset ] = hi & 0xFF;
4844 } else {
4845 this.view[offset ] = (hi >>> 24) & 0xFF;
4846 this.view[offset+1] = (hi >>> 16) & 0xFF;
4847 this.view[offset+2] = (hi >>> 8) & 0xFF;
4848 this.view[offset+3] = hi & 0xFF;
4849 offset += 4;
4850 this.view[offset ] = (lo >>> 24) & 0xFF;
4851 this.view[offset+1] = (lo >>> 16) & 0xFF;
4852 this.view[offset+2] = (lo >>> 8) & 0xFF;
4853 this.view[offset+3] = lo & 0xFF;
4854 }
4855 if (relative) this.offset += 8;
4856 return this;
4857 };
4858
4859 /**
4860 * Writes a 64bit signed integer. This is an alias of {@link ByteBuffer#writeInt64}.
4861 * @param {number|!Long} value Value to write
4862 * @param {number=} offset Offset to write to. Will use and increase {@link ByteBuffer#offset} by `8` if omitted.
4863 * @returns {!ByteBuffer} this
4864 * @expose
4865 */
4866 ByteBufferPrototype.writeLong = ByteBufferPrototype.writeInt64;
4867
4868 /**
4869 * Reads a 64bit signed integer.
4870 * @param {number=} offset Offset to read from. Will use and increase {@link ByteBuffer#offset} by `8` if omitted.
4871 * @returns {!Long}
4872 * @expose
4873 */
4874 ByteBufferPrototype.readInt64 = function(offset) {
4875 var relative = typeof offset === 'undefined';
4876 if (relative) offset = this.offset;
4877 if (!this.noAssert) {
4878 if (typeof offset !== 'number' || offset % 1 !== 0)
4879 throw TypeError("Illegal offset: "+offset+" (not an integer)");
4880 offset >>>= 0;
4881 if (offset < 0 || offset + 8 > this.buffer.byteLength)
4882 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+8+") <= "+this.buffer.byteLength);
4883 }
4884 var lo = 0,
4885 hi = 0;
4886 if (this.littleEndian) {
4887 lo = this.view[offset+2] << 16;
4888 lo |= this.view[offset+1] << 8;
4889 lo |= this.view[offset ];
4890 lo += this.view[offset+3] << 24 >>> 0;
4891 offset += 4;
4892 hi = this.view[offset+2] << 16;
4893 hi |= this.view[offset+1] << 8;
4894 hi |= this.view[offset ];
4895 hi += this.view[offset+3] << 24 >>> 0;
4896 } else {
4897 hi = this.view[offset+1] << 16;
4898 hi |= this.view[offset+2] << 8;
4899 hi |= this.view[offset+3];
4900 hi += this.view[offset ] << 24 >>> 0;
4901 offset += 4;
4902 lo = this.view[offset+1] << 16;
4903 lo |= this.view[offset+2] << 8;
4904 lo |= this.view[offset+3];
4905 lo += this.view[offset ] << 24 >>> 0;
4906 }
4907 var value = new Long(lo, hi, false);
4908 if (relative) this.offset += 8;
4909 return value;
4910 };
4911
4912 /**
4913 * Reads a 64bit signed integer. This is an alias of {@link ByteBuffer#readInt64}.
4914 * @param {number=} offset Offset to read from. Will use and increase {@link ByteBuffer#offset} by `8` if omitted.
4915 * @returns {!Long}
4916 * @expose
4917 */
4918 ByteBufferPrototype.readLong = ByteBufferPrototype.readInt64;
4919
4920 /**
4921 * Writes a 64bit unsigned integer.
4922 * @param {number|!Long} value Value to write
4923 * @param {number=} offset Offset to write to. Will use and increase {@link ByteBuffer#offset} by `8` if omitted.
4924 * @returns {!ByteBuffer} this
4925 * @expose
4926 */
4927 ByteBufferPrototype.writeUint64 = function(value, offset) {
4928 var relative = typeof offset === 'undefined';
4929 if (relative) offset = this.offset;
4930 if (!this.noAssert) {
4931 if (typeof value === 'number')
4932 value = Long.fromNumber(value);
4933 else if (typeof value === 'string')
4934 value = Long.fromString(value);
4935 else if (!(value && value instanceof Long))
4936 throw TypeError("Illegal value: "+value+" (not an integer or Long)");
4937 if (typeof offset !== 'number' || offset % 1 !== 0)
4938 throw TypeError("Illegal offset: "+offset+" (not an integer)");
4939 offset >>>= 0;
4940 if (offset < 0 || offset + 0 > this.buffer.byteLength)
4941 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+0+") <= "+this.buffer.byteLength);
4942 }
4943 if (typeof value === 'number')
4944 value = Long.fromNumber(value);
4945 else if (typeof value === 'string')
4946 value = Long.fromString(value);
4947 offset += 8;
4948 var capacity7 = this.buffer.byteLength;
4949 if (offset > capacity7)
4950 this.resize((capacity7 *= 2) > offset ? capacity7 : offset);
4951 offset -= 8;
4952 var lo = value.low,
4953 hi = value.high;
4954 if (this.littleEndian) {
4955 this.view[offset+3] = (lo >>> 24) & 0xFF;
4956 this.view[offset+2] = (lo >>> 16) & 0xFF;
4957 this.view[offset+1] = (lo >>> 8) & 0xFF;
4958 this.view[offset ] = lo & 0xFF;
4959 offset += 4;
4960 this.view[offset+3] = (hi >>> 24) & 0xFF;
4961 this.view[offset+2] = (hi >>> 16) & 0xFF;
4962 this.view[offset+1] = (hi >>> 8) & 0xFF;
4963 this.view[offset ] = hi & 0xFF;
4964 } else {
4965 this.view[offset ] = (hi >>> 24) & 0xFF;
4966 this.view[offset+1] = (hi >>> 16) & 0xFF;
4967 this.view[offset+2] = (hi >>> 8) & 0xFF;
4968 this.view[offset+3] = hi & 0xFF;
4969 offset += 4;
4970 this.view[offset ] = (lo >>> 24) & 0xFF;
4971 this.view[offset+1] = (lo >>> 16) & 0xFF;
4972 this.view[offset+2] = (lo >>> 8) & 0xFF;
4973 this.view[offset+3] = lo & 0xFF;
4974 }
4975 if (relative) this.offset += 8;
4976 return this;
4977 };
4978
4979 /**
4980 * Writes a 64bit unsigned integer. This is an alias of {@link ByteBuffer#writeUint64}.
4981 * @function
4982 * @param {number|!Long} value Value to write
4983 * @param {number=} offset Offset to write to. Will use and increase {@link ByteBuffer#offset} by `8` if omitted.
4984 * @returns {!ByteBuffer} this
4985 * @expose
4986 */
4987 ByteBufferPrototype.writeUInt64 = ByteBufferPrototype.writeUint64;
4988
4989 /**
4990 * Reads a 64bit unsigned integer.
4991 * @param {number=} offset Offset to read from. Will use and increase {@link ByteBuffer#offset} by `8` if omitted.
4992 * @returns {!Long}
4993 * @expose
4994 */
4995 ByteBufferPrototype.readUint64 = function(offset) {
4996 var relative = typeof offset === 'undefined';
4997 if (relative) offset = this.offset;
4998 if (!this.noAssert) {
4999 if (typeof offset !== 'number' || offset % 1 !== 0)
5000 throw TypeError("Illegal offset: "+offset+" (not an integer)");
5001 offset >>>= 0;
5002 if (offset < 0 || offset + 8 > this.buffer.byteLength)
5003 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+8+") <= "+this.buffer.byteLength);
5004 }
5005 var lo = 0,
5006 hi = 0;
5007 if (this.littleEndian) {
5008 lo = this.view[offset+2] << 16;
5009 lo |= this.view[offset+1] << 8;
5010 lo |= this.view[offset ];
5011 lo += this.view[offset+3] << 24 >>> 0;
5012 offset += 4;
5013 hi = this.view[offset+2] << 16;
5014 hi |= this.view[offset+1] << 8;
5015 hi |= this.view[offset ];
5016 hi += this.view[offset+3] << 24 >>> 0;
5017 } else {
5018 hi = this.view[offset+1] << 16;
5019 hi |= this.view[offset+2] << 8;
5020 hi |= this.view[offset+3];
5021 hi += this.view[offset ] << 24 >>> 0;
5022 offset += 4;
5023 lo = this.view[offset+1] << 16;
5024 lo |= this.view[offset+2] << 8;
5025 lo |= this.view[offset+3];
5026 lo += this.view[offset ] << 24 >>> 0;
5027 }
5028 var value = new Long(lo, hi, true);
5029 if (relative) this.offset += 8;
5030 return value;
5031 };
5032
5033 /**
5034 * Reads a 64bit unsigned integer. This is an alias of {@link ByteBuffer#readUint64}.
5035 * @function
5036 * @param {number=} offset Offset to read from. Will use and increase {@link ByteBuffer#offset} by `8` if omitted.
5037 * @returns {!Long}
5038 * @expose
5039 */
5040 ByteBufferPrototype.readUInt64 = ByteBufferPrototype.readUint64;
5041
5042 } // Long
5043
5044
5045 // types/floats/float32
5046
5047 /*
5048 ieee754 - https://github.com/feross/ieee754
5049
5050 The MIT License (MIT)
5051
5052 Copyright (c) Feross Aboukhadijeh
5053
5054 Permission is hereby granted, free of charge, to any person obtaining a copy
5055 of this software and associated documentation files (the "Software"), to deal
5056 in the Software without restriction, including without limitation the rights
5057 to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
5058 copies of the Software, and to permit persons to whom the Software is
5059 furnished to do so, subject to the following conditions:
5060
5061 The above copyright notice and this permission notice shall be included in
5062 all copies or substantial portions of the Software.
5063
5064 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
5065 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
5066 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
5067 AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
5068 LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
5069 OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
5070 THE SOFTWARE.
5071 */
5072
5073 /**
5074 * Reads an IEEE754 float from a byte array.
5075 * @param {!Array} buffer
5076 * @param {number} offset
5077 * @param {boolean} isLE
5078 * @param {number} mLen
5079 * @param {number} nBytes
5080 * @returns {number}
5081 * @inner
5082 */
5083 function ieee754_read(buffer, offset, isLE, mLen, nBytes) {
5084 var e, m,
5085 eLen = nBytes * 8 - mLen - 1,
5086 eMax = (1 << eLen) - 1,
5087 eBias = eMax >> 1,
5088 nBits = -7,
5089 i = isLE ? (nBytes - 1) : 0,
5090 d = isLE ? -1 : 1,
5091 s = buffer[offset + i];
5092
5093 i += d;
5094
5095 e = s & ((1 << (-nBits)) - 1);
5096 s >>= (-nBits);
5097 nBits += eLen;
5098 for (; nBits > 0; e = e * 256 + buffer[offset + i], i += d, nBits -= 8) {}
5099
5100 m = e & ((1 << (-nBits)) - 1);
5101 e >>= (-nBits);
5102 nBits += mLen;
5103 for (; nBits > 0; m = m * 256 + buffer[offset + i], i += d, nBits -= 8) {}
5104
5105 if (e === 0) {
5106 e = 1 - eBias;
5107 } else if (e === eMax) {
5108 return m ? NaN : ((s ? -1 : 1) * Infinity);
5109 } else {
5110 m = m + Math.pow(2, mLen);
5111 e = e - eBias;
5112 }
5113 return (s ? -1 : 1) * m * Math.pow(2, e - mLen);
5114 }
5115
5116 /**
5117 * Writes an IEEE754 float to a byte array.
5118 * @param {!Array} buffer
5119 * @param {number} value
5120 * @param {number} offset
5121 * @param {boolean} isLE
5122 * @param {number} mLen
5123 * @param {number} nBytes
5124 * @inner
5125 */
5126 function ieee754_write(buffer, value, offset, isLE, mLen, nBytes) {
5127 var e, m, c,
5128 eLen = nBytes * 8 - mLen - 1,
5129 eMax = (1 << eLen) - 1,
5130 eBias = eMax >> 1,
5131 rt = (mLen === 23 ? Math.pow(2, -24) - Math.pow(2, -77) : 0),
5132 i = isLE ? 0 : (nBytes - 1),
5133 d = isLE ? 1 : -1,
5134 s = value < 0 || (value === 0 && 1 / value < 0) ? 1 : 0;
5135
5136 value = Math.abs(value);
5137
5138 if (isNaN(value) || value === Infinity) {
5139 m = isNaN(value) ? 1 : 0;
5140 e = eMax;
5141 } else {
5142 e = Math.floor(Math.log(value) / Math.LN2);
5143 if (value * (c = Math.pow(2, -e)) < 1) {
5144 e--;
5145 c *= 2;
5146 }
5147 if (e + eBias >= 1) {
5148 value += rt / c;
5149 } else {
5150 value += rt * Math.pow(2, 1 - eBias);
5151 }
5152 if (value * c >= 2) {
5153 e++;
5154 c /= 2;
5155 }
5156
5157 if (e + eBias >= eMax) {
5158 m = 0;
5159 e = eMax;
5160 } else if (e + eBias >= 1) {
5161 m = (value * c - 1) * Math.pow(2, mLen);
5162 e = e + eBias;
5163 } else {
5164 m = value * Math.pow(2, eBias - 1) * Math.pow(2, mLen);
5165 e = 0;
5166 }
5167 }
5168
5169 for (; mLen >= 8; buffer[offset + i] = m & 0xff, i += d, m /= 256, mLen -= 8) {}
5170
5171 e = (e << mLen) | m;
5172 eLen += mLen;
5173 for (; eLen > 0; buffer[offset + i] = e & 0xff, i += d, e /= 256, eLen -= 8) {}
5174
5175 buffer[offset + i - d] |= s * 128;
5176 }
5177
5178 /**
5179 * Writes a 32bit float.
5180 * @param {number} value Value to write
5181 * @param {number=} offset Offset to write to. Will use and increase {@link ByteBuffer#offset} by `4` if omitted.
5182 * @returns {!ByteBuffer} this
5183 * @expose
5184 */
5185 ByteBufferPrototype.writeFloat32 = function(value, offset) {
5186 var relative = typeof offset === 'undefined';
5187 if (relative) offset = this.offset;
5188 if (!this.noAssert) {
5189 if (typeof value !== 'number')
5190 throw TypeError("Illegal value: "+value+" (not a number)");
5191 if (typeof offset !== 'number' || offset % 1 !== 0)
5192 throw TypeError("Illegal offset: "+offset+" (not an integer)");
5193 offset >>>= 0;
5194 if (offset < 0 || offset + 0 > this.buffer.byteLength)
5195 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+0+") <= "+this.buffer.byteLength);
5196 }
5197 offset += 4;
5198 var capacity8 = this.buffer.byteLength;
5199 if (offset > capacity8)
5200 this.resize((capacity8 *= 2) > offset ? capacity8 : offset);
5201 offset -= 4;
5202 ieee754_write(this.view, value, offset, this.littleEndian, 23, 4);
5203 if (relative) this.offset += 4;
5204 return this;
5205 };
5206
5207 /**
5208 * Writes a 32bit float. This is an alias of {@link ByteBuffer#writeFloat32}.
5209 * @function
5210 * @param {number} value Value to write
5211 * @param {number=} offset Offset to write to. Will use and increase {@link ByteBuffer#offset} by `4` if omitted.
5212 * @returns {!ByteBuffer} this
5213 * @expose
5214 */
5215 ByteBufferPrototype.writeFloat = ByteBufferPrototype.writeFloat32;
5216
5217 /**
5218 * Reads a 32bit float.
5219 * @param {number=} offset Offset to read from. Will use and increase {@link ByteBuffer#offset} by `4` if omitted.
5220 * @returns {number}
5221 * @expose
5222 */
5223 ByteBufferPrototype.readFloat32 = function(offset) {
5224 var relative = typeof offset === 'undefined';
5225 if (relative) offset = this.offset;
5226 if (!this.noAssert) {
5227 if (typeof offset !== 'number' || offset % 1 !== 0)
5228 throw TypeError("Illegal offset: "+offset+" (not an integer)");
5229 offset >>>= 0;
5230 if (offset < 0 || offset + 4 > this.buffer.byteLength)
5231 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+4+") <= "+this.buffer.byteLength);
5232 }
5233 var value = ieee754_read(this.view, offset, this.littleEndian, 23, 4);
5234 if (relative) this.offset += 4;
5235 return value;
5236 };
5237
5238 /**
5239 * Reads a 32bit float. This is an alias of {@link ByteBuffer#readFloat32}.
5240 * @function
5241 * @param {number=} offset Offset to read from. Will use and increase {@link ByteBuffer#offset} by `4` if omitted.
5242 * @returns {number}
5243 * @expose
5244 */
5245 ByteBufferPrototype.readFloat = ByteBufferPrototype.readFloat32;
5246
5247 // types/floats/float64
5248
5249 /**
5250 * Writes a 64bit float.
5251 * @param {number} value Value to write
5252 * @param {number=} offset Offset to write to. Will use and increase {@link ByteBuffer#offset} by `8` if omitted.
5253 * @returns {!ByteBuffer} this
5254 * @expose
5255 */
5256 ByteBufferPrototype.writeFloat64 = function(value, offset) {
5257 var relative = typeof offset === 'undefined';
5258 if (relative) offset = this.offset;
5259 if (!this.noAssert) {
5260 if (typeof value !== 'number')
5261 throw TypeError("Illegal value: "+value+" (not a number)");
5262 if (typeof offset !== 'number' || offset % 1 !== 0)
5263 throw TypeError("Illegal offset: "+offset+" (not an integer)");
5264 offset >>>= 0;
5265 if (offset < 0 || offset + 0 > this.buffer.byteLength)
5266 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+0+") <= "+this.buffer.byteLength);
5267 }
5268 offset += 8;
5269 var capacity9 = this.buffer.byteLength;
5270 if (offset > capacity9)
5271 this.resize((capacity9 *= 2) > offset ? capacity9 : offset);
5272 offset -= 8;
5273 ieee754_write(this.view, value, offset, this.littleEndian, 52, 8);
5274 if (relative) this.offset += 8;
5275 return this;
5276 };
5277
5278 /**
5279 * Writes a 64bit float. This is an alias of {@link ByteBuffer#writeFloat64}.
5280 * @function
5281 * @param {number} value Value to write
5282 * @param {number=} offset Offset to write to. Will use and increase {@link ByteBuffer#offset} by `8` if omitted.
5283 * @returns {!ByteBuffer} this
5284 * @expose
5285 */
5286 ByteBufferPrototype.writeDouble = ByteBufferPrototype.writeFloat64;
5287
5288 /**
5289 * Reads a 64bit float.
5290 * @param {number=} offset Offset to read from. Will use and increase {@link ByteBuffer#offset} by `8` if omitted.
5291 * @returns {number}
5292 * @expose
5293 */
5294 ByteBufferPrototype.readFloat64 = function(offset) {
5295 var relative = typeof offset === 'undefined';
5296 if (relative) offset = this.offset;
5297 if (!this.noAssert) {
5298 if (typeof offset !== 'number' || offset % 1 !== 0)
5299 throw TypeError("Illegal offset: "+offset+" (not an integer)");
5300 offset >>>= 0;
5301 if (offset < 0 || offset + 8 > this.buffer.byteLength)
5302 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+8+") <= "+this.buffer.byteLength);
5303 }
5304 var value = ieee754_read(this.view, offset, this.littleEndian, 52, 8);
5305 if (relative) this.offset += 8;
5306 return value;
5307 };
5308
5309 /**
5310 * Reads a 64bit float. This is an alias of {@link ByteBuffer#readFloat64}.
5311 * @function
5312 * @param {number=} offset Offset to read from. Will use and increase {@link ByteBuffer#offset} by `8` if omitted.
5313 * @returns {number}
5314 * @expose
5315 */
5316 ByteBufferPrototype.readDouble = ByteBufferPrototype.readFloat64;
5317
5318
5319 // types/varints/varint32
5320
5321 /**
5322 * Maximum number of bytes required to store a 32bit base 128 variable-length integer.
5323 * @type {number}
5324 * @const
5325 * @expose
5326 */
5327 ByteBuffer.MAX_VARINT32_BYTES = 5;
5328
5329 /**
5330 * Calculates the actual number of bytes required to store a 32bit base 128 variable-length integer.
5331 * @param {number} value Value to encode
5332 * @returns {number} Number of bytes required. Capped to {@link ByteBuffer.MAX_VARINT32_BYTES}
5333 * @expose
5334 */
5335 ByteBuffer.calculateVarint32 = function(value) {
5336 // ref: src/google/protobuf/io/coded_stream.cc
5337 value = value >>> 0;
5338 if (value < 1 << 7 ) return 1;
5339 else if (value < 1 << 14) return 2;
5340 else if (value < 1 << 21) return 3;
5341 else if (value < 1 << 28) return 4;
5342 else return 5;
5343 };
5344
5345 /**
5346 * Zigzag encodes a signed 32bit integer so that it can be effectively used with varint encoding.
5347 * @param {number} n Signed 32bit integer
5348 * @returns {number} Unsigned zigzag encoded 32bit integer
5349 * @expose
5350 */
5351 ByteBuffer.zigZagEncode32 = function(n) {
5352 return (((n |= 0) << 1) ^ (n >> 31)) >>> 0; // ref: src/google/protobuf/wire_format_lite.h
5353 };
5354
5355 /**
5356 * Decodes a zigzag encoded signed 32bit integer.
5357 * @param {number} n Unsigned zigzag encoded 32bit integer
5358 * @returns {number} Signed 32bit integer
5359 * @expose
5360 */
5361 ByteBuffer.zigZagDecode32 = function(n) {
5362 return ((n >>> 1) ^ -(n & 1)) | 0; // // ref: src/google/protobuf/wire_format_lite.h
5363 };
5364
5365 /**
5366 * Writes a 32bit base 128 variable-length integer.
5367 * @param {number} value Value to write
5368 * @param {number=} offset Offset to write to. Will use and increase {@link ByteBuffer#offset} by the number of bytes
5369 * written if omitted.
5370 * @returns {!ByteBuffer|number} this if `offset` is omitted, else the actual number of bytes written
5371 * @expose
5372 */
5373 ByteBufferPrototype.writeVarint32 = function(value, offset) {
5374 var relative = typeof offset === 'undefined';
5375 if (relative) offset = this.offset;
5376 if (!this.noAssert) {
5377 if (typeof value !== 'number' || value % 1 !== 0)
5378 throw TypeError("Illegal value: "+value+" (not an integer)");
5379 value |= 0;
5380 if (typeof offset !== 'number' || offset % 1 !== 0)
5381 throw TypeError("Illegal offset: "+offset+" (not an integer)");
5382 offset >>>= 0;
5383 if (offset < 0 || offset + 0 > this.buffer.byteLength)
5384 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+0+") <= "+this.buffer.byteLength);
5385 }
5386 var size = ByteBuffer.calculateVarint32(value),
5387 b;
5388 offset += size;
5389 var capacity10 = this.buffer.byteLength;
5390 if (offset > capacity10)
5391 this.resize((capacity10 *= 2) > offset ? capacity10 : offset);
5392 offset -= size;
5393 value >>>= 0;
5394 while (value >= 0x80) {
5395 b = (value & 0x7f) | 0x80;
5396 this.view[offset++] = b;
5397 value >>>= 7;
5398 }
5399 this.view[offset++] = value;
5400 if (relative) {
5401 this.offset = offset;
5402 return this;
5403 }
5404 return size;
5405 };
5406
5407 /**
5408 * Writes a zig-zag encoded (signed) 32bit base 128 variable-length integer.
5409 * @param {number} value Value to write
5410 * @param {number=} offset Offset to write to. Will use and increase {@link ByteBuffer#offset} by the number of bytes
5411 * written if omitted.
5412 * @returns {!ByteBuffer|number} this if `offset` is omitted, else the actual number of bytes written
5413 * @expose
5414 */
5415 ByteBufferPrototype.writeVarint32ZigZag = function(value, offset) {
5416 return this.writeVarint32(ByteBuffer.zigZagEncode32(value), offset);
5417 };
5418
5419 /**
5420 * Reads a 32bit base 128 variable-length integer.
5421 * @param {number=} offset Offset to read from. Will use and increase {@link ByteBuffer#offset} by the number of bytes
5422 * written if omitted.
5423 * @returns {number|!{value: number, length: number}} The value read if offset is omitted, else the value read
5424 * and the actual number of bytes read.
5425 * @throws {Error} If it's not a valid varint. Has a property `truncated = true` if there is not enough data available
5426 * to fully decode the varint.
5427 * @expose
5428 */
5429 ByteBufferPrototype.readVarint32 = function(offset) {
5430 var relative = typeof offset === 'undefined';
5431 if (relative) offset = this.offset;
5432 if (!this.noAssert) {
5433 if (typeof offset !== 'number' || offset % 1 !== 0)
5434 throw TypeError("Illegal offset: "+offset+" (not an integer)");
5435 offset >>>= 0;
5436 if (offset < 0 || offset + 1 > this.buffer.byteLength)
5437 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+1+") <= "+this.buffer.byteLength);
5438 }
5439 var c = 0,
5440 value = 0 >>> 0,
5441 b;
5442 do {
5443 if (!this.noAssert && offset > this.limit) {
5444 var err = Error("Truncated");
5445 err['truncated'] = true;
5446 throw err;
5447 }
5448 b = this.view[offset++];
5449 if (c < 5)
5450 value |= (b & 0x7f) << (7*c);
5451 ++c;
5452 } while ((b & 0x80) !== 0);
5453 value |= 0;
5454 if (relative) {
5455 this.offset = offset;
5456 return value;
5457 }
5458 return {
5459 "value": value,
5460 "length": c
5461 };
5462 };
5463
5464 /**
5465 * Reads a zig-zag encoded (signed) 32bit base 128 variable-length integer.
5466 * @param {number=} offset Offset to read from. Will use and increase {@link ByteBuffer#offset} by the number of bytes
5467 * written if omitted.
5468 * @returns {number|!{value: number, length: number}} The value read if offset is omitted, else the value read
5469 * and the actual number of bytes read.
5470 * @throws {Error} If it's not a valid varint
5471 * @expose
5472 */
5473 ByteBufferPrototype.readVarint32ZigZag = function(offset) {
5474 var val = this.readVarint32(offset);
5475 if (typeof val === 'object')
5476 val["value"] = ByteBuffer.zigZagDecode32(val["value"]);
5477 else
5478 val = ByteBuffer.zigZagDecode32(val);
5479 return val;
5480 };
5481
5482 // types/varints/varint64
5483
5484 if (Long) {
5485
5486 /**
5487 * Maximum number of bytes required to store a 64bit base 128 variable-length integer.
5488 * @type {number}
5489 * @const
5490 * @expose
5491 */
5492 ByteBuffer.MAX_VARINT64_BYTES = 10;
5493
5494 /**
5495 * Calculates the actual number of bytes required to store a 64bit base 128 variable-length integer.
5496 * @param {number|!Long} value Value to encode
5497 * @returns {number} Number of bytes required. Capped to {@link ByteBuffer.MAX_VARINT64_BYTES}
5498 * @expose
5499 */
5500 ByteBuffer.calculateVarint64 = function(value) {
5501 if (typeof value === 'number')
5502 value = Long.fromNumber(value);
5503 else if (typeof value === 'string')
5504 value = Long.fromString(value);
5505 // ref: src/google/protobuf/io/coded_stream.cc
5506 var part0 = value.toInt() >>> 0,
5507 part1 = value.shiftRightUnsigned(28).toInt() >>> 0,
5508 part2 = value.shiftRightUnsigned(56).toInt() >>> 0;
5509 if (part2 == 0) {
5510 if (part1 == 0) {
5511 if (part0 < 1 << 14)
5512 return part0 < 1 << 7 ? 1 : 2;
5513 else
5514 return part0 < 1 << 21 ? 3 : 4;
5515 } else {
5516 if (part1 < 1 << 14)
5517 return part1 < 1 << 7 ? 5 : 6;
5518 else
5519 return part1 < 1 << 21 ? 7 : 8;
5520 }
5521 } else
5522 return part2 < 1 << 7 ? 9 : 10;
5523 };
5524
5525 /**
5526 * Zigzag encodes a signed 64bit integer so that it can be effectively used with varint encoding.
5527 * @param {number|!Long} value Signed long
5528 * @returns {!Long} Unsigned zigzag encoded long
5529 * @expose
5530 */
5531 ByteBuffer.zigZagEncode64 = function(value) {
5532 if (typeof value === 'number')
5533 value = Long.fromNumber(value, false);
5534 else if (typeof value === 'string')
5535 value = Long.fromString(value, false);
5536 else if (value.unsigned !== false) value = value.toSigned();
5537 // ref: src/google/protobuf/wire_format_lite.h
5538 return value.shiftLeft(1).xor(value.shiftRight(63)).toUnsigned();
5539 };
5540
5541 /**
5542 * Decodes a zigzag encoded signed 64bit integer.
5543 * @param {!Long|number} value Unsigned zigzag encoded long or JavaScript number
5544 * @returns {!Long} Signed long
5545 * @expose
5546 */
5547 ByteBuffer.zigZagDecode64 = function(value) {
5548 if (typeof value === 'number')
5549 value = Long.fromNumber(value, false);
5550 else if (typeof value === 'string')
5551 value = Long.fromString(value, false);
5552 else if (value.unsigned !== false) value = value.toSigned();
5553 // ref: src/google/protobuf/wire_format_lite.h
5554 return value.shiftRightUnsigned(1).xor(value.and(Long.ONE).toSigned().negate()).toSigned();
5555 };
5556
5557 /**
5558 * Writes a 64bit base 128 variable-length integer.
5559 * @param {number|Long} value Value to write
5560 * @param {number=} offset Offset to write to. Will use and increase {@link ByteBuffer#offset} by the number of bytes
5561 * written if omitted.
5562 * @returns {!ByteBuffer|number} `this` if offset is omitted, else the actual number of bytes written.
5563 * @expose
5564 */
5565 ByteBufferPrototype.writeVarint64 = function(value, offset) {
5566 var relative = typeof offset === 'undefined';
5567 if (relative) offset = this.offset;
5568 if (!this.noAssert) {
5569 if (typeof value === 'number')
5570 value = Long.fromNumber(value);
5571 else if (typeof value === 'string')
5572 value = Long.fromString(value);
5573 else if (!(value && value instanceof Long))
5574 throw TypeError("Illegal value: "+value+" (not an integer or Long)");
5575 if (typeof offset !== 'number' || offset % 1 !== 0)
5576 throw TypeError("Illegal offset: "+offset+" (not an integer)");
5577 offset >>>= 0;
5578 if (offset < 0 || offset + 0 > this.buffer.byteLength)
5579 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+0+") <= "+this.buffer.byteLength);
5580 }
5581 if (typeof value === 'number')
5582 value = Long.fromNumber(value, false);
5583 else if (typeof value === 'string')
5584 value = Long.fromString(value, false);
5585 else if (value.unsigned !== false) value = value.toSigned();
5586 var size = ByteBuffer.calculateVarint64(value),
5587 part0 = value.toInt() >>> 0,
5588 part1 = value.shiftRightUnsigned(28).toInt() >>> 0,
5589 part2 = value.shiftRightUnsigned(56).toInt() >>> 0;
5590 offset += size;
5591 var capacity11 = this.buffer.byteLength;
5592 if (offset > capacity11)
5593 this.resize((capacity11 *= 2) > offset ? capacity11 : offset);
5594 offset -= size;
5595 switch (size) {
5596 case 10: this.view[offset+9] = (part2 >>> 7) & 0x01;
5597 case 9 : this.view[offset+8] = size !== 9 ? (part2 ) | 0x80 : (part2 ) & 0x7F;
5598 case 8 : this.view[offset+7] = size !== 8 ? (part1 >>> 21) | 0x80 : (part1 >>> 21) & 0x7F;
5599 case 7 : this.view[offset+6] = size !== 7 ? (part1 >>> 14) | 0x80 : (part1 >>> 14) & 0x7F;
5600 case 6 : this.view[offset+5] = size !== 6 ? (part1 >>> 7) | 0x80 : (part1 >>> 7) & 0x7F;
5601 case 5 : this.view[offset+4] = size !== 5 ? (part1 ) | 0x80 : (part1 ) & 0x7F;
5602 case 4 : this.view[offset+3] = size !== 4 ? (part0 >>> 21) | 0x80 : (part0 >>> 21) & 0x7F;
5603 case 3 : this.view[offset+2] = size !== 3 ? (part0 >>> 14) | 0x80 : (part0 >>> 14) & 0x7F;
5604 case 2 : this.view[offset+1] = size !== 2 ? (part0 >>> 7) | 0x80 : (part0 >>> 7) & 0x7F;
5605 case 1 : this.view[offset ] = size !== 1 ? (part0 ) | 0x80 : (part0 ) & 0x7F;
5606 }
5607 if (relative) {
5608 this.offset += size;
5609 return this;
5610 } else {
5611 return size;
5612 }
5613 };
5614
5615 /**
5616 * Writes a zig-zag encoded 64bit base 128 variable-length integer.
5617 * @param {number|Long} value Value to write
5618 * @param {number=} offset Offset to write to. Will use and increase {@link ByteBuffer#offset} by the number of bytes
5619 * written if omitted.
5620 * @returns {!ByteBuffer|number} `this` if offset is omitted, else the actual number of bytes written.
5621 * @expose
5622 */
5623 ByteBufferPrototype.writeVarint64ZigZag = function(value, offset) {
5624 return this.writeVarint64(ByteBuffer.zigZagEncode64(value), offset);
5625 };
5626
5627 /**
5628 * Reads a 64bit base 128 variable-length integer. Requires Long.js.
5629 * @param {number=} offset Offset to read from. Will use and increase {@link ByteBuffer#offset} by the number of bytes
5630 * read if omitted.
5631 * @returns {!Long|!{value: Long, length: number}} The value read if offset is omitted, else the value read and
5632 * the actual number of bytes read.
5633 * @throws {Error} If it's not a valid varint
5634 * @expose
5635 */
5636 ByteBufferPrototype.readVarint64 = function(offset) {
5637 var relative = typeof offset === 'undefined';
5638 if (relative) offset = this.offset;
5639 if (!this.noAssert) {
5640 if (typeof offset !== 'number' || offset % 1 !== 0)
5641 throw TypeError("Illegal offset: "+offset+" (not an integer)");
5642 offset >>>= 0;
5643 if (offset < 0 || offset + 1 > this.buffer.byteLength)
5644 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+1+") <= "+this.buffer.byteLength);
5645 }
5646 // ref: src/google/protobuf/io/coded_stream.cc
5647 var start = offset,
5648 part0 = 0,
5649 part1 = 0,
5650 part2 = 0,
5651 b = 0;
5652 b = this.view[offset++]; part0 = (b & 0x7F) ; if ( b & 0x80 ) {
5653 b = this.view[offset++]; part0 |= (b & 0x7F) << 7; if ((b & 0x80) || (this.noAssert && typeof b === 'undefined')) {
5654 b = this.view[offset++]; part0 |= (b & 0x7F) << 14; if ((b & 0x80) || (this.noAssert && typeof b === 'undefined')) {
5655 b = this.view[offset++]; part0 |= (b & 0x7F) << 21; if ((b & 0x80) || (this.noAssert && typeof b === 'undefined')) {
5656 b = this.view[offset++]; part1 = (b & 0x7F) ; if ((b & 0x80) || (this.noAssert && typeof b === 'undefined')) {
5657 b = this.view[offset++]; part1 |= (b & 0x7F) << 7; if ((b & 0x80) || (this.noAssert && typeof b === 'undefined')) {
5658 b = this.view[offset++]; part1 |= (b & 0x7F) << 14; if ((b & 0x80) || (this.noAssert && typeof b === 'undefined')) {
5659 b = this.view[offset++]; part1 |= (b & 0x7F) << 21; if ((b & 0x80) || (this.noAssert && typeof b === 'undefined')) {
5660 b = this.view[offset++]; part2 = (b & 0x7F) ; if ((b & 0x80) || (this.noAssert && typeof b === 'undefined')) {
5661 b = this.view[offset++]; part2 |= (b & 0x7F) << 7; if ((b & 0x80) || (this.noAssert && typeof b === 'undefined')) {
5662 throw Error("Buffer overrun"); }}}}}}}}}}
5663 var value = Long.fromBits(part0 | (part1 << 28), (part1 >>> 4) | (part2) << 24, false);
5664 if (relative) {
5665 this.offset = offset;
5666 return value;
5667 } else {
5668 return {
5669 'value': value,
5670 'length': offset-start
5671 };
5672 }
5673 };
5674
5675 /**
5676 * Reads a zig-zag encoded 64bit base 128 variable-length integer. Requires Long.js.
5677 * @param {number=} offset Offset to read from. Will use and increase {@link ByteBuffer#offset} by the number of bytes
5678 * read if omitted.
5679 * @returns {!Long|!{value: Long, length: number}} The value read if offset is omitted, else the value read and
5680 * the actual number of bytes read.
5681 * @throws {Error} If it's not a valid varint
5682 * @expose
5683 */
5684 ByteBufferPrototype.readVarint64ZigZag = function(offset) {
5685 var val = this.readVarint64(offset);
5686 if (val && val['value'] instanceof Long)
5687 val["value"] = ByteBuffer.zigZagDecode64(val["value"]);
5688 else
5689 val = ByteBuffer.zigZagDecode64(val);
5690 return val;
5691 };
5692
5693 } // Long
5694
5695
5696 // types/strings/cstring
5697
5698 /**
5699 * Writes a NULL-terminated UTF8 encoded string. For this to work the specified string must not contain any NULL
5700 * characters itself.
5701 * @param {string} str String to write
5702 * @param {number=} offset Offset to write to. Will use and increase {@link ByteBuffer#offset} by the number of bytes
5703 * contained in `str` + 1 if omitted.
5704 * @returns {!ByteBuffer|number} this if offset is omitted, else the actual number of bytes written
5705 * @expose
5706 */
5707 ByteBufferPrototype.writeCString = function(str, offset) {
5708 var relative = typeof offset === 'undefined';
5709 if (relative) offset = this.offset;
5710 var i,
5711 k = str.length;
5712 if (!this.noAssert) {
5713 if (typeof str !== 'string')
5714 throw TypeError("Illegal str: Not a string");
5715 for (i=0; i<k; ++i) {
5716 if (str.charCodeAt(i) === 0)
5717 throw RangeError("Illegal str: Contains NULL-characters");
5718 }
5719 if (typeof offset !== 'number' || offset % 1 !== 0)
5720 throw TypeError("Illegal offset: "+offset+" (not an integer)");
5721 offset >>>= 0;
5722 if (offset < 0 || offset + 0 > this.buffer.byteLength)
5723 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+0+") <= "+this.buffer.byteLength);
5724 }
5725 // UTF8 strings do not contain zero bytes in between except for the zero character, so:
5726 k = utfx.calculateUTF16asUTF8(stringSource(str))[1];
5727 offset += k+1;
5728 var capacity12 = this.buffer.byteLength;
5729 if (offset > capacity12)
5730 this.resize((capacity12 *= 2) > offset ? capacity12 : offset);
5731 offset -= k+1;
5732 utfx.encodeUTF16toUTF8(stringSource(str), function(b) {
5733 this.view[offset++] = b;
5734 }.bind(this));
5735 this.view[offset++] = 0;
5736 if (relative) {
5737 this.offset = offset;
5738 return this;
5739 }
5740 return k;
5741 };
5742
5743 /**
5744 * Reads a NULL-terminated UTF8 encoded string. For this to work the string read must not contain any NULL characters
5745 * itself.
5746 * @param {number=} offset Offset to read from. Will use and increase {@link ByteBuffer#offset} by the number of bytes
5747 * read if omitted.
5748 * @returns {string|!{string: string, length: number}} The string read if offset is omitted, else the string
5749 * read and the actual number of bytes read.
5750 * @expose
5751 */
5752 ByteBufferPrototype.readCString = function(offset) {
5753 var relative = typeof offset === 'undefined';
5754 if (relative) offset = this.offset;
5755 if (!this.noAssert) {
5756 if (typeof offset !== 'number' || offset % 1 !== 0)
5757 throw TypeError("Illegal offset: "+offset+" (not an integer)");
5758 offset >>>= 0;
5759 if (offset < 0 || offset + 1 > this.buffer.byteLength)
5760 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+1+") <= "+this.buffer.byteLength);
5761 }
5762 var start = offset;
5763 // UTF8 strings do not contain zero bytes in between except for the zero character itself, so:
5764 var sd, b = -1;
5765 utfx.decodeUTF8toUTF16(function() {
5766 if (b === 0) return null;
5767 if (offset >= this.limit)
5768 throw RangeError("Illegal range: Truncated data, "+offset+" < "+this.limit);
5769 b = this.view[offset++];
5770 return b === 0 ? null : b;
5771 }.bind(this), sd = stringDestination(), true);
5772 if (relative) {
5773 this.offset = offset;
5774 return sd();
5775 } else {
5776 return {
5777 "string": sd(),
5778 "length": offset - start
5779 };
5780 }
5781 };
5782
5783 // types/strings/istring
5784
5785 /**
5786 * Writes a length as uint32 prefixed UTF8 encoded string.
5787 * @param {string} str String to write
5788 * @param {number=} offset Offset to write to. Will use and increase {@link ByteBuffer#offset} by the number of bytes
5789 * written if omitted.
5790 * @returns {!ByteBuffer|number} `this` if `offset` is omitted, else the actual number of bytes written
5791 * @expose
5792 * @see ByteBuffer#writeVarint32
5793 */
5794 ByteBufferPrototype.writeIString = function(str, offset) {
5795 var relative = typeof offset === 'undefined';
5796 if (relative) offset = this.offset;
5797 if (!this.noAssert) {
5798 if (typeof str !== 'string')
5799 throw TypeError("Illegal str: Not a string");
5800 if (typeof offset !== 'number' || offset % 1 !== 0)
5801 throw TypeError("Illegal offset: "+offset+" (not an integer)");
5802 offset >>>= 0;
5803 if (offset < 0 || offset + 0 > this.buffer.byteLength)
5804 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+0+") <= "+this.buffer.byteLength);
5805 }
5806 var start = offset,
5807 k;
5808 k = utfx.calculateUTF16asUTF8(stringSource(str), this.noAssert)[1];
5809 offset += 4+k;
5810 var capacity13 = this.buffer.byteLength;
5811 if (offset > capacity13)
5812 this.resize((capacity13 *= 2) > offset ? capacity13 : offset);
5813 offset -= 4+k;
5814 if (this.littleEndian) {
5815 this.view[offset+3] = (k >>> 24) & 0xFF;
5816 this.view[offset+2] = (k >>> 16) & 0xFF;
5817 this.view[offset+1] = (k >>> 8) & 0xFF;
5818 this.view[offset ] = k & 0xFF;
5819 } else {
5820 this.view[offset ] = (k >>> 24) & 0xFF;
5821 this.view[offset+1] = (k >>> 16) & 0xFF;
5822 this.view[offset+2] = (k >>> 8) & 0xFF;
5823 this.view[offset+3] = k & 0xFF;
5824 }
5825 offset += 4;
5826 utfx.encodeUTF16toUTF8(stringSource(str), function(b) {
5827 this.view[offset++] = b;
5828 }.bind(this));
5829 if (offset !== start + 4 + k)
5830 throw RangeError("Illegal range: Truncated data, "+offset+" == "+(offset+4+k));
5831 if (relative) {
5832 this.offset = offset;
5833 return this;
5834 }
5835 return offset - start;
5836 };
5837
5838 /**
5839 * Reads a length as uint32 prefixed UTF8 encoded string.
5840 * @param {number=} offset Offset to read from. Will use and increase {@link ByteBuffer#offset} by the number of bytes
5841 * read if omitted.
5842 * @returns {string|!{string: string, length: number}} The string read if offset is omitted, else the string
5843 * read and the actual number of bytes read.
5844 * @expose
5845 * @see ByteBuffer#readVarint32
5846 */
5847 ByteBufferPrototype.readIString = function(offset) {
5848 var relative = typeof offset === 'undefined';
5849 if (relative) offset = this.offset;
5850 if (!this.noAssert) {
5851 if (typeof offset !== 'number' || offset % 1 !== 0)
5852 throw TypeError("Illegal offset: "+offset+" (not an integer)");
5853 offset >>>= 0;
5854 if (offset < 0 || offset + 4 > this.buffer.byteLength)
5855 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+4+") <= "+this.buffer.byteLength);
5856 }
5857 var start = offset;
5858 var len = this.readUint32(offset);
5859 var str = this.readUTF8String(len, ByteBuffer.METRICS_BYTES, offset += 4);
5860 offset += str['length'];
5861 if (relative) {
5862 this.offset = offset;
5863 return str['string'];
5864 } else {
5865 return {
5866 'string': str['string'],
5867 'length': offset - start
5868 };
5869 }
5870 };
5871
5872 // types/strings/utf8string
5873
5874 /**
5875 * Metrics representing number of UTF8 characters. Evaluates to `c`.
5876 * @type {string}
5877 * @const
5878 * @expose
5879 */
5880 ByteBuffer.METRICS_CHARS = 'c';
5881
5882 /**
5883 * Metrics representing number of bytes. Evaluates to `b`.
5884 * @type {string}
5885 * @const
5886 * @expose
5887 */
5888 ByteBuffer.METRICS_BYTES = 'b';
5889
5890 /**
5891 * Writes an UTF8 encoded string.
5892 * @param {string} str String to write
5893 * @param {number=} offset Offset to write to. Will use and increase {@link ByteBuffer#offset} if omitted.
5894 * @returns {!ByteBuffer|number} this if offset is omitted, else the actual number of bytes written.
5895 * @expose
5896 */
5897 ByteBufferPrototype.writeUTF8String = function(str, offset) {
5898 var relative = typeof offset === 'undefined';
5899 if (relative) offset = this.offset;
5900 if (!this.noAssert) {
5901 if (typeof offset !== 'number' || offset % 1 !== 0)
5902 throw TypeError("Illegal offset: "+offset+" (not an integer)");
5903 offset >>>= 0;
5904 if (offset < 0 || offset + 0 > this.buffer.byteLength)
5905 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+0+") <= "+this.buffer.byteLength);
5906 }
5907 var k;
5908 var start = offset;
5909 k = utfx.calculateUTF16asUTF8(stringSource(str))[1];
5910 offset += k;
5911 var capacity14 = this.buffer.byteLength;
5912 if (offset > capacity14)
5913 this.resize((capacity14 *= 2) > offset ? capacity14 : offset);
5914 offset -= k;
5915 utfx.encodeUTF16toUTF8(stringSource(str), function(b) {
5916 this.view[offset++] = b;
5917 }.bind(this));
5918 if (relative) {
5919 this.offset = offset;
5920 return this;
5921 }
5922 return offset - start;
5923 };
5924
5925 /**
5926 * Writes an UTF8 encoded string. This is an alias of {@link ByteBuffer#writeUTF8String}.
5927 * @function
5928 * @param {string} str String to write
5929 * @param {number=} offset Offset to write to. Will use and increase {@link ByteBuffer#offset} if omitted.
5930 * @returns {!ByteBuffer|number} this if offset is omitted, else the actual number of bytes written.
5931 * @expose
5932 */
5933 ByteBufferPrototype.writeString = ByteBufferPrototype.writeUTF8String;
5934
5935 /**
5936 * Calculates the number of UTF8 characters of a string. JavaScript itself uses UTF-16, so that a string's
5937 * `length` property does not reflect its actual UTF8 size if it contains code points larger than 0xFFFF.
5938 * @param {string} str String to calculate
5939 * @returns {number} Number of UTF8 characters
5940 * @expose
5941 */
5942 ByteBuffer.calculateUTF8Chars = function(str) {
5943 return utfx.calculateUTF16asUTF8(stringSource(str))[0];
5944 };
5945
5946 /**
5947 * Calculates the number of UTF8 bytes of a string.
5948 * @param {string} str String to calculate
5949 * @returns {number} Number of UTF8 bytes
5950 * @expose
5951 */
5952 ByteBuffer.calculateUTF8Bytes = function(str) {
5953 return utfx.calculateUTF16asUTF8(stringSource(str))[1];
5954 };
5955
5956 /**
5957 * Calculates the number of UTF8 bytes of a string. This is an alias of {@link ByteBuffer.calculateUTF8Bytes}.
5958 * @function
5959 * @param {string} str String to calculate
5960 * @returns {number} Number of UTF8 bytes
5961 * @expose
5962 */
5963 ByteBuffer.calculateString = ByteBuffer.calculateUTF8Bytes;
5964
5965 /**
5966 * Reads an UTF8 encoded string.
5967 * @param {number} length Number of characters or bytes to read.
5968 * @param {string=} metrics Metrics specifying what `length` is meant to count. Defaults to
5969 * {@link ByteBuffer.METRICS_CHARS}.
5970 * @param {number=} offset Offset to read from. Will use and increase {@link ByteBuffer#offset} by the number of bytes
5971 * read if omitted.
5972 * @returns {string|!{string: string, length: number}} The string read if offset is omitted, else the string
5973 * read and the actual number of bytes read.
5974 * @expose
5975 */
5976 ByteBufferPrototype.readUTF8String = function(length, metrics, offset) {
5977 if (typeof metrics === 'number') {
5978 offset = metrics;
5979 metrics = undefined;
5980 }
5981 var relative = typeof offset === 'undefined';
5982 if (relative) offset = this.offset;
5983 if (typeof metrics === 'undefined') metrics = ByteBuffer.METRICS_CHARS;
5984 if (!this.noAssert) {
5985 if (typeof length !== 'number' || length % 1 !== 0)
5986 throw TypeError("Illegal length: "+length+" (not an integer)");
5987 length |= 0;
5988 if (typeof offset !== 'number' || offset % 1 !== 0)
5989 throw TypeError("Illegal offset: "+offset+" (not an integer)");
5990 offset >>>= 0;
5991 if (offset < 0 || offset + 0 > this.buffer.byteLength)
5992 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+0+") <= "+this.buffer.byteLength);
5993 }
5994 var i = 0,
5995 start = offset,
5996 sd;
5997 if (metrics === ByteBuffer.METRICS_CHARS) { // The same for node and the browser
5998 sd = stringDestination();
5999 utfx.decodeUTF8(function() {
6000 return i < length && offset < this.limit ? this.view[offset++] : null;
6001 }.bind(this), function(cp) {
6002 ++i; utfx.UTF8toUTF16(cp, sd);
6003 });
6004 if (i !== length)
6005 throw RangeError("Illegal range: Truncated data, "+i+" == "+length);
6006 if (relative) {
6007 this.offset = offset;
6008 return sd();
6009 } else {
6010 return {
6011 "string": sd(),
6012 "length": offset - start
6013 };
6014 }
6015 } else if (metrics === ByteBuffer.METRICS_BYTES) {
6016 if (!this.noAssert) {
6017 if (typeof offset !== 'number' || offset % 1 !== 0)
6018 throw TypeError("Illegal offset: "+offset+" (not an integer)");
6019 offset >>>= 0;
6020 if (offset < 0 || offset + length > this.buffer.byteLength)
6021 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+length+") <= "+this.buffer.byteLength);
6022 }
6023 var k = offset + length;
6024 utfx.decodeUTF8toUTF16(function() {
6025 return offset < k ? this.view[offset++] : null;
6026 }.bind(this), sd = stringDestination(), this.noAssert);
6027 if (offset !== k)
6028 throw RangeError("Illegal range: Truncated data, "+offset+" == "+k);
6029 if (relative) {
6030 this.offset = offset;
6031 return sd();
6032 } else {
6033 return {
6034 'string': sd(),
6035 'length': offset - start
6036 };
6037 }
6038 } else
6039 throw TypeError("Unsupported metrics: "+metrics);
6040 };
6041
6042 /**
6043 * Reads an UTF8 encoded string. This is an alias of {@link ByteBuffer#readUTF8String}.
6044 * @function
6045 * @param {number} length Number of characters or bytes to read
6046 * @param {number=} metrics Metrics specifying what `n` is meant to count. Defaults to
6047 * {@link ByteBuffer.METRICS_CHARS}.
6048 * @param {number=} offset Offset to read from. Will use and increase {@link ByteBuffer#offset} by the number of bytes
6049 * read if omitted.
6050 * @returns {string|!{string: string, length: number}} The string read if offset is omitted, else the string
6051 * read and the actual number of bytes read.
6052 * @expose
6053 */
6054 ByteBufferPrototype.readString = ByteBufferPrototype.readUTF8String;
6055
6056 // types/strings/vstring
6057
6058 /**
6059 * Writes a length as varint32 prefixed UTF8 encoded string.
6060 * @param {string} str String to write
6061 * @param {number=} offset Offset to write to. Will use and increase {@link ByteBuffer#offset} by the number of bytes
6062 * written if omitted.
6063 * @returns {!ByteBuffer|number} `this` if `offset` is omitted, else the actual number of bytes written
6064 * @expose
6065 * @see ByteBuffer#writeVarint32
6066 */
6067 ByteBufferPrototype.writeVString = function(str, offset) {
6068 var relative = typeof offset === 'undefined';
6069 if (relative) offset = this.offset;
6070 if (!this.noAssert) {
6071 if (typeof str !== 'string')
6072 throw TypeError("Illegal str: Not a string");
6073 if (typeof offset !== 'number' || offset % 1 !== 0)
6074 throw TypeError("Illegal offset: "+offset+" (not an integer)");
6075 offset >>>= 0;
6076 if (offset < 0 || offset + 0 > this.buffer.byteLength)
6077 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+0+") <= "+this.buffer.byteLength);
6078 }
6079 var start = offset,
6080 k, l;
6081 k = utfx.calculateUTF16asUTF8(stringSource(str), this.noAssert)[1];
6082 l = ByteBuffer.calculateVarint32(k);
6083 offset += l+k;
6084 var capacity15 = this.buffer.byteLength;
6085 if (offset > capacity15)
6086 this.resize((capacity15 *= 2) > offset ? capacity15 : offset);
6087 offset -= l+k;
6088 offset += this.writeVarint32(k, offset);
6089 utfx.encodeUTF16toUTF8(stringSource(str), function(b) {
6090 this.view[offset++] = b;
6091 }.bind(this));
6092 if (offset !== start+k+l)
6093 throw RangeError("Illegal range: Truncated data, "+offset+" == "+(offset+k+l));
6094 if (relative) {
6095 this.offset = offset;
6096 return this;
6097 }
6098 return offset - start;
6099 };
6100
6101 /**
6102 * Reads a length as varint32 prefixed UTF8 encoded string.
6103 * @param {number=} offset Offset to read from. Will use and increase {@link ByteBuffer#offset} by the number of bytes
6104 * read if omitted.
6105 * @returns {string|!{string: string, length: number}} The string read if offset is omitted, else the string
6106 * read and the actual number of bytes read.
6107 * @expose
6108 * @see ByteBuffer#readVarint32
6109 */
6110 ByteBufferPrototype.readVString = function(offset) {
6111 var relative = typeof offset === 'undefined';
6112 if (relative) offset = this.offset;
6113 if (!this.noAssert) {
6114 if (typeof offset !== 'number' || offset % 1 !== 0)
6115 throw TypeError("Illegal offset: "+offset+" (not an integer)");
6116 offset >>>= 0;
6117 if (offset < 0 || offset + 1 > this.buffer.byteLength)
6118 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+1+") <= "+this.buffer.byteLength);
6119 }
6120 var start = offset;
6121 var len = this.readVarint32(offset);
6122 var str = this.readUTF8String(len['value'], ByteBuffer.METRICS_BYTES, offset += len['length']);
6123 offset += str['length'];
6124 if (relative) {
6125 this.offset = offset;
6126 return str['string'];
6127 } else {
6128 return {
6129 'string': str['string'],
6130 'length': offset - start
6131 };
6132 }
6133 };
6134
6135
6136 /**
6137 * Appends some data to this ByteBuffer. This will overwrite any contents behind the specified offset up to the appended
6138 * data's length.
6139 * @param {!ByteBuffer|!ArrayBuffer|!Uint8Array|string} source Data to append. If `source` is a ByteBuffer, its offsets
6140 * will be modified according to the performed read operation.
6141 * @param {(string|number)=} encoding Encoding if `data` is a string ("base64", "hex", "binary", defaults to "utf8")
6142 * @param {number=} offset Offset to append at. Will use and increase {@link ByteBuffer#offset} by the number of bytes
6143 * written if omitted.
6144 * @returns {!ByteBuffer} this
6145 * @expose
6146 * @example A relative `<01 02>03.append(<04 05>)` will result in `<01 02 04 05>, 04 05|`
6147 * @example An absolute `<01 02>03.append(04 05>, 1)` will result in `<01 04>05, 04 05|`
6148 */
6149 ByteBufferPrototype.append = function(source, encoding, offset) {
6150 if (typeof encoding === 'number' || typeof encoding !== 'string') {
6151 offset = encoding;
6152 encoding = undefined;
6153 }
6154 var relative = typeof offset === 'undefined';
6155 if (relative) offset = this.offset;
6156 if (!this.noAssert) {
6157 if (typeof offset !== 'number' || offset % 1 !== 0)
6158 throw TypeError("Illegal offset: "+offset+" (not an integer)");
6159 offset >>>= 0;
6160 if (offset < 0 || offset + 0 > this.buffer.byteLength)
6161 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+0+") <= "+this.buffer.byteLength);
6162 }
6163 if (!(source instanceof ByteBuffer))
6164 source = ByteBuffer.wrap(source, encoding);
6165 var length = source.limit - source.offset;
6166 if (length <= 0) return this; // Nothing to append
6167 offset += length;
6168 var capacity16 = this.buffer.byteLength;
6169 if (offset > capacity16)
6170 this.resize((capacity16 *= 2) > offset ? capacity16 : offset);
6171 offset -= length;
6172 this.view.set(source.view.subarray(source.offset, source.limit), offset);
6173 source.offset += length;
6174 if (relative) this.offset += length;
6175 return this;
6176 };
6177
6178 /**
6179 * Appends this ByteBuffer's contents to another ByteBuffer. This will overwrite any contents at and after the
6180 specified offset up to the length of this ByteBuffer's data.
6181 * @param {!ByteBuffer} target Target ByteBuffer
6182 * @param {number=} offset Offset to append to. Will use and increase {@link ByteBuffer#offset} by the number of bytes
6183 * read if omitted.
6184 * @returns {!ByteBuffer} this
6185 * @expose
6186 * @see ByteBuffer#append
6187 */
6188 ByteBufferPrototype.appendTo = function(target, offset) {
6189 target.append(this, offset);
6190 return this;
6191 };
6192
6193 /**
6194 * Enables or disables assertions of argument types and offsets. Assertions are enabled by default but you can opt to
6195 * disable them if your code already makes sure that everything is valid.
6196 * @param {boolean} assert `true` to enable assertions, otherwise `false`
6197 * @returns {!ByteBuffer} this
6198 * @expose
6199 */
6200 ByteBufferPrototype.assert = function(assert) {
6201 this.noAssert = !assert;
6202 return this;
6203 };
6204
6205 /**
6206 * Gets the capacity of this ByteBuffer's backing buffer.
6207 * @returns {number} Capacity of the backing buffer
6208 * @expose
6209 */
6210 ByteBufferPrototype.capacity = function() {
6211 return this.buffer.byteLength;
6212 };
6213 /**
6214 * Clears this ByteBuffer's offsets by setting {@link ByteBuffer#offset} to `0` and {@link ByteBuffer#limit} to the
6215 * backing buffer's capacity. Discards {@link ByteBuffer#markedOffset}.
6216 * @returns {!ByteBuffer} this
6217 * @expose
6218 */
6219 ByteBufferPrototype.clear = function() {
6220 this.offset = 0;
6221 this.limit = this.buffer.byteLength;
6222 this.markedOffset = -1;
6223 return this;
6224 };
6225
6226 /**
6227 * Creates a cloned instance of this ByteBuffer, preset with this ByteBuffer's values for {@link ByteBuffer#offset},
6228 * {@link ByteBuffer#markedOffset} and {@link ByteBuffer#limit}.
6229 * @param {boolean=} copy Whether to copy the backing buffer or to return another view on the same, defaults to `false`
6230 * @returns {!ByteBuffer} Cloned instance
6231 * @expose
6232 */
6233 ByteBufferPrototype.clone = function(copy) {
6234 var bb = new ByteBuffer(0, this.littleEndian, this.noAssert);
6235 if (copy) {
6236 bb.buffer = new ArrayBuffer(this.buffer.byteLength);
6237 bb.view = new Uint8Array(bb.buffer);
6238 } else {
6239 bb.buffer = this.buffer;
6240 bb.view = this.view;
6241 }
6242 bb.offset = this.offset;
6243 bb.markedOffset = this.markedOffset;
6244 bb.limit = this.limit;
6245 return bb;
6246 };
6247
6248 /**
6249 * Compacts this ByteBuffer to be backed by a {@link ByteBuffer#buffer} of its contents' length. Contents are the bytes
6250 * between {@link ByteBuffer#offset} and {@link ByteBuffer#limit}. Will set `offset = 0` and `limit = capacity` and
6251 * adapt {@link ByteBuffer#markedOffset} to the same relative position if set.
6252 * @param {number=} begin Offset to start at, defaults to {@link ByteBuffer#offset}
6253 * @param {number=} end Offset to end at, defaults to {@link ByteBuffer#limit}
6254 * @returns {!ByteBuffer} this
6255 * @expose
6256 */
6257 ByteBufferPrototype.compact = function(begin, end) {
6258 if (typeof begin === 'undefined') begin = this.offset;
6259 if (typeof end === 'undefined') end = this.limit;
6260 if (!this.noAssert) {
6261 if (typeof begin !== 'number' || begin % 1 !== 0)
6262 throw TypeError("Illegal begin: Not an integer");
6263 begin >>>= 0;
6264 if (typeof end !== 'number' || end % 1 !== 0)
6265 throw TypeError("Illegal end: Not an integer");
6266 end >>>= 0;
6267 if (begin < 0 || begin > end || end > this.buffer.byteLength)
6268 throw RangeError("Illegal range: 0 <= "+begin+" <= "+end+" <= "+this.buffer.byteLength);
6269 }
6270 if (begin === 0 && end === this.buffer.byteLength)
6271 return this; // Already compacted
6272 var len = end - begin;
6273 if (len === 0) {
6274 this.buffer = EMPTY_BUFFER;
6275 this.view = null;
6276 if (this.markedOffset >= 0) this.markedOffset -= begin;
6277 this.offset = 0;
6278 this.limit = 0;
6279 return this;
6280 }
6281 var buffer = new ArrayBuffer(len);
6282 var view = new Uint8Array(buffer);
6283 view.set(this.view.subarray(begin, end));
6284 this.buffer = buffer;
6285 this.view = view;
6286 if (this.markedOffset >= 0) this.markedOffset -= begin;
6287 this.offset = 0;
6288 this.limit = len;
6289 return this;
6290 };
6291
6292 /**
6293 * Creates a copy of this ByteBuffer's contents. Contents are the bytes between {@link ByteBuffer#offset} and
6294 * {@link ByteBuffer#limit}.
6295 * @param {number=} begin Begin offset, defaults to {@link ByteBuffer#offset}.
6296 * @param {number=} end End offset, defaults to {@link ByteBuffer#limit}.
6297 * @returns {!ByteBuffer} Copy
6298 * @expose
6299 */
6300 ByteBufferPrototype.copy = function(begin, end) {
6301 if (typeof begin === 'undefined') begin = this.offset;
6302 if (typeof end === 'undefined') end = this.limit;
6303 if (!this.noAssert) {
6304 if (typeof begin !== 'number' || begin % 1 !== 0)
6305 throw TypeError("Illegal begin: Not an integer");
6306 begin >>>= 0;
6307 if (typeof end !== 'number' || end % 1 !== 0)
6308 throw TypeError("Illegal end: Not an integer");
6309 end >>>= 0;
6310 if (begin < 0 || begin > end || end > this.buffer.byteLength)
6311 throw RangeError("Illegal range: 0 <= "+begin+" <= "+end+" <= "+this.buffer.byteLength);
6312 }
6313 if (begin === end)
6314 return new ByteBuffer(0, this.littleEndian, this.noAssert);
6315 var capacity = end - begin,
6316 bb = new ByteBuffer(capacity, this.littleEndian, this.noAssert);
6317 bb.offset = 0;
6318 bb.limit = capacity;
6319 if (bb.markedOffset >= 0) bb.markedOffset -= begin;
6320 this.copyTo(bb, 0, begin, end);
6321 return bb;
6322 };
6323
6324 /**
6325 * Copies this ByteBuffer's contents to another ByteBuffer. Contents are the bytes between {@link ByteBuffer#offset} and
6326 * {@link ByteBuffer#limit}.
6327 * @param {!ByteBuffer} target Target ByteBuffer
6328 * @param {number=} targetOffset Offset to copy to. Will use and increase the target's {@link ByteBuffer#offset}
6329 * by the number of bytes copied if omitted.
6330 * @param {number=} sourceOffset Offset to start copying from. Will use and increase {@link ByteBuffer#offset} by the
6331 * number of bytes copied if omitted.
6332 * @param {number=} sourceLimit Offset to end copying from, defaults to {@link ByteBuffer#limit}
6333 * @returns {!ByteBuffer} this
6334 * @expose
6335 */
6336 ByteBufferPrototype.copyTo = function(target, targetOffset, sourceOffset, sourceLimit) {
6337 var relative,
6338 targetRelative;
6339 if (!this.noAssert) {
6340 if (!ByteBuffer.isByteBuffer(target))
6341 throw TypeError("Illegal target: Not a ByteBuffer");
6342 }
6343 targetOffset = (targetRelative = typeof targetOffset === 'undefined') ? target.offset : targetOffset | 0;
6344 sourceOffset = (relative = typeof sourceOffset === 'undefined') ? this.offset : sourceOffset | 0;
6345 sourceLimit = typeof sourceLimit === 'undefined' ? this.limit : sourceLimit | 0;
6346
6347 if (targetOffset < 0 || targetOffset > target.buffer.byteLength)
6348 throw RangeError("Illegal target range: 0 <= "+targetOffset+" <= "+target.buffer.byteLength);
6349 if (sourceOffset < 0 || sourceLimit > this.buffer.byteLength)
6350 throw RangeError("Illegal source range: 0 <= "+sourceOffset+" <= "+this.buffer.byteLength);
6351
6352 var len = sourceLimit - sourceOffset;
6353 if (len === 0)
6354 return target; // Nothing to copy
6355
6356 target.ensureCapacity(targetOffset + len);
6357
6358 target.view.set(this.view.subarray(sourceOffset, sourceLimit), targetOffset);
6359
6360 if (relative) this.offset += len;
6361 if (targetRelative) target.offset += len;
6362
6363 return this;
6364 };
6365
6366 /**
6367 * Makes sure that this ByteBuffer is backed by a {@link ByteBuffer#buffer} of at least the specified capacity. If the
6368 * current capacity is exceeded, it will be doubled. If double the current capacity is less than the required capacity,
6369 * the required capacity will be used instead.
6370 * @param {number} capacity Required capacity
6371 * @returns {!ByteBuffer} this
6372 * @expose
6373 */
6374 ByteBufferPrototype.ensureCapacity = function(capacity) {
6375 var current = this.buffer.byteLength;
6376 if (current < capacity)
6377 return this.resize((current *= 2) > capacity ? current : capacity);
6378 return this;
6379 };
6380
6381 /**
6382 * Overwrites this ByteBuffer's contents with the specified value. Contents are the bytes between
6383 * {@link ByteBuffer#offset} and {@link ByteBuffer#limit}.
6384 * @param {number|string} value Byte value to fill with. If given as a string, the first character is used.
6385 * @param {number=} begin Begin offset. Will use and increase {@link ByteBuffer#offset} by the number of bytes
6386 * written if omitted. defaults to {@link ByteBuffer#offset}.
6387 * @param {number=} end End offset, defaults to {@link ByteBuffer#limit}.
6388 * @returns {!ByteBuffer} this
6389 * @expose
6390 * @example `someByteBuffer.clear().fill(0)` fills the entire backing buffer with zeroes
6391 */
6392 ByteBufferPrototype.fill = function(value, begin, end) {
6393 var relative = typeof begin === 'undefined';
6394 if (relative) begin = this.offset;
6395 if (typeof value === 'string' && value.length > 0)
6396 value = value.charCodeAt(0);
6397 if (typeof begin === 'undefined') begin = this.offset;
6398 if (typeof end === 'undefined') end = this.limit;
6399 if (!this.noAssert) {
6400 if (typeof value !== 'number' || value % 1 !== 0)
6401 throw TypeError("Illegal value: "+value+" (not an integer)");
6402 value |= 0;
6403 if (typeof begin !== 'number' || begin % 1 !== 0)
6404 throw TypeError("Illegal begin: Not an integer");
6405 begin >>>= 0;
6406 if (typeof end !== 'number' || end % 1 !== 0)
6407 throw TypeError("Illegal end: Not an integer");
6408 end >>>= 0;
6409 if (begin < 0 || begin > end || end > this.buffer.byteLength)
6410 throw RangeError("Illegal range: 0 <= "+begin+" <= "+end+" <= "+this.buffer.byteLength);
6411 }
6412 if (begin >= end)
6413 return this; // Nothing to fill
6414 while (begin < end) this.view[begin++] = value;
6415 if (relative) this.offset = begin;
6416 return this;
6417 };
6418
6419 /**
6420 * Makes this ByteBuffer ready for a new sequence of write or relative read operations. Sets `limit = offset` and
6421 * `offset = 0`. Make sure always to flip a ByteBuffer when all relative read or write operations are complete.
6422 * @returns {!ByteBuffer} this
6423 * @expose
6424 */
6425 ByteBufferPrototype.flip = function() {
6426 this.limit = this.offset;
6427 this.offset = 0;
6428 return this;
6429 };
6430 /**
6431 * Marks an offset on this ByteBuffer to be used later.
6432 * @param {number=} offset Offset to mark. Defaults to {@link ByteBuffer#offset}.
6433 * @returns {!ByteBuffer} this
6434 * @throws {TypeError} If `offset` is not a valid number
6435 * @throws {RangeError} If `offset` is out of bounds
6436 * @see ByteBuffer#reset
6437 * @expose
6438 */
6439 ByteBufferPrototype.mark = function(offset) {
6440 offset = typeof offset === 'undefined' ? this.offset : offset;
6441 if (!this.noAssert) {
6442 if (typeof offset !== 'number' || offset % 1 !== 0)
6443 throw TypeError("Illegal offset: "+offset+" (not an integer)");
6444 offset >>>= 0;
6445 if (offset < 0 || offset + 0 > this.buffer.byteLength)
6446 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+0+") <= "+this.buffer.byteLength);
6447 }
6448 this.markedOffset = offset;
6449 return this;
6450 };
6451 /**
6452 * Sets the byte order.
6453 * @param {boolean} littleEndian `true` for little endian byte order, `false` for big endian
6454 * @returns {!ByteBuffer} this
6455 * @expose
6456 */
6457 ByteBufferPrototype.order = function(littleEndian) {
6458 if (!this.noAssert) {
6459 if (typeof littleEndian !== 'boolean')
6460 throw TypeError("Illegal littleEndian: Not a boolean");
6461 }
6462 this.littleEndian = !!littleEndian;
6463 return this;
6464 };
6465
6466 /**
6467 * Switches (to) little endian byte order.
6468 * @param {boolean=} littleEndian Defaults to `true`, otherwise uses big endian
6469 * @returns {!ByteBuffer} this
6470 * @expose
6471 */
6472 ByteBufferPrototype.LE = function(littleEndian) {
6473 this.littleEndian = typeof littleEndian !== 'undefined' ? !!littleEndian : true;
6474 return this;
6475 };
6476
6477 /**
6478 * Switches (to) big endian byte order.
6479 * @param {boolean=} bigEndian Defaults to `true`, otherwise uses little endian
6480 * @returns {!ByteBuffer} this
6481 * @expose
6482 */
6483 ByteBufferPrototype.BE = function(bigEndian) {
6484 this.littleEndian = typeof bigEndian !== 'undefined' ? !bigEndian : false;
6485 return this;
6486 };
6487 /**
6488 * Prepends some data to this ByteBuffer. This will overwrite any contents before the specified offset up to the
6489 * prepended data's length. If there is not enough space available before the specified `offset`, the backing buffer
6490 * will be resized and its contents moved accordingly.
6491 * @param {!ByteBuffer|string|!ArrayBuffer} source Data to prepend. If `source` is a ByteBuffer, its offset will be
6492 * modified according to the performed read operation.
6493 * @param {(string|number)=} encoding Encoding if `data` is a string ("base64", "hex", "binary", defaults to "utf8")
6494 * @param {number=} offset Offset to prepend at. Will use and decrease {@link ByteBuffer#offset} by the number of bytes
6495 * prepended if omitted.
6496 * @returns {!ByteBuffer} this
6497 * @expose
6498 * @example A relative `00<01 02 03>.prepend(<04 05>)` results in `<04 05 01 02 03>, 04 05|`
6499 * @example An absolute `00<01 02 03>.prepend(<04 05>, 2)` results in `04<05 02 03>, 04 05|`
6500 */
6501 ByteBufferPrototype.prepend = function(source, encoding, offset) {
6502 if (typeof encoding === 'number' || typeof encoding !== 'string') {
6503 offset = encoding;
6504 encoding = undefined;
6505 }
6506 var relative = typeof offset === 'undefined';
6507 if (relative) offset = this.offset;
6508 if (!this.noAssert) {
6509 if (typeof offset !== 'number' || offset % 1 !== 0)
6510 throw TypeError("Illegal offset: "+offset+" (not an integer)");
6511 offset >>>= 0;
6512 if (offset < 0 || offset + 0 > this.buffer.byteLength)
6513 throw RangeError("Illegal offset: 0 <= "+offset+" (+"+0+") <= "+this.buffer.byteLength);
6514 }
6515 if (!(source instanceof ByteBuffer))
6516 source = ByteBuffer.wrap(source, encoding);
6517 var len = source.limit - source.offset;
6518 if (len <= 0) return this; // Nothing to prepend
6519 var diff = len - offset;
6520 if (diff > 0) { // Not enough space before offset, so resize + move
6521 var buffer = new ArrayBuffer(this.buffer.byteLength + diff);
6522 var view = new Uint8Array(buffer);
6523 view.set(this.view.subarray(offset, this.buffer.byteLength), len);
6524 this.buffer = buffer;
6525 this.view = view;
6526 this.offset += diff;
6527 if (this.markedOffset >= 0) this.markedOffset += diff;
6528 this.limit += diff;
6529 offset += diff;
6530 } else {
6531 var arrayView = new Uint8Array(this.buffer);
6532 }
6533 this.view.set(source.view.subarray(source.offset, source.limit), offset - len);
6534
6535 source.offset = source.limit;
6536 if (relative)
6537 this.offset -= len;
6538 return this;
6539 };
6540
6541 /**
6542 * Prepends this ByteBuffer to another ByteBuffer. This will overwrite any contents before the specified offset up to the
6543 * prepended data's length. If there is not enough space available before the specified `offset`, the backing buffer
6544 * will be resized and its contents moved accordingly.
6545 * @param {!ByteBuffer} target Target ByteBuffer
6546 * @param {number=} offset Offset to prepend at. Will use and decrease {@link ByteBuffer#offset} by the number of bytes
6547 * prepended if omitted.
6548 * @returns {!ByteBuffer} this
6549 * @expose
6550 * @see ByteBuffer#prepend
6551 */
6552 ByteBufferPrototype.prependTo = function(target, offset) {
6553 target.prepend(this, offset);
6554 return this;
6555 };
6556 /**
6557 * Prints debug information about this ByteBuffer's contents.
6558 * @param {function(string)=} out Output function to call, defaults to console.log
6559 * @expose
6560 */
6561 ByteBufferPrototype.printDebug = function(out) {
6562 if (typeof out !== 'function') out = console.log.bind(console);
6563 out(
6564 this.toString()+"\n"+
6565 "-------------------------------------------------------------------\n"+
6566 this.toDebug(/* columns */ true)
6567 );
6568 };
6569
6570 /**
6571 * Gets the number of remaining readable bytes. Contents are the bytes between {@link ByteBuffer#offset} and
6572 * {@link ByteBuffer#limit}, so this returns `limit - offset`.
6573 * @returns {number} Remaining readable bytes. May be negative if `offset > limit`.
6574 * @expose
6575 */
6576 ByteBufferPrototype.remaining = function() {
6577 return this.limit - this.offset;
6578 };
6579 /**
6580 * Resets this ByteBuffer's {@link ByteBuffer#offset}. If an offset has been marked through {@link ByteBuffer#mark}
6581 * before, `offset` will be set to {@link ByteBuffer#markedOffset}, which will then be discarded. If no offset has been
6582 * marked, sets `offset = 0`.
6583 * @returns {!ByteBuffer} this
6584 * @see ByteBuffer#mark
6585 * @expose
6586 */
6587 ByteBufferPrototype.reset = function() {
6588 if (this.markedOffset >= 0) {
6589 this.offset = this.markedOffset;
6590 this.markedOffset = -1;
6591 } else {
6592 this.offset = 0;
6593 }
6594 return this;
6595 };
6596 /**
6597 * Resizes this ByteBuffer to be backed by a buffer of at least the given capacity. Will do nothing if already that
6598 * large or larger.
6599 * @param {number} capacity Capacity required
6600 * @returns {!ByteBuffer} this
6601 * @throws {TypeError} If `capacity` is not a number
6602 * @throws {RangeError} If `capacity < 0`
6603 * @expose
6604 */
6605 ByteBufferPrototype.resize = function(capacity) {
6606 if (!this.noAssert) {
6607 if (typeof capacity !== 'number' || capacity % 1 !== 0)
6608 throw TypeError("Illegal capacity: "+capacity+" (not an integer)");
6609 capacity |= 0;
6610 if (capacity < 0)
6611 throw RangeError("Illegal capacity: 0 <= "+capacity);
6612 }
6613 if (this.buffer.byteLength < capacity) {
6614 var buffer = new ArrayBuffer(capacity);
6615 var view = new Uint8Array(buffer);
6616 view.set(this.view);
6617 this.buffer = buffer;
6618 this.view = view;
6619 }
6620 return this;
6621 };
6622 /**
6623 * Reverses this ByteBuffer's contents.
6624 * @param {number=} begin Offset to start at, defaults to {@link ByteBuffer#offset}
6625 * @param {number=} end Offset to end at, defaults to {@link ByteBuffer#limit}
6626 * @returns {!ByteBuffer} this
6627 * @expose
6628 */
6629 ByteBufferPrototype.reverse = function(begin, end) {
6630 if (typeof begin === 'undefined') begin = this.offset;
6631 if (typeof end === 'undefined') end = this.limit;
6632 if (!this.noAssert) {
6633 if (typeof begin !== 'number' || begin % 1 !== 0)
6634 throw TypeError("Illegal begin: Not an integer");
6635 begin >>>= 0;
6636 if (typeof end !== 'number' || end % 1 !== 0)
6637 throw TypeError("Illegal end: Not an integer");
6638 end >>>= 0;
6639 if (begin < 0 || begin > end || end > this.buffer.byteLength)
6640 throw RangeError("Illegal range: 0 <= "+begin+" <= "+end+" <= "+this.buffer.byteLength);
6641 }
6642 if (begin === end)
6643 return this; // Nothing to reverse
6644 Array.prototype.reverse.call(this.view.subarray(begin, end));
6645 return this;
6646 };
6647 /**
6648 * Skips the next `length` bytes. This will just advance
6649 * @param {number} length Number of bytes to skip. May also be negative to move the offset back.
6650 * @returns {!ByteBuffer} this
6651 * @expose
6652 */
6653 ByteBufferPrototype.skip = function(length) {
6654 if (!this.noAssert) {
6655 if (typeof length !== 'number' || length % 1 !== 0)
6656 throw TypeError("Illegal length: "+length+" (not an integer)");
6657 length |= 0;
6658 }
6659 var offset = this.offset + length;
6660 if (!this.noAssert) {
6661 if (offset < 0 || offset > this.buffer.byteLength)
6662 throw RangeError("Illegal length: 0 <= "+this.offset+" + "+length+" <= "+this.buffer.byteLength);
6663 }
6664 this.offset = offset;
6665 return this;
6666 };
6667
6668 /**
6669 * Slices this ByteBuffer by creating a cloned instance with `offset = begin` and `limit = end`.
6670 * @param {number=} begin Begin offset, defaults to {@link ByteBuffer#offset}.
6671 * @param {number=} end End offset, defaults to {@link ByteBuffer#limit}.
6672 * @returns {!ByteBuffer} Clone of this ByteBuffer with slicing applied, backed by the same {@link ByteBuffer#buffer}
6673 * @expose
6674 */
6675 ByteBufferPrototype.slice = function(begin, end) {
6676 if (typeof begin === 'undefined') begin = this.offset;
6677 if (typeof end === 'undefined') end = this.limit;
6678 if (!this.noAssert) {
6679 if (typeof begin !== 'number' || begin % 1 !== 0)
6680 throw TypeError("Illegal begin: Not an integer");
6681 begin >>>= 0;
6682 if (typeof end !== 'number' || end % 1 !== 0)
6683 throw TypeError("Illegal end: Not an integer");
6684 end >>>= 0;
6685 if (begin < 0 || begin > end || end > this.buffer.byteLength)
6686 throw RangeError("Illegal range: 0 <= "+begin+" <= "+end+" <= "+this.buffer.byteLength);
6687 }
6688 var bb = this.clone();
6689 bb.offset = begin;
6690 bb.limit = end;
6691 return bb;
6692 };
6693 /**
6694 * Returns a copy of the backing buffer that contains this ByteBuffer's contents. Contents are the bytes between
6695 * {@link ByteBuffer#offset} and {@link ByteBuffer#limit}.
6696 * @param {boolean=} forceCopy If `true` returns a copy, otherwise returns a view referencing the same memory if
6697 * possible. Defaults to `false`
6698 * @returns {!ArrayBuffer} Contents as an ArrayBuffer
6699 * @expose
6700 */
6701 ByteBufferPrototype.toBuffer = function(forceCopy) {
6702 var offset = this.offset,
6703 limit = this.limit;
6704 if (!this.noAssert) {
6705 if (typeof offset !== 'number' || offset % 1 !== 0)
6706 throw TypeError("Illegal offset: Not an integer");
6707 offset >>>= 0;
6708 if (typeof limit !== 'number' || limit % 1 !== 0)
6709 throw TypeError("Illegal limit: Not an integer");
6710 limit >>>= 0;
6711 if (offset < 0 || offset > limit || limit > this.buffer.byteLength)
6712 throw RangeError("Illegal range: 0 <= "+offset+" <= "+limit+" <= "+this.buffer.byteLength);
6713 }
6714 // NOTE: It's not possible to have another ArrayBuffer reference the same memory as the backing buffer. This is
6715 // possible with Uint8Array#subarray only, but we have to return an ArrayBuffer by contract. So:
6716 if (!forceCopy && offset === 0 && limit === this.buffer.byteLength)
6717 return this.buffer;
6718 if (offset === limit)
6719 return EMPTY_BUFFER;
6720 var buffer = new ArrayBuffer(limit - offset);
6721 new Uint8Array(buffer).set(new Uint8Array(this.buffer).subarray(offset, limit), 0);
6722 return buffer;
6723 };
6724
6725 /**
6726 * Returns a raw buffer compacted to contain this ByteBuffer's contents. Contents are the bytes between
6727 * {@link ByteBuffer#offset} and {@link ByteBuffer#limit}. This is an alias of {@link ByteBuffer#toBuffer}.
6728 * @function
6729 * @param {boolean=} forceCopy If `true` returns a copy, otherwise returns a view referencing the same memory.
6730 * Defaults to `false`
6731 * @returns {!ArrayBuffer} Contents as an ArrayBuffer
6732 * @expose
6733 */
6734 ByteBufferPrototype.toArrayBuffer = ByteBufferPrototype.toBuffer;
6735
6736 /**
6737 * Converts the ByteBuffer's contents to a string.
6738 * @param {string=} encoding Output encoding. Returns an informative string representation if omitted but also allows
6739 * direct conversion to "utf8", "hex", "base64" and "binary" encoding. "debug" returns a hex representation with
6740 * highlighted offsets.
6741 * @param {number=} begin Offset to begin at, defaults to {@link ByteBuffer#offset}
6742 * @param {number=} end Offset to end at, defaults to {@link ByteBuffer#limit}
6743 * @returns {string} String representation
6744 * @throws {Error} If `encoding` is invalid
6745 * @expose
6746 */
6747 ByteBufferPrototype.toString = function(encoding, begin, end) {
6748 if (typeof encoding === 'undefined')
6749 return "ByteBufferAB(offset="+this.offset+",markedOffset="+this.markedOffset+",limit="+this.limit+",capacity="+this.capacity()+")";
6750 if (typeof encoding === 'number')
6751 encoding = "utf8",
6752 begin = encoding,
6753 end = begin;
6754 switch (encoding) {
6755 case "utf8":
6756 return this.toUTF8(begin, end);
6757 case "base64":
6758 return this.toBase64(begin, end);
6759 case "hex":
6760 return this.toHex(begin, end);
6761 case "binary":
6762 return this.toBinary(begin, end);
6763 case "debug":
6764 return this.toDebug();
6765 case "columns":
6766 return this.toColumns();
6767 default:
6768 throw Error("Unsupported encoding: "+encoding);
6769 }
6770 };
6771
6772 // lxiv-embeddable
6773
6774 /**
6775 * lxiv-embeddable (c) 2014 Daniel Wirtz <dcode@dcode.io>
6776 * Released under the Apache License, Version 2.0
6777 * see: https://github.com/dcodeIO/lxiv for details
6778 */
6779 var lxiv = function() {
6780
6781 /**
6782 * lxiv namespace.
6783 * @type {!Object.<string,*>}
6784 * @exports lxiv
6785 */
6786 var lxiv = {};
6787
6788 /**
6789 * Character codes for output.
6790 * @type {!Array.<number>}
6791 * @inner
6792 */
6793 var aout = [
6794 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80,
6795 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 97, 98, 99, 100, 101, 102,
6796 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116, 117, 118,
6797 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 43, 47
6798 ];
6799
6800 /**
6801 * Character codes for input.
6802 * @type {!Array.<number>}
6803 * @inner
6804 */
6805 var ain = [];
6806 for (var i=0, k=aout.length; i<k; ++i)
6807 ain[aout[i]] = i;
6808
6809 /**
6810 * Encodes bytes to base64 char codes.
6811 * @param {!function():number|null} src Bytes source as a function returning the next byte respectively `null` if
6812 * there are no more bytes left.
6813 * @param {!function(number)} dst Characters destination as a function successively called with each encoded char
6814 * code.
6815 */
6816 lxiv.encode = function(src, dst) {
6817 var b, t;
6818 while ((b = src()) !== null) {
6819 dst(aout[(b>>2)&0x3f]);
6820 t = (b&0x3)<<4;
6821 if ((b = src()) !== null) {
6822 t |= (b>>4)&0xf;
6823 dst(aout[(t|((b>>4)&0xf))&0x3f]);
6824 t = (b&0xf)<<2;
6825 if ((b = src()) !== null)
6826 dst(aout[(t|((b>>6)&0x3))&0x3f]),
6827 dst(aout[b&0x3f]);
6828 else
6829 dst(aout[t&0x3f]),
6830 dst(61);
6831 } else
6832 dst(aout[t&0x3f]),
6833 dst(61),
6834 dst(61);
6835 }
6836 };
6837
6838 /**
6839 * Decodes base64 char codes to bytes.
6840 * @param {!function():number|null} src Characters source as a function returning the next char code respectively
6841 * `null` if there are no more characters left.
6842 * @param {!function(number)} dst Bytes destination as a function successively called with the next byte.
6843 * @throws {Error} If a character code is invalid
6844 */
6845 lxiv.decode = function(src, dst) {
6846 var c, t1, t2;
6847 function fail(c) {
6848 throw Error("Illegal character code: "+c);
6849 }
6850 while ((c = src()) !== null) {
6851 t1 = ain[c];
6852 if (typeof t1 === 'undefined') fail(c);
6853 if ((c = src()) !== null) {
6854 t2 = ain[c];
6855 if (typeof t2 === 'undefined') fail(c);
6856 dst((t1<<2)>>>0|(t2&0x30)>>4);
6857 if ((c = src()) !== null) {
6858 t1 = ain[c];
6859 if (typeof t1 === 'undefined')
6860 if (c === 61) break; else fail(c);
6861 dst(((t2&0xf)<<4)>>>0|(t1&0x3c)>>2);
6862 if ((c = src()) !== null) {
6863 t2 = ain[c];
6864 if (typeof t2 === 'undefined')
6865 if (c === 61) break; else fail(c);
6866 dst(((t1&0x3)<<6)>>>0|t2);
6867 }
6868 }
6869 }
6870 }
6871 };
6872
6873 /**
6874 * Tests if a string is valid base64.
6875 * @param {string} str String to test
6876 * @returns {boolean} `true` if valid, otherwise `false`
6877 */
6878 lxiv.test = function(str) {
6879 return /^(?:[A-Za-z0-9+/]{4})*(?:[A-Za-z0-9+/]{2}==|[A-Za-z0-9+/]{3}=)?$/.test(str);
6880 };
6881
6882 return lxiv;
6883 }();
6884
6885 // encodings/base64
6886
6887 /**
6888 * Encodes this ByteBuffer's contents to a base64 encoded string.
6889 * @param {number=} begin Offset to begin at, defaults to {@link ByteBuffer#offset}.
6890 * @param {number=} end Offset to end at, defaults to {@link ByteBuffer#limit}.
6891 * @returns {string} Base64 encoded string
6892 * @throws {RangeError} If `begin` or `end` is out of bounds
6893 * @expose
6894 */
6895 ByteBufferPrototype.toBase64 = function(begin, end) {
6896 if (typeof begin === 'undefined')
6897 begin = this.offset;
6898 if (typeof end === 'undefined')
6899 end = this.limit;
6900 begin = begin | 0; end = end | 0;
6901 if (begin < 0 || end > this.capacity || begin > end)
6902 throw RangeError("begin, end");
6903 var sd; lxiv.encode(function() {
6904 return begin < end ? this.view[begin++] : null;
6905 }.bind(this), sd = stringDestination());
6906 return sd();
6907 };
6908
6909 /**
6910 * Decodes a base64 encoded string to a ByteBuffer.
6911 * @param {string} str String to decode
6912 * @param {boolean=} littleEndian Whether to use little or big endian byte order. Defaults to
6913 * {@link ByteBuffer.DEFAULT_ENDIAN}.
6914 * @returns {!ByteBuffer} ByteBuffer
6915 * @expose
6916 */
6917 ByteBuffer.fromBase64 = function(str, littleEndian) {
6918 if (typeof str !== 'string')
6919 throw TypeError("str");
6920 var bb = new ByteBuffer(str.length/4*3, littleEndian),
6921 i = 0;
6922 lxiv.decode(stringSource(str), function(b) {
6923 bb.view[i++] = b;
6924 });
6925 bb.limit = i;
6926 return bb;
6927 };
6928
6929 /**
6930 * Encodes a binary string to base64 like `window.btoa` does.
6931 * @param {string} str Binary string
6932 * @returns {string} Base64 encoded string
6933 * @see https://developer.mozilla.org/en-US/docs/Web/API/Window.btoa
6934 * @expose
6935 */
6936 ByteBuffer.btoa = function(str) {
6937 return ByteBuffer.fromBinary(str).toBase64();
6938 };
6939
6940 /**
6941 * Decodes a base64 encoded string to binary like `window.atob` does.
6942 * @param {string} b64 Base64 encoded string
6943 * @returns {string} Binary string
6944 * @see https://developer.mozilla.org/en-US/docs/Web/API/Window.atob
6945 * @expose
6946 */
6947 ByteBuffer.atob = function(b64) {
6948 return ByteBuffer.fromBase64(b64).toBinary();
6949 };
6950
6951 // encodings/binary
6952
6953 /**
6954 * Encodes this ByteBuffer to a binary encoded string, that is using only characters 0x00-0xFF as bytes.
6955 * @param {number=} begin Offset to begin at. Defaults to {@link ByteBuffer#offset}.
6956 * @param {number=} end Offset to end at. Defaults to {@link ByteBuffer#limit}.
6957 * @returns {string} Binary encoded string
6958 * @throws {RangeError} If `offset > limit`
6959 * @expose
6960 */
6961 ByteBufferPrototype.toBinary = function(begin, end) {
6962 if (typeof begin === 'undefined')
6963 begin = this.offset;
6964 if (typeof end === 'undefined')
6965 end = this.limit;
6966 begin |= 0; end |= 0;
6967 if (begin < 0 || end > this.capacity() || begin > end)
6968 throw RangeError("begin, end");
6969 if (begin === end)
6970 return "";
6971 var chars = [],
6972 parts = [];
6973 while (begin < end) {
6974 chars.push(this.view[begin++]);
6975 if (chars.length >= 1024)
6976 parts.push(String.fromCharCode.apply(String, chars)),
6977 chars = [];
6978 }
6979 return parts.join('') + String.fromCharCode.apply(String, chars);
6980 };
6981
6982 /**
6983 * Decodes a binary encoded string, that is using only characters 0x00-0xFF as bytes, to a ByteBuffer.
6984 * @param {string} str String to decode
6985 * @param {boolean=} littleEndian Whether to use little or big endian byte order. Defaults to
6986 * {@link ByteBuffer.DEFAULT_ENDIAN}.
6987 * @returns {!ByteBuffer} ByteBuffer
6988 * @expose
6989 */
6990 ByteBuffer.fromBinary = function(str, littleEndian) {
6991 if (typeof str !== 'string')
6992 throw TypeError("str");
6993 var i = 0,
6994 k = str.length,
6995 charCode,
6996 bb = new ByteBuffer(k, littleEndian);
6997 while (i<k) {
6998 charCode = str.charCodeAt(i);
6999 if (charCode > 0xff)
7000 throw RangeError("illegal char code: "+charCode);
7001 bb.view[i++] = charCode;
7002 }
7003 bb.limit = k;
7004 return bb;
7005 };
7006
7007 // encodings/debug
7008
7009 /**
7010 * Encodes this ByteBuffer to a hex encoded string with marked offsets. Offset symbols are:
7011 * * `<` : offset,
7012 * * `'` : markedOffset,
7013 * * `>` : limit,
7014 * * `|` : offset and limit,
7015 * * `[` : offset and markedOffset,
7016 * * `]` : markedOffset and limit,
7017 * * `!` : offset, markedOffset and limit
7018 * @param {boolean=} columns If `true` returns two columns hex + ascii, defaults to `false`
7019 * @returns {string|!Array.<string>} Debug string or array of lines if `asArray = true`
7020 * @expose
7021 * @example `>00'01 02<03` contains four bytes with `limit=0, markedOffset=1, offset=3`
7022 * @example `00[01 02 03>` contains four bytes with `offset=markedOffset=1, limit=4`
7023 * @example `00|01 02 03` contains four bytes with `offset=limit=1, markedOffset=-1`
7024 * @example `|` contains zero bytes with `offset=limit=0, markedOffset=-1`
7025 */
7026 ByteBufferPrototype.toDebug = function(columns) {
7027 var i = -1,
7028 k = this.buffer.byteLength,
7029 b,
7030 hex = "",
7031 asc = "",
7032 out = "";
7033 while (i<k) {
7034 if (i !== -1) {
7035 b = this.view[i];
7036 if (b < 0x10) hex += "0"+b.toString(16).toUpperCase();
7037 else hex += b.toString(16).toUpperCase();
7038 if (columns)
7039 asc += b > 32 && b < 127 ? String.fromCharCode(b) : '.';
7040 }
7041 ++i;
7042 if (columns) {
7043 if (i > 0 && i % 16 === 0 && i !== k) {
7044 while (hex.length < 3*16+3) hex += " ";
7045 out += hex+asc+"\n";
7046 hex = asc = "";
7047 }
7048 }
7049 if (i === this.offset && i === this.limit)
7050 hex += i === this.markedOffset ? "!" : "|";
7051 else if (i === this.offset)
7052 hex += i === this.markedOffset ? "[" : "<";
7053 else if (i === this.limit)
7054 hex += i === this.markedOffset ? "]" : ">";
7055 else
7056 hex += i === this.markedOffset ? "'" : (columns || (i !== 0 && i !== k) ? " " : "");
7057 }
7058 if (columns && hex !== " ") {
7059 while (hex.length < 3*16+3)
7060 hex += " ";
7061 out += hex + asc + "\n";
7062 }
7063 return columns ? out : hex;
7064 };
7065
7066 /**
7067 * Decodes a hex encoded string with marked offsets to a ByteBuffer.
7068 * @param {string} str Debug string to decode (not be generated with `columns = true`)
7069 * @param {boolean=} littleEndian Whether to use little or big endian byte order. Defaults to
7070 * {@link ByteBuffer.DEFAULT_ENDIAN}.
7071 * @param {boolean=} noAssert Whether to skip assertions of offsets and values. Defaults to
7072 * {@link ByteBuffer.DEFAULT_NOASSERT}.
7073 * @returns {!ByteBuffer} ByteBuffer
7074 * @expose
7075 * @see ByteBuffer#toDebug
7076 */
7077 ByteBuffer.fromDebug = function(str, littleEndian, noAssert) {
7078 var k = str.length,
7079 bb = new ByteBuffer(((k+1)/3)|0, littleEndian, noAssert);
7080 var i = 0, j = 0, ch, b,
7081 rs = false, // Require symbol next
7082 ho = false, hm = false, hl = false, // Already has offset (ho), markedOffset (hm), limit (hl)?
7083 fail = false;
7084 while (i<k) {
7085 switch (ch = str.charAt(i++)) {
7086 case '!':
7087 if (!noAssert) {
7088 if (ho || hm || hl) {
7089 fail = true;
7090 break;
7091 }
7092 ho = hm = hl = true;
7093 }
7094 bb.offset = bb.markedOffset = bb.limit = j;
7095 rs = false;
7096 break;
7097 case '|':
7098 if (!noAssert) {
7099 if (ho || hl) {
7100 fail = true;
7101 break;
7102 }
7103 ho = hl = true;
7104 }
7105 bb.offset = bb.limit = j;
7106 rs = false;
7107 break;
7108 case '[':
7109 if (!noAssert) {
7110 if (ho || hm) {
7111 fail = true;
7112 break;
7113 }
7114 ho = hm = true;
7115 }
7116 bb.offset = bb.markedOffset = j;
7117 rs = false;
7118 break;
7119 case '<':
7120 if (!noAssert) {
7121 if (ho) {
7122 fail = true;
7123 break;
7124 }
7125 ho = true;
7126 }
7127 bb.offset = j;
7128 rs = false;
7129 break;
7130 case ']':
7131 if (!noAssert) {
7132 if (hl || hm) {
7133 fail = true;
7134 break;
7135 }
7136 hl = hm = true;
7137 }
7138 bb.limit = bb.markedOffset = j;
7139 rs = false;
7140 break;
7141 case '>':
7142 if (!noAssert) {
7143 if (hl) {
7144 fail = true;
7145 break;
7146 }
7147 hl = true;
7148 }
7149 bb.limit = j;
7150 rs = false;
7151 break;
7152 case "'":
7153 if (!noAssert) {
7154 if (hm) {
7155 fail = true;
7156 break;
7157 }
7158 hm = true;
7159 }
7160 bb.markedOffset = j;
7161 rs = false;
7162 break;
7163 case ' ':
7164 rs = false;
7165 break;
7166 default:
7167 if (!noAssert) {
7168 if (rs) {
7169 fail = true;
7170 break;
7171 }
7172 }
7173 b = parseInt(ch+str.charAt(i++), 16);
7174 if (!noAssert) {
7175 if (isNaN(b) || b < 0 || b > 255)
7176 throw TypeError("Illegal str: Not a debug encoded string");
7177 }
7178 bb.view[j++] = b;
7179 rs = true;
7180 }
7181 if (fail)
7182 throw TypeError("Illegal str: Invalid symbol at "+i);
7183 }
7184 if (!noAssert) {
7185 if (!ho || !hl)
7186 throw TypeError("Illegal str: Missing offset or limit");
7187 if (j<bb.buffer.byteLength)
7188 throw TypeError("Illegal str: Not a debug encoded string (is it hex?) "+j+" < "+k);
7189 }
7190 return bb;
7191 };
7192
7193 // encodings/hex
7194
7195 /**
7196 * Encodes this ByteBuffer's contents to a hex encoded string.
7197 * @param {number=} begin Offset to begin at. Defaults to {@link ByteBuffer#offset}.
7198 * @param {number=} end Offset to end at. Defaults to {@link ByteBuffer#limit}.
7199 * @returns {string} Hex encoded string
7200 * @expose
7201 */
7202 ByteBufferPrototype.toHex = function(begin, end) {
7203 begin = typeof begin === 'undefined' ? this.offset : begin;
7204 end = typeof end === 'undefined' ? this.limit : end;
7205 if (!this.noAssert) {
7206 if (typeof begin !== 'number' || begin % 1 !== 0)
7207 throw TypeError("Illegal begin: Not an integer");
7208 begin >>>= 0;
7209 if (typeof end !== 'number' || end % 1 !== 0)
7210 throw TypeError("Illegal end: Not an integer");
7211 end >>>= 0;
7212 if (begin < 0 || begin > end || end > this.buffer.byteLength)
7213 throw RangeError("Illegal range: 0 <= "+begin+" <= "+end+" <= "+this.buffer.byteLength);
7214 }
7215 var out = new Array(end - begin),
7216 b;
7217 while (begin < end) {
7218 b = this.view[begin++];
7219 if (b < 0x10)
7220 out.push("0", b.toString(16));
7221 else out.push(b.toString(16));
7222 }
7223 return out.join('');
7224 };
7225
7226 /**
7227 * Decodes a hex encoded string to a ByteBuffer.
7228 * @param {string} str String to decode
7229 * @param {boolean=} littleEndian Whether to use little or big endian byte order. Defaults to
7230 * {@link ByteBuffer.DEFAULT_ENDIAN}.
7231 * @param {boolean=} noAssert Whether to skip assertions of offsets and values. Defaults to
7232 * {@link ByteBuffer.DEFAULT_NOASSERT}.
7233 * @returns {!ByteBuffer} ByteBuffer
7234 * @expose
7235 */
7236 ByteBuffer.fromHex = function(str, littleEndian, noAssert) {
7237 if (!noAssert) {
7238 if (typeof str !== 'string')
7239 throw TypeError("Illegal str: Not a string");
7240 if (str.length % 2 !== 0)
7241 throw TypeError("Illegal str: Length not a multiple of 2");
7242 }
7243 var k = str.length,
7244 bb = new ByteBuffer((k / 2) | 0, littleEndian),
7245 b;
7246 for (var i=0, j=0; i<k; i+=2) {
7247 b = parseInt(str.substring(i, i+2), 16);
7248 if (!noAssert)
7249 if (!isFinite(b) || b < 0 || b > 255)
7250 throw TypeError("Illegal str: Contains non-hex characters");
7251 bb.view[j++] = b;
7252 }
7253 bb.limit = j;
7254 return bb;
7255 };
7256
7257 // utfx-embeddable
7258
7259 /**
7260 * utfx-embeddable (c) 2014 Daniel Wirtz <dcode@dcode.io>
7261 * Released under the Apache License, Version 2.0
7262 * see: https://github.com/dcodeIO/utfx for details
7263 */
7264 var utfx = function() {
7265
7266 /**
7267 * utfx namespace.
7268 * @inner
7269 * @type {!Object.<string,*>}
7270 */
7271 var utfx = {};
7272
7273 /**
7274 * Maximum valid code point.
7275 * @type {number}
7276 * @const
7277 */
7278 utfx.MAX_CODEPOINT = 0x10FFFF;
7279
7280 /**
7281 * Encodes UTF8 code points to UTF8 bytes.
7282 * @param {(!function():number|null) | number} src Code points source, either as a function returning the next code point
7283 * respectively `null` if there are no more code points left or a single numeric code point.
7284 * @param {!function(number)} dst Bytes destination as a function successively called with the next byte
7285 */
7286 utfx.encodeUTF8 = function(src, dst) {
7287 var cp = null;
7288 if (typeof src === 'number')
7289 cp = src,
7290 src = function() { return null; };
7291 while (cp !== null || (cp = src()) !== null) {
7292 if (cp < 0x80)
7293 dst(cp&0x7F);
7294 else if (cp < 0x800)
7295 dst(((cp>>6)&0x1F)|0xC0),
7296 dst((cp&0x3F)|0x80);
7297 else if (cp < 0x10000)
7298 dst(((cp>>12)&0x0F)|0xE0),
7299 dst(((cp>>6)&0x3F)|0x80),
7300 dst((cp&0x3F)|0x80);
7301 else
7302 dst(((cp>>18)&0x07)|0xF0),
7303 dst(((cp>>12)&0x3F)|0x80),
7304 dst(((cp>>6)&0x3F)|0x80),
7305 dst((cp&0x3F)|0x80);
7306 cp = null;
7307 }
7308 };
7309
7310 /**
7311 * Decodes UTF8 bytes to UTF8 code points.
7312 * @param {!function():number|null} src Bytes source as a function returning the next byte respectively `null` if there
7313 * are no more bytes left.
7314 * @param {!function(number)} dst Code points destination as a function successively called with each decoded code point.
7315 * @throws {RangeError} If a starting byte is invalid in UTF8
7316 * @throws {Error} If the last sequence is truncated. Has an array property `bytes` holding the
7317 * remaining bytes.
7318 */
7319 utfx.decodeUTF8 = function(src, dst) {
7320 var a, b, c, d, fail = function(b) {
7321 b = b.slice(0, b.indexOf(null));
7322 var err = Error(b.toString());
7323 err.name = "TruncatedError";
7324 err['bytes'] = b;
7325 throw err;
7326 };
7327 while ((a = src()) !== null) {
7328 if ((a&0x80) === 0)
7329 dst(a);
7330 else if ((a&0xE0) === 0xC0)
7331 ((b = src()) === null) && fail([a, b]),
7332 dst(((a&0x1F)<<6) | (b&0x3F));
7333 else if ((a&0xF0) === 0xE0)
7334 ((b=src()) === null || (c=src()) === null) && fail([a, b, c]),
7335 dst(((a&0x0F)<<12) | ((b&0x3F)<<6) | (c&0x3F));
7336 else if ((a&0xF8) === 0xF0)
7337 ((b=src()) === null || (c=src()) === null || (d=src()) === null) && fail([a, b, c ,d]),
7338 dst(((a&0x07)<<18) | ((b&0x3F)<<12) | ((c&0x3F)<<6) | (d&0x3F));
7339 else throw RangeError("Illegal starting byte: "+a);
7340 }
7341 };
7342
7343 /**
7344 * Converts UTF16 characters to UTF8 code points.
7345 * @param {!function():number|null} src Characters source as a function returning the next char code respectively
7346 * `null` if there are no more characters left.
7347 * @param {!function(number)} dst Code points destination as a function successively called with each converted code
7348 * point.
7349 */
7350 utfx.UTF16toUTF8 = function(src, dst) {
7351 var c1, c2 = null;
7352 while (true) {
7353 if ((c1 = c2 !== null ? c2 : src()) === null)
7354 break;
7355 if (c1 >= 0xD800 && c1 <= 0xDFFF) {
7356 if ((c2 = src()) !== null) {
7357 if (c2 >= 0xDC00 && c2 <= 0xDFFF) {
7358 dst((c1-0xD800)*0x400+c2-0xDC00+0x10000);
7359 c2 = null; continue;
7360 }
7361 }
7362 }
7363 dst(c1);
7364 }
7365 if (c2 !== null) dst(c2);
7366 };
7367
7368 /**
7369 * Converts UTF8 code points to UTF16 characters.
7370 * @param {(!function():number|null) | number} src Code points source, either as a function returning the next code point
7371 * respectively `null` if there are no more code points left or a single numeric code point.
7372 * @param {!function(number)} dst Characters destination as a function successively called with each converted char code.
7373 * @throws {RangeError} If a code point is out of range
7374 */
7375 utfx.UTF8toUTF16 = function(src, dst) {
7376 var cp = null;
7377 if (typeof src === 'number')
7378 cp = src, src = function() { return null; };
7379 while (cp !== null || (cp = src()) !== null) {
7380 if (cp <= 0xFFFF)
7381 dst(cp);
7382 else
7383 cp -= 0x10000,
7384 dst((cp>>10)+0xD800),
7385 dst((cp%0x400)+0xDC00);
7386 cp = null;
7387 }
7388 };
7389
7390 /**
7391 * Converts and encodes UTF16 characters to UTF8 bytes.
7392 * @param {!function():number|null} src Characters source as a function returning the next char code respectively `null`
7393 * if there are no more characters left.
7394 * @param {!function(number)} dst Bytes destination as a function successively called with the next byte.
7395 */
7396 utfx.encodeUTF16toUTF8 = function(src, dst) {
7397 utfx.UTF16toUTF8(src, function(cp) {
7398 utfx.encodeUTF8(cp, dst);
7399 });
7400 };
7401
7402 /**
7403 * Decodes and converts UTF8 bytes to UTF16 characters.
7404 * @param {!function():number|null} src Bytes source as a function returning the next byte respectively `null` if there
7405 * are no more bytes left.
7406 * @param {!function(number)} dst Characters destination as a function successively called with each converted char code.
7407 * @throws {RangeError} If a starting byte is invalid in UTF8
7408 * @throws {Error} If the last sequence is truncated. Has an array property `bytes` holding the remaining bytes.
7409 */
7410 utfx.decodeUTF8toUTF16 = function(src, dst) {
7411 utfx.decodeUTF8(src, function(cp) {
7412 utfx.UTF8toUTF16(cp, dst);
7413 });
7414 };
7415
7416 /**
7417 * Calculates the byte length of an UTF8 code point.
7418 * @param {number} cp UTF8 code point
7419 * @returns {number} Byte length
7420 */
7421 utfx.calculateCodePoint = function(cp) {
7422 return (cp < 0x80) ? 1 : (cp < 0x800) ? 2 : (cp < 0x10000) ? 3 : 4;
7423 };
7424
7425 /**
7426 * Calculates the number of UTF8 bytes required to store UTF8 code points.
7427 * @param {(!function():number|null)} src Code points source as a function returning the next code point respectively
7428 * `null` if there are no more code points left.
7429 * @returns {number} The number of UTF8 bytes required
7430 */
7431 utfx.calculateUTF8 = function(src) {
7432 var cp, l=0;
7433 while ((cp = src()) !== null)
7434 l += (cp < 0x80) ? 1 : (cp < 0x800) ? 2 : (cp < 0x10000) ? 3 : 4;
7435 return l;
7436 };
7437
7438 /**
7439 * Calculates the number of UTF8 code points respectively UTF8 bytes required to store UTF16 char codes.
7440 * @param {(!function():number|null)} src Characters source as a function returning the next char code respectively
7441 * `null` if there are no more characters left.
7442 * @returns {!Array.<number>} The number of UTF8 code points at index 0 and the number of UTF8 bytes required at index 1.
7443 */
7444 utfx.calculateUTF16asUTF8 = function(src) {
7445 var n=0, l=0;
7446 utfx.UTF16toUTF8(src, function(cp) {
7447 ++n; l += (cp < 0x80) ? 1 : (cp < 0x800) ? 2 : (cp < 0x10000) ? 3 : 4;
7448 });
7449 return [n,l];
7450 };
7451
7452 return utfx;
7453 }();
7454
7455 // encodings/utf8
7456
7457 /**
7458 * Encodes this ByteBuffer's contents between {@link ByteBuffer#offset} and {@link ByteBuffer#limit} to an UTF8 encoded
7459 * string.
7460 * @returns {string} Hex encoded string
7461 * @throws {RangeError} If `offset > limit`
7462 * @expose
7463 */
7464 ByteBufferPrototype.toUTF8 = function(begin, end) {
7465 if (typeof begin === 'undefined') begin = this.offset;
7466 if (typeof end === 'undefined') end = this.limit;
7467 if (!this.noAssert) {
7468 if (typeof begin !== 'number' || begin % 1 !== 0)
7469 throw TypeError("Illegal begin: Not an integer");
7470 begin >>>= 0;
7471 if (typeof end !== 'number' || end % 1 !== 0)
7472 throw TypeError("Illegal end: Not an integer");
7473 end >>>= 0;
7474 if (begin < 0 || begin > end || end > this.buffer.byteLength)
7475 throw RangeError("Illegal range: 0 <= "+begin+" <= "+end+" <= "+this.buffer.byteLength);
7476 }
7477 var sd; try {
7478 utfx.decodeUTF8toUTF16(function() {
7479 return begin < end ? this.view[begin++] : null;
7480 }.bind(this), sd = stringDestination());
7481 } catch (e) {
7482 if (begin !== end)
7483 throw RangeError("Illegal range: Truncated data, "+begin+" != "+end);
7484 }
7485 return sd();
7486 };
7487
7488 /**
7489 * Decodes an UTF8 encoded string to a ByteBuffer.
7490 * @param {string} str String to decode
7491 * @param {boolean=} littleEndian Whether to use little or big endian byte order. Defaults to
7492 * {@link ByteBuffer.DEFAULT_ENDIAN}.
7493 * @param {boolean=} noAssert Whether to skip assertions of offsets and values. Defaults to
7494 * {@link ByteBuffer.DEFAULT_NOASSERT}.
7495 * @returns {!ByteBuffer} ByteBuffer
7496 * @expose
7497 */
7498 ByteBuffer.fromUTF8 = function(str, littleEndian, noAssert) {
7499 if (!noAssert)
7500 if (typeof str !== 'string')
7501 throw TypeError("Illegal str: Not a string");
7502 var bb = new ByteBuffer(utfx.calculateUTF16asUTF8(stringSource(str), true)[1], littleEndian, noAssert),
7503 i = 0;
7504 utfx.encodeUTF16toUTF8(stringSource(str), function(b) {
7505 bb.view[i++] = b;
7506 });
7507 bb.limit = i;
7508 return bb;
7509 };
7510
7511 return ByteBuffer;
7512 });
7513 });
7514
7515 var _nodeResolve_empty = {};
7516
7517 var _nodeResolve_empty$1 = /*#__PURE__*/Object.freeze({
7518 __proto__: null,
7519 'default': _nodeResolve_empty
7520 });
7521
7522 var require$$2 = getCjsExportFromNamespace(_nodeResolve_empty$1);
7523
7524 var protobufLight = createCommonjsModule(function (module) {
7525 /*
7526 Copyright 2013 Daniel Wirtz <dcode@dcode.io>
7527
7528 Licensed under the Apache License, Version 2.0 (the "License");
7529 you may not use this file except in compliance with the License.
7530 You may obtain a copy of the License at
7531
7532 http://www.apache.org/licenses/LICENSE-2.0
7533
7534 Unless required by applicable law or agreed to in writing, software
7535 distributed under the License is distributed on an "AS IS" BASIS,
7536 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
7537 See the License for the specific language governing permissions and
7538 limitations under the License.
7539 */
7540
7541 /**
7542 * @license protobuf.js (c) 2013 Daniel Wirtz <dcode@dcode.io>
7543 * Released under the Apache License, Version 2.0
7544 * see: https://github.com/dcodeIO/protobuf.js for details
7545 */
7546 (function(global, factory) {
7547
7548 /* AMD */ if (typeof commonjsRequire === "function" && 'object' === "object" && module && module["exports"])
7549 module["exports"] = factory(bytebuffer, true);
7550 /* Global */ else
7551 (global["dcodeIO"] = global["dcodeIO"] || {})["ProtoBuf"] = factory(global["dcodeIO"]["ByteBuffer"]);
7552
7553 })(commonjsGlobal, function(ByteBuffer, isCommonJS) {
7554
7555 /**
7556 * The ProtoBuf namespace.
7557 * @exports ProtoBuf
7558 * @namespace
7559 * @expose
7560 */
7561 var ProtoBuf = {};
7562
7563 /**
7564 * @type {!function(new: ByteBuffer, ...[*])}
7565 * @expose
7566 */
7567 ProtoBuf.ByteBuffer = ByteBuffer;
7568
7569 /**
7570 * @type {?function(new: Long, ...[*])}
7571 * @expose
7572 */
7573 ProtoBuf.Long = ByteBuffer.Long || null;
7574
7575 /**
7576 * ProtoBuf.js version.
7577 * @type {string}
7578 * @const
7579 * @expose
7580 */
7581 ProtoBuf.VERSION = "5.0.3";
7582
7583 /**
7584 * Wire types.
7585 * @type {Object.<string,number>}
7586 * @const
7587 * @expose
7588 */
7589 ProtoBuf.WIRE_TYPES = {};
7590
7591 /**
7592 * Varint wire type.
7593 * @type {number}
7594 * @expose
7595 */
7596 ProtoBuf.WIRE_TYPES.VARINT = 0;
7597
7598 /**
7599 * Fixed 64 bits wire type.
7600 * @type {number}
7601 * @const
7602 * @expose
7603 */
7604 ProtoBuf.WIRE_TYPES.BITS64 = 1;
7605
7606 /**
7607 * Length delimited wire type.
7608 * @type {number}
7609 * @const
7610 * @expose
7611 */
7612 ProtoBuf.WIRE_TYPES.LDELIM = 2;
7613
7614 /**
7615 * Start group wire type.
7616 * @type {number}
7617 * @const
7618 * @expose
7619 */
7620 ProtoBuf.WIRE_TYPES.STARTGROUP = 3;
7621
7622 /**
7623 * End group wire type.
7624 * @type {number}
7625 * @const
7626 * @expose
7627 */
7628 ProtoBuf.WIRE_TYPES.ENDGROUP = 4;
7629
7630 /**
7631 * Fixed 32 bits wire type.
7632 * @type {number}
7633 * @const
7634 * @expose
7635 */
7636 ProtoBuf.WIRE_TYPES.BITS32 = 5;
7637
7638 /**
7639 * Packable wire types.
7640 * @type {!Array.<number>}
7641 * @const
7642 * @expose
7643 */
7644 ProtoBuf.PACKABLE_WIRE_TYPES = [
7645 ProtoBuf.WIRE_TYPES.VARINT,
7646 ProtoBuf.WIRE_TYPES.BITS64,
7647 ProtoBuf.WIRE_TYPES.BITS32
7648 ];
7649
7650 /**
7651 * Types.
7652 * @dict
7653 * @type {!Object.<string,{name: string, wireType: number, defaultValue: *}>}
7654 * @const
7655 * @expose
7656 */
7657 ProtoBuf.TYPES = {
7658 // According to the protobuf spec.
7659 "int32": {
7660 name: "int32",
7661 wireType: ProtoBuf.WIRE_TYPES.VARINT,
7662 defaultValue: 0
7663 },
7664 "uint32": {
7665 name: "uint32",
7666 wireType: ProtoBuf.WIRE_TYPES.VARINT,
7667 defaultValue: 0
7668 },
7669 "sint32": {
7670 name: "sint32",
7671 wireType: ProtoBuf.WIRE_TYPES.VARINT,
7672 defaultValue: 0
7673 },
7674 "int64": {
7675 name: "int64",
7676 wireType: ProtoBuf.WIRE_TYPES.VARINT,
7677 defaultValue: ProtoBuf.Long ? ProtoBuf.Long.ZERO : undefined
7678 },
7679 "uint64": {
7680 name: "uint64",
7681 wireType: ProtoBuf.WIRE_TYPES.VARINT,
7682 defaultValue: ProtoBuf.Long ? ProtoBuf.Long.UZERO : undefined
7683 },
7684 "sint64": {
7685 name: "sint64",
7686 wireType: ProtoBuf.WIRE_TYPES.VARINT,
7687 defaultValue: ProtoBuf.Long ? ProtoBuf.Long.ZERO : undefined
7688 },
7689 "bool": {
7690 name: "bool",
7691 wireType: ProtoBuf.WIRE_TYPES.VARINT,
7692 defaultValue: false
7693 },
7694 "double": {
7695 name: "double",
7696 wireType: ProtoBuf.WIRE_TYPES.BITS64,
7697 defaultValue: 0
7698 },
7699 "string": {
7700 name: "string",
7701 wireType: ProtoBuf.WIRE_TYPES.LDELIM,
7702 defaultValue: ""
7703 },
7704 "bytes": {
7705 name: "bytes",
7706 wireType: ProtoBuf.WIRE_TYPES.LDELIM,
7707 defaultValue: null // overridden in the code, must be a unique instance
7708 },
7709 "fixed32": {
7710 name: "fixed32",
7711 wireType: ProtoBuf.WIRE_TYPES.BITS32,
7712 defaultValue: 0
7713 },
7714 "sfixed32": {
7715 name: "sfixed32",
7716 wireType: ProtoBuf.WIRE_TYPES.BITS32,
7717 defaultValue: 0
7718 },
7719 "fixed64": {
7720 name: "fixed64",
7721 wireType: ProtoBuf.WIRE_TYPES.BITS64,
7722 defaultValue: ProtoBuf.Long ? ProtoBuf.Long.UZERO : undefined
7723 },
7724 "sfixed64": {
7725 name: "sfixed64",
7726 wireType: ProtoBuf.WIRE_TYPES.BITS64,
7727 defaultValue: ProtoBuf.Long ? ProtoBuf.Long.ZERO : undefined
7728 },
7729 "float": {
7730 name: "float",
7731 wireType: ProtoBuf.WIRE_TYPES.BITS32,
7732 defaultValue: 0
7733 },
7734 "enum": {
7735 name: "enum",
7736 wireType: ProtoBuf.WIRE_TYPES.VARINT,
7737 defaultValue: 0
7738 },
7739 "message": {
7740 name: "message",
7741 wireType: ProtoBuf.WIRE_TYPES.LDELIM,
7742 defaultValue: null
7743 },
7744 "group": {
7745 name: "group",
7746 wireType: ProtoBuf.WIRE_TYPES.STARTGROUP,
7747 defaultValue: null
7748 }
7749 };
7750
7751 /**
7752 * Valid map key types.
7753 * @type {!Array.<!Object.<string,{name: string, wireType: number, defaultValue: *}>>}
7754 * @const
7755 * @expose
7756 */
7757 ProtoBuf.MAP_KEY_TYPES = [
7758 ProtoBuf.TYPES["int32"],
7759 ProtoBuf.TYPES["sint32"],
7760 ProtoBuf.TYPES["sfixed32"],
7761 ProtoBuf.TYPES["uint32"],
7762 ProtoBuf.TYPES["fixed32"],
7763 ProtoBuf.TYPES["int64"],
7764 ProtoBuf.TYPES["sint64"],
7765 ProtoBuf.TYPES["sfixed64"],
7766 ProtoBuf.TYPES["uint64"],
7767 ProtoBuf.TYPES["fixed64"],
7768 ProtoBuf.TYPES["bool"],
7769 ProtoBuf.TYPES["string"],
7770 ProtoBuf.TYPES["bytes"]
7771 ];
7772
7773 /**
7774 * Minimum field id.
7775 * @type {number}
7776 * @const
7777 * @expose
7778 */
7779 ProtoBuf.ID_MIN = 1;
7780
7781 /**
7782 * Maximum field id.
7783 * @type {number}
7784 * @const
7785 * @expose
7786 */
7787 ProtoBuf.ID_MAX = 0x1FFFFFFF;
7788
7789 /**
7790 * If set to `true`, field names will be converted from underscore notation to camel case. Defaults to `false`.
7791 * Must be set prior to parsing.
7792 * @type {boolean}
7793 * @expose
7794 */
7795 ProtoBuf.convertFieldsToCamelCase = false;
7796
7797 /**
7798 * By default, messages are populated with (setX, set_x) accessors for each field. This can be disabled by
7799 * setting this to `false` prior to building messages.
7800 * @type {boolean}
7801 * @expose
7802 */
7803 ProtoBuf.populateAccessors = true;
7804
7805 /**
7806 * By default, messages are populated with default values if a field is not present on the wire. To disable
7807 * this behavior, set this setting to `false`.
7808 * @type {boolean}
7809 * @expose
7810 */
7811 ProtoBuf.populateDefaults = true;
7812
7813 /**
7814 * @alias ProtoBuf.Util
7815 * @expose
7816 */
7817 ProtoBuf.Util = (function() {
7818
7819 /**
7820 * ProtoBuf utilities.
7821 * @exports ProtoBuf.Util
7822 * @namespace
7823 */
7824 var Util = {};
7825
7826 /**
7827 * Flag if running in node or not.
7828 * @type {boolean}
7829 * @const
7830 * @expose
7831 */
7832 Util.IS_NODE = !!(
7833 typeof process === 'object' && process+'' === '[object process]' && !process['browser']
7834 );
7835
7836 /**
7837 * Constructs a XMLHttpRequest object.
7838 * @return {XMLHttpRequest}
7839 * @throws {Error} If XMLHttpRequest is not supported
7840 * @expose
7841 */
7842 Util.XHR = function() {
7843 // No dependencies please, ref: http://www.quirksmode.org/js/xmlhttp.html
7844 var XMLHttpFactories = [
7845 function () {return new XMLHttpRequest()},
7846 function () {return new ActiveXObject("Msxml2.XMLHTTP")},
7847 function () {return new ActiveXObject("Msxml3.XMLHTTP")},
7848 function () {return new ActiveXObject("Microsoft.XMLHTTP")}
7849 ];
7850 /** @type {?XMLHttpRequest} */
7851 var xhr = null;
7852 for (var i=0;i<XMLHttpFactories.length;i++) {
7853 try { xhr = XMLHttpFactories[i](); }
7854 catch (e) { continue; }
7855 break;
7856 }
7857 if (!xhr)
7858 throw Error("XMLHttpRequest is not supported");
7859 return xhr;
7860 };
7861
7862 /**
7863 * Fetches a resource.
7864 * @param {string} path Resource path
7865 * @param {function(?string)=} callback Callback receiving the resource's contents. If omitted the resource will
7866 * be fetched synchronously. If the request failed, contents will be null.
7867 * @return {?string|undefined} Resource contents if callback is omitted (null if the request failed), else undefined.
7868 * @expose
7869 */
7870 Util.fetch = function(path, callback) {
7871 if (callback && typeof callback != 'function')
7872 callback = null;
7873 if (Util.IS_NODE) {
7874 var fs = require$$2;
7875 if (callback) {
7876 fs.readFile(path, function(err, data) {
7877 if (err)
7878 callback(null);
7879 else
7880 callback(""+data);
7881 });
7882 } else
7883 try {
7884 return fs.readFileSync(path);
7885 } catch (e) {
7886 return null;
7887 }
7888 } else {
7889 var xhr = Util.XHR();
7890 xhr.open('GET', path, callback ? true : false);
7891 // xhr.setRequestHeader('User-Agent', 'XMLHTTP/1.0');
7892 xhr.setRequestHeader('Accept', 'text/plain');
7893 if (typeof xhr.overrideMimeType === 'function') xhr.overrideMimeType('text/plain');
7894 if (callback) {
7895 xhr.onreadystatechange = function() {
7896 if (xhr.readyState != 4) return;
7897 if (/* remote */ xhr.status == 200 || /* local */ (xhr.status == 0 && typeof xhr.responseText === 'string'))
7898 callback(xhr.responseText);
7899 else
7900 callback(null);
7901 };
7902 if (xhr.readyState == 4)
7903 return;
7904 xhr.send(null);
7905 } else {
7906 xhr.send(null);
7907 if (/* remote */ xhr.status == 200 || /* local */ (xhr.status == 0 && typeof xhr.responseText === 'string'))
7908 return xhr.responseText;
7909 return null;
7910 }
7911 }
7912 };
7913
7914 /**
7915 * Converts a string to camel case.
7916 * @param {string} str
7917 * @returns {string}
7918 * @expose
7919 */
7920 Util.toCamelCase = function(str) {
7921 return str.replace(/_([a-zA-Z])/g, function ($0, $1) {
7922 return $1.toUpperCase();
7923 });
7924 };
7925
7926 return Util;
7927 })();
7928
7929 /**
7930 * Language expressions.
7931 * @type {!Object.<string,!RegExp>}
7932 * @expose
7933 */
7934 ProtoBuf.Lang = {
7935
7936 // Characters always ending a statement
7937 DELIM: /[\s\{\}=;:\[\],'"\(\)<>]/g,
7938
7939 // Field rules
7940 RULE: /^(?:required|optional|repeated|map)$/,
7941
7942 // Field types
7943 TYPE: /^(?:double|float|int32|uint32|sint32|int64|uint64|sint64|fixed32|sfixed32|fixed64|sfixed64|bool|string|bytes)$/,
7944
7945 // Names
7946 NAME: /^[a-zA-Z_][a-zA-Z_0-9]*$/,
7947
7948 // Type definitions
7949 TYPEDEF: /^[a-zA-Z][a-zA-Z_0-9]*$/,
7950
7951 // Type references
7952 TYPEREF: /^(?:\.?[a-zA-Z_][a-zA-Z_0-9]*)(?:\.[a-zA-Z_][a-zA-Z_0-9]*)*$/,
7953
7954 // Fully qualified type references
7955 FQTYPEREF: /^(?:\.[a-zA-Z_][a-zA-Z_0-9]*)+$/,
7956
7957 // All numbers
7958 NUMBER: /^-?(?:[1-9][0-9]*|0|0[xX][0-9a-fA-F]+|0[0-7]+|([0-9]*(\.[0-9]*)?([Ee][+-]?[0-9]+)?)|inf|nan)$/,
7959
7960 // Decimal numbers
7961 NUMBER_DEC: /^(?:[1-9][0-9]*|0)$/,
7962
7963 // Hexadecimal numbers
7964 NUMBER_HEX: /^0[xX][0-9a-fA-F]+$/,
7965
7966 // Octal numbers
7967 NUMBER_OCT: /^0[0-7]+$/,
7968
7969 // Floating point numbers
7970 NUMBER_FLT: /^([0-9]*(\.[0-9]*)?([Ee][+-]?[0-9]+)?|inf|nan)$/,
7971
7972 // Booleans
7973 BOOL: /^(?:true|false)$/i,
7974
7975 // Id numbers
7976 ID: /^(?:[1-9][0-9]*|0|0[xX][0-9a-fA-F]+|0[0-7]+)$/,
7977
7978 // Negative id numbers (enum values)
7979 NEGID: /^\-?(?:[1-9][0-9]*|0|0[xX][0-9a-fA-F]+|0[0-7]+)$/,
7980
7981 // Whitespaces
7982 WHITESPACE: /\s/,
7983
7984 // All strings
7985 STRING: /(?:"([^"\\]*(?:\\.[^"\\]*)*)")|(?:'([^'\\]*(?:\\.[^'\\]*)*)')/g,
7986
7987 // Double quoted strings
7988 STRING_DQ: /(?:"([^"\\]*(?:\\.[^"\\]*)*)")/g,
7989
7990 // Single quoted strings
7991 STRING_SQ: /(?:'([^'\\]*(?:\\.[^'\\]*)*)')/g
7992 };
7993
7994
7995 /**
7996 * @alias ProtoBuf.Reflect
7997 * @expose
7998 */
7999 ProtoBuf.Reflect = (function(ProtoBuf) {
8000
8001 /**
8002 * Reflection types.
8003 * @exports ProtoBuf.Reflect
8004 * @namespace
8005 */
8006 var Reflect = {};
8007
8008 /**
8009 * Constructs a Reflect base class.
8010 * @exports ProtoBuf.Reflect.T
8011 * @constructor
8012 * @abstract
8013 * @param {!ProtoBuf.Builder} builder Builder reference
8014 * @param {?ProtoBuf.Reflect.T} parent Parent object
8015 * @param {string} name Object name
8016 */
8017 var T = function(builder, parent, name) {
8018
8019 /**
8020 * Builder reference.
8021 * @type {!ProtoBuf.Builder}
8022 * @expose
8023 */
8024 this.builder = builder;
8025
8026 /**
8027 * Parent object.
8028 * @type {?ProtoBuf.Reflect.T}
8029 * @expose
8030 */
8031 this.parent = parent;
8032
8033 /**
8034 * Object name in namespace.
8035 * @type {string}
8036 * @expose
8037 */
8038 this.name = name;
8039
8040 /**
8041 * Fully qualified class name
8042 * @type {string}
8043 * @expose
8044 */
8045 this.className;
8046 };
8047
8048 /**
8049 * @alias ProtoBuf.Reflect.T.prototype
8050 * @inner
8051 */
8052 var TPrototype = T.prototype;
8053
8054 /**
8055 * Returns the fully qualified name of this object.
8056 * @returns {string} Fully qualified name as of ".PATH.TO.THIS"
8057 * @expose
8058 */
8059 TPrototype.fqn = function() {
8060 var name = this.name,
8061 ptr = this;
8062 do {
8063 ptr = ptr.parent;
8064 if (ptr == null)
8065 break;
8066 name = ptr.name+"."+name;
8067 } while (true);
8068 return name;
8069 };
8070
8071 /**
8072 * Returns a string representation of this Reflect object (its fully qualified name).
8073 * @param {boolean=} includeClass Set to true to include the class name. Defaults to false.
8074 * @return String representation
8075 * @expose
8076 */
8077 TPrototype.toString = function(includeClass) {
8078 return (includeClass ? this.className + " " : "") + this.fqn();
8079 };
8080
8081 /**
8082 * Builds this type.
8083 * @throws {Error} If this type cannot be built directly
8084 * @expose
8085 */
8086 TPrototype.build = function() {
8087 throw Error(this.toString(true)+" cannot be built directly");
8088 };
8089
8090 /**
8091 * @alias ProtoBuf.Reflect.T
8092 * @expose
8093 */
8094 Reflect.T = T;
8095
8096 /**
8097 * Constructs a new Namespace.
8098 * @exports ProtoBuf.Reflect.Namespace
8099 * @param {!ProtoBuf.Builder} builder Builder reference
8100 * @param {?ProtoBuf.Reflect.Namespace} parent Namespace parent
8101 * @param {string} name Namespace name
8102 * @param {Object.<string,*>=} options Namespace options
8103 * @param {string?} syntax The syntax level of this definition (e.g., proto3)
8104 * @constructor
8105 * @extends ProtoBuf.Reflect.T
8106 */
8107 var Namespace = function(builder, parent, name, options, syntax) {
8108 T.call(this, builder, parent, name);
8109
8110 /**
8111 * @override
8112 */
8113 this.className = "Namespace";
8114
8115 /**
8116 * Children inside the namespace.
8117 * @type {!Array.<ProtoBuf.Reflect.T>}
8118 */
8119 this.children = [];
8120
8121 /**
8122 * Options.
8123 * @type {!Object.<string, *>}
8124 */
8125 this.options = options || {};
8126
8127 /**
8128 * Syntax level (e.g., proto2 or proto3).
8129 * @type {!string}
8130 */
8131 this.syntax = syntax || "proto2";
8132 };
8133
8134 /**
8135 * @alias ProtoBuf.Reflect.Namespace.prototype
8136 * @inner
8137 */
8138 var NamespacePrototype = Namespace.prototype = Object.create(T.prototype);
8139
8140 /**
8141 * Returns an array of the namespace's children.
8142 * @param {ProtoBuf.Reflect.T=} type Filter type (returns instances of this type only). Defaults to null (all children).
8143 * @return {Array.<ProtoBuf.Reflect.T>}
8144 * @expose
8145 */
8146 NamespacePrototype.getChildren = function(type) {
8147 type = type || null;
8148 if (type == null)
8149 return this.children.slice();
8150 var children = [];
8151 for (var i=0, k=this.children.length; i<k; ++i)
8152 if (this.children[i] instanceof type)
8153 children.push(this.children[i]);
8154 return children;
8155 };
8156
8157 /**
8158 * Adds a child to the namespace.
8159 * @param {ProtoBuf.Reflect.T} child Child
8160 * @throws {Error} If the child cannot be added (duplicate)
8161 * @expose
8162 */
8163 NamespacePrototype.addChild = function(child) {
8164 var other;
8165 if (other = this.getChild(child.name)) {
8166 // Try to revert camelcase transformation on collision
8167 if (other instanceof Message.Field && other.name !== other.originalName && this.getChild(other.originalName) === null)
8168 other.name = other.originalName; // Revert previous first (effectively keeps both originals)
8169 else if (child instanceof Message.Field && child.name !== child.originalName && this.getChild(child.originalName) === null)
8170 child.name = child.originalName;
8171 else
8172 throw Error("Duplicate name in namespace "+this.toString(true)+": "+child.name);
8173 }
8174 this.children.push(child);
8175 };
8176
8177 /**
8178 * Gets a child by its name or id.
8179 * @param {string|number} nameOrId Child name or id
8180 * @return {?ProtoBuf.Reflect.T} The child or null if not found
8181 * @expose
8182 */
8183 NamespacePrototype.getChild = function(nameOrId) {
8184 var key = typeof nameOrId === 'number' ? 'id' : 'name';
8185 for (var i=0, k=this.children.length; i<k; ++i)
8186 if (this.children[i][key] === nameOrId)
8187 return this.children[i];
8188 return null;
8189 };
8190
8191 /**
8192 * Resolves a reflect object inside of this namespace.
8193 * @param {string|!Array.<string>} qn Qualified name to resolve
8194 * @param {boolean=} excludeNonNamespace Excludes non-namespace types, defaults to `false`
8195 * @return {?ProtoBuf.Reflect.Namespace} The resolved type or null if not found
8196 * @expose
8197 */
8198 NamespacePrototype.resolve = function(qn, excludeNonNamespace) {
8199 var part = typeof qn === 'string' ? qn.split(".") : qn,
8200 ptr = this,
8201 i = 0;
8202 if (part[i] === "") { // Fully qualified name, e.g. ".My.Message'
8203 while (ptr.parent !== null)
8204 ptr = ptr.parent;
8205 i++;
8206 }
8207 var child;
8208 do {
8209 do {
8210 if (!(ptr instanceof Reflect.Namespace)) {
8211 ptr = null;
8212 break;
8213 }
8214 child = ptr.getChild(part[i]);
8215 if (!child || !(child instanceof Reflect.T) || (excludeNonNamespace && !(child instanceof Reflect.Namespace))) {
8216 ptr = null;
8217 break;
8218 }
8219 ptr = child; i++;
8220 } while (i < part.length);
8221 if (ptr != null)
8222 break; // Found
8223 // Else search the parent
8224 if (this.parent !== null)
8225 return this.parent.resolve(qn, excludeNonNamespace);
8226 } while (ptr != null);
8227 return ptr;
8228 };
8229
8230 /**
8231 * Determines the shortest qualified name of the specified type, if any, relative to this namespace.
8232 * @param {!ProtoBuf.Reflect.T} t Reflection type
8233 * @returns {string} The shortest qualified name or, if there is none, the fqn
8234 * @expose
8235 */
8236 NamespacePrototype.qn = function(t) {
8237 var part = [], ptr = t;
8238 do {
8239 part.unshift(ptr.name);
8240 ptr = ptr.parent;
8241 } while (ptr !== null);
8242 for (var len=1; len <= part.length; len++) {
8243 var qn = part.slice(part.length-len);
8244 if (t === this.resolve(qn, t instanceof Reflect.Namespace))
8245 return qn.join(".");
8246 }
8247 return t.fqn();
8248 };
8249
8250 /**
8251 * Builds the namespace and returns the runtime counterpart.
8252 * @return {Object.<string,Function|Object>} Runtime namespace
8253 * @expose
8254 */
8255 NamespacePrototype.build = function() {
8256 /** @dict */
8257 var ns = {};
8258 var children = this.children;
8259 for (var i=0, k=children.length, child; i<k; ++i) {
8260 child = children[i];
8261 if (child instanceof Namespace)
8262 ns[child.name] = child.build();
8263 }
8264 if (Object.defineProperty)
8265 Object.defineProperty(ns, "$options", { "value": this.buildOpt() });
8266 return ns;
8267 };
8268
8269 /**
8270 * Builds the namespace's '$options' property.
8271 * @return {Object.<string,*>}
8272 */
8273 NamespacePrototype.buildOpt = function() {
8274 var opt = {},
8275 keys = Object.keys(this.options);
8276 for (var i=0, k=keys.length; i<k; ++i) {
8277 var key = keys[i],
8278 val = this.options[keys[i]];
8279 // TODO: Options are not resolved, yet.
8280 // if (val instanceof Namespace) {
8281 // opt[key] = val.build();
8282 // } else {
8283 opt[key] = val;
8284 // }
8285 }
8286 return opt;
8287 };
8288
8289 /**
8290 * Gets the value assigned to the option with the specified name.
8291 * @param {string=} name Returns the option value if specified, otherwise all options are returned.
8292 * @return {*|Object.<string,*>}null} Option value or NULL if there is no such option
8293 */
8294 NamespacePrototype.getOption = function(name) {
8295 if (typeof name === 'undefined')
8296 return this.options;
8297 return typeof this.options[name] !== 'undefined' ? this.options[name] : null;
8298 };
8299
8300 /**
8301 * @alias ProtoBuf.Reflect.Namespace
8302 * @expose
8303 */
8304 Reflect.Namespace = Namespace;
8305
8306 /**
8307 * Constructs a new Element implementation that checks and converts values for a
8308 * particular field type, as appropriate.
8309 *
8310 * An Element represents a single value: either the value of a singular field,
8311 * or a value contained in one entry of a repeated field or map field. This
8312 * class does not implement these higher-level concepts; it only encapsulates
8313 * the low-level typechecking and conversion.
8314 *
8315 * @exports ProtoBuf.Reflect.Element
8316 * @param {{name: string, wireType: number}} type Resolved data type
8317 * @param {ProtoBuf.Reflect.T|null} resolvedType Resolved type, if relevant
8318 * (e.g. submessage field).
8319 * @param {boolean} isMapKey Is this element a Map key? The value will be
8320 * converted to string form if so.
8321 * @param {string} syntax Syntax level of defining message type, e.g.,
8322 * proto2 or proto3.
8323 * @param {string} name Name of the field containing this element (for error
8324 * messages)
8325 * @constructor
8326 */
8327 var Element = function(type, resolvedType, isMapKey, syntax, name) {
8328
8329 /**
8330 * Element type, as a string (e.g., int32).
8331 * @type {{name: string, wireType: number}}
8332 */
8333 this.type = type;
8334
8335 /**
8336 * Element type reference to submessage or enum definition, if needed.
8337 * @type {ProtoBuf.Reflect.T|null}
8338 */
8339 this.resolvedType = resolvedType;
8340
8341 /**
8342 * Element is a map key.
8343 * @type {boolean}
8344 */
8345 this.isMapKey = isMapKey;
8346
8347 /**
8348 * Syntax level of defining message type, e.g., proto2 or proto3.
8349 * @type {string}
8350 */
8351 this.syntax = syntax;
8352
8353 /**
8354 * Name of the field containing this element (for error messages)
8355 * @type {string}
8356 */
8357 this.name = name;
8358
8359 if (isMapKey && ProtoBuf.MAP_KEY_TYPES.indexOf(type) < 0)
8360 throw Error("Invalid map key type: " + type.name);
8361 };
8362
8363 var ElementPrototype = Element.prototype;
8364
8365 /**
8366 * Obtains a (new) default value for the specified type.
8367 * @param type {string|{name: string, wireType: number}} Field type
8368 * @returns {*} Default value
8369 * @inner
8370 */
8371 function mkDefault(type) {
8372 if (typeof type === 'string')
8373 type = ProtoBuf.TYPES[type];
8374 if (typeof type.defaultValue === 'undefined')
8375 throw Error("default value for type "+type.name+" is not supported");
8376 if (type == ProtoBuf.TYPES["bytes"])
8377 return new ByteBuffer(0);
8378 return type.defaultValue;
8379 }
8380
8381 /**
8382 * Returns the default value for this field in proto3.
8383 * @function
8384 * @param type {string|{name: string, wireType: number}} the field type
8385 * @returns {*} Default value
8386 */
8387 Element.defaultFieldValue = mkDefault;
8388
8389 /**
8390 * Makes a Long from a value.
8391 * @param {{low: number, high: number, unsigned: boolean}|string|number} value Value
8392 * @param {boolean=} unsigned Whether unsigned or not, defaults to reuse it from Long-like objects or to signed for
8393 * strings and numbers
8394 * @returns {!Long}
8395 * @throws {Error} If the value cannot be converted to a Long
8396 * @inner
8397 */
8398 function mkLong(value, unsigned) {
8399 if (value && typeof value.low === 'number' && typeof value.high === 'number' && typeof value.unsigned === 'boolean'
8400 && value.low === value.low && value.high === value.high)
8401 return new ProtoBuf.Long(value.low, value.high, typeof unsigned === 'undefined' ? value.unsigned : unsigned);
8402 if (typeof value === 'string')
8403 return ProtoBuf.Long.fromString(value, unsigned || false, 10);
8404 if (typeof value === 'number')
8405 return ProtoBuf.Long.fromNumber(value, unsigned || false);
8406 throw Error("not convertible to Long");
8407 }
8408
8409 ElementPrototype.toString = function() {
8410 return (this.name || '') + (this.isMapKey ? 'map' : 'value') + ' element';
8411 };
8412
8413 /**
8414 * Checks if the given value can be set for an element of this type (singular
8415 * field or one element of a repeated field or map).
8416 * @param {*} value Value to check
8417 * @return {*} Verified, maybe adjusted, value
8418 * @throws {Error} If the value cannot be verified for this element slot
8419 * @expose
8420 */
8421 ElementPrototype.verifyValue = function(value) {
8422 var self = this;
8423 function fail(val, msg) {
8424 throw Error("Illegal value for "+self.toString(true)+" of type "+self.type.name+": "+val+" ("+msg+")");
8425 }
8426 switch (this.type) {
8427 // Signed 32bit
8428 case ProtoBuf.TYPES["int32"]:
8429 case ProtoBuf.TYPES["sint32"]:
8430 case ProtoBuf.TYPES["sfixed32"]:
8431 // Account for !NaN: value === value
8432 if (typeof value !== 'number' || (value === value && value % 1 !== 0))
8433 fail(typeof value, "not an integer");
8434 return value > 4294967295 ? value | 0 : value;
8435
8436 // Unsigned 32bit
8437 case ProtoBuf.TYPES["uint32"]:
8438 case ProtoBuf.TYPES["fixed32"]:
8439 if (typeof value !== 'number' || (value === value && value % 1 !== 0))
8440 fail(typeof value, "not an integer");
8441 return value < 0 ? value >>> 0 : value;
8442
8443 // Signed 64bit
8444 case ProtoBuf.TYPES["int64"]:
8445 case ProtoBuf.TYPES["sint64"]:
8446 case ProtoBuf.TYPES["sfixed64"]: {
8447 if (ProtoBuf.Long)
8448 try {
8449 return mkLong(value, false);
8450 } catch (e) {
8451 fail(typeof value, e.message);
8452 }
8453 else
8454 fail(typeof value, "requires Long.js");
8455 }
8456
8457 // Unsigned 64bit
8458 case ProtoBuf.TYPES["uint64"]:
8459 case ProtoBuf.TYPES["fixed64"]: {
8460 if (ProtoBuf.Long)
8461 try {
8462 return mkLong(value, true);
8463 } catch (e) {
8464 fail(typeof value, e.message);
8465 }
8466 else
8467 fail(typeof value, "requires Long.js");
8468 }
8469
8470 // Bool
8471 case ProtoBuf.TYPES["bool"]:
8472 if (typeof value !== 'boolean')
8473 fail(typeof value, "not a boolean");
8474 return value;
8475
8476 // Float
8477 case ProtoBuf.TYPES["float"]:
8478 case ProtoBuf.TYPES["double"]:
8479 if (typeof value !== 'number')
8480 fail(typeof value, "not a number");
8481 return value;
8482
8483 // Length-delimited string
8484 case ProtoBuf.TYPES["string"]:
8485 if (typeof value !== 'string' && !(value && value instanceof String))
8486 fail(typeof value, "not a string");
8487 return ""+value; // Convert String object to string
8488
8489 // Length-delimited bytes
8490 case ProtoBuf.TYPES["bytes"]:
8491 if (ByteBuffer.isByteBuffer(value))
8492 return value;
8493 return ByteBuffer.wrap(value, "base64");
8494
8495 // Constant enum value
8496 case ProtoBuf.TYPES["enum"]: {
8497 var values = this.resolvedType.getChildren(ProtoBuf.Reflect.Enum.Value);
8498 for (i=0; i<values.length; i++)
8499 if (values[i].name == value)
8500 return values[i].id;
8501 else if (values[i].id == value)
8502 return values[i].id;
8503
8504 if (this.syntax === 'proto3') {
8505 // proto3: just make sure it's an integer.
8506 if (typeof value !== 'number' || (value === value && value % 1 !== 0))
8507 fail(typeof value, "not an integer");
8508 if (value > 4294967295 || value < 0)
8509 fail(typeof value, "not in range for uint32");
8510 return value;
8511 } else {
8512 // proto2 requires enum values to be valid.
8513 fail(value, "not a valid enum value");
8514 }
8515 }
8516 // Embedded message
8517 case ProtoBuf.TYPES["group"]:
8518 case ProtoBuf.TYPES["message"]: {
8519 if (!value || typeof value !== 'object')
8520 fail(typeof value, "object expected");
8521 if (value instanceof this.resolvedType.clazz)
8522 return value;
8523 if (value instanceof ProtoBuf.Builder.Message) {
8524 // Mismatched type: Convert to object (see: https://github.com/dcodeIO/ProtoBuf.js/issues/180)
8525 var obj = {};
8526 for (var i in value)
8527 if (value.hasOwnProperty(i))
8528 obj[i] = value[i];
8529 value = obj;
8530 }
8531 // Else let's try to construct one from a key-value object
8532 return new (this.resolvedType.clazz)(value); // May throw for a hundred of reasons
8533 }
8534 }
8535
8536 // We should never end here
8537 throw Error("[INTERNAL] Illegal value for "+this.toString(true)+": "+value+" (undefined type "+this.type+")");
8538 };
8539
8540 /**
8541 * Calculates the byte length of an element on the wire.
8542 * @param {number} id Field number
8543 * @param {*} value Field value
8544 * @returns {number} Byte length
8545 * @throws {Error} If the value cannot be calculated
8546 * @expose
8547 */
8548 ElementPrototype.calculateLength = function(id, value) {
8549 if (value === null) return 0; // Nothing to encode
8550 // Tag has already been written
8551 var n;
8552 switch (this.type) {
8553 case ProtoBuf.TYPES["int32"]:
8554 return value < 0 ? ByteBuffer.calculateVarint64(value) : ByteBuffer.calculateVarint32(value);
8555 case ProtoBuf.TYPES["uint32"]:
8556 return ByteBuffer.calculateVarint32(value);
8557 case ProtoBuf.TYPES["sint32"]:
8558 return ByteBuffer.calculateVarint32(ByteBuffer.zigZagEncode32(value));
8559 case ProtoBuf.TYPES["fixed32"]:
8560 case ProtoBuf.TYPES["sfixed32"]:
8561 case ProtoBuf.TYPES["float"]:
8562 return 4;
8563 case ProtoBuf.TYPES["int64"]:
8564 case ProtoBuf.TYPES["uint64"]:
8565 return ByteBuffer.calculateVarint64(value);
8566 case ProtoBuf.TYPES["sint64"]:
8567 return ByteBuffer.calculateVarint64(ByteBuffer.zigZagEncode64(value));
8568 case ProtoBuf.TYPES["fixed64"]:
8569 case ProtoBuf.TYPES["sfixed64"]:
8570 return 8;
8571 case ProtoBuf.TYPES["bool"]:
8572 return 1;
8573 case ProtoBuf.TYPES["enum"]:
8574 return ByteBuffer.calculateVarint32(value);
8575 case ProtoBuf.TYPES["double"]:
8576 return 8;
8577 case ProtoBuf.TYPES["string"]:
8578 n = ByteBuffer.calculateUTF8Bytes(value);
8579 return ByteBuffer.calculateVarint32(n) + n;
8580 case ProtoBuf.TYPES["bytes"]:
8581 if (value.remaining() < 0)
8582 throw Error("Illegal value for "+this.toString(true)+": "+value.remaining()+" bytes remaining");
8583 return ByteBuffer.calculateVarint32(value.remaining()) + value.remaining();
8584 case ProtoBuf.TYPES["message"]:
8585 n = this.resolvedType.calculate(value);
8586 return ByteBuffer.calculateVarint32(n) + n;
8587 case ProtoBuf.TYPES["group"]:
8588 n = this.resolvedType.calculate(value);
8589 return n + ByteBuffer.calculateVarint32((id << 3) | ProtoBuf.WIRE_TYPES.ENDGROUP);
8590 }
8591 // We should never end here
8592 throw Error("[INTERNAL] Illegal value to encode in "+this.toString(true)+": "+value+" (unknown type)");
8593 };
8594
8595 /**
8596 * Encodes a value to the specified buffer. Does not encode the key.
8597 * @param {number} id Field number
8598 * @param {*} value Field value
8599 * @param {ByteBuffer} buffer ByteBuffer to encode to
8600 * @return {ByteBuffer} The ByteBuffer for chaining
8601 * @throws {Error} If the value cannot be encoded
8602 * @expose
8603 */
8604 ElementPrototype.encodeValue = function(id, value, buffer) {
8605 if (value === null) return buffer; // Nothing to encode
8606 // Tag has already been written
8607
8608 switch (this.type) {
8609 // 32bit signed varint
8610 case ProtoBuf.TYPES["int32"]:
8611 // "If you use int32 or int64 as the type for a negative number, the resulting varint is always ten bytes
8612 // long – it is, effectively, treated like a very large unsigned integer." (see #122)
8613 if (value < 0)
8614 buffer.writeVarint64(value);
8615 else
8616 buffer.writeVarint32(value);
8617 break;
8618
8619 // 32bit unsigned varint
8620 case ProtoBuf.TYPES["uint32"]:
8621 buffer.writeVarint32(value);
8622 break;
8623
8624 // 32bit varint zig-zag
8625 case ProtoBuf.TYPES["sint32"]:
8626 buffer.writeVarint32ZigZag(value);
8627 break;
8628
8629 // Fixed unsigned 32bit
8630 case ProtoBuf.TYPES["fixed32"]:
8631 buffer.writeUint32(value);
8632 break;
8633
8634 // Fixed signed 32bit
8635 case ProtoBuf.TYPES["sfixed32"]:
8636 buffer.writeInt32(value);
8637 break;
8638
8639 // 64bit varint as-is
8640 case ProtoBuf.TYPES["int64"]:
8641 case ProtoBuf.TYPES["uint64"]:
8642 buffer.writeVarint64(value); // throws
8643 break;
8644
8645 // 64bit varint zig-zag
8646 case ProtoBuf.TYPES["sint64"]:
8647 buffer.writeVarint64ZigZag(value); // throws
8648 break;
8649
8650 // Fixed unsigned 64bit
8651 case ProtoBuf.TYPES["fixed64"]:
8652 buffer.writeUint64(value); // throws
8653 break;
8654
8655 // Fixed signed 64bit
8656 case ProtoBuf.TYPES["sfixed64"]:
8657 buffer.writeInt64(value); // throws
8658 break;
8659
8660 // Bool
8661 case ProtoBuf.TYPES["bool"]:
8662 if (typeof value === 'string')
8663 buffer.writeVarint32(value.toLowerCase() === 'false' ? 0 : !!value);
8664 else
8665 buffer.writeVarint32(value ? 1 : 0);
8666 break;
8667
8668 // Constant enum value
8669 case ProtoBuf.TYPES["enum"]:
8670 buffer.writeVarint32(value);
8671 break;
8672
8673 // 32bit float
8674 case ProtoBuf.TYPES["float"]:
8675 buffer.writeFloat32(value);
8676 break;
8677
8678 // 64bit float
8679 case ProtoBuf.TYPES["double"]:
8680 buffer.writeFloat64(value);
8681 break;
8682
8683 // Length-delimited string
8684 case ProtoBuf.TYPES["string"]:
8685 buffer.writeVString(value);
8686 break;
8687
8688 // Length-delimited bytes
8689 case ProtoBuf.TYPES["bytes"]:
8690 if (value.remaining() < 0)
8691 throw Error("Illegal value for "+this.toString(true)+": "+value.remaining()+" bytes remaining");
8692 var prevOffset = value.offset;
8693 buffer.writeVarint32(value.remaining());
8694 buffer.append(value);
8695 value.offset = prevOffset;
8696 break;
8697
8698 // Embedded message
8699 case ProtoBuf.TYPES["message"]:
8700 var bb = new ByteBuffer().LE();
8701 this.resolvedType.encode(value, bb);
8702 buffer.writeVarint32(bb.offset);
8703 buffer.append(bb.flip());
8704 break;
8705
8706 // Legacy group
8707 case ProtoBuf.TYPES["group"]:
8708 this.resolvedType.encode(value, buffer);
8709 buffer.writeVarint32((id << 3) | ProtoBuf.WIRE_TYPES.ENDGROUP);
8710 break;
8711
8712 default:
8713 // We should never end here
8714 throw Error("[INTERNAL] Illegal value to encode in "+this.toString(true)+": "+value+" (unknown type)");
8715 }
8716 return buffer;
8717 };
8718
8719 /**
8720 * Decode one element value from the specified buffer.
8721 * @param {ByteBuffer} buffer ByteBuffer to decode from
8722 * @param {number} wireType The field wire type
8723 * @param {number} id The field number
8724 * @return {*} Decoded value
8725 * @throws {Error} If the field cannot be decoded
8726 * @expose
8727 */
8728 ElementPrototype.decode = function(buffer, wireType, id) {
8729 if (wireType != this.type.wireType)
8730 throw Error("Unexpected wire type for element");
8731
8732 var value, nBytes;
8733 switch (this.type) {
8734 // 32bit signed varint
8735 case ProtoBuf.TYPES["int32"]:
8736 return buffer.readVarint32() | 0;
8737
8738 // 32bit unsigned varint
8739 case ProtoBuf.TYPES["uint32"]:
8740 return buffer.readVarint32() >>> 0;
8741
8742 // 32bit signed varint zig-zag
8743 case ProtoBuf.TYPES["sint32"]:
8744 return buffer.readVarint32ZigZag() | 0;
8745
8746 // Fixed 32bit unsigned
8747 case ProtoBuf.TYPES["fixed32"]:
8748 return buffer.readUint32() >>> 0;
8749
8750 case ProtoBuf.TYPES["sfixed32"]:
8751 return buffer.readInt32() | 0;
8752
8753 // 64bit signed varint
8754 case ProtoBuf.TYPES["int64"]:
8755 return buffer.readVarint64();
8756
8757 // 64bit unsigned varint
8758 case ProtoBuf.TYPES["uint64"]:
8759 return buffer.readVarint64().toUnsigned();
8760
8761 // 64bit signed varint zig-zag
8762 case ProtoBuf.TYPES["sint64"]:
8763 return buffer.readVarint64ZigZag();
8764
8765 // Fixed 64bit unsigned
8766 case ProtoBuf.TYPES["fixed64"]:
8767 return buffer.readUint64();
8768
8769 // Fixed 64bit signed
8770 case ProtoBuf.TYPES["sfixed64"]:
8771 return buffer.readInt64();
8772
8773 // Bool varint
8774 case ProtoBuf.TYPES["bool"]:
8775 return !!buffer.readVarint32();
8776
8777 // Constant enum value (varint)
8778 case ProtoBuf.TYPES["enum"]:
8779 // The following Builder.Message#set will already throw
8780 return buffer.readVarint32();
8781
8782 // 32bit float
8783 case ProtoBuf.TYPES["float"]:
8784 return buffer.readFloat();
8785
8786 // 64bit float
8787 case ProtoBuf.TYPES["double"]:
8788 return buffer.readDouble();
8789
8790 // Length-delimited string
8791 case ProtoBuf.TYPES["string"]:
8792 return buffer.readVString();
8793
8794 // Length-delimited bytes
8795 case ProtoBuf.TYPES["bytes"]: {
8796 nBytes = buffer.readVarint32();
8797 if (buffer.remaining() < nBytes)
8798 throw Error("Illegal number of bytes for "+this.toString(true)+": "+nBytes+" required but got only "+buffer.remaining());
8799 value = buffer.clone(); // Offset already set
8800 value.limit = value.offset+nBytes;
8801 buffer.offset += nBytes;
8802 return value;
8803 }
8804
8805 // Length-delimited embedded message
8806 case ProtoBuf.TYPES["message"]: {
8807 nBytes = buffer.readVarint32();
8808 return this.resolvedType.decode(buffer, nBytes);
8809 }
8810
8811 // Legacy group
8812 case ProtoBuf.TYPES["group"]:
8813 return this.resolvedType.decode(buffer, -1, id);
8814 }
8815
8816 // We should never end here
8817 throw Error("[INTERNAL] Illegal decode type");
8818 };
8819
8820 /**
8821 * Converts a value from a string to the canonical element type.
8822 *
8823 * Legal only when isMapKey is true.
8824 *
8825 * @param {string} str The string value
8826 * @returns {*} The value
8827 */
8828 ElementPrototype.valueFromString = function(str) {
8829 if (!this.isMapKey) {
8830 throw Error("valueFromString() called on non-map-key element");
8831 }
8832
8833 switch (this.type) {
8834 case ProtoBuf.TYPES["int32"]:
8835 case ProtoBuf.TYPES["sint32"]:
8836 case ProtoBuf.TYPES["sfixed32"]:
8837 case ProtoBuf.TYPES["uint32"]:
8838 case ProtoBuf.TYPES["fixed32"]:
8839 return this.verifyValue(parseInt(str));
8840
8841 case ProtoBuf.TYPES["int64"]:
8842 case ProtoBuf.TYPES["sint64"]:
8843 case ProtoBuf.TYPES["sfixed64"]:
8844 case ProtoBuf.TYPES["uint64"]:
8845 case ProtoBuf.TYPES["fixed64"]:
8846 // Long-based fields support conversions from string already.
8847 return this.verifyValue(str);
8848
8849 case ProtoBuf.TYPES["bool"]:
8850 return str === "true";
8851
8852 case ProtoBuf.TYPES["string"]:
8853 return this.verifyValue(str);
8854
8855 case ProtoBuf.TYPES["bytes"]:
8856 return ByteBuffer.fromBinary(str);
8857 }
8858 };
8859
8860 /**
8861 * Converts a value from the canonical element type to a string.
8862 *
8863 * It should be the case that `valueFromString(valueToString(val))` returns
8864 * a value equivalent to `verifyValue(val)` for every legal value of `val`
8865 * according to this element type.
8866 *
8867 * This may be used when the element must be stored or used as a string,
8868 * e.g., as a map key on an Object.
8869 *
8870 * Legal only when isMapKey is true.
8871 *
8872 * @param {*} val The value
8873 * @returns {string} The string form of the value.
8874 */
8875 ElementPrototype.valueToString = function(value) {
8876 if (!this.isMapKey) {
8877 throw Error("valueToString() called on non-map-key element");
8878 }
8879
8880 if (this.type === ProtoBuf.TYPES["bytes"]) {
8881 return value.toString("binary");
8882 } else {
8883 return value.toString();
8884 }
8885 };
8886
8887 /**
8888 * @alias ProtoBuf.Reflect.Element
8889 * @expose
8890 */
8891 Reflect.Element = Element;
8892
8893 /**
8894 * Constructs a new Message.
8895 * @exports ProtoBuf.Reflect.Message
8896 * @param {!ProtoBuf.Builder} builder Builder reference
8897 * @param {!ProtoBuf.Reflect.Namespace} parent Parent message or namespace
8898 * @param {string} name Message name
8899 * @param {Object.<string,*>=} options Message options
8900 * @param {boolean=} isGroup `true` if this is a legacy group
8901 * @param {string?} syntax The syntax level of this definition (e.g., proto3)
8902 * @constructor
8903 * @extends ProtoBuf.Reflect.Namespace
8904 */
8905 var Message = function(builder, parent, name, options, isGroup, syntax) {
8906 Namespace.call(this, builder, parent, name, options, syntax);
8907
8908 /**
8909 * @override
8910 */
8911 this.className = "Message";
8912
8913 /**
8914 * Extensions range.
8915 * @type {!Array.<number>|undefined}
8916 * @expose
8917 */
8918 this.extensions = undefined;
8919
8920 /**
8921 * Runtime message class.
8922 * @type {?function(new:ProtoBuf.Builder.Message)}
8923 * @expose
8924 */
8925 this.clazz = null;
8926
8927 /**
8928 * Whether this is a legacy group or not.
8929 * @type {boolean}
8930 * @expose
8931 */
8932 this.isGroup = !!isGroup;
8933
8934 // The following cached collections are used to efficiently iterate over or look up fields when decoding.
8935
8936 /**
8937 * Cached fields.
8938 * @type {?Array.<!ProtoBuf.Reflect.Message.Field>}
8939 * @private
8940 */
8941 this._fields = null;
8942
8943 /**
8944 * Cached fields by id.
8945 * @type {?Object.<number,!ProtoBuf.Reflect.Message.Field>}
8946 * @private
8947 */
8948 this._fieldsById = null;
8949
8950 /**
8951 * Cached fields by name.
8952 * @type {?Object.<string,!ProtoBuf.Reflect.Message.Field>}
8953 * @private
8954 */
8955 this._fieldsByName = null;
8956 };
8957
8958 /**
8959 * @alias ProtoBuf.Reflect.Message.prototype
8960 * @inner
8961 */
8962 var MessagePrototype = Message.prototype = Object.create(Namespace.prototype);
8963
8964 /**
8965 * Builds the message and returns the runtime counterpart, which is a fully functional class.
8966 * @see ProtoBuf.Builder.Message
8967 * @param {boolean=} rebuild Whether to rebuild or not, defaults to false
8968 * @return {ProtoBuf.Reflect.Message} Message class
8969 * @throws {Error} If the message cannot be built
8970 * @expose
8971 */
8972 MessagePrototype.build = function(rebuild) {
8973 if (this.clazz && !rebuild)
8974 return this.clazz;
8975
8976 // Create the runtime Message class in its own scope
8977 var clazz = (function(ProtoBuf, T) {
8978
8979 var fields = T.getChildren(ProtoBuf.Reflect.Message.Field),
8980 oneofs = T.getChildren(ProtoBuf.Reflect.Message.OneOf);
8981
8982 /**
8983 * Constructs a new runtime Message.
8984 * @name ProtoBuf.Builder.Message
8985 * @class Barebone of all runtime messages.
8986 * @param {!Object.<string,*>|string} values Preset values
8987 * @param {...string} var_args
8988 * @constructor
8989 * @throws {Error} If the message cannot be created
8990 */
8991 var Message = function(values, var_args) {
8992 ProtoBuf.Builder.Message.call(this);
8993
8994 // Create virtual oneof properties
8995 for (var i=0, k=oneofs.length; i<k; ++i)
8996 this[oneofs[i].name] = null;
8997 // Create fields and set default values
8998 for (i=0, k=fields.length; i<k; ++i) {
8999 var field = fields[i];
9000 this[field.name] =
9001 field.repeated ? [] :
9002 (field.map ? new ProtoBuf.Map(field) : null);
9003 if ((field.required || T.syntax === 'proto3') &&
9004 field.defaultValue !== null)
9005 this[field.name] = field.defaultValue;
9006 }
9007
9008 if (arguments.length > 0) {
9009 var value;
9010 // Set field values from a values object
9011 if (arguments.length === 1 && values !== null && typeof values === 'object' &&
9012 /* not _another_ Message */ (typeof values.encode !== 'function' || values instanceof Message) &&
9013 /* not a repeated field */ !Array.isArray(values) &&
9014 /* not a Map */ !(values instanceof ProtoBuf.Map) &&
9015 /* not a ByteBuffer */ !ByteBuffer.isByteBuffer(values) &&
9016 /* not an ArrayBuffer */ !(values instanceof ArrayBuffer) &&
9017 /* not a Long */ !(ProtoBuf.Long && values instanceof ProtoBuf.Long)) {
9018 this.$set(values);
9019 } else // Set field values from arguments, in declaration order
9020 for (i=0, k=arguments.length; i<k; ++i)
9021 if (typeof (value = arguments[i]) !== 'undefined')
9022 this.$set(fields[i].name, value); // May throw
9023 }
9024 };
9025
9026 /**
9027 * @alias ProtoBuf.Builder.Message.prototype
9028 * @inner
9029 */
9030 var MessagePrototype = Message.prototype = Object.create(ProtoBuf.Builder.Message.prototype);
9031
9032 /**
9033 * Adds a value to a repeated field.
9034 * @name ProtoBuf.Builder.Message#add
9035 * @function
9036 * @param {string} key Field name
9037 * @param {*} value Value to add
9038 * @param {boolean=} noAssert Whether to assert the value or not (asserts by default)
9039 * @returns {!ProtoBuf.Builder.Message} this
9040 * @throws {Error} If the value cannot be added
9041 * @expose
9042 */
9043 MessagePrototype.add = function(key, value, noAssert) {
9044 var field = T._fieldsByName[key];
9045 if (!noAssert) {
9046 if (!field)
9047 throw Error(this+"#"+key+" is undefined");
9048 if (!(field instanceof ProtoBuf.Reflect.Message.Field))
9049 throw Error(this+"#"+key+" is not a field: "+field.toString(true)); // May throw if it's an enum or embedded message
9050 if (!field.repeated)
9051 throw Error(this+"#"+key+" is not a repeated field");
9052 value = field.verifyValue(value, true);
9053 }
9054 if (this[key] === null)
9055 this[key] = [];
9056 this[key].push(value);
9057 return this;
9058 };
9059
9060 /**
9061 * Adds a value to a repeated field. This is an alias for {@link ProtoBuf.Builder.Message#add}.
9062 * @name ProtoBuf.Builder.Message#$add
9063 * @function
9064 * @param {string} key Field name
9065 * @param {*} value Value to add
9066 * @param {boolean=} noAssert Whether to assert the value or not (asserts by default)
9067 * @returns {!ProtoBuf.Builder.Message} this
9068 * @throws {Error} If the value cannot be added
9069 * @expose
9070 */
9071 MessagePrototype.$add = MessagePrototype.add;
9072
9073 /**
9074 * Sets a field's value.
9075 * @name ProtoBuf.Builder.Message#set
9076 * @function
9077 * @param {string|!Object.<string,*>} keyOrObj String key or plain object holding multiple values
9078 * @param {(*|boolean)=} value Value to set if key is a string, otherwise omitted
9079 * @param {boolean=} noAssert Whether to not assert for an actual field / proper value type, defaults to `false`
9080 * @returns {!ProtoBuf.Builder.Message} this
9081 * @throws {Error} If the value cannot be set
9082 * @expose
9083 */
9084 MessagePrototype.set = function(keyOrObj, value, noAssert) {
9085 if (keyOrObj && typeof keyOrObj === 'object') {
9086 noAssert = value;
9087 for (var ikey in keyOrObj) {
9088 // Check if virtual oneof field - don't set these
9089 if (keyOrObj.hasOwnProperty(ikey) && typeof (value = keyOrObj[ikey]) !== 'undefined' && T._oneofsByName[ikey] === undefined)
9090 this.$set(ikey, value, noAssert);
9091 }
9092 return this;
9093 }
9094 var field = T._fieldsByName[keyOrObj];
9095 if (!noAssert) {
9096 if (!field)
9097 throw Error(this+"#"+keyOrObj+" is not a field: undefined");
9098 if (!(field instanceof ProtoBuf.Reflect.Message.Field))
9099 throw Error(this+"#"+keyOrObj+" is not a field: "+field.toString(true));
9100 this[field.name] = (value = field.verifyValue(value)); // May throw
9101 } else
9102 this[keyOrObj] = value;
9103 if (field && field.oneof) { // Field is part of an OneOf (not a virtual OneOf field)
9104 var currentField = this[field.oneof.name]; // Virtual field references currently set field
9105 if (value !== null) {
9106 if (currentField !== null && currentField !== field.name)
9107 this[currentField] = null; // Clear currently set field
9108 this[field.oneof.name] = field.name; // Point virtual field at this field
9109 } else if (/* value === null && */currentField === keyOrObj)
9110 this[field.oneof.name] = null; // Clear virtual field (current field explicitly cleared)
9111 }
9112 return this;
9113 };
9114
9115 /**
9116 * Sets a field's value. This is an alias for [@link ProtoBuf.Builder.Message#set}.
9117 * @name ProtoBuf.Builder.Message#$set
9118 * @function
9119 * @param {string|!Object.<string,*>} keyOrObj String key or plain object holding multiple values
9120 * @param {(*|boolean)=} value Value to set if key is a string, otherwise omitted
9121 * @param {boolean=} noAssert Whether to not assert the value, defaults to `false`
9122 * @throws {Error} If the value cannot be set
9123 * @expose
9124 */
9125 MessagePrototype.$set = MessagePrototype.set;
9126
9127 /**
9128 * Gets a field's value.
9129 * @name ProtoBuf.Builder.Message#get
9130 * @function
9131 * @param {string} key Key
9132 * @param {boolean=} noAssert Whether to not assert for an actual field, defaults to `false`
9133 * @return {*} Value
9134 * @throws {Error} If there is no such field
9135 * @expose
9136 */
9137 MessagePrototype.get = function(key, noAssert) {
9138 if (noAssert)
9139 return this[key];
9140 var field = T._fieldsByName[key];
9141 if (!field || !(field instanceof ProtoBuf.Reflect.Message.Field))
9142 throw Error(this+"#"+key+" is not a field: undefined");
9143 if (!(field instanceof ProtoBuf.Reflect.Message.Field))
9144 throw Error(this+"#"+key+" is not a field: "+field.toString(true));
9145 return this[field.name];
9146 };
9147
9148 /**
9149 * Gets a field's value. This is an alias for {@link ProtoBuf.Builder.Message#$get}.
9150 * @name ProtoBuf.Builder.Message#$get
9151 * @function
9152 * @param {string} key Key
9153 * @return {*} Value
9154 * @throws {Error} If there is no such field
9155 * @expose
9156 */
9157 MessagePrototype.$get = MessagePrototype.get;
9158
9159 // Getters and setters
9160
9161 for (var i=0; i<fields.length; i++) {
9162 var field = fields[i];
9163 // no setters for extension fields as these are named by their fqn
9164 if (field instanceof ProtoBuf.Reflect.Message.ExtensionField)
9165 continue;
9166
9167 if (T.builder.options['populateAccessors'])
9168 (function(field) {
9169 // set/get[SomeValue]
9170 var Name = field.originalName.replace(/(_[a-zA-Z])/g, function(match) {
9171 return match.toUpperCase().replace('_','');
9172 });
9173 Name = Name.substring(0,1).toUpperCase() + Name.substring(1);
9174
9175 // set/get_[some_value] FIXME: Do we really need these?
9176 var name = field.originalName.replace(/([A-Z])/g, function(match) {
9177 return "_"+match;
9178 });
9179
9180 /**
9181 * The current field's unbound setter function.
9182 * @function
9183 * @param {*} value
9184 * @param {boolean=} noAssert
9185 * @returns {!ProtoBuf.Builder.Message}
9186 * @inner
9187 */
9188 var setter = function(value, noAssert) {
9189 this[field.name] = noAssert ? value : field.verifyValue(value);
9190 return this;
9191 };
9192
9193 /**
9194 * The current field's unbound getter function.
9195 * @function
9196 * @returns {*}
9197 * @inner
9198 */
9199 var getter = function() {
9200 return this[field.name];
9201 };
9202
9203 if (T.getChild("set"+Name) === null)
9204 /**
9205 * Sets a value. This method is present for each field, but only if there is no name conflict with
9206 * another field.
9207 * @name ProtoBuf.Builder.Message#set[SomeField]
9208 * @function
9209 * @param {*} value Value to set
9210 * @param {boolean=} noAssert Whether to not assert the value, defaults to `false`
9211 * @returns {!ProtoBuf.Builder.Message} this
9212 * @abstract
9213 * @throws {Error} If the value cannot be set
9214 */
9215 MessagePrototype["set"+Name] = setter;
9216
9217 if (T.getChild("set_"+name) === null)
9218 /**
9219 * Sets a value. This method is present for each field, but only if there is no name conflict with
9220 * another field.
9221 * @name ProtoBuf.Builder.Message#set_[some_field]
9222 * @function
9223 * @param {*} value Value to set
9224 * @param {boolean=} noAssert Whether to not assert the value, defaults to `false`
9225 * @returns {!ProtoBuf.Builder.Message} this
9226 * @abstract
9227 * @throws {Error} If the value cannot be set
9228 */
9229 MessagePrototype["set_"+name] = setter;
9230
9231 if (T.getChild("get"+Name) === null)
9232 /**
9233 * Gets a value. This method is present for each field, but only if there is no name conflict with
9234 * another field.
9235 * @name ProtoBuf.Builder.Message#get[SomeField]
9236 * @function
9237 * @abstract
9238 * @return {*} The value
9239 */
9240 MessagePrototype["get"+Name] = getter;
9241
9242 if (T.getChild("get_"+name) === null)
9243 /**
9244 * Gets a value. This method is present for each field, but only if there is no name conflict with
9245 * another field.
9246 * @name ProtoBuf.Builder.Message#get_[some_field]
9247 * @function
9248 * @return {*} The value
9249 * @abstract
9250 */
9251 MessagePrototype["get_"+name] = getter;
9252
9253 })(field);
9254 }
9255
9256 // En-/decoding
9257
9258 /**
9259 * Encodes the message.
9260 * @name ProtoBuf.Builder.Message#$encode
9261 * @function
9262 * @param {(!ByteBuffer|boolean)=} buffer ByteBuffer to encode to. Will create a new one and flip it if omitted.
9263 * @param {boolean=} noVerify Whether to not verify field values, defaults to `false`
9264 * @return {!ByteBuffer} Encoded message as a ByteBuffer
9265 * @throws {Error} If the message cannot be encoded or if required fields are missing. The later still
9266 * returns the encoded ByteBuffer in the `encoded` property on the error.
9267 * @expose
9268 * @see ProtoBuf.Builder.Message#encode64
9269 * @see ProtoBuf.Builder.Message#encodeHex
9270 * @see ProtoBuf.Builder.Message#encodeAB
9271 */
9272 MessagePrototype.encode = function(buffer, noVerify) {
9273 if (typeof buffer === 'boolean')
9274 noVerify = buffer,
9275 buffer = undefined;
9276 var isNew = false;
9277 if (!buffer)
9278 buffer = new ByteBuffer(),
9279 isNew = true;
9280 var le = buffer.littleEndian;
9281 try {
9282 T.encode(this, buffer.LE(), noVerify);
9283 return (isNew ? buffer.flip() : buffer).LE(le);
9284 } catch (e) {
9285 buffer.LE(le);
9286 throw(e);
9287 }
9288 };
9289
9290 /**
9291 * Encodes a message using the specified data payload.
9292 * @param {!Object.<string,*>} data Data payload
9293 * @param {(!ByteBuffer|boolean)=} buffer ByteBuffer to encode to. Will create a new one and flip it if omitted.
9294 * @param {boolean=} noVerify Whether to not verify field values, defaults to `false`
9295 * @return {!ByteBuffer} Encoded message as a ByteBuffer
9296 * @expose
9297 */
9298 Message.encode = function(data, buffer, noVerify) {
9299 return new Message(data).encode(buffer, noVerify);
9300 };
9301
9302 /**
9303 * Calculates the byte length of the message.
9304 * @name ProtoBuf.Builder.Message#calculate
9305 * @function
9306 * @returns {number} Byte length
9307 * @throws {Error} If the message cannot be calculated or if required fields are missing.
9308 * @expose
9309 */
9310 MessagePrototype.calculate = function() {
9311 return T.calculate(this);
9312 };
9313
9314 /**
9315 * Encodes the varint32 length-delimited message.
9316 * @name ProtoBuf.Builder.Message#encodeDelimited
9317 * @function
9318 * @param {(!ByteBuffer|boolean)=} buffer ByteBuffer to encode to. Will create a new one and flip it if omitted.
9319 * @param {boolean=} noVerify Whether to not verify field values, defaults to `false`
9320 * @return {!ByteBuffer} Encoded message as a ByteBuffer
9321 * @throws {Error} If the message cannot be encoded or if required fields are missing. The later still
9322 * returns the encoded ByteBuffer in the `encoded` property on the error.
9323 * @expose
9324 */
9325 MessagePrototype.encodeDelimited = function(buffer, noVerify) {
9326 var isNew = false;
9327 if (!buffer)
9328 buffer = new ByteBuffer(),
9329 isNew = true;
9330 var enc = new ByteBuffer().LE();
9331 T.encode(this, enc, noVerify).flip();
9332 buffer.writeVarint32(enc.remaining());
9333 buffer.append(enc);
9334 return isNew ? buffer.flip() : buffer;
9335 };
9336
9337 /**
9338 * Directly encodes the message to an ArrayBuffer.
9339 * @name ProtoBuf.Builder.Message#encodeAB
9340 * @function
9341 * @return {ArrayBuffer} Encoded message as ArrayBuffer
9342 * @throws {Error} If the message cannot be encoded or if required fields are missing. The later still
9343 * returns the encoded ArrayBuffer in the `encoded` property on the error.
9344 * @expose
9345 */
9346 MessagePrototype.encodeAB = function() {
9347 try {
9348 return this.encode().toArrayBuffer();
9349 } catch (e) {
9350 if (e["encoded"]) e["encoded"] = e["encoded"].toArrayBuffer();
9351 throw(e);
9352 }
9353 };
9354
9355 /**
9356 * Returns the message as an ArrayBuffer. This is an alias for {@link ProtoBuf.Builder.Message#encodeAB}.
9357 * @name ProtoBuf.Builder.Message#toArrayBuffer
9358 * @function
9359 * @return {ArrayBuffer} Encoded message as ArrayBuffer
9360 * @throws {Error} If the message cannot be encoded or if required fields are missing. The later still
9361 * returns the encoded ArrayBuffer in the `encoded` property on the error.
9362 * @expose
9363 */
9364 MessagePrototype.toArrayBuffer = MessagePrototype.encodeAB;
9365
9366 /**
9367 * Directly encodes the message to a node Buffer.
9368 * @name ProtoBuf.Builder.Message#encodeNB
9369 * @function
9370 * @return {!Buffer}
9371 * @throws {Error} If the message cannot be encoded, not running under node.js or if required fields are
9372 * missing. The later still returns the encoded node Buffer in the `encoded` property on the error.
9373 * @expose
9374 */
9375 MessagePrototype.encodeNB = function() {
9376 try {
9377 return this.encode().toBuffer();
9378 } catch (e) {
9379 if (e["encoded"]) e["encoded"] = e["encoded"].toBuffer();
9380 throw(e);
9381 }
9382 };
9383
9384 /**
9385 * Returns the message as a node Buffer. This is an alias for {@link ProtoBuf.Builder.Message#encodeNB}.
9386 * @name ProtoBuf.Builder.Message#toBuffer
9387 * @function
9388 * @return {!Buffer}
9389 * @throws {Error} If the message cannot be encoded or if required fields are missing. The later still
9390 * returns the encoded node Buffer in the `encoded` property on the error.
9391 * @expose
9392 */
9393 MessagePrototype.toBuffer = MessagePrototype.encodeNB;
9394
9395 /**
9396 * Directly encodes the message to a base64 encoded string.
9397 * @name ProtoBuf.Builder.Message#encode64
9398 * @function
9399 * @return {string} Base64 encoded string
9400 * @throws {Error} If the underlying buffer cannot be encoded or if required fields are missing. The later
9401 * still returns the encoded base64 string in the `encoded` property on the error.
9402 * @expose
9403 */
9404 MessagePrototype.encode64 = function() {
9405 try {
9406 return this.encode().toBase64();
9407 } catch (e) {
9408 if (e["encoded"]) e["encoded"] = e["encoded"].toBase64();
9409 throw(e);
9410 }
9411 };
9412
9413 /**
9414 * Returns the message as a base64 encoded string. This is an alias for {@link ProtoBuf.Builder.Message#encode64}.
9415 * @name ProtoBuf.Builder.Message#toBase64
9416 * @function
9417 * @return {string} Base64 encoded string
9418 * @throws {Error} If the message cannot be encoded or if required fields are missing. The later still
9419 * returns the encoded base64 string in the `encoded` property on the error.
9420 * @expose
9421 */
9422 MessagePrototype.toBase64 = MessagePrototype.encode64;
9423
9424 /**
9425 * Directly encodes the message to a hex encoded string.
9426 * @name ProtoBuf.Builder.Message#encodeHex
9427 * @function
9428 * @return {string} Hex encoded string
9429 * @throws {Error} If the underlying buffer cannot be encoded or if required fields are missing. The later
9430 * still returns the encoded hex string in the `encoded` property on the error.
9431 * @expose
9432 */
9433 MessagePrototype.encodeHex = function() {
9434 try {
9435 return this.encode().toHex();
9436 } catch (e) {
9437 if (e["encoded"]) e["encoded"] = e["encoded"].toHex();
9438 throw(e);
9439 }
9440 };
9441
9442 /**
9443 * Returns the message as a hex encoded string. This is an alias for {@link ProtoBuf.Builder.Message#encodeHex}.
9444 * @name ProtoBuf.Builder.Message#toHex
9445 * @function
9446 * @return {string} Hex encoded string
9447 * @throws {Error} If the message cannot be encoded or if required fields are missing. The later still
9448 * returns the encoded hex string in the `encoded` property on the error.
9449 * @expose
9450 */
9451 MessagePrototype.toHex = MessagePrototype.encodeHex;
9452
9453 /**
9454 * Clones a message object or field value to a raw object.
9455 * @param {*} obj Object to clone
9456 * @param {boolean} binaryAsBase64 Whether to include binary data as base64 strings or as a buffer otherwise
9457 * @param {boolean} longsAsStrings Whether to encode longs as strings
9458 * @param {!ProtoBuf.Reflect.T=} resolvedType The resolved field type if a field
9459 * @returns {*} Cloned object
9460 * @inner
9461 */
9462 function cloneRaw(obj, binaryAsBase64, longsAsStrings, resolvedType) {
9463 if (obj === null || typeof obj !== 'object') {
9464 // Convert enum values to their respective names
9465 if (resolvedType && resolvedType instanceof ProtoBuf.Reflect.Enum) {
9466 var name = ProtoBuf.Reflect.Enum.getName(resolvedType.object, obj);
9467 if (name !== null)
9468 return name;
9469 }
9470 // Pass-through string, number, boolean, null...
9471 return obj;
9472 }
9473 // Convert ByteBuffers to raw buffer or strings
9474 if (ByteBuffer.isByteBuffer(obj))
9475 return binaryAsBase64 ? obj.toBase64() : obj.toBuffer();
9476 // Convert Longs to proper objects or strings
9477 if (ProtoBuf.Long.isLong(obj))
9478 return longsAsStrings ? obj.toString() : ProtoBuf.Long.fromValue(obj);
9479 var clone;
9480 // Clone arrays
9481 if (Array.isArray(obj)) {
9482 clone = [];
9483 obj.forEach(function(v, k) {
9484 clone[k] = cloneRaw(v, binaryAsBase64, longsAsStrings, resolvedType);
9485 });
9486 return clone;
9487 }
9488 clone = {};
9489 // Convert maps to objects
9490 if (obj instanceof ProtoBuf.Map) {
9491 var it = obj.entries();
9492 for (var e = it.next(); !e.done; e = it.next())
9493 clone[obj.keyElem.valueToString(e.value[0])] = cloneRaw(e.value[1], binaryAsBase64, longsAsStrings, obj.valueElem.resolvedType);
9494 return clone;
9495 }
9496 // Everything else is a non-null object
9497 var type = obj.$type,
9498 field = undefined;
9499 for (var i in obj)
9500 if (obj.hasOwnProperty(i)) {
9501 if (type && (field = type.getChild(i)))
9502 clone[i] = cloneRaw(obj[i], binaryAsBase64, longsAsStrings, field.resolvedType);
9503 else
9504 clone[i] = cloneRaw(obj[i], binaryAsBase64, longsAsStrings);
9505 }
9506 return clone;
9507 }
9508
9509 /**
9510 * Returns the message's raw payload.
9511 * @param {boolean=} binaryAsBase64 Whether to include binary data as base64 strings instead of Buffers, defaults to `false`
9512 * @param {boolean} longsAsStrings Whether to encode longs as strings
9513 * @returns {Object.<string,*>} Raw payload
9514 * @expose
9515 */
9516 MessagePrototype.toRaw = function(binaryAsBase64, longsAsStrings) {
9517 return cloneRaw(this, !!binaryAsBase64, !!longsAsStrings, this.$type);
9518 };
9519
9520 /**
9521 * Encodes a message to JSON.
9522 * @returns {string} JSON string
9523 * @expose
9524 */
9525 MessagePrototype.encodeJSON = function() {
9526 return JSON.stringify(
9527 cloneRaw(this,
9528 /* binary-as-base64 */ true,
9529 /* longs-as-strings */ true,
9530 this.$type
9531 )
9532 );
9533 };
9534
9535 /**
9536 * Decodes a message from the specified buffer or string.
9537 * @name ProtoBuf.Builder.Message.decode
9538 * @function
9539 * @param {!ByteBuffer|!ArrayBuffer|!Buffer|string} buffer Buffer to decode from
9540 * @param {(number|string)=} length Message length. Defaults to decode all the remainig data.
9541 * @param {string=} enc Encoding if buffer is a string: hex, utf8 (not recommended), defaults to base64
9542 * @return {!ProtoBuf.Builder.Message} Decoded message
9543 * @throws {Error} If the message cannot be decoded or if required fields are missing. The later still
9544 * returns the decoded message with missing fields in the `decoded` property on the error.
9545 * @expose
9546 * @see ProtoBuf.Builder.Message.decode64
9547 * @see ProtoBuf.Builder.Message.decodeHex
9548 */
9549 Message.decode = function(buffer, length, enc) {
9550 if (typeof length === 'string')
9551 enc = length,
9552 length = -1;
9553 if (typeof buffer === 'string')
9554 buffer = ByteBuffer.wrap(buffer, enc ? enc : "base64");
9555 else if (!ByteBuffer.isByteBuffer(buffer))
9556 buffer = ByteBuffer.wrap(buffer); // May throw
9557 var le = buffer.littleEndian;
9558 try {
9559 var msg = T.decode(buffer.LE(), length);
9560 buffer.LE(le);
9561 return msg;
9562 } catch (e) {
9563 buffer.LE(le);
9564 throw(e);
9565 }
9566 };
9567
9568 /**
9569 * Decodes a varint32 length-delimited message from the specified buffer or string.
9570 * @name ProtoBuf.Builder.Message.decodeDelimited
9571 * @function
9572 * @param {!ByteBuffer|!ArrayBuffer|!Buffer|string} buffer Buffer to decode from
9573 * @param {string=} enc Encoding if buffer is a string: hex, utf8 (not recommended), defaults to base64
9574 * @return {ProtoBuf.Builder.Message} Decoded message or `null` if not enough bytes are available yet
9575 * @throws {Error} If the message cannot be decoded or if required fields are missing. The later still
9576 * returns the decoded message with missing fields in the `decoded` property on the error.
9577 * @expose
9578 */
9579 Message.decodeDelimited = function(buffer, enc) {
9580 if (typeof buffer === 'string')
9581 buffer = ByteBuffer.wrap(buffer, enc ? enc : "base64");
9582 else if (!ByteBuffer.isByteBuffer(buffer))
9583 buffer = ByteBuffer.wrap(buffer); // May throw
9584 if (buffer.remaining() < 1)
9585 return null;
9586 var off = buffer.offset,
9587 len = buffer.readVarint32();
9588 if (buffer.remaining() < len) {
9589 buffer.offset = off;
9590 return null;
9591 }
9592 try {
9593 var msg = T.decode(buffer.slice(buffer.offset, buffer.offset + len).LE());
9594 buffer.offset += len;
9595 return msg;
9596 } catch (err) {
9597 buffer.offset += len;
9598 throw err;
9599 }
9600 };
9601
9602 /**
9603 * Decodes the message from the specified base64 encoded string.
9604 * @name ProtoBuf.Builder.Message.decode64
9605 * @function
9606 * @param {string} str String to decode from
9607 * @return {!ProtoBuf.Builder.Message} Decoded message
9608 * @throws {Error} If the message cannot be decoded or if required fields are missing. The later still
9609 * returns the decoded message with missing fields in the `decoded` property on the error.
9610 * @expose
9611 */
9612 Message.decode64 = function(str) {
9613 return Message.decode(str, "base64");
9614 };
9615
9616 /**
9617 * Decodes the message from the specified hex encoded string.
9618 * @name ProtoBuf.Builder.Message.decodeHex
9619 * @function
9620 * @param {string} str String to decode from
9621 * @return {!ProtoBuf.Builder.Message} Decoded message
9622 * @throws {Error} If the message cannot be decoded or if required fields are missing. The later still
9623 * returns the decoded message with missing fields in the `decoded` property on the error.
9624 * @expose
9625 */
9626 Message.decodeHex = function(str) {
9627 return Message.decode(str, "hex");
9628 };
9629
9630 /**
9631 * Decodes the message from a JSON string.
9632 * @name ProtoBuf.Builder.Message.decodeJSON
9633 * @function
9634 * @param {string} str String to decode from
9635 * @return {!ProtoBuf.Builder.Message} Decoded message
9636 * @throws {Error} If the message cannot be decoded or if required fields are
9637 * missing.
9638 * @expose
9639 */
9640 Message.decodeJSON = function(str) {
9641 return new Message(JSON.parse(str));
9642 };
9643
9644 // Utility
9645
9646 /**
9647 * Returns a string representation of this Message.
9648 * @name ProtoBuf.Builder.Message#toString
9649 * @function
9650 * @return {string} String representation as of ".Fully.Qualified.MessageName"
9651 * @expose
9652 */
9653 MessagePrototype.toString = function() {
9654 return T.toString();
9655 };
9656
9657 if (Object.defineProperty)
9658 Object.defineProperty(Message, '$options', { "value": T.buildOpt() }),
9659 Object.defineProperty(MessagePrototype, "$options", { "value": Message["$options"] }),
9660 Object.defineProperty(Message, "$type", { "value": T }),
9661 Object.defineProperty(MessagePrototype, "$type", { "value": T });
9662
9663 return Message;
9664
9665 })(ProtoBuf, this);
9666
9667 // Static enums and prototyped sub-messages / cached collections
9668 this._fields = [];
9669 this._fieldsById = {};
9670 this._fieldsByName = {};
9671 this._oneofsByName = {};
9672 for (var i=0, k=this.children.length, child; i<k; i++) {
9673 child = this.children[i];
9674 if (child instanceof Enum || child instanceof Message || child instanceof Service) {
9675 if (clazz.hasOwnProperty(child.name))
9676 throw Error("Illegal reflect child of "+this.toString(true)+": "+child.toString(true)+" cannot override static property '"+child.name+"'");
9677 clazz[child.name] = child.build();
9678 } else if (child instanceof Message.Field)
9679 child.build(),
9680 this._fields.push(child),
9681 this._fieldsById[child.id] = child,
9682 this._fieldsByName[child.name] = child;
9683 else if (child instanceof Message.OneOf) {
9684 this._oneofsByName[child.name] = child;
9685 }
9686 else if (!(child instanceof Message.OneOf) && !(child instanceof Extension)) // Not built
9687 throw Error("Illegal reflect child of "+this.toString(true)+": "+this.children[i].toString(true));
9688 }
9689
9690 return this.clazz = clazz;
9691 };
9692
9693 /**
9694 * Encodes a runtime message's contents to the specified buffer.
9695 * @param {!ProtoBuf.Builder.Message} message Runtime message to encode
9696 * @param {ByteBuffer} buffer ByteBuffer to write to
9697 * @param {boolean=} noVerify Whether to not verify field values, defaults to `false`
9698 * @return {ByteBuffer} The ByteBuffer for chaining
9699 * @throws {Error} If required fields are missing or the message cannot be encoded for another reason
9700 * @expose
9701 */
9702 MessagePrototype.encode = function(message, buffer, noVerify) {
9703 var fieldMissing = null,
9704 field;
9705 for (var i=0, k=this._fields.length, val; i<k; ++i) {
9706 field = this._fields[i];
9707 val = message[field.name];
9708 if (field.required && val === null) {
9709 if (fieldMissing === null)
9710 fieldMissing = field;
9711 } else
9712 field.encode(noVerify ? val : field.verifyValue(val), buffer, message);
9713 }
9714 if (fieldMissing !== null) {
9715 var err = Error("Missing at least one required field for "+this.toString(true)+": "+fieldMissing);
9716 err["encoded"] = buffer; // Still expose what we got
9717 throw(err);
9718 }
9719 return buffer;
9720 };
9721
9722 /**
9723 * Calculates a runtime message's byte length.
9724 * @param {!ProtoBuf.Builder.Message} message Runtime message to encode
9725 * @returns {number} Byte length
9726 * @throws {Error} If required fields are missing or the message cannot be calculated for another reason
9727 * @expose
9728 */
9729 MessagePrototype.calculate = function(message) {
9730 for (var n=0, i=0, k=this._fields.length, field, val; i<k; ++i) {
9731 field = this._fields[i];
9732 val = message[field.name];
9733 if (field.required && val === null)
9734 throw Error("Missing at least one required field for "+this.toString(true)+": "+field);
9735 else
9736 n += field.calculate(val, message);
9737 }
9738 return n;
9739 };
9740
9741 /**
9742 * Skips all data until the end of the specified group has been reached.
9743 * @param {number} expectedId Expected GROUPEND id
9744 * @param {!ByteBuffer} buf ByteBuffer
9745 * @returns {boolean} `true` if a value as been skipped, `false` if the end has been reached
9746 * @throws {Error} If it wasn't possible to find the end of the group (buffer overrun or end tag mismatch)
9747 * @inner
9748 */
9749 function skipTillGroupEnd(expectedId, buf) {
9750 var tag = buf.readVarint32(), // Throws on OOB
9751 wireType = tag & 0x07,
9752 id = tag >>> 3;
9753 switch (wireType) {
9754 case ProtoBuf.WIRE_TYPES.VARINT:
9755 do tag = buf.readUint8();
9756 while ((tag & 0x80) === 0x80);
9757 break;
9758 case ProtoBuf.WIRE_TYPES.BITS64:
9759 buf.offset += 8;
9760 break;
9761 case ProtoBuf.WIRE_TYPES.LDELIM:
9762 tag = buf.readVarint32(); // reads the varint
9763 buf.offset += tag; // skips n bytes
9764 break;
9765 case ProtoBuf.WIRE_TYPES.STARTGROUP:
9766 skipTillGroupEnd(id, buf);
9767 break;
9768 case ProtoBuf.WIRE_TYPES.ENDGROUP:
9769 if (id === expectedId)
9770 return false;
9771 else
9772 throw Error("Illegal GROUPEND after unknown group: "+id+" ("+expectedId+" expected)");
9773 case ProtoBuf.WIRE_TYPES.BITS32:
9774 buf.offset += 4;
9775 break;
9776 default:
9777 throw Error("Illegal wire type in unknown group "+expectedId+": "+wireType);
9778 }
9779 return true;
9780 }
9781
9782 /**
9783 * Decodes an encoded message and returns the decoded message.
9784 * @param {ByteBuffer} buffer ByteBuffer to decode from
9785 * @param {number=} length Message length. Defaults to decode all remaining data.
9786 * @param {number=} expectedGroupEndId Expected GROUPEND id if this is a legacy group
9787 * @return {ProtoBuf.Builder.Message} Decoded message
9788 * @throws {Error} If the message cannot be decoded
9789 * @expose
9790 */
9791 MessagePrototype.decode = function(buffer, length, expectedGroupEndId) {
9792 if (typeof length !== 'number')
9793 length = -1;
9794 var start = buffer.offset,
9795 msg = new (this.clazz)(),
9796 tag, wireType, id, field;
9797 while (buffer.offset < start+length || (length === -1 && buffer.remaining() > 0)) {
9798 tag = buffer.readVarint32();
9799 wireType = tag & 0x07;
9800 id = tag >>> 3;
9801 if (wireType === ProtoBuf.WIRE_TYPES.ENDGROUP) {
9802 if (id !== expectedGroupEndId)
9803 throw Error("Illegal group end indicator for "+this.toString(true)+": "+id+" ("+(expectedGroupEndId ? expectedGroupEndId+" expected" : "not a group")+")");
9804 break;
9805 }
9806 if (!(field = this._fieldsById[id])) {
9807 // "messages created by your new code can be parsed by your old code: old binaries simply ignore the new field when parsing."
9808 switch (wireType) {
9809 case ProtoBuf.WIRE_TYPES.VARINT:
9810 buffer.readVarint32();
9811 break;
9812 case ProtoBuf.WIRE_TYPES.BITS32:
9813 buffer.offset += 4;
9814 break;
9815 case ProtoBuf.WIRE_TYPES.BITS64:
9816 buffer.offset += 8;
9817 break;
9818 case ProtoBuf.WIRE_TYPES.LDELIM:
9819 var len = buffer.readVarint32();
9820 buffer.offset += len;
9821 break;
9822 case ProtoBuf.WIRE_TYPES.STARTGROUP:
9823 while (skipTillGroupEnd(id, buffer)) {}
9824 break;
9825 default:
9826 throw Error("Illegal wire type for unknown field "+id+" in "+this.toString(true)+"#decode: "+wireType);
9827 }
9828 continue;
9829 }
9830 if (field.repeated && !field.options["packed"]) {
9831 msg[field.name].push(field.decode(wireType, buffer));
9832 } else if (field.map) {
9833 var keyval = field.decode(wireType, buffer);
9834 msg[field.name].set(keyval[0], keyval[1]);
9835 } else {
9836 msg[field.name] = field.decode(wireType, buffer);
9837 if (field.oneof) { // Field is part of an OneOf (not a virtual OneOf field)
9838 var currentField = msg[field.oneof.name]; // Virtual field references currently set field
9839 if (currentField !== null && currentField !== field.name)
9840 msg[currentField] = null; // Clear currently set field
9841 msg[field.oneof.name] = field.name; // Point virtual field at this field
9842 }
9843 }
9844 }
9845
9846 // Check if all required fields are present and set default values for optional fields that are not
9847 for (var i=0, k=this._fields.length; i<k; ++i) {
9848 field = this._fields[i];
9849 if (msg[field.name] === null) {
9850 if (this.syntax === "proto3") { // Proto3 sets default values by specification
9851 msg[field.name] = field.defaultValue;
9852 } else if (field.required) {
9853 var err = Error("Missing at least one required field for " + this.toString(true) + ": " + field.name);
9854 err["decoded"] = msg; // Still expose what we got
9855 throw(err);
9856 } else if (ProtoBuf.populateDefaults && field.defaultValue !== null)
9857 msg[field.name] = field.defaultValue;
9858 }
9859 }
9860 return msg;
9861 };
9862
9863 /**
9864 * @alias ProtoBuf.Reflect.Message
9865 * @expose
9866 */
9867 Reflect.Message = Message;
9868
9869 /**
9870 * Constructs a new Message Field.
9871 * @exports ProtoBuf.Reflect.Message.Field
9872 * @param {!ProtoBuf.Builder} builder Builder reference
9873 * @param {!ProtoBuf.Reflect.Message} message Message reference
9874 * @param {string} rule Rule, one of requried, optional, repeated
9875 * @param {string?} keytype Key data type, if any.
9876 * @param {string} type Data type, e.g. int32
9877 * @param {string} name Field name
9878 * @param {number} id Unique field id
9879 * @param {Object.<string,*>=} options Options
9880 * @param {!ProtoBuf.Reflect.Message.OneOf=} oneof Enclosing OneOf
9881 * @param {string?} syntax The syntax level of this definition (e.g., proto3)
9882 * @constructor
9883 * @extends ProtoBuf.Reflect.T
9884 */
9885 var Field = function(builder, message, rule, keytype, type, name, id, options, oneof, syntax) {
9886 T.call(this, builder, message, name);
9887
9888 /**
9889 * @override
9890 */
9891 this.className = "Message.Field";
9892
9893 /**
9894 * Message field required flag.
9895 * @type {boolean}
9896 * @expose
9897 */
9898 this.required = rule === "required";
9899
9900 /**
9901 * Message field repeated flag.
9902 * @type {boolean}
9903 * @expose
9904 */
9905 this.repeated = rule === "repeated";
9906
9907 /**
9908 * Message field map flag.
9909 * @type {boolean}
9910 * @expose
9911 */
9912 this.map = rule === "map";
9913
9914 /**
9915 * Message field key type. Type reference string if unresolved, protobuf
9916 * type if resolved. Valid only if this.map === true, null otherwise.
9917 * @type {string|{name: string, wireType: number}|null}
9918 * @expose
9919 */
9920 this.keyType = keytype || null;
9921
9922 /**
9923 * Message field type. Type reference string if unresolved, protobuf type if
9924 * resolved. In a map field, this is the value type.
9925 * @type {string|{name: string, wireType: number}}
9926 * @expose
9927 */
9928 this.type = type;
9929
9930 /**
9931 * Resolved type reference inside the global namespace.
9932 * @type {ProtoBuf.Reflect.T|null}
9933 * @expose
9934 */
9935 this.resolvedType = null;
9936
9937 /**
9938 * Unique message field id.
9939 * @type {number}
9940 * @expose
9941 */
9942 this.id = id;
9943
9944 /**
9945 * Message field options.
9946 * @type {!Object.<string,*>}
9947 * @dict
9948 * @expose
9949 */
9950 this.options = options || {};
9951
9952 /**
9953 * Default value.
9954 * @type {*}
9955 * @expose
9956 */
9957 this.defaultValue = null;
9958
9959 /**
9960 * Enclosing OneOf.
9961 * @type {?ProtoBuf.Reflect.Message.OneOf}
9962 * @expose
9963 */
9964 this.oneof = oneof || null;
9965
9966 /**
9967 * Syntax level of this definition (e.g., proto3).
9968 * @type {string}
9969 * @expose
9970 */
9971 this.syntax = syntax || 'proto2';
9972
9973 /**
9974 * Original field name.
9975 * @type {string}
9976 * @expose
9977 */
9978 this.originalName = this.name; // Used to revert camelcase transformation on naming collisions
9979
9980 /**
9981 * Element implementation. Created in build() after types are resolved.
9982 * @type {ProtoBuf.Element}
9983 * @expose
9984 */
9985 this.element = null;
9986
9987 /**
9988 * Key element implementation, for map fields. Created in build() after
9989 * types are resolved.
9990 * @type {ProtoBuf.Element}
9991 * @expose
9992 */
9993 this.keyElement = null;
9994
9995 // Convert field names to camel case notation if the override is set
9996 if (this.builder.options['convertFieldsToCamelCase'] && !(this instanceof Message.ExtensionField))
9997 this.name = ProtoBuf.Util.toCamelCase(this.name);
9998 };
9999
10000 /**
10001 * @alias ProtoBuf.Reflect.Message.Field.prototype
10002 * @inner
10003 */
10004 var FieldPrototype = Field.prototype = Object.create(T.prototype);
10005
10006 /**
10007 * Builds the field.
10008 * @override
10009 * @expose
10010 */
10011 FieldPrototype.build = function() {
10012 this.element = new Element(this.type, this.resolvedType, false, this.syntax, this.name);
10013 if (this.map)
10014 this.keyElement = new Element(this.keyType, undefined, true, this.syntax, this.name);
10015
10016 // In proto3, fields do not have field presence, and every field is set to
10017 // its type's default value ("", 0, 0.0, or false).
10018 if (this.syntax === 'proto3' && !this.repeated && !this.map)
10019 this.defaultValue = Element.defaultFieldValue(this.type);
10020
10021 // Otherwise, default values are present when explicitly specified
10022 else if (typeof this.options['default'] !== 'undefined')
10023 this.defaultValue = this.verifyValue(this.options['default']);
10024 };
10025
10026 /**
10027 * Checks if the given value can be set for this field.
10028 * @param {*} value Value to check
10029 * @param {boolean=} skipRepeated Whether to skip the repeated value check or not. Defaults to false.
10030 * @return {*} Verified, maybe adjusted, value
10031 * @throws {Error} If the value cannot be set for this field
10032 * @expose
10033 */
10034 FieldPrototype.verifyValue = function(value, skipRepeated) {
10035 skipRepeated = skipRepeated || false;
10036 var self = this;
10037 function fail(val, msg) {
10038 throw Error("Illegal value for "+self.toString(true)+" of type "+self.type.name+": "+val+" ("+msg+")");
10039 }
10040 if (value === null) { // NULL values for optional fields
10041 if (this.required)
10042 fail(typeof value, "required");
10043 if (this.syntax === 'proto3' && this.type !== ProtoBuf.TYPES["message"])
10044 fail(typeof value, "proto3 field without field presence cannot be null");
10045 return null;
10046 }
10047 var i;
10048 if (this.repeated && !skipRepeated) { // Repeated values as arrays
10049 if (!Array.isArray(value))
10050 value = [value];
10051 var res = [];
10052 for (i=0; i<value.length; i++)
10053 res.push(this.element.verifyValue(value[i]));
10054 return res;
10055 }
10056 if (this.map && !skipRepeated) { // Map values as objects
10057 if (!(value instanceof ProtoBuf.Map)) {
10058 // If not already a Map, attempt to convert.
10059 if (!(value instanceof Object)) {
10060 fail(typeof value,
10061 "expected ProtoBuf.Map or raw object for map field");
10062 }
10063 return new ProtoBuf.Map(this, value);
10064 } else {
10065 return value;
10066 }
10067 }
10068 // All non-repeated fields expect no array
10069 if (!this.repeated && Array.isArray(value))
10070 fail(typeof value, "no array expected");
10071
10072 return this.element.verifyValue(value);
10073 };
10074
10075 /**
10076 * Determines whether the field will have a presence on the wire given its
10077 * value.
10078 * @param {*} value Verified field value
10079 * @param {!ProtoBuf.Builder.Message} message Runtime message
10080 * @return {boolean} Whether the field will be present on the wire
10081 */
10082 FieldPrototype.hasWirePresence = function(value, message) {
10083 if (this.syntax !== 'proto3')
10084 return (value !== null);
10085 if (this.oneof && message[this.oneof.name] === this.name)
10086 return true;
10087 switch (this.type) {
10088 case ProtoBuf.TYPES["int32"]:
10089 case ProtoBuf.TYPES["sint32"]:
10090 case ProtoBuf.TYPES["sfixed32"]:
10091 case ProtoBuf.TYPES["uint32"]:
10092 case ProtoBuf.TYPES["fixed32"]:
10093 return value !== 0;
10094
10095 case ProtoBuf.TYPES["int64"]:
10096 case ProtoBuf.TYPES["sint64"]:
10097 case ProtoBuf.TYPES["sfixed64"]:
10098 case ProtoBuf.TYPES["uint64"]:
10099 case ProtoBuf.TYPES["fixed64"]:
10100 return value.low !== 0 || value.high !== 0;
10101
10102 case ProtoBuf.TYPES["bool"]:
10103 return value;
10104
10105 case ProtoBuf.TYPES["float"]:
10106 case ProtoBuf.TYPES["double"]:
10107 return value !== 0.0;
10108
10109 case ProtoBuf.TYPES["string"]:
10110 return value.length > 0;
10111
10112 case ProtoBuf.TYPES["bytes"]:
10113 return value.remaining() > 0;
10114
10115 case ProtoBuf.TYPES["enum"]:
10116 return value !== 0;
10117
10118 case ProtoBuf.TYPES["message"]:
10119 return value !== null;
10120 default:
10121 return true;
10122 }
10123 };
10124
10125 /**
10126 * Encodes the specified field value to the specified buffer.
10127 * @param {*} value Verified field value
10128 * @param {ByteBuffer} buffer ByteBuffer to encode to
10129 * @param {!ProtoBuf.Builder.Message} message Runtime message
10130 * @return {ByteBuffer} The ByteBuffer for chaining
10131 * @throws {Error} If the field cannot be encoded
10132 * @expose
10133 */
10134 FieldPrototype.encode = function(value, buffer, message) {
10135 if (this.type === null || typeof this.type !== 'object')
10136 throw Error("[INTERNAL] Unresolved type in "+this.toString(true)+": "+this.type);
10137 if (value === null || (this.repeated && value.length == 0))
10138 return buffer; // Optional omitted
10139 try {
10140 if (this.repeated) {
10141 var i;
10142 // "Only repeated fields of primitive numeric types (types which use the varint, 32-bit, or 64-bit wire
10143 // types) can be declared 'packed'."
10144 if (this.options["packed"] && ProtoBuf.PACKABLE_WIRE_TYPES.indexOf(this.type.wireType) >= 0) {
10145 // "All of the elements of the field are packed into a single key-value pair with wire type 2
10146 // (length-delimited). Each element is encoded the same way it would be normally, except without a
10147 // tag preceding it."
10148 buffer.writeVarint32((this.id << 3) | ProtoBuf.WIRE_TYPES.LDELIM);
10149 buffer.ensureCapacity(buffer.offset += 1); // We do not know the length yet, so let's assume a varint of length 1
10150 var start = buffer.offset; // Remember where the contents begin
10151 for (i=0; i<value.length; i++)
10152 this.element.encodeValue(this.id, value[i], buffer);
10153 var len = buffer.offset-start,
10154 varintLen = ByteBuffer.calculateVarint32(len);
10155 if (varintLen > 1) { // We need to move the contents
10156 var contents = buffer.slice(start, buffer.offset);
10157 start += varintLen-1;
10158 buffer.offset = start;
10159 buffer.append(contents);
10160 }
10161 buffer.writeVarint32(len, start-varintLen);
10162 } else {
10163 // "If your message definition has repeated elements (without the [packed=true] option), the encoded
10164 // message has zero or more key-value pairs with the same tag number"
10165 for (i=0; i<value.length; i++)
10166 buffer.writeVarint32((this.id << 3) | this.type.wireType),
10167 this.element.encodeValue(this.id, value[i], buffer);
10168 }
10169 } else if (this.map) {
10170 // Write out each map entry as a submessage.
10171 value.forEach(function(val, key, m) {
10172 // Compute the length of the submessage (key, val) pair.
10173 var length =
10174 ByteBuffer.calculateVarint32((1 << 3) | this.keyType.wireType) +
10175 this.keyElement.calculateLength(1, key) +
10176 ByteBuffer.calculateVarint32((2 << 3) | this.type.wireType) +
10177 this.element.calculateLength(2, val);
10178
10179 // Submessage with wire type of length-delimited.
10180 buffer.writeVarint32((this.id << 3) | ProtoBuf.WIRE_TYPES.LDELIM);
10181 buffer.writeVarint32(length);
10182
10183 // Write out the key and val.
10184 buffer.writeVarint32((1 << 3) | this.keyType.wireType);
10185 this.keyElement.encodeValue(1, key, buffer);
10186 buffer.writeVarint32((2 << 3) | this.type.wireType);
10187 this.element.encodeValue(2, val, buffer);
10188 }, this);
10189 } else {
10190 if (this.hasWirePresence(value, message)) {
10191 buffer.writeVarint32((this.id << 3) | this.type.wireType);
10192 this.element.encodeValue(this.id, value, buffer);
10193 }
10194 }
10195 } catch (e) {
10196 throw Error("Illegal value for "+this.toString(true)+": "+value+" ("+e+")");
10197 }
10198 return buffer;
10199 };
10200
10201 /**
10202 * Calculates the length of this field's value on the network level.
10203 * @param {*} value Field value
10204 * @param {!ProtoBuf.Builder.Message} message Runtime message
10205 * @returns {number} Byte length
10206 * @expose
10207 */
10208 FieldPrototype.calculate = function(value, message) {
10209 value = this.verifyValue(value); // May throw
10210 if (this.type === null || typeof this.type !== 'object')
10211 throw Error("[INTERNAL] Unresolved type in "+this.toString(true)+": "+this.type);
10212 if (value === null || (this.repeated && value.length == 0))
10213 return 0; // Optional omitted
10214 var n = 0;
10215 try {
10216 if (this.repeated) {
10217 var i, ni;
10218 if (this.options["packed"] && ProtoBuf.PACKABLE_WIRE_TYPES.indexOf(this.type.wireType) >= 0) {
10219 n += ByteBuffer.calculateVarint32((this.id << 3) | ProtoBuf.WIRE_TYPES.LDELIM);
10220 ni = 0;
10221 for (i=0; i<value.length; i++)
10222 ni += this.element.calculateLength(this.id, value[i]);
10223 n += ByteBuffer.calculateVarint32(ni);
10224 n += ni;
10225 } else {
10226 for (i=0; i<value.length; i++)
10227 n += ByteBuffer.calculateVarint32((this.id << 3) | this.type.wireType),
10228 n += this.element.calculateLength(this.id, value[i]);
10229 }
10230 } else if (this.map) {
10231 // Each map entry becomes a submessage.
10232 value.forEach(function(val, key, m) {
10233 // Compute the length of the submessage (key, val) pair.
10234 var length =
10235 ByteBuffer.calculateVarint32((1 << 3) | this.keyType.wireType) +
10236 this.keyElement.calculateLength(1, key) +
10237 ByteBuffer.calculateVarint32((2 << 3) | this.type.wireType) +
10238 this.element.calculateLength(2, val);
10239
10240 n += ByteBuffer.calculateVarint32((this.id << 3) | ProtoBuf.WIRE_TYPES.LDELIM);
10241 n += ByteBuffer.calculateVarint32(length);
10242 n += length;
10243 }, this);
10244 } else {
10245 if (this.hasWirePresence(value, message)) {
10246 n += ByteBuffer.calculateVarint32((this.id << 3) | this.type.wireType);
10247 n += this.element.calculateLength(this.id, value);
10248 }
10249 }
10250 } catch (e) {
10251 throw Error("Illegal value for "+this.toString(true)+": "+value+" ("+e+")");
10252 }
10253 return n;
10254 };
10255
10256 /**
10257 * Decode the field value from the specified buffer.
10258 * @param {number} wireType Leading wire type
10259 * @param {ByteBuffer} buffer ByteBuffer to decode from
10260 * @param {boolean=} skipRepeated Whether to skip the repeated check or not. Defaults to false.
10261 * @return {*} Decoded value: array for packed repeated fields, [key, value] for
10262 * map fields, or an individual value otherwise.
10263 * @throws {Error} If the field cannot be decoded
10264 * @expose
10265 */
10266 FieldPrototype.decode = function(wireType, buffer, skipRepeated) {
10267 var value, nBytes;
10268
10269 // We expect wireType to match the underlying type's wireType unless we see
10270 // a packed repeated field, or unless this is a map field.
10271 var wireTypeOK =
10272 (!this.map && wireType == this.type.wireType) ||
10273 (!skipRepeated && this.repeated && this.options["packed"] &&
10274 wireType == ProtoBuf.WIRE_TYPES.LDELIM) ||
10275 (this.map && wireType == ProtoBuf.WIRE_TYPES.LDELIM);
10276 if (!wireTypeOK)
10277 throw Error("Illegal wire type for field "+this.toString(true)+": "+wireType+" ("+this.type.wireType+" expected)");
10278
10279 // Handle packed repeated fields.
10280 if (wireType == ProtoBuf.WIRE_TYPES.LDELIM && this.repeated && this.options["packed"] && ProtoBuf.PACKABLE_WIRE_TYPES.indexOf(this.type.wireType) >= 0) {
10281 if (!skipRepeated) {
10282 nBytes = buffer.readVarint32();
10283 nBytes = buffer.offset + nBytes; // Limit
10284 var values = [];
10285 while (buffer.offset < nBytes)
10286 values.push(this.decode(this.type.wireType, buffer, true));
10287 return values;
10288 }
10289 // Read the next value otherwise...
10290 }
10291
10292 // Handle maps.
10293 if (this.map) {
10294 // Read one (key, value) submessage, and return [key, value]
10295 var key = Element.defaultFieldValue(this.keyType);
10296 value = Element.defaultFieldValue(this.type);
10297
10298 // Read the length
10299 nBytes = buffer.readVarint32();
10300 if (buffer.remaining() < nBytes)
10301 throw Error("Illegal number of bytes for "+this.toString(true)+": "+nBytes+" required but got only "+buffer.remaining());
10302
10303 // Get a sub-buffer of this key/value submessage
10304 var msgbuf = buffer.clone();
10305 msgbuf.limit = msgbuf.offset + nBytes;
10306 buffer.offset += nBytes;
10307
10308 while (msgbuf.remaining() > 0) {
10309 var tag = msgbuf.readVarint32();
10310 wireType = tag & 0x07;
10311 var id = tag >>> 3;
10312 if (id === 1) {
10313 key = this.keyElement.decode(msgbuf, wireType, id);
10314 } else if (id === 2) {
10315 value = this.element.decode(msgbuf, wireType, id);
10316 } else {
10317 throw Error("Unexpected tag in map field key/value submessage");
10318 }
10319 }
10320
10321 return [key, value];
10322 }
10323
10324 // Handle singular and non-packed repeated field values.
10325 return this.element.decode(buffer, wireType, this.id);
10326 };
10327
10328 /**
10329 * @alias ProtoBuf.Reflect.Message.Field
10330 * @expose
10331 */
10332 Reflect.Message.Field = Field;
10333
10334 /**
10335 * Constructs a new Message ExtensionField.
10336 * @exports ProtoBuf.Reflect.Message.ExtensionField
10337 * @param {!ProtoBuf.Builder} builder Builder reference
10338 * @param {!ProtoBuf.Reflect.Message} message Message reference
10339 * @param {string} rule Rule, one of requried, optional, repeated
10340 * @param {string} type Data type, e.g. int32
10341 * @param {string} name Field name
10342 * @param {number} id Unique field id
10343 * @param {!Object.<string,*>=} options Options
10344 * @constructor
10345 * @extends ProtoBuf.Reflect.Message.Field
10346 */
10347 var ExtensionField = function(builder, message, rule, type, name, id, options) {
10348 Field.call(this, builder, message, rule, /* keytype = */ null, type, name, id, options);
10349
10350 /**
10351 * Extension reference.
10352 * @type {!ProtoBuf.Reflect.Extension}
10353 * @expose
10354 */
10355 this.extension;
10356 };
10357
10358 // Extends Field
10359 ExtensionField.prototype = Object.create(Field.prototype);
10360
10361 /**
10362 * @alias ProtoBuf.Reflect.Message.ExtensionField
10363 * @expose
10364 */
10365 Reflect.Message.ExtensionField = ExtensionField;
10366
10367 /**
10368 * Constructs a new Message OneOf.
10369 * @exports ProtoBuf.Reflect.Message.OneOf
10370 * @param {!ProtoBuf.Builder} builder Builder reference
10371 * @param {!ProtoBuf.Reflect.Message} message Message reference
10372 * @param {string} name OneOf name
10373 * @constructor
10374 * @extends ProtoBuf.Reflect.T
10375 */
10376 var OneOf = function(builder, message, name) {
10377 T.call(this, builder, message, name);
10378
10379 /**
10380 * Enclosed fields.
10381 * @type {!Array.<!ProtoBuf.Reflect.Message.Field>}
10382 * @expose
10383 */
10384 this.fields = [];
10385 };
10386
10387 /**
10388 * @alias ProtoBuf.Reflect.Message.OneOf
10389 * @expose
10390 */
10391 Reflect.Message.OneOf = OneOf;
10392
10393 /**
10394 * Constructs a new Enum.
10395 * @exports ProtoBuf.Reflect.Enum
10396 * @param {!ProtoBuf.Builder} builder Builder reference
10397 * @param {!ProtoBuf.Reflect.T} parent Parent Reflect object
10398 * @param {string} name Enum name
10399 * @param {Object.<string,*>=} options Enum options
10400 * @param {string?} syntax The syntax level (e.g., proto3)
10401 * @constructor
10402 * @extends ProtoBuf.Reflect.Namespace
10403 */
10404 var Enum = function(builder, parent, name, options, syntax) {
10405 Namespace.call(this, builder, parent, name, options, syntax);
10406
10407 /**
10408 * @override
10409 */
10410 this.className = "Enum";
10411
10412 /**
10413 * Runtime enum object.
10414 * @type {Object.<string,number>|null}
10415 * @expose
10416 */
10417 this.object = null;
10418 };
10419
10420 /**
10421 * Gets the string name of an enum value.
10422 * @param {!ProtoBuf.Builder.Enum} enm Runtime enum
10423 * @param {number} value Enum value
10424 * @returns {?string} Name or `null` if not present
10425 * @expose
10426 */
10427 Enum.getName = function(enm, value) {
10428 var keys = Object.keys(enm);
10429 for (var i=0, key; i<keys.length; ++i)
10430 if (enm[key = keys[i]] === value)
10431 return key;
10432 return null;
10433 };
10434
10435 /**
10436 * @alias ProtoBuf.Reflect.Enum.prototype
10437 * @inner
10438 */
10439 var EnumPrototype = Enum.prototype = Object.create(Namespace.prototype);
10440
10441 /**
10442 * Builds this enum and returns the runtime counterpart.
10443 * @param {boolean} rebuild Whether to rebuild or not, defaults to false
10444 * @returns {!Object.<string,number>}
10445 * @expose
10446 */
10447 EnumPrototype.build = function(rebuild) {
10448 if (this.object && !rebuild)
10449 return this.object;
10450 var enm = new ProtoBuf.Builder.Enum(),
10451 values = this.getChildren(Enum.Value);
10452 for (var i=0, k=values.length; i<k; ++i)
10453 enm[values[i]['name']] = values[i]['id'];
10454 if (Object.defineProperty)
10455 Object.defineProperty(enm, '$options', {
10456 "value": this.buildOpt(),
10457 "enumerable": false
10458 });
10459 return this.object = enm;
10460 };
10461
10462 /**
10463 * @alias ProtoBuf.Reflect.Enum
10464 * @expose
10465 */
10466 Reflect.Enum = Enum;
10467
10468 /**
10469 * Constructs a new Enum Value.
10470 * @exports ProtoBuf.Reflect.Enum.Value
10471 * @param {!ProtoBuf.Builder} builder Builder reference
10472 * @param {!ProtoBuf.Reflect.Enum} enm Enum reference
10473 * @param {string} name Field name
10474 * @param {number} id Unique field id
10475 * @constructor
10476 * @extends ProtoBuf.Reflect.T
10477 */
10478 var Value = function(builder, enm, name, id) {
10479 T.call(this, builder, enm, name);
10480
10481 /**
10482 * @override
10483 */
10484 this.className = "Enum.Value";
10485
10486 /**
10487 * Unique enum value id.
10488 * @type {number}
10489 * @expose
10490 */
10491 this.id = id;
10492 };
10493
10494 // Extends T
10495 Value.prototype = Object.create(T.prototype);
10496
10497 /**
10498 * @alias ProtoBuf.Reflect.Enum.Value
10499 * @expose
10500 */
10501 Reflect.Enum.Value = Value;
10502
10503 /**
10504 * An extension (field).
10505 * @exports ProtoBuf.Reflect.Extension
10506 * @constructor
10507 * @param {!ProtoBuf.Builder} builder Builder reference
10508 * @param {!ProtoBuf.Reflect.T} parent Parent object
10509 * @param {string} name Object name
10510 * @param {!ProtoBuf.Reflect.Message.Field} field Extension field
10511 */
10512 var Extension = function(builder, parent, name, field) {
10513 T.call(this, builder, parent, name);
10514
10515 /**
10516 * Extended message field.
10517 * @type {!ProtoBuf.Reflect.Message.Field}
10518 * @expose
10519 */
10520 this.field = field;
10521 };
10522
10523 // Extends T
10524 Extension.prototype = Object.create(T.prototype);
10525
10526 /**
10527 * @alias ProtoBuf.Reflect.Extension
10528 * @expose
10529 */
10530 Reflect.Extension = Extension;
10531
10532 /**
10533 * Constructs a new Service.
10534 * @exports ProtoBuf.Reflect.Service
10535 * @param {!ProtoBuf.Builder} builder Builder reference
10536 * @param {!ProtoBuf.Reflect.Namespace} root Root
10537 * @param {string} name Service name
10538 * @param {Object.<string,*>=} options Options
10539 * @constructor
10540 * @extends ProtoBuf.Reflect.Namespace
10541 */
10542 var Service = function(builder, root, name, options) {
10543 Namespace.call(this, builder, root, name, options);
10544
10545 /**
10546 * @override
10547 */
10548 this.className = "Service";
10549
10550 /**
10551 * Built runtime service class.
10552 * @type {?function(new:ProtoBuf.Builder.Service)}
10553 */
10554 this.clazz = null;
10555 };
10556
10557 /**
10558 * @alias ProtoBuf.Reflect.Service.prototype
10559 * @inner
10560 */
10561 var ServicePrototype = Service.prototype = Object.create(Namespace.prototype);
10562
10563 /**
10564 * Builds the service and returns the runtime counterpart, which is a fully functional class.
10565 * @see ProtoBuf.Builder.Service
10566 * @param {boolean=} rebuild Whether to rebuild or not
10567 * @return {Function} Service class
10568 * @throws {Error} If the message cannot be built
10569 * @expose
10570 */
10571 ServicePrototype.build = function(rebuild) {
10572 if (this.clazz && !rebuild)
10573 return this.clazz;
10574
10575 // Create the runtime Service class in its own scope
10576 return this.clazz = (function(ProtoBuf, T) {
10577
10578 /**
10579 * Constructs a new runtime Service.
10580 * @name ProtoBuf.Builder.Service
10581 * @param {function(string, ProtoBuf.Builder.Message, function(Error, ProtoBuf.Builder.Message=))=} rpcImpl RPC implementation receiving the method name and the message
10582 * @class Barebone of all runtime services.
10583 * @constructor
10584 * @throws {Error} If the service cannot be created
10585 */
10586 var Service = function(rpcImpl) {
10587 ProtoBuf.Builder.Service.call(this);
10588
10589 /**
10590 * Service implementation.
10591 * @name ProtoBuf.Builder.Service#rpcImpl
10592 * @type {!function(string, ProtoBuf.Builder.Message, function(Error, ProtoBuf.Builder.Message=))}
10593 * @expose
10594 */
10595 this.rpcImpl = rpcImpl || function(name, msg, callback) {
10596 // This is what a user has to implement: A function receiving the method name, the actual message to
10597 // send (type checked) and the callback that's either provided with the error as its first
10598 // argument or null and the actual response message.
10599 setTimeout(callback.bind(this, Error("Not implemented, see: https://github.com/dcodeIO/ProtoBuf.js/wiki/Services")), 0); // Must be async!
10600 };
10601 };
10602
10603 /**
10604 * @alias ProtoBuf.Builder.Service.prototype
10605 * @inner
10606 */
10607 var ServicePrototype = Service.prototype = Object.create(ProtoBuf.Builder.Service.prototype);
10608
10609 /**
10610 * Asynchronously performs an RPC call using the given RPC implementation.
10611 * @name ProtoBuf.Builder.Service.[Method]
10612 * @function
10613 * @param {!function(string, ProtoBuf.Builder.Message, function(Error, ProtoBuf.Builder.Message=))} rpcImpl RPC implementation
10614 * @param {ProtoBuf.Builder.Message} req Request
10615 * @param {function(Error, (ProtoBuf.Builder.Message|ByteBuffer|Buffer|string)=)} callback Callback receiving
10616 * the error if any and the response either as a pre-parsed message or as its raw bytes
10617 * @abstract
10618 */
10619
10620 /**
10621 * Asynchronously performs an RPC call using the instance's RPC implementation.
10622 * @name ProtoBuf.Builder.Service#[Method]
10623 * @function
10624 * @param {ProtoBuf.Builder.Message} req Request
10625 * @param {function(Error, (ProtoBuf.Builder.Message|ByteBuffer|Buffer|string)=)} callback Callback receiving
10626 * the error if any and the response either as a pre-parsed message or as its raw bytes
10627 * @abstract
10628 */
10629
10630 var rpc = T.getChildren(ProtoBuf.Reflect.Service.RPCMethod);
10631 for (var i=0; i<rpc.length; i++) {
10632 (function(method) {
10633
10634 // service#Method(message, callback)
10635 ServicePrototype[method.name] = function(req, callback) {
10636 try {
10637 try {
10638 // If given as a buffer, decode the request. Will throw a TypeError if not a valid buffer.
10639 req = method.resolvedRequestType.clazz.decode(ByteBuffer.wrap(req));
10640 } catch (err) {
10641 if (!(err instanceof TypeError))
10642 throw err;
10643 }
10644 if (req === null || typeof req !== 'object')
10645 throw Error("Illegal arguments");
10646 if (!(req instanceof method.resolvedRequestType.clazz))
10647 req = new method.resolvedRequestType.clazz(req);
10648 this.rpcImpl(method.fqn(), req, function(err, res) { // Assumes that this is properly async
10649 if (err) {
10650 callback(err);
10651 return;
10652 }
10653 // Coalesce to empty string when service response has empty content
10654 if (res === null)
10655 res = '';
10656 try { res = method.resolvedResponseType.clazz.decode(res); } catch (notABuffer) {}
10657 if (!res || !(res instanceof method.resolvedResponseType.clazz)) {
10658 callback(Error("Illegal response type received in service method "+ T.name+"#"+method.name));
10659 return;
10660 }
10661 callback(null, res);
10662 });
10663 } catch (err) {
10664 setTimeout(callback.bind(this, err), 0);
10665 }
10666 };
10667
10668 // Service.Method(rpcImpl, message, callback)
10669 Service[method.name] = function(rpcImpl, req, callback) {
10670 new Service(rpcImpl)[method.name](req, callback);
10671 };
10672
10673 if (Object.defineProperty)
10674 Object.defineProperty(Service[method.name], "$options", { "value": method.buildOpt() }),
10675 Object.defineProperty(ServicePrototype[method.name], "$options", { "value": Service[method.name]["$options"] });
10676 })(rpc[i]);
10677 }
10678
10679 if (Object.defineProperty)
10680 Object.defineProperty(Service, "$options", { "value": T.buildOpt() }),
10681 Object.defineProperty(ServicePrototype, "$options", { "value": Service["$options"] }),
10682 Object.defineProperty(Service, "$type", { "value": T }),
10683 Object.defineProperty(ServicePrototype, "$type", { "value": T });
10684
10685 return Service;
10686
10687 })(ProtoBuf, this);
10688 };
10689
10690 /**
10691 * @alias ProtoBuf.Reflect.Service
10692 * @expose
10693 */
10694 Reflect.Service = Service;
10695
10696 /**
10697 * Abstract service method.
10698 * @exports ProtoBuf.Reflect.Service.Method
10699 * @param {!ProtoBuf.Builder} builder Builder reference
10700 * @param {!ProtoBuf.Reflect.Service} svc Service
10701 * @param {string} name Method name
10702 * @param {Object.<string,*>=} options Options
10703 * @constructor
10704 * @extends ProtoBuf.Reflect.T
10705 */
10706 var Method = function(builder, svc, name, options) {
10707 T.call(this, builder, svc, name);
10708
10709 /**
10710 * @override
10711 */
10712 this.className = "Service.Method";
10713
10714 /**
10715 * Options.
10716 * @type {Object.<string, *>}
10717 * @expose
10718 */
10719 this.options = options || {};
10720 };
10721
10722 /**
10723 * @alias ProtoBuf.Reflect.Service.Method.prototype
10724 * @inner
10725 */
10726 var MethodPrototype = Method.prototype = Object.create(T.prototype);
10727
10728 /**
10729 * Builds the method's '$options' property.
10730 * @name ProtoBuf.Reflect.Service.Method#buildOpt
10731 * @function
10732 * @return {Object.<string,*>}
10733 */
10734 MethodPrototype.buildOpt = NamespacePrototype.buildOpt;
10735
10736 /**
10737 * @alias ProtoBuf.Reflect.Service.Method
10738 * @expose
10739 */
10740 Reflect.Service.Method = Method;
10741
10742 /**
10743 * RPC service method.
10744 * @exports ProtoBuf.Reflect.Service.RPCMethod
10745 * @param {!ProtoBuf.Builder} builder Builder reference
10746 * @param {!ProtoBuf.Reflect.Service} svc Service
10747 * @param {string} name Method name
10748 * @param {string} request Request message name
10749 * @param {string} response Response message name
10750 * @param {boolean} request_stream Whether requests are streamed
10751 * @param {boolean} response_stream Whether responses are streamed
10752 * @param {Object.<string,*>=} options Options
10753 * @constructor
10754 * @extends ProtoBuf.Reflect.Service.Method
10755 */
10756 var RPCMethod = function(builder, svc, name, request, response, request_stream, response_stream, options) {
10757 Method.call(this, builder, svc, name, options);
10758
10759 /**
10760 * @override
10761 */
10762 this.className = "Service.RPCMethod";
10763
10764 /**
10765 * Request message name.
10766 * @type {string}
10767 * @expose
10768 */
10769 this.requestName = request;
10770
10771 /**
10772 * Response message name.
10773 * @type {string}
10774 * @expose
10775 */
10776 this.responseName = response;
10777
10778 /**
10779 * Whether requests are streamed
10780 * @type {bool}
10781 * @expose
10782 */
10783 this.requestStream = request_stream;
10784
10785 /**
10786 * Whether responses are streamed
10787 * @type {bool}
10788 * @expose
10789 */
10790 this.responseStream = response_stream;
10791
10792 /**
10793 * Resolved request message type.
10794 * @type {ProtoBuf.Reflect.Message}
10795 * @expose
10796 */
10797 this.resolvedRequestType = null;
10798
10799 /**
10800 * Resolved response message type.
10801 * @type {ProtoBuf.Reflect.Message}
10802 * @expose
10803 */
10804 this.resolvedResponseType = null;
10805 };
10806
10807 // Extends Method
10808 RPCMethod.prototype = Object.create(Method.prototype);
10809
10810 /**
10811 * @alias ProtoBuf.Reflect.Service.RPCMethod
10812 * @expose
10813 */
10814 Reflect.Service.RPCMethod = RPCMethod;
10815
10816 return Reflect;
10817
10818 })(ProtoBuf);
10819
10820 /**
10821 * @alias ProtoBuf.Builder
10822 * @expose
10823 */
10824 ProtoBuf.Builder = (function(ProtoBuf, Lang, Reflect) {
10825
10826 /**
10827 * Constructs a new Builder.
10828 * @exports ProtoBuf.Builder
10829 * @class Provides the functionality to build protocol messages.
10830 * @param {Object.<string,*>=} options Options
10831 * @constructor
10832 */
10833 var Builder = function(options) {
10834
10835 /**
10836 * Namespace.
10837 * @type {ProtoBuf.Reflect.Namespace}
10838 * @expose
10839 */
10840 this.ns = new Reflect.Namespace(this, null, ""); // Global namespace
10841
10842 /**
10843 * Namespace pointer.
10844 * @type {ProtoBuf.Reflect.T}
10845 * @expose
10846 */
10847 this.ptr = this.ns;
10848
10849 /**
10850 * Resolved flag.
10851 * @type {boolean}
10852 * @expose
10853 */
10854 this.resolved = false;
10855
10856 /**
10857 * The current building result.
10858 * @type {Object.<string,ProtoBuf.Builder.Message|Object>|null}
10859 * @expose
10860 */
10861 this.result = null;
10862
10863 /**
10864 * Imported files.
10865 * @type {Array.<string>}
10866 * @expose
10867 */
10868 this.files = {};
10869
10870 /**
10871 * Import root override.
10872 * @type {?string}
10873 * @expose
10874 */
10875 this.importRoot = null;
10876
10877 /**
10878 * Options.
10879 * @type {!Object.<string, *>}
10880 * @expose
10881 */
10882 this.options = options || {};
10883 };
10884
10885 /**
10886 * @alias ProtoBuf.Builder.prototype
10887 * @inner
10888 */
10889 var BuilderPrototype = Builder.prototype;
10890
10891 // ----- Definition tests -----
10892
10893 /**
10894 * Tests if a definition most likely describes a message.
10895 * @param {!Object} def
10896 * @returns {boolean}
10897 * @expose
10898 */
10899 Builder.isMessage = function(def) {
10900 // Messages require a string name
10901 if (typeof def["name"] !== 'string')
10902 return false;
10903 // Messages do not contain values (enum) or rpc methods (service)
10904 if (typeof def["values"] !== 'undefined' || typeof def["rpc"] !== 'undefined')
10905 return false;
10906 return true;
10907 };
10908
10909 /**
10910 * Tests if a definition most likely describes a message field.
10911 * @param {!Object} def
10912 * @returns {boolean}
10913 * @expose
10914 */
10915 Builder.isMessageField = function(def) {
10916 // Message fields require a string rule, name and type and an id
10917 if (typeof def["rule"] !== 'string' || typeof def["name"] !== 'string' || typeof def["type"] !== 'string' || typeof def["id"] === 'undefined')
10918 return false;
10919 return true;
10920 };
10921
10922 /**
10923 * Tests if a definition most likely describes an enum.
10924 * @param {!Object} def
10925 * @returns {boolean}
10926 * @expose
10927 */
10928 Builder.isEnum = function(def) {
10929 // Enums require a string name
10930 if (typeof def["name"] !== 'string')
10931 return false;
10932 // Enums require at least one value
10933 if (typeof def["values"] === 'undefined' || !Array.isArray(def["values"]) || def["values"].length === 0)
10934 return false;
10935 return true;
10936 };
10937
10938 /**
10939 * Tests if a definition most likely describes a service.
10940 * @param {!Object} def
10941 * @returns {boolean}
10942 * @expose
10943 */
10944 Builder.isService = function(def) {
10945 // Services require a string name and an rpc object
10946 if (typeof def["name"] !== 'string' || typeof def["rpc"] !== 'object' || !def["rpc"])
10947 return false;
10948 return true;
10949 };
10950
10951 /**
10952 * Tests if a definition most likely describes an extended message
10953 * @param {!Object} def
10954 * @returns {boolean}
10955 * @expose
10956 */
10957 Builder.isExtend = function(def) {
10958 // Extends rquire a string ref
10959 if (typeof def["ref"] !== 'string')
10960 return false;
10961 return true;
10962 };
10963
10964 // ----- Building -----
10965
10966 /**
10967 * Resets the pointer to the root namespace.
10968 * @returns {!ProtoBuf.Builder} this
10969 * @expose
10970 */
10971 BuilderPrototype.reset = function() {
10972 this.ptr = this.ns;
10973 return this;
10974 };
10975
10976 /**
10977 * Defines a namespace on top of the current pointer position and places the pointer on it.
10978 * @param {string} namespace
10979 * @return {!ProtoBuf.Builder} this
10980 * @expose
10981 */
10982 BuilderPrototype.define = function(namespace) {
10983 if (typeof namespace !== 'string' || !Lang.TYPEREF.test(namespace))
10984 throw Error("illegal namespace: "+namespace);
10985 namespace.split(".").forEach(function(part) {
10986 var ns = this.ptr.getChild(part);
10987 if (ns === null) // Keep existing
10988 this.ptr.addChild(ns = new Reflect.Namespace(this, this.ptr, part));
10989 this.ptr = ns;
10990 }, this);
10991 return this;
10992 };
10993
10994 /**
10995 * Creates the specified definitions at the current pointer position.
10996 * @param {!Array.<!Object>} defs Messages, enums or services to create
10997 * @returns {!ProtoBuf.Builder} this
10998 * @throws {Error} If a message definition is invalid
10999 * @expose
11000 */
11001 BuilderPrototype.create = function(defs) {
11002 if (!defs)
11003 return this; // Nothing to create
11004 if (!Array.isArray(defs))
11005 defs = [defs];
11006 else {
11007 if (defs.length === 0)
11008 return this;
11009 defs = defs.slice();
11010 }
11011
11012 // It's quite hard to keep track of scopes and memory here, so let's do this iteratively.
11013 var stack = [defs];
11014 while (stack.length > 0) {
11015 defs = stack.pop();
11016
11017 if (!Array.isArray(defs)) // Stack always contains entire namespaces
11018 throw Error("not a valid namespace: "+JSON.stringify(defs));
11019
11020 while (defs.length > 0) {
11021 var def = defs.shift(); // Namespaces always contain an array of messages, enums and services
11022
11023 if (Builder.isMessage(def)) {
11024 var obj = new Reflect.Message(this, this.ptr, def["name"], def["options"], def["isGroup"], def["syntax"]);
11025
11026 // Create OneOfs
11027 var oneofs = {};
11028 if (def["oneofs"])
11029 Object.keys(def["oneofs"]).forEach(function(name) {
11030 obj.addChild(oneofs[name] = new Reflect.Message.OneOf(this, obj, name));
11031 }, this);
11032
11033 // Create fields
11034 if (def["fields"])
11035 def["fields"].forEach(function(fld) {
11036 if (obj.getChild(fld["id"]|0) !== null)
11037 throw Error("duplicate or invalid field id in "+obj.name+": "+fld['id']);
11038 if (fld["options"] && typeof fld["options"] !== 'object')
11039 throw Error("illegal field options in "+obj.name+"#"+fld["name"]);
11040 var oneof = null;
11041 if (typeof fld["oneof"] === 'string' && !(oneof = oneofs[fld["oneof"]]))
11042 throw Error("illegal oneof in "+obj.name+"#"+fld["name"]+": "+fld["oneof"]);
11043 fld = new Reflect.Message.Field(this, obj, fld["rule"], fld["keytype"], fld["type"], fld["name"], fld["id"], fld["options"], oneof, def["syntax"]);
11044 if (oneof)
11045 oneof.fields.push(fld);
11046 obj.addChild(fld);
11047 }, this);
11048
11049 // Push children to stack
11050 var subObj = [];
11051 if (def["enums"])
11052 def["enums"].forEach(function(enm) {
11053 subObj.push(enm);
11054 });
11055 if (def["messages"])
11056 def["messages"].forEach(function(msg) {
11057 subObj.push(msg);
11058 });
11059 if (def["services"])
11060 def["services"].forEach(function(svc) {
11061 subObj.push(svc);
11062 });
11063
11064 // Set extension ranges
11065 if (def["extensions"]) {
11066 if (typeof def["extensions"][0] === 'number') // pre 5.0.1
11067 obj.extensions = [ def["extensions"] ];
11068 else
11069 obj.extensions = def["extensions"];
11070 }
11071
11072 // Create on top of current namespace
11073 this.ptr.addChild(obj);
11074 if (subObj.length > 0) {
11075 stack.push(defs); // Push the current level back
11076 defs = subObj; // Continue processing sub level
11077 subObj = null;
11078 this.ptr = obj; // And move the pointer to this namespace
11079 obj = null;
11080 continue;
11081 }
11082 subObj = null;
11083
11084 } else if (Builder.isEnum(def)) {
11085
11086 obj = new Reflect.Enum(this, this.ptr, def["name"], def["options"], def["syntax"]);
11087 def["values"].forEach(function(val) {
11088 obj.addChild(new Reflect.Enum.Value(this, obj, val["name"], val["id"]));
11089 }, this);
11090 this.ptr.addChild(obj);
11091
11092 } else if (Builder.isService(def)) {
11093
11094 obj = new Reflect.Service(this, this.ptr, def["name"], def["options"]);
11095 Object.keys(def["rpc"]).forEach(function(name) {
11096 var mtd = def["rpc"][name];
11097 obj.addChild(new Reflect.Service.RPCMethod(this, obj, name, mtd["request"], mtd["response"], !!mtd["request_stream"], !!mtd["response_stream"], mtd["options"]));
11098 }, this);
11099 this.ptr.addChild(obj);
11100
11101 } else if (Builder.isExtend(def)) {
11102
11103 obj = this.ptr.resolve(def["ref"], true);
11104 if (obj) {
11105 def["fields"].forEach(function(fld) {
11106 if (obj.getChild(fld['id']|0) !== null)
11107 throw Error("duplicate extended field id in "+obj.name+": "+fld['id']);
11108 // Check if field id is allowed to be extended
11109 if (obj.extensions) {
11110 var valid = false;
11111 obj.extensions.forEach(function(range) {
11112 if (fld["id"] >= range[0] && fld["id"] <= range[1])
11113 valid = true;
11114 });
11115 if (!valid)
11116 throw Error("illegal extended field id in "+obj.name+": "+fld['id']+" (not within valid ranges)");
11117 }
11118 // Convert extension field names to camel case notation if the override is set
11119 var name = fld["name"];
11120 if (this.options['convertFieldsToCamelCase'])
11121 name = ProtoBuf.Util.toCamelCase(name);
11122 // see #161: Extensions use their fully qualified name as their runtime key and...
11123 var field = new Reflect.Message.ExtensionField(this, obj, fld["rule"], fld["type"], this.ptr.fqn()+'.'+name, fld["id"], fld["options"]);
11124 // ...are added on top of the current namespace as an extension which is used for
11125 // resolving their type later on (the extension always keeps the original name to
11126 // prevent naming collisions)
11127 var ext = new Reflect.Extension(this, this.ptr, fld["name"], field);
11128 field.extension = ext;
11129 this.ptr.addChild(ext);
11130 obj.addChild(field);
11131 }, this);
11132
11133 } else if (!/\.?google\.protobuf\./.test(def["ref"])) // Silently skip internal extensions
11134 throw Error("extended message "+def["ref"]+" is not defined");
11135
11136 } else
11137 throw Error("not a valid definition: "+JSON.stringify(def));
11138
11139 def = null;
11140 obj = null;
11141 }
11142 // Break goes here
11143 defs = null;
11144 this.ptr = this.ptr.parent; // Namespace done, continue at parent
11145 }
11146 this.resolved = false; // Require re-resolve
11147 this.result = null; // Require re-build
11148 return this;
11149 };
11150
11151 /**
11152 * Propagates syntax to all children.
11153 * @param {!Object} parent
11154 * @inner
11155 */
11156 function propagateSyntax(parent) {
11157 if (parent['messages']) {
11158 parent['messages'].forEach(function(child) {
11159 child["syntax"] = parent["syntax"];
11160 propagateSyntax(child);
11161 });
11162 }
11163 if (parent['enums']) {
11164 parent['enums'].forEach(function(child) {
11165 child["syntax"] = parent["syntax"];
11166 });
11167 }
11168 }
11169
11170 /**
11171 * Imports another definition into this builder.
11172 * @param {Object.<string,*>} json Parsed import
11173 * @param {(string|{root: string, file: string})=} filename Imported file name
11174 * @returns {!ProtoBuf.Builder} this
11175 * @throws {Error} If the definition or file cannot be imported
11176 * @expose
11177 */
11178 BuilderPrototype["import"] = function(json, filename) {
11179 var delim = '/';
11180
11181 // Make sure to skip duplicate imports
11182
11183 if (typeof filename === 'string') {
11184
11185 if (ProtoBuf.Util.IS_NODE)
11186 filename = require$$2['resolve'](filename);
11187 if (this.files[filename] === true)
11188 return this.reset();
11189 this.files[filename] = true;
11190
11191 } else if (typeof filename === 'object') { // Object with root, file.
11192
11193 var root = filename.root;
11194 if (ProtoBuf.Util.IS_NODE)
11195 root = require$$2['resolve'](root);
11196 if (root.indexOf("\\") >= 0 || filename.file.indexOf("\\") >= 0)
11197 delim = '\\';
11198 var fname;
11199 if (ProtoBuf.Util.IS_NODE)
11200 fname = require$$2['join'](root, filename.file);
11201 else
11202 fname = root + delim + filename.file;
11203 if (this.files[fname] === true)
11204 return this.reset();
11205 this.files[fname] = true;
11206 }
11207
11208 // Import imports
11209
11210 if (json['imports'] && json['imports'].length > 0) {
11211 var importRoot,
11212 resetRoot = false;
11213
11214 if (typeof filename === 'object') { // If an import root is specified, override
11215
11216 this.importRoot = filename["root"]; resetRoot = true; // ... and reset afterwards
11217 importRoot = this.importRoot;
11218 filename = filename["file"];
11219 if (importRoot.indexOf("\\") >= 0 || filename.indexOf("\\") >= 0)
11220 delim = '\\';
11221
11222 } else if (typeof filename === 'string') {
11223
11224 if (this.importRoot) // If import root is overridden, use it
11225 importRoot = this.importRoot;
11226 else { // Otherwise compute from filename
11227 if (filename.indexOf("/") >= 0) { // Unix
11228 importRoot = filename.replace(/\/[^\/]*$/, "");
11229 if (/* /file.proto */ importRoot === "")
11230 importRoot = "/";
11231 } else if (filename.indexOf("\\") >= 0) { // Windows
11232 importRoot = filename.replace(/\\[^\\]*$/, "");
11233 delim = '\\';
11234 } else
11235 importRoot = ".";
11236 }
11237
11238 } else
11239 importRoot = null;
11240
11241 for (var i=0; i<json['imports'].length; i++) {
11242 if (typeof json['imports'][i] === 'string') { // Import file
11243 if (!importRoot)
11244 throw Error("cannot determine import root");
11245 var importFilename = json['imports'][i];
11246 if (importFilename === "google/protobuf/descriptor.proto")
11247 continue; // Not needed and therefore not used
11248 if (ProtoBuf.Util.IS_NODE)
11249 importFilename = require$$2['join'](importRoot, importFilename);
11250 else
11251 importFilename = importRoot + delim + importFilename;
11252 if (this.files[importFilename] === true)
11253 continue; // Already imported
11254 if (/\.proto$/i.test(importFilename) && !ProtoBuf.DotProto) // If this is a light build
11255 importFilename = importFilename.replace(/\.proto$/, ".json"); // always load the JSON file
11256 var contents = ProtoBuf.Util.fetch(importFilename);
11257 if (contents === null)
11258 throw Error("failed to import '"+importFilename+"' in '"+filename+"': file not found");
11259 if (/\.json$/i.test(importFilename)) // Always possible
11260 this["import"](JSON.parse(contents+""), importFilename); // May throw
11261 else
11262 this["import"](ProtoBuf.DotProto.Parser.parse(contents), importFilename); // May throw
11263 } else // Import structure
11264 if (!filename)
11265 this["import"](json['imports'][i]);
11266 else if (/\.(\w+)$/.test(filename)) // With extension: Append _importN to the name portion to make it unique
11267 this["import"](json['imports'][i], filename.replace(/^(.+)\.(\w+)$/, function($0, $1, $2) { return $1+"_import"+i+"."+$2; }));
11268 else // Without extension: Append _importN to make it unique
11269 this["import"](json['imports'][i], filename+"_import"+i);
11270 }
11271 if (resetRoot) // Reset import root override when all imports are done
11272 this.importRoot = null;
11273 }
11274
11275 // Import structures
11276
11277 if (json['package'])
11278 this.define(json['package']);
11279 if (json['syntax'])
11280 propagateSyntax(json);
11281 var base = this.ptr;
11282 if (json['options'])
11283 Object.keys(json['options']).forEach(function(key) {
11284 base.options[key] = json['options'][key];
11285 });
11286 if (json['messages'])
11287 this.create(json['messages']),
11288 this.ptr = base;
11289 if (json['enums'])
11290 this.create(json['enums']),
11291 this.ptr = base;
11292 if (json['services'])
11293 this.create(json['services']),
11294 this.ptr = base;
11295 if (json['extends'])
11296 this.create(json['extends']);
11297
11298 return this.reset();
11299 };
11300
11301 /**
11302 * Resolves all namespace objects.
11303 * @throws {Error} If a type cannot be resolved
11304 * @returns {!ProtoBuf.Builder} this
11305 * @expose
11306 */
11307 BuilderPrototype.resolveAll = function() {
11308 // Resolve all reflected objects
11309 var res;
11310 if (this.ptr == null || typeof this.ptr.type === 'object')
11311 return this; // Done (already resolved)
11312
11313 if (this.ptr instanceof Reflect.Namespace) { // Resolve children
11314
11315 this.ptr.children.forEach(function(child) {
11316 this.ptr = child;
11317 this.resolveAll();
11318 }, this);
11319
11320 } else if (this.ptr instanceof Reflect.Message.Field) { // Resolve type
11321
11322 if (!Lang.TYPE.test(this.ptr.type)) {
11323 if (!Lang.TYPEREF.test(this.ptr.type))
11324 throw Error("illegal type reference in "+this.ptr.toString(true)+": "+this.ptr.type);
11325 res = (this.ptr instanceof Reflect.Message.ExtensionField ? this.ptr.extension.parent : this.ptr.parent).resolve(this.ptr.type, true);
11326 if (!res)
11327 throw Error("unresolvable type reference in "+this.ptr.toString(true)+": "+this.ptr.type);
11328 this.ptr.resolvedType = res;
11329 if (res instanceof Reflect.Enum) {
11330 this.ptr.type = ProtoBuf.TYPES["enum"];
11331 if (this.ptr.syntax === 'proto3' && res.syntax !== 'proto3')
11332 throw Error("proto3 message cannot reference proto2 enum");
11333 }
11334 else if (res instanceof Reflect.Message)
11335 this.ptr.type = res.isGroup ? ProtoBuf.TYPES["group"] : ProtoBuf.TYPES["message"];
11336 else
11337 throw Error("illegal type reference in "+this.ptr.toString(true)+": "+this.ptr.type);
11338 } else
11339 this.ptr.type = ProtoBuf.TYPES[this.ptr.type];
11340
11341 // If it's a map field, also resolve the key type. The key type can be only a numeric, string, or bool type
11342 // (i.e., no enums or messages), so we don't need to resolve against the current namespace.
11343 if (this.ptr.map) {
11344 if (!Lang.TYPE.test(this.ptr.keyType))
11345 throw Error("illegal key type for map field in "+this.ptr.toString(true)+": "+this.ptr.keyType);
11346 this.ptr.keyType = ProtoBuf.TYPES[this.ptr.keyType];
11347 }
11348
11349 // If it's a repeated and packable field then proto3 mandates it should be packed by
11350 // default
11351 if (
11352 this.ptr.syntax === 'proto3' &&
11353 this.ptr.repeated && this.ptr.options.packed === undefined &&
11354 ProtoBuf.PACKABLE_WIRE_TYPES.indexOf(this.ptr.type.wireType) !== -1
11355 ) {
11356 this.ptr.options.packed = true;
11357 }
11358
11359 } else if (this.ptr instanceof ProtoBuf.Reflect.Service.Method) {
11360
11361 if (this.ptr instanceof ProtoBuf.Reflect.Service.RPCMethod) {
11362 res = this.ptr.parent.resolve(this.ptr.requestName, true);
11363 if (!res || !(res instanceof ProtoBuf.Reflect.Message))
11364 throw Error("Illegal type reference in "+this.ptr.toString(true)+": "+this.ptr.requestName);
11365 this.ptr.resolvedRequestType = res;
11366 res = this.ptr.parent.resolve(this.ptr.responseName, true);
11367 if (!res || !(res instanceof ProtoBuf.Reflect.Message))
11368 throw Error("Illegal type reference in "+this.ptr.toString(true)+": "+this.ptr.responseName);
11369 this.ptr.resolvedResponseType = res;
11370 } else // Should not happen as nothing else is implemented
11371 throw Error("illegal service type in "+this.ptr.toString(true));
11372
11373 } else if (
11374 !(this.ptr instanceof ProtoBuf.Reflect.Message.OneOf) && // Not built
11375 !(this.ptr instanceof ProtoBuf.Reflect.Extension) && // Not built
11376 !(this.ptr instanceof ProtoBuf.Reflect.Enum.Value) // Built in enum
11377 )
11378 throw Error("illegal object in namespace: "+typeof(this.ptr)+": "+this.ptr);
11379
11380 return this.reset();
11381 };
11382
11383 /**
11384 * Builds the protocol. This will first try to resolve all definitions and, if this has been successful,
11385 * return the built package.
11386 * @param {(string|Array.<string>)=} path Specifies what to return. If omitted, the entire namespace will be returned.
11387 * @returns {!ProtoBuf.Builder.Message|!Object.<string,*>}
11388 * @throws {Error} If a type could not be resolved
11389 * @expose
11390 */
11391 BuilderPrototype.build = function(path) {
11392 this.reset();
11393 if (!this.resolved)
11394 this.resolveAll(),
11395 this.resolved = true,
11396 this.result = null; // Require re-build
11397 if (this.result === null) // (Re-)Build
11398 this.result = this.ns.build();
11399 if (!path)
11400 return this.result;
11401 var part = typeof path === 'string' ? path.split(".") : path,
11402 ptr = this.result; // Build namespace pointer (no hasChild etc.)
11403 for (var i=0; i<part.length; i++)
11404 if (ptr[part[i]])
11405 ptr = ptr[part[i]];
11406 else {
11407 ptr = null;
11408 break;
11409 }
11410 return ptr;
11411 };
11412
11413 /**
11414 * Similar to {@link ProtoBuf.Builder#build}, but looks up the internal reflection descriptor.
11415 * @param {string=} path Specifies what to return. If omitted, the entire namespace wiil be returned.
11416 * @param {boolean=} excludeNonNamespace Excludes non-namespace types like fields, defaults to `false`
11417 * @returns {?ProtoBuf.Reflect.T} Reflection descriptor or `null` if not found
11418 */
11419 BuilderPrototype.lookup = function(path, excludeNonNamespace) {
11420 return path ? this.ns.resolve(path, excludeNonNamespace) : this.ns;
11421 };
11422
11423 /**
11424 * Returns a string representation of this object.
11425 * @return {string} String representation as of "Builder"
11426 * @expose
11427 */
11428 BuilderPrototype.toString = function() {
11429 return "Builder";
11430 };
11431
11432 // ----- Base classes -----
11433 // Exist for the sole purpose of being able to "... instanceof ProtoBuf.Builder.Message" etc.
11434
11435 /**
11436 * @alias ProtoBuf.Builder.Message
11437 */
11438 Builder.Message = function() {};
11439
11440 /**
11441 * @alias ProtoBuf.Builder.Enum
11442 */
11443 Builder.Enum = function() {};
11444
11445 /**
11446 * @alias ProtoBuf.Builder.Message
11447 */
11448 Builder.Service = function() {};
11449
11450 return Builder;
11451
11452 })(ProtoBuf, ProtoBuf.Lang, ProtoBuf.Reflect);
11453
11454 /**
11455 * @alias ProtoBuf.Map
11456 * @expose
11457 */
11458 ProtoBuf.Map = (function(ProtoBuf, Reflect) {
11459
11460 /**
11461 * Constructs a new Map. A Map is a container that is used to implement map
11462 * fields on message objects. It closely follows the ES6 Map API; however,
11463 * it is distinct because we do not want to depend on external polyfills or
11464 * on ES6 itself.
11465 *
11466 * @exports ProtoBuf.Map
11467 * @param {!ProtoBuf.Reflect.Field} field Map field
11468 * @param {Object.<string,*>=} contents Initial contents
11469 * @constructor
11470 */
11471 var Map = function(field, contents) {
11472 if (!field.map)
11473 throw Error("field is not a map");
11474
11475 /**
11476 * The field corresponding to this map.
11477 * @type {!ProtoBuf.Reflect.Field}
11478 */
11479 this.field = field;
11480
11481 /**
11482 * Element instance corresponding to key type.
11483 * @type {!ProtoBuf.Reflect.Element}
11484 */
11485 this.keyElem = new Reflect.Element(field.keyType, null, true, field.syntax);
11486
11487 /**
11488 * Element instance corresponding to value type.
11489 * @type {!ProtoBuf.Reflect.Element}
11490 */
11491 this.valueElem = new Reflect.Element(field.type, field.resolvedType, false, field.syntax);
11492
11493 /**
11494 * Internal map: stores mapping of (string form of key) -> (key, value)
11495 * pair.
11496 *
11497 * We provide map semantics for arbitrary key types, but we build on top
11498 * of an Object, which has only string keys. In order to avoid the need
11499 * to convert a string key back to its native type in many situations,
11500 * we store the native key value alongside the value. Thus, we only need
11501 * a one-way mapping from a key type to its string form that guarantees
11502 * uniqueness and equality (i.e., str(K1) === str(K2) if and only if K1
11503 * === K2).
11504 *
11505 * @type {!Object<string, {key: *, value: *}>}
11506 */
11507 this.map = {};
11508
11509 /**
11510 * Returns the number of elements in the map.
11511 */
11512 Object.defineProperty(this, "size", {
11513 get: function() { return Object.keys(this.map).length; }
11514 });
11515
11516 // Fill initial contents from a raw object.
11517 if (contents) {
11518 var keys = Object.keys(contents);
11519 for (var i = 0; i < keys.length; i++) {
11520 var key = this.keyElem.valueFromString(keys[i]);
11521 var val = this.valueElem.verifyValue(contents[keys[i]]);
11522 this.map[this.keyElem.valueToString(key)] =
11523 { key: key, value: val };
11524 }
11525 }
11526 };
11527
11528 var MapPrototype = Map.prototype;
11529
11530 /**
11531 * Helper: return an iterator over an array.
11532 * @param {!Array<*>} arr the array
11533 * @returns {!Object} an iterator
11534 * @inner
11535 */
11536 function arrayIterator(arr) {
11537 var idx = 0;
11538 return {
11539 next: function() {
11540 if (idx < arr.length)
11541 return { done: false, value: arr[idx++] };
11542 return { done: true };
11543 }
11544 }
11545 }
11546
11547 /**
11548 * Clears the map.
11549 */
11550 MapPrototype.clear = function() {
11551 this.map = {};
11552 };
11553
11554 /**
11555 * Deletes a particular key from the map.
11556 * @returns {boolean} Whether any entry with this key was deleted.
11557 */
11558 MapPrototype["delete"] = function(key) {
11559 var keyValue = this.keyElem.valueToString(this.keyElem.verifyValue(key));
11560 var hadKey = keyValue in this.map;
11561 delete this.map[keyValue];
11562 return hadKey;
11563 };
11564
11565 /**
11566 * Returns an iterator over [key, value] pairs in the map.
11567 * @returns {Object} The iterator
11568 */
11569 MapPrototype.entries = function() {
11570 var entries = [];
11571 var strKeys = Object.keys(this.map);
11572 for (var i = 0, entry; i < strKeys.length; i++)
11573 entries.push([(entry=this.map[strKeys[i]]).key, entry.value]);
11574 return arrayIterator(entries);
11575 };
11576
11577 /**
11578 * Returns an iterator over keys in the map.
11579 * @returns {Object} The iterator
11580 */
11581 MapPrototype.keys = function() {
11582 var keys = [];
11583 var strKeys = Object.keys(this.map);
11584 for (var i = 0; i < strKeys.length; i++)
11585 keys.push(this.map[strKeys[i]].key);
11586 return arrayIterator(keys);
11587 };
11588
11589 /**
11590 * Returns an iterator over values in the map.
11591 * @returns {!Object} The iterator
11592 */
11593 MapPrototype.values = function() {
11594 var values = [];
11595 var strKeys = Object.keys(this.map);
11596 for (var i = 0; i < strKeys.length; i++)
11597 values.push(this.map[strKeys[i]].value);
11598 return arrayIterator(values);
11599 };
11600
11601 /**
11602 * Iterates over entries in the map, calling a function on each.
11603 * @param {function(this:*, *, *, *)} cb The callback to invoke with value, key, and map arguments.
11604 * @param {Object=} thisArg The `this` value for the callback
11605 */
11606 MapPrototype.forEach = function(cb, thisArg) {
11607 var strKeys = Object.keys(this.map);
11608 for (var i = 0, entry; i < strKeys.length; i++)
11609 cb.call(thisArg, (entry=this.map[strKeys[i]]).value, entry.key, this);
11610 };
11611
11612 /**
11613 * Sets a key in the map to the given value.
11614 * @param {*} key The key
11615 * @param {*} value The value
11616 * @returns {!ProtoBuf.Map} The map instance
11617 */
11618 MapPrototype.set = function(key, value) {
11619 var keyValue = this.keyElem.verifyValue(key);
11620 var valValue = this.valueElem.verifyValue(value);
11621 this.map[this.keyElem.valueToString(keyValue)] =
11622 { key: keyValue, value: valValue };
11623 return this;
11624 };
11625
11626 /**
11627 * Gets the value corresponding to a key in the map.
11628 * @param {*} key The key
11629 * @returns {*|undefined} The value, or `undefined` if key not present
11630 */
11631 MapPrototype.get = function(key) {
11632 var keyValue = this.keyElem.valueToString(this.keyElem.verifyValue(key));
11633 if (!(keyValue in this.map))
11634 return undefined;
11635 return this.map[keyValue].value;
11636 };
11637
11638 /**
11639 * Determines whether the given key is present in the map.
11640 * @param {*} key The key
11641 * @returns {boolean} `true` if the key is present
11642 */
11643 MapPrototype.has = function(key) {
11644 var keyValue = this.keyElem.valueToString(this.keyElem.verifyValue(key));
11645 return (keyValue in this.map);
11646 };
11647
11648 return Map;
11649 })(ProtoBuf, ProtoBuf.Reflect);
11650
11651
11652 /**
11653 * Constructs a new empty Builder.
11654 * @param {Object.<string,*>=} options Builder options, defaults to global options set on ProtoBuf
11655 * @return {!ProtoBuf.Builder} Builder
11656 * @expose
11657 */
11658 ProtoBuf.newBuilder = function(options) {
11659 options = options || {};
11660 if (typeof options['convertFieldsToCamelCase'] === 'undefined')
11661 options['convertFieldsToCamelCase'] = ProtoBuf.convertFieldsToCamelCase;
11662 if (typeof options['populateAccessors'] === 'undefined')
11663 options['populateAccessors'] = ProtoBuf.populateAccessors;
11664 return new ProtoBuf.Builder(options);
11665 };
11666
11667 /**
11668 * Loads a .json definition and returns the Builder.
11669 * @param {!*|string} json JSON definition
11670 * @param {(ProtoBuf.Builder|string|{root: string, file: string})=} builder Builder to append to. Will create a new one if omitted.
11671 * @param {(string|{root: string, file: string})=} filename The corresponding file name if known. Must be specified for imports.
11672 * @return {ProtoBuf.Builder} Builder to create new messages
11673 * @throws {Error} If the definition cannot be parsed or built
11674 * @expose
11675 */
11676 ProtoBuf.loadJson = function(json, builder, filename) {
11677 if (typeof builder === 'string' || (builder && typeof builder["file"] === 'string' && typeof builder["root"] === 'string'))
11678 filename = builder,
11679 builder = null;
11680 if (!builder || typeof builder !== 'object')
11681 builder = ProtoBuf.newBuilder();
11682 if (typeof json === 'string')
11683 json = JSON.parse(json);
11684 builder["import"](json, filename);
11685 builder.resolveAll();
11686 return builder;
11687 };
11688
11689 /**
11690 * Loads a .json file and returns the Builder.
11691 * @param {string|!{root: string, file: string}} filename Path to json file or an object specifying 'file' with
11692 * an overridden 'root' path for all imported files.
11693 * @param {function(?Error, !ProtoBuf.Builder=)=} callback Callback that will receive `null` as the first and
11694 * the Builder as its second argument on success, otherwise the error as its first argument. If omitted, the
11695 * file will be read synchronously and this function will return the Builder.
11696 * @param {ProtoBuf.Builder=} builder Builder to append to. Will create a new one if omitted.
11697 * @return {?ProtoBuf.Builder|undefined} The Builder if synchronous (no callback specified, will be NULL if the
11698 * request has failed), else undefined
11699 * @expose
11700 */
11701 ProtoBuf.loadJsonFile = function(filename, callback, builder) {
11702 if (callback && typeof callback === 'object')
11703 builder = callback,
11704 callback = null;
11705 else if (!callback || typeof callback !== 'function')
11706 callback = null;
11707 if (callback)
11708 return ProtoBuf.Util.fetch(typeof filename === 'string' ? filename : filename["root"]+"/"+filename["file"], function(contents) {
11709 if (contents === null) {
11710 callback(Error("Failed to fetch file"));
11711 return;
11712 }
11713 try {
11714 callback(null, ProtoBuf.loadJson(JSON.parse(contents), builder, filename));
11715 } catch (e) {
11716 callback(e);
11717 }
11718 });
11719 var contents = ProtoBuf.Util.fetch(typeof filename === 'object' ? filename["root"]+"/"+filename["file"] : filename);
11720 return contents === null ? null : ProtoBuf.loadJson(JSON.parse(contents), builder, filename);
11721 };
11722
11723 return ProtoBuf;
11724 });
11725 });
11726
11727 var messageCompiled = protobufLight.newBuilder({})['import']({
11728 "package": 'push_server.messages2',
11729 syntax: 'proto2',
11730 options: {
11731 objc_class_prefix: 'AVIM'
11732 },
11733 messages: [{
11734 name: 'JsonObjectMessage',
11735 syntax: 'proto2',
11736 fields: [{
11737 rule: 'required',
11738 type: 'string',
11739 name: 'data',
11740 id: 1
11741 }]
11742 }, {
11743 name: 'UnreadTuple',
11744 syntax: 'proto2',
11745 fields: [{
11746 rule: 'required',
11747 type: 'string',
11748 name: 'cid',
11749 id: 1
11750 }, {
11751 rule: 'required',
11752 type: 'int32',
11753 name: 'unread',
11754 id: 2
11755 }, {
11756 rule: 'optional',
11757 type: 'string',
11758 name: 'mid',
11759 id: 3
11760 }, {
11761 rule: 'optional',
11762 type: 'int64',
11763 name: 'timestamp',
11764 id: 4
11765 }, {
11766 rule: 'optional',
11767 type: 'string',
11768 name: 'from',
11769 id: 5
11770 }, {
11771 rule: 'optional',
11772 type: 'string',
11773 name: 'data',
11774 id: 6
11775 }, {
11776 rule: 'optional',
11777 type: 'int64',
11778 name: 'patchTimestamp',
11779 id: 7
11780 }, {
11781 rule: 'optional',
11782 type: 'bool',
11783 name: 'mentioned',
11784 id: 8
11785 }, {
11786 rule: 'optional',
11787 type: 'bytes',
11788 name: 'binaryMsg',
11789 id: 9
11790 }, {
11791 rule: 'optional',
11792 type: 'int32',
11793 name: 'convType',
11794 id: 10
11795 }]
11796 }, {
11797 name: 'LogItem',
11798 syntax: 'proto2',
11799 fields: [{
11800 rule: 'optional',
11801 type: 'string',
11802 name: 'from',
11803 id: 1
11804 }, {
11805 rule: 'optional',
11806 type: 'string',
11807 name: 'data',
11808 id: 2
11809 }, {
11810 rule: 'optional',
11811 type: 'int64',
11812 name: 'timestamp',
11813 id: 3
11814 }, {
11815 rule: 'optional',
11816 type: 'string',
11817 name: 'msgId',
11818 id: 4
11819 }, {
11820 rule: 'optional',
11821 type: 'int64',
11822 name: 'ackAt',
11823 id: 5
11824 }, {
11825 rule: 'optional',
11826 type: 'int64',
11827 name: 'readAt',
11828 id: 6
11829 }, {
11830 rule: 'optional',
11831 type: 'int64',
11832 name: 'patchTimestamp',
11833 id: 7
11834 }, {
11835 rule: 'optional',
11836 type: 'bool',
11837 name: 'mentionAll',
11838 id: 8
11839 }, {
11840 rule: 'repeated',
11841 type: 'string',
11842 name: 'mentionPids',
11843 id: 9
11844 }, {
11845 rule: 'optional',
11846 type: 'bool',
11847 name: 'bin',
11848 id: 10
11849 }, {
11850 rule: 'optional',
11851 type: 'int32',
11852 name: 'convType',
11853 id: 11
11854 }]
11855 }, {
11856 name: 'ConvMemberInfo',
11857 syntax: 'proto2',
11858 fields: [{
11859 rule: 'optional',
11860 type: 'string',
11861 name: 'pid',
11862 id: 1
11863 }, {
11864 rule: 'optional',
11865 type: 'string',
11866 name: 'role',
11867 id: 2
11868 }, {
11869 rule: 'optional',
11870 type: 'string',
11871 name: 'infoId',
11872 id: 3
11873 }]
11874 }, {
11875 name: 'DataCommand',
11876 syntax: 'proto2',
11877 fields: [{
11878 rule: 'repeated',
11879 type: 'string',
11880 name: 'ids',
11881 id: 1
11882 }, {
11883 rule: 'repeated',
11884 type: 'JsonObjectMessage',
11885 name: 'msg',
11886 id: 2
11887 }, {
11888 rule: 'optional',
11889 type: 'bool',
11890 name: 'offline',
11891 id: 3
11892 }]
11893 }, {
11894 name: 'SessionCommand',
11895 syntax: 'proto2',
11896 fields: [{
11897 rule: 'optional',
11898 type: 'int64',
11899 name: 't',
11900 id: 1
11901 }, {
11902 rule: 'optional',
11903 type: 'string',
11904 name: 'n',
11905 id: 2
11906 }, {
11907 rule: 'optional',
11908 type: 'string',
11909 name: 's',
11910 id: 3
11911 }, {
11912 rule: 'optional',
11913 type: 'string',
11914 name: 'ua',
11915 id: 4
11916 }, {
11917 rule: 'optional',
11918 type: 'bool',
11919 name: 'r',
11920 id: 5
11921 }, {
11922 rule: 'optional',
11923 type: 'string',
11924 name: 'tag',
11925 id: 6
11926 }, {
11927 rule: 'optional',
11928 type: 'string',
11929 name: 'deviceId',
11930 id: 7
11931 }, {
11932 rule: 'repeated',
11933 type: 'string',
11934 name: 'sessionPeerIds',
11935 id: 8
11936 }, {
11937 rule: 'repeated',
11938 type: 'string',
11939 name: 'onlineSessionPeerIds',
11940 id: 9
11941 }, {
11942 rule: 'optional',
11943 type: 'string',
11944 name: 'st',
11945 id: 10
11946 }, {
11947 rule: 'optional',
11948 type: 'int32',
11949 name: 'stTtl',
11950 id: 11
11951 }, {
11952 rule: 'optional',
11953 type: 'int32',
11954 name: 'code',
11955 id: 12
11956 }, {
11957 rule: 'optional',
11958 type: 'string',
11959 name: 'reason',
11960 id: 13
11961 }, {
11962 rule: 'optional',
11963 type: 'string',
11964 name: 'deviceToken',
11965 id: 14
11966 }, {
11967 rule: 'optional',
11968 type: 'bool',
11969 name: 'sp',
11970 id: 15
11971 }, {
11972 rule: 'optional',
11973 type: 'string',
11974 name: 'detail',
11975 id: 16
11976 }, {
11977 rule: 'optional',
11978 type: 'int64',
11979 name: 'lastUnreadNotifTime',
11980 id: 17
11981 }, {
11982 rule: 'optional',
11983 type: 'int64',
11984 name: 'lastPatchTime',
11985 id: 18
11986 }, {
11987 rule: 'optional',
11988 type: 'int64',
11989 name: 'configBitmap',
11990 id: 19
11991 }]
11992 }, {
11993 name: 'ErrorCommand',
11994 syntax: 'proto2',
11995 fields: [{
11996 rule: 'required',
11997 type: 'int32',
11998 name: 'code',
11999 id: 1
12000 }, {
12001 rule: 'required',
12002 type: 'string',
12003 name: 'reason',
12004 id: 2
12005 }, {
12006 rule: 'optional',
12007 type: 'int32',
12008 name: 'appCode',
12009 id: 3
12010 }, {
12011 rule: 'optional',
12012 type: 'string',
12013 name: 'detail',
12014 id: 4
12015 }, {
12016 rule: 'repeated',
12017 type: 'string',
12018 name: 'pids',
12019 id: 5
12020 }, {
12021 rule: 'optional',
12022 type: 'string',
12023 name: 'appMsg',
12024 id: 6
12025 }]
12026 }, {
12027 name: 'DirectCommand',
12028 syntax: 'proto2',
12029 fields: [{
12030 rule: 'optional',
12031 type: 'string',
12032 name: 'msg',
12033 id: 1
12034 }, {
12035 rule: 'optional',
12036 type: 'string',
12037 name: 'uid',
12038 id: 2
12039 }, {
12040 rule: 'optional',
12041 type: 'string',
12042 name: 'fromPeerId',
12043 id: 3
12044 }, {
12045 rule: 'optional',
12046 type: 'int64',
12047 name: 'timestamp',
12048 id: 4
12049 }, {
12050 rule: 'optional',
12051 type: 'bool',
12052 name: 'offline',
12053 id: 5
12054 }, {
12055 rule: 'optional',
12056 type: 'bool',
12057 name: 'hasMore',
12058 id: 6
12059 }, {
12060 rule: 'repeated',
12061 type: 'string',
12062 name: 'toPeerIds',
12063 id: 7
12064 }, {
12065 rule: 'optional',
12066 type: 'bool',
12067 name: 'r',
12068 id: 10
12069 }, {
12070 rule: 'optional',
12071 type: 'string',
12072 name: 'cid',
12073 id: 11
12074 }, {
12075 rule: 'optional',
12076 type: 'string',
12077 name: 'id',
12078 id: 12
12079 }, {
12080 rule: 'optional',
12081 type: 'bool',
12082 name: 'transient',
12083 id: 13
12084 }, {
12085 rule: 'optional',
12086 type: 'string',
12087 name: 'dt',
12088 id: 14
12089 }, {
12090 rule: 'optional',
12091 type: 'string',
12092 name: 'roomId',
12093 id: 15
12094 }, {
12095 rule: 'optional',
12096 type: 'string',
12097 name: 'pushData',
12098 id: 16
12099 }, {
12100 rule: 'optional',
12101 type: 'bool',
12102 name: 'will',
12103 id: 17
12104 }, {
12105 rule: 'optional',
12106 type: 'int64',
12107 name: 'patchTimestamp',
12108 id: 18
12109 }, {
12110 rule: 'optional',
12111 type: 'bytes',
12112 name: 'binaryMsg',
12113 id: 19
12114 }, {
12115 rule: 'repeated',
12116 type: 'string',
12117 name: 'mentionPids',
12118 id: 20
12119 }, {
12120 rule: 'optional',
12121 type: 'bool',
12122 name: 'mentionAll',
12123 id: 21
12124 }, {
12125 rule: 'optional',
12126 type: 'int32',
12127 name: 'convType',
12128 id: 22
12129 }]
12130 }, {
12131 name: 'AckCommand',
12132 syntax: 'proto2',
12133 fields: [{
12134 rule: 'optional',
12135 type: 'int32',
12136 name: 'code',
12137 id: 1
12138 }, {
12139 rule: 'optional',
12140 type: 'string',
12141 name: 'reason',
12142 id: 2
12143 }, {
12144 rule: 'optional',
12145 type: 'string',
12146 name: 'mid',
12147 id: 3
12148 }, {
12149 rule: 'optional',
12150 type: 'string',
12151 name: 'cid',
12152 id: 4
12153 }, {
12154 rule: 'optional',
12155 type: 'int64',
12156 name: 't',
12157 id: 5
12158 }, {
12159 rule: 'optional',
12160 type: 'string',
12161 name: 'uid',
12162 id: 6
12163 }, {
12164 rule: 'optional',
12165 type: 'int64',
12166 name: 'fromts',
12167 id: 7
12168 }, {
12169 rule: 'optional',
12170 type: 'int64',
12171 name: 'tots',
12172 id: 8
12173 }, {
12174 rule: 'optional',
12175 type: 'string',
12176 name: 'type',
12177 id: 9
12178 }, {
12179 rule: 'repeated',
12180 type: 'string',
12181 name: 'ids',
12182 id: 10
12183 }, {
12184 rule: 'optional',
12185 type: 'int32',
12186 name: 'appCode',
12187 id: 11
12188 }, {
12189 rule: 'optional',
12190 type: 'string',
12191 name: 'appMsg',
12192 id: 12
12193 }]
12194 }, {
12195 name: 'UnreadCommand',
12196 syntax: 'proto2',
12197 fields: [{
12198 rule: 'repeated',
12199 type: 'UnreadTuple',
12200 name: 'convs',
12201 id: 1
12202 }, {
12203 rule: 'optional',
12204 type: 'int64',
12205 name: 'notifTime',
12206 id: 2
12207 }]
12208 }, {
12209 name: 'ConvCommand',
12210 syntax: 'proto2',
12211 fields: [{
12212 rule: 'repeated',
12213 type: 'string',
12214 name: 'm',
12215 id: 1
12216 }, {
12217 rule: 'optional',
12218 type: 'bool',
12219 name: 'transient',
12220 id: 2
12221 }, {
12222 rule: 'optional',
12223 type: 'bool',
12224 name: 'unique',
12225 id: 3
12226 }, {
12227 rule: 'optional',
12228 type: 'string',
12229 name: 'cid',
12230 id: 4
12231 }, {
12232 rule: 'optional',
12233 type: 'string',
12234 name: 'cdate',
12235 id: 5
12236 }, {
12237 rule: 'optional',
12238 type: 'string',
12239 name: 'initBy',
12240 id: 6
12241 }, {
12242 rule: 'optional',
12243 type: 'string',
12244 name: 'sort',
12245 id: 7
12246 }, {
12247 rule: 'optional',
12248 type: 'int32',
12249 name: 'limit',
12250 id: 8
12251 }, {
12252 rule: 'optional',
12253 type: 'int32',
12254 name: 'skip',
12255 id: 9
12256 }, {
12257 rule: 'optional',
12258 type: 'int32',
12259 name: 'flag',
12260 id: 10
12261 }, {
12262 rule: 'optional',
12263 type: 'int32',
12264 name: 'count',
12265 id: 11
12266 }, {
12267 rule: 'optional',
12268 type: 'string',
12269 name: 'udate',
12270 id: 12
12271 }, {
12272 rule: 'optional',
12273 type: 'int64',
12274 name: 't',
12275 id: 13
12276 }, {
12277 rule: 'optional',
12278 type: 'string',
12279 name: 'n',
12280 id: 14
12281 }, {
12282 rule: 'optional',
12283 type: 'string',
12284 name: 's',
12285 id: 15
12286 }, {
12287 rule: 'optional',
12288 type: 'bool',
12289 name: 'statusSub',
12290 id: 16
12291 }, {
12292 rule: 'optional',
12293 type: 'bool',
12294 name: 'statusPub',
12295 id: 17
12296 }, {
12297 rule: 'optional',
12298 type: 'int32',
12299 name: 'statusTTL',
12300 id: 18
12301 }, {
12302 rule: 'optional',
12303 type: 'string',
12304 name: 'uniqueId',
12305 id: 19
12306 }, {
12307 rule: 'optional',
12308 type: 'string',
12309 name: 'targetClientId',
12310 id: 20
12311 }, {
12312 rule: 'optional',
12313 type: 'int64',
12314 name: 'maxReadTimestamp',
12315 id: 21
12316 }, {
12317 rule: 'optional',
12318 type: 'int64',
12319 name: 'maxAckTimestamp',
12320 id: 22
12321 }, {
12322 rule: 'optional',
12323 type: 'bool',
12324 name: 'queryAllMembers',
12325 id: 23
12326 }, {
12327 rule: 'repeated',
12328 type: 'MaxReadTuple',
12329 name: 'maxReadTuples',
12330 id: 24
12331 }, {
12332 rule: 'repeated',
12333 type: 'string',
12334 name: 'cids',
12335 id: 25
12336 }, {
12337 rule: 'optional',
12338 type: 'ConvMemberInfo',
12339 name: 'info',
12340 id: 26
12341 }, {
12342 rule: 'optional',
12343 type: 'bool',
12344 name: 'tempConv',
12345 id: 27
12346 }, {
12347 rule: 'optional',
12348 type: 'int32',
12349 name: 'tempConvTTL',
12350 id: 28
12351 }, {
12352 rule: 'repeated',
12353 type: 'string',
12354 name: 'tempConvIds',
12355 id: 29
12356 }, {
12357 rule: 'repeated',
12358 type: 'string',
12359 name: 'allowedPids',
12360 id: 30
12361 }, {
12362 rule: 'repeated',
12363 type: 'ErrorCommand',
12364 name: 'failedPids',
12365 id: 31
12366 }, {
12367 rule: 'optional',
12368 type: 'string',
12369 name: 'next',
12370 id: 40
12371 }, {
12372 rule: 'optional',
12373 type: 'JsonObjectMessage',
12374 name: 'results',
12375 id: 100
12376 }, {
12377 rule: 'optional',
12378 type: 'JsonObjectMessage',
12379 name: 'where',
12380 id: 101
12381 }, {
12382 rule: 'optional',
12383 type: 'JsonObjectMessage',
12384 name: 'attr',
12385 id: 103
12386 }, {
12387 rule: 'optional',
12388 type: 'JsonObjectMessage',
12389 name: 'attrModified',
12390 id: 104
12391 }]
12392 }, {
12393 name: 'RoomCommand',
12394 syntax: 'proto2',
12395 fields: [{
12396 rule: 'optional',
12397 type: 'string',
12398 name: 'roomId',
12399 id: 1
12400 }, {
12401 rule: 'optional',
12402 type: 'string',
12403 name: 's',
12404 id: 2
12405 }, {
12406 rule: 'optional',
12407 type: 'int64',
12408 name: 't',
12409 id: 3
12410 }, {
12411 rule: 'optional',
12412 type: 'string',
12413 name: 'n',
12414 id: 4
12415 }, {
12416 rule: 'optional',
12417 type: 'bool',
12418 name: 'transient',
12419 id: 5
12420 }, {
12421 rule: 'repeated',
12422 type: 'string',
12423 name: 'roomPeerIds',
12424 id: 6
12425 }, {
12426 rule: 'optional',
12427 type: 'string',
12428 name: 'byPeerId',
12429 id: 7
12430 }]
12431 }, {
12432 name: 'LogsCommand',
12433 syntax: 'proto2',
12434 fields: [{
12435 rule: 'optional',
12436 type: 'string',
12437 name: 'cid',
12438 id: 1
12439 }, {
12440 rule: 'optional',
12441 type: 'int32',
12442 name: 'l',
12443 id: 2
12444 }, {
12445 rule: 'optional',
12446 type: 'int32',
12447 name: 'limit',
12448 id: 3
12449 }, {
12450 rule: 'optional',
12451 type: 'int64',
12452 name: 't',
12453 id: 4
12454 }, {
12455 rule: 'optional',
12456 type: 'int64',
12457 name: 'tt',
12458 id: 5
12459 }, {
12460 rule: 'optional',
12461 type: 'string',
12462 name: 'tmid',
12463 id: 6
12464 }, {
12465 rule: 'optional',
12466 type: 'string',
12467 name: 'mid',
12468 id: 7
12469 }, {
12470 rule: 'optional',
12471 type: 'string',
12472 name: 'checksum',
12473 id: 8
12474 }, {
12475 rule: 'optional',
12476 type: 'bool',
12477 name: 'stored',
12478 id: 9
12479 }, {
12480 rule: 'optional',
12481 type: 'QueryDirection',
12482 name: 'direction',
12483 id: 10,
12484 options: {
12485 "default": 'OLD'
12486 }
12487 }, {
12488 rule: 'optional',
12489 type: 'bool',
12490 name: 'tIncluded',
12491 id: 11
12492 }, {
12493 rule: 'optional',
12494 type: 'bool',
12495 name: 'ttIncluded',
12496 id: 12
12497 }, {
12498 rule: 'optional',
12499 type: 'int32',
12500 name: 'lctype',
12501 id: 13
12502 }, {
12503 rule: 'repeated',
12504 type: 'LogItem',
12505 name: 'logs',
12506 id: 105
12507 }],
12508 enums: [{
12509 name: 'QueryDirection',
12510 syntax: 'proto2',
12511 values: [{
12512 name: 'OLD',
12513 id: 1
12514 }, {
12515 name: 'NEW',
12516 id: 2
12517 }]
12518 }]
12519 }, {
12520 name: 'RcpCommand',
12521 syntax: 'proto2',
12522 fields: [{
12523 rule: 'optional',
12524 type: 'string',
12525 name: 'id',
12526 id: 1
12527 }, {
12528 rule: 'optional',
12529 type: 'string',
12530 name: 'cid',
12531 id: 2
12532 }, {
12533 rule: 'optional',
12534 type: 'int64',
12535 name: 't',
12536 id: 3
12537 }, {
12538 rule: 'optional',
12539 type: 'bool',
12540 name: 'read',
12541 id: 4
12542 }, {
12543 rule: 'optional',
12544 type: 'string',
12545 name: 'from',
12546 id: 5
12547 }]
12548 }, {
12549 name: 'ReadTuple',
12550 syntax: 'proto2',
12551 fields: [{
12552 rule: 'required',
12553 type: 'string',
12554 name: 'cid',
12555 id: 1
12556 }, {
12557 rule: 'optional',
12558 type: 'int64',
12559 name: 'timestamp',
12560 id: 2
12561 }, {
12562 rule: 'optional',
12563 type: 'string',
12564 name: 'mid',
12565 id: 3
12566 }]
12567 }, {
12568 name: 'MaxReadTuple',
12569 syntax: 'proto2',
12570 fields: [{
12571 rule: 'optional',
12572 type: 'string',
12573 name: 'pid',
12574 id: 1
12575 }, {
12576 rule: 'optional',
12577 type: 'int64',
12578 name: 'maxAckTimestamp',
12579 id: 2
12580 }, {
12581 rule: 'optional',
12582 type: 'int64',
12583 name: 'maxReadTimestamp',
12584 id: 3
12585 }]
12586 }, {
12587 name: 'ReadCommand',
12588 syntax: 'proto2',
12589 fields: [{
12590 rule: 'optional',
12591 type: 'string',
12592 name: 'cid',
12593 id: 1
12594 }, {
12595 rule: 'repeated',
12596 type: 'string',
12597 name: 'cids',
12598 id: 2
12599 }, {
12600 rule: 'repeated',
12601 type: 'ReadTuple',
12602 name: 'convs',
12603 id: 3
12604 }]
12605 }, {
12606 name: 'PresenceCommand',
12607 syntax: 'proto2',
12608 fields: [{
12609 rule: 'optional',
12610 type: 'StatusType',
12611 name: 'status',
12612 id: 1
12613 }, {
12614 rule: 'repeated',
12615 type: 'string',
12616 name: 'sessionPeerIds',
12617 id: 2
12618 }, {
12619 rule: 'optional',
12620 type: 'string',
12621 name: 'cid',
12622 id: 3
12623 }]
12624 }, {
12625 name: 'ReportCommand',
12626 syntax: 'proto2',
12627 fields: [{
12628 rule: 'optional',
12629 type: 'bool',
12630 name: 'initiative',
12631 id: 1
12632 }, {
12633 rule: 'optional',
12634 type: 'string',
12635 name: 'type',
12636 id: 2
12637 }, {
12638 rule: 'optional',
12639 type: 'string',
12640 name: 'data',
12641 id: 3
12642 }]
12643 }, {
12644 name: 'PatchItem',
12645 syntax: 'proto2',
12646 fields: [{
12647 rule: 'optional',
12648 type: 'string',
12649 name: 'cid',
12650 id: 1
12651 }, {
12652 rule: 'optional',
12653 type: 'string',
12654 name: 'mid',
12655 id: 2
12656 }, {
12657 rule: 'optional',
12658 type: 'int64',
12659 name: 'timestamp',
12660 id: 3
12661 }, {
12662 rule: 'optional',
12663 type: 'bool',
12664 name: 'recall',
12665 id: 4
12666 }, {
12667 rule: 'optional',
12668 type: 'string',
12669 name: 'data',
12670 id: 5
12671 }, {
12672 rule: 'optional',
12673 type: 'int64',
12674 name: 'patchTimestamp',
12675 id: 6
12676 }, {
12677 rule: 'optional',
12678 type: 'string',
12679 name: 'from',
12680 id: 7
12681 }, {
12682 rule: 'optional',
12683 type: 'bytes',
12684 name: 'binaryMsg',
12685 id: 8
12686 }, {
12687 rule: 'optional',
12688 type: 'bool',
12689 name: 'mentionAll',
12690 id: 9
12691 }, {
12692 rule: 'repeated',
12693 type: 'string',
12694 name: 'mentionPids',
12695 id: 10
12696 }, {
12697 rule: 'optional',
12698 type: 'int64',
12699 name: 'patchCode',
12700 id: 11
12701 }, {
12702 rule: 'optional',
12703 type: 'string',
12704 name: 'patchReason',
12705 id: 12
12706 }]
12707 }, {
12708 name: 'PatchCommand',
12709 syntax: 'proto2',
12710 fields: [{
12711 rule: 'repeated',
12712 type: 'PatchItem',
12713 name: 'patches',
12714 id: 1
12715 }, {
12716 rule: 'optional',
12717 type: 'int64',
12718 name: 'lastPatchTime',
12719 id: 2
12720 }]
12721 }, {
12722 name: 'PubsubCommand',
12723 syntax: 'proto2',
12724 fields: [{
12725 rule: 'optional',
12726 type: 'string',
12727 name: 'cid',
12728 id: 1
12729 }, {
12730 rule: 'repeated',
12731 type: 'string',
12732 name: 'cids',
12733 id: 2
12734 }, {
12735 rule: 'optional',
12736 type: 'string',
12737 name: 'topic',
12738 id: 3
12739 }, {
12740 rule: 'optional',
12741 type: 'string',
12742 name: 'subtopic',
12743 id: 4
12744 }, {
12745 rule: 'repeated',
12746 type: 'string',
12747 name: 'topics',
12748 id: 5
12749 }, {
12750 rule: 'repeated',
12751 type: 'string',
12752 name: 'subtopics',
12753 id: 6
12754 }, {
12755 rule: 'optional',
12756 type: 'JsonObjectMessage',
12757 name: 'results',
12758 id: 7
12759 }]
12760 }, {
12761 name: 'BlacklistCommand',
12762 syntax: 'proto2',
12763 fields: [{
12764 rule: 'optional',
12765 type: 'string',
12766 name: 'srcCid',
12767 id: 1
12768 }, {
12769 rule: 'repeated',
12770 type: 'string',
12771 name: 'toPids',
12772 id: 2
12773 }, {
12774 rule: 'optional',
12775 type: 'string',
12776 name: 'srcPid',
12777 id: 3
12778 }, {
12779 rule: 'repeated',
12780 type: 'string',
12781 name: 'toCids',
12782 id: 4
12783 }, {
12784 rule: 'optional',
12785 type: 'int32',
12786 name: 'limit',
12787 id: 5
12788 }, {
12789 rule: 'optional',
12790 type: 'string',
12791 name: 'next',
12792 id: 6
12793 }, {
12794 rule: 'repeated',
12795 type: 'string',
12796 name: 'blockedPids',
12797 id: 8
12798 }, {
12799 rule: 'repeated',
12800 type: 'string',
12801 name: 'blockedCids',
12802 id: 9
12803 }, {
12804 rule: 'repeated',
12805 type: 'string',
12806 name: 'allowedPids',
12807 id: 10
12808 }, {
12809 rule: 'repeated',
12810 type: 'ErrorCommand',
12811 name: 'failedPids',
12812 id: 11
12813 }, {
12814 rule: 'optional',
12815 type: 'int64',
12816 name: 't',
12817 id: 12
12818 }, {
12819 rule: 'optional',
12820 type: 'string',
12821 name: 'n',
12822 id: 13
12823 }, {
12824 rule: 'optional',
12825 type: 'string',
12826 name: 's',
12827 id: 14
12828 }]
12829 }, {
12830 name: 'GenericCommand',
12831 syntax: 'proto2',
12832 fields: [{
12833 rule: 'optional',
12834 type: 'CommandType',
12835 name: 'cmd',
12836 id: 1
12837 }, {
12838 rule: 'optional',
12839 type: 'OpType',
12840 name: 'op',
12841 id: 2
12842 }, {
12843 rule: 'optional',
12844 type: 'string',
12845 name: 'appId',
12846 id: 3
12847 }, {
12848 rule: 'optional',
12849 type: 'string',
12850 name: 'peerId',
12851 id: 4
12852 }, {
12853 rule: 'optional',
12854 type: 'int32',
12855 name: 'i',
12856 id: 5
12857 }, {
12858 rule: 'optional',
12859 type: 'string',
12860 name: 'installationId',
12861 id: 6
12862 }, {
12863 rule: 'optional',
12864 type: 'int32',
12865 name: 'priority',
12866 id: 7
12867 }, {
12868 rule: 'optional',
12869 type: 'int32',
12870 name: 'service',
12871 id: 8
12872 }, {
12873 rule: 'optional',
12874 type: 'int64',
12875 name: 'serverTs',
12876 id: 9
12877 }, {
12878 rule: 'optional',
12879 type: 'int64',
12880 name: 'clientTs',
12881 id: 10
12882 }, {
12883 rule: 'optional',
12884 type: 'int32',
12885 name: 'notificationType',
12886 id: 11
12887 }, {
12888 rule: 'optional',
12889 type: 'DataCommand',
12890 name: 'dataMessage',
12891 id: 101
12892 }, {
12893 rule: 'optional',
12894 type: 'SessionCommand',
12895 name: 'sessionMessage',
12896 id: 102
12897 }, {
12898 rule: 'optional',
12899 type: 'ErrorCommand',
12900 name: 'errorMessage',
12901 id: 103
12902 }, {
12903 rule: 'optional',
12904 type: 'DirectCommand',
12905 name: 'directMessage',
12906 id: 104
12907 }, {
12908 rule: 'optional',
12909 type: 'AckCommand',
12910 name: 'ackMessage',
12911 id: 105
12912 }, {
12913 rule: 'optional',
12914 type: 'UnreadCommand',
12915 name: 'unreadMessage',
12916 id: 106
12917 }, {
12918 rule: 'optional',
12919 type: 'ReadCommand',
12920 name: 'readMessage',
12921 id: 107
12922 }, {
12923 rule: 'optional',
12924 type: 'RcpCommand',
12925 name: 'rcpMessage',
12926 id: 108
12927 }, {
12928 rule: 'optional',
12929 type: 'LogsCommand',
12930 name: 'logsMessage',
12931 id: 109
12932 }, {
12933 rule: 'optional',
12934 type: 'ConvCommand',
12935 name: 'convMessage',
12936 id: 110
12937 }, {
12938 rule: 'optional',
12939 type: 'RoomCommand',
12940 name: 'roomMessage',
12941 id: 111
12942 }, {
12943 rule: 'optional',
12944 type: 'PresenceCommand',
12945 name: 'presenceMessage',
12946 id: 112
12947 }, {
12948 rule: 'optional',
12949 type: 'ReportCommand',
12950 name: 'reportMessage',
12951 id: 113
12952 }, {
12953 rule: 'optional',
12954 type: 'PatchCommand',
12955 name: 'patchMessage',
12956 id: 114
12957 }, {
12958 rule: 'optional',
12959 type: 'PubsubCommand',
12960 name: 'pubsubMessage',
12961 id: 115
12962 }, {
12963 rule: 'optional',
12964 type: 'BlacklistCommand',
12965 name: 'blacklistMessage',
12966 id: 116
12967 }]
12968 }],
12969 enums: [{
12970 name: 'CommandType',
12971 syntax: 'proto2',
12972 values: [{
12973 name: 'session',
12974 id: 0
12975 }, {
12976 name: 'conv',
12977 id: 1
12978 }, {
12979 name: 'direct',
12980 id: 2
12981 }, {
12982 name: 'ack',
12983 id: 3
12984 }, {
12985 name: 'rcp',
12986 id: 4
12987 }, {
12988 name: 'unread',
12989 id: 5
12990 }, {
12991 name: 'logs',
12992 id: 6
12993 }, {
12994 name: 'error',
12995 id: 7
12996 }, {
12997 name: 'login',
12998 id: 8
12999 }, {
13000 name: 'data',
13001 id: 9
13002 }, {
13003 name: 'room',
13004 id: 10
13005 }, {
13006 name: 'read',
13007 id: 11
13008 }, {
13009 name: 'presence',
13010 id: 12
13011 }, {
13012 name: 'report',
13013 id: 13
13014 }, {
13015 name: 'echo',
13016 id: 14
13017 }, {
13018 name: 'loggedin',
13019 id: 15
13020 }, {
13021 name: 'logout',
13022 id: 16
13023 }, {
13024 name: 'loggedout',
13025 id: 17
13026 }, {
13027 name: 'patch',
13028 id: 18
13029 }, {
13030 name: 'pubsub',
13031 id: 19
13032 }, {
13033 name: 'blacklist',
13034 id: 20
13035 }, {
13036 name: 'goaway',
13037 id: 21
13038 }]
13039 }, {
13040 name: 'OpType',
13041 syntax: 'proto2',
13042 values: [{
13043 name: 'open',
13044 id: 1
13045 }, {
13046 name: 'add',
13047 id: 2
13048 }, {
13049 name: 'remove',
13050 id: 3
13051 }, {
13052 name: 'close',
13053 id: 4
13054 }, {
13055 name: 'opened',
13056 id: 5
13057 }, {
13058 name: 'closed',
13059 id: 6
13060 }, {
13061 name: 'query',
13062 id: 7
13063 }, {
13064 name: 'query_result',
13065 id: 8
13066 }, {
13067 name: 'conflict',
13068 id: 9
13069 }, {
13070 name: 'added',
13071 id: 10
13072 }, {
13073 name: 'removed',
13074 id: 11
13075 }, {
13076 name: 'refresh',
13077 id: 12
13078 }, {
13079 name: 'refreshed',
13080 id: 13
13081 }, {
13082 name: 'start',
13083 id: 30
13084 }, {
13085 name: 'started',
13086 id: 31
13087 }, {
13088 name: 'joined',
13089 id: 32
13090 }, {
13091 name: 'members_joined',
13092 id: 33
13093 }, {
13094 name: 'left',
13095 id: 39
13096 }, {
13097 name: 'members_left',
13098 id: 40
13099 }, {
13100 name: 'results',
13101 id: 42
13102 }, {
13103 name: 'count',
13104 id: 43
13105 }, {
13106 name: 'result',
13107 id: 44
13108 }, {
13109 name: 'update',
13110 id: 45
13111 }, {
13112 name: 'updated',
13113 id: 46
13114 }, {
13115 name: 'mute',
13116 id: 47
13117 }, {
13118 name: 'unmute',
13119 id: 48
13120 }, {
13121 name: 'status',
13122 id: 49
13123 }, {
13124 name: 'members',
13125 id: 50
13126 }, {
13127 name: 'max_read',
13128 id: 51
13129 }, {
13130 name: 'is_member',
13131 id: 52
13132 }, {
13133 name: 'member_info_update',
13134 id: 53
13135 }, {
13136 name: 'member_info_updated',
13137 id: 54
13138 }, {
13139 name: 'member_info_changed',
13140 id: 55
13141 }, {
13142 name: 'join',
13143 id: 80
13144 }, {
13145 name: 'invite',
13146 id: 81
13147 }, {
13148 name: 'leave',
13149 id: 82
13150 }, {
13151 name: 'kick',
13152 id: 83
13153 }, {
13154 name: 'reject',
13155 id: 84
13156 }, {
13157 name: 'invited',
13158 id: 85
13159 }, {
13160 name: 'kicked',
13161 id: 86
13162 }, {
13163 name: 'upload',
13164 id: 100
13165 }, {
13166 name: 'uploaded',
13167 id: 101
13168 }, {
13169 name: 'subscribe',
13170 id: 120
13171 }, {
13172 name: 'subscribed',
13173 id: 121
13174 }, {
13175 name: 'unsubscribe',
13176 id: 122
13177 }, {
13178 name: 'unsubscribed',
13179 id: 123
13180 }, {
13181 name: 'is_subscribed',
13182 id: 124
13183 }, {
13184 name: 'modify',
13185 id: 150
13186 }, {
13187 name: 'modified',
13188 id: 151
13189 }, {
13190 name: 'block',
13191 id: 170
13192 }, {
13193 name: 'unblock',
13194 id: 171
13195 }, {
13196 name: 'blocked',
13197 id: 172
13198 }, {
13199 name: 'unblocked',
13200 id: 173
13201 }, {
13202 name: 'members_blocked',
13203 id: 174
13204 }, {
13205 name: 'members_unblocked',
13206 id: 175
13207 }, {
13208 name: 'check_block',
13209 id: 176
13210 }, {
13211 name: 'check_result',
13212 id: 177
13213 }, {
13214 name: 'add_shutup',
13215 id: 180
13216 }, {
13217 name: 'remove_shutup',
13218 id: 181
13219 }, {
13220 name: 'query_shutup',
13221 id: 182
13222 }, {
13223 name: 'shutup_added',
13224 id: 183
13225 }, {
13226 name: 'shutup_removed',
13227 id: 184
13228 }, {
13229 name: 'shutup_result',
13230 id: 185
13231 }, {
13232 name: 'shutuped',
13233 id: 186
13234 }, {
13235 name: 'unshutuped',
13236 id: 187
13237 }, {
13238 name: 'members_shutuped',
13239 id: 188
13240 }, {
13241 name: 'members_unshutuped',
13242 id: 189
13243 }, {
13244 name: 'check_shutup',
13245 id: 190
13246 }]
13247 }, {
13248 name: 'StatusType',
13249 syntax: 'proto2',
13250 values: [{
13251 name: 'on',
13252 id: 1
13253 }, {
13254 name: 'off',
13255 id: 2
13256 }]
13257 }],
13258 isNamespace: true
13259 }).build();
13260
13261 var _messages$push_server = messageCompiled.push_server.messages2,
13262 JsonObjectMessage = _messages$push_server.JsonObjectMessage,
13263 UnreadTuple = _messages$push_server.UnreadTuple,
13264 LogItem = _messages$push_server.LogItem,
13265 DataCommand = _messages$push_server.DataCommand,
13266 SessionCommand = _messages$push_server.SessionCommand,
13267 ErrorCommand = _messages$push_server.ErrorCommand,
13268 DirectCommand = _messages$push_server.DirectCommand,
13269 AckCommand = _messages$push_server.AckCommand,
13270 UnreadCommand = _messages$push_server.UnreadCommand,
13271 ConvCommand = _messages$push_server.ConvCommand,
13272 RoomCommand = _messages$push_server.RoomCommand,
13273 LogsCommand = _messages$push_server.LogsCommand,
13274 RcpCommand = _messages$push_server.RcpCommand,
13275 ReadTuple = _messages$push_server.ReadTuple,
13276 MaxReadTuple = _messages$push_server.MaxReadTuple,
13277 ReadCommand = _messages$push_server.ReadCommand,
13278 PresenceCommand = _messages$push_server.PresenceCommand,
13279 ReportCommand = _messages$push_server.ReportCommand,
13280 GenericCommand = _messages$push_server.GenericCommand,
13281 BlacklistCommand = _messages$push_server.BlacklistCommand,
13282 PatchCommand = _messages$push_server.PatchCommand,
13283 PatchItem = _messages$push_server.PatchItem,
13284 ConvMemberInfo = _messages$push_server.ConvMemberInfo,
13285 CommandType = _messages$push_server.CommandType,
13286 OpType = _messages$push_server.OpType,
13287 StatusType = _messages$push_server.StatusType;
13288
13289 var message = /*#__PURE__*/Object.freeze({
13290 __proto__: null,
13291 JsonObjectMessage: JsonObjectMessage,
13292 UnreadTuple: UnreadTuple,
13293 LogItem: LogItem,
13294 DataCommand: DataCommand,
13295 SessionCommand: SessionCommand,
13296 ErrorCommand: ErrorCommand,
13297 DirectCommand: DirectCommand,
13298 AckCommand: AckCommand,
13299 UnreadCommand: UnreadCommand,
13300 ConvCommand: ConvCommand,
13301 RoomCommand: RoomCommand,
13302 LogsCommand: LogsCommand,
13303 RcpCommand: RcpCommand,
13304 ReadTuple: ReadTuple,
13305 MaxReadTuple: MaxReadTuple,
13306 ReadCommand: ReadCommand,
13307 PresenceCommand: PresenceCommand,
13308 ReportCommand: ReportCommand,
13309 GenericCommand: GenericCommand,
13310 BlacklistCommand: BlacklistCommand,
13311 PatchCommand: PatchCommand,
13312 PatchItem: PatchItem,
13313 ConvMemberInfo: ConvMemberInfo,
13314 CommandType: CommandType,
13315 OpType: OpType,
13316 StatusType: StatusType
13317 });
13318
13319 var eventemitter3 = createCommonjsModule(function (module) {
13320
13321 var has = Object.prototype.hasOwnProperty
13322 , prefix = '~';
13323
13324 /**
13325 * Constructor to create a storage for our `EE` objects.
13326 * An `Events` instance is a plain object whose properties are event names.
13327 *
13328 * @constructor
13329 * @private
13330 */
13331 function Events() {}
13332
13333 //
13334 // We try to not inherit from `Object.prototype`. In some engines creating an
13335 // instance in this way is faster than calling `Object.create(null)` directly.
13336 // If `Object.create(null)` is not supported we prefix the event names with a
13337 // character to make sure that the built-in object properties are not
13338 // overridden or used as an attack vector.
13339 //
13340 if (Object.create) {
13341 Events.prototype = Object.create(null);
13342
13343 //
13344 // This hack is needed because the `__proto__` property is still inherited in
13345 // some old browsers like Android 4, iPhone 5.1, Opera 11 and Safari 5.
13346 //
13347 if (!new Events().__proto__) prefix = false;
13348 }
13349
13350 /**
13351 * Representation of a single event listener.
13352 *
13353 * @param {Function} fn The listener function.
13354 * @param {*} context The context to invoke the listener with.
13355 * @param {Boolean} [once=false] Specify if the listener is a one-time listener.
13356 * @constructor
13357 * @private
13358 */
13359 function EE(fn, context, once) {
13360 this.fn = fn;
13361 this.context = context;
13362 this.once = once || false;
13363 }
13364
13365 /**
13366 * Add a listener for a given event.
13367 *
13368 * @param {EventEmitter} emitter Reference to the `EventEmitter` instance.
13369 * @param {(String|Symbol)} event The event name.
13370 * @param {Function} fn The listener function.
13371 * @param {*} context The context to invoke the listener with.
13372 * @param {Boolean} once Specify if the listener is a one-time listener.
13373 * @returns {EventEmitter}
13374 * @private
13375 */
13376 function addListener(emitter, event, fn, context, once) {
13377 if (typeof fn !== 'function') {
13378 throw new TypeError('The listener must be a function');
13379 }
13380
13381 var listener = new EE(fn, context || emitter, once)
13382 , evt = prefix ? prefix + event : event;
13383
13384 if (!emitter._events[evt]) emitter._events[evt] = listener, emitter._eventsCount++;
13385 else if (!emitter._events[evt].fn) emitter._events[evt].push(listener);
13386 else emitter._events[evt] = [emitter._events[evt], listener];
13387
13388 return emitter;
13389 }
13390
13391 /**
13392 * Clear event by name.
13393 *
13394 * @param {EventEmitter} emitter Reference to the `EventEmitter` instance.
13395 * @param {(String|Symbol)} evt The Event name.
13396 * @private
13397 */
13398 function clearEvent(emitter, evt) {
13399 if (--emitter._eventsCount === 0) emitter._events = new Events();
13400 else delete emitter._events[evt];
13401 }
13402
13403 /**
13404 * Minimal `EventEmitter` interface that is molded against the Node.js
13405 * `EventEmitter` interface.
13406 *
13407 * @constructor
13408 * @public
13409 */
13410 function EventEmitter() {
13411 this._events = new Events();
13412 this._eventsCount = 0;
13413 }
13414
13415 /**
13416 * Return an array listing the events for which the emitter has registered
13417 * listeners.
13418 *
13419 * @returns {Array}
13420 * @public
13421 */
13422 EventEmitter.prototype.eventNames = function eventNames() {
13423 var names = []
13424 , events
13425 , name;
13426
13427 if (this._eventsCount === 0) return names;
13428
13429 for (name in (events = this._events)) {
13430 if (has.call(events, name)) names.push(prefix ? name.slice(1) : name);
13431 }
13432
13433 if (Object.getOwnPropertySymbols) {
13434 return names.concat(Object.getOwnPropertySymbols(events));
13435 }
13436
13437 return names;
13438 };
13439
13440 /**
13441 * Return the listeners registered for a given event.
13442 *
13443 * @param {(String|Symbol)} event The event name.
13444 * @returns {Array} The registered listeners.
13445 * @public
13446 */
13447 EventEmitter.prototype.listeners = function listeners(event) {
13448 var evt = prefix ? prefix + event : event
13449 , handlers = this._events[evt];
13450
13451 if (!handlers) return [];
13452 if (handlers.fn) return [handlers.fn];
13453
13454 for (var i = 0, l = handlers.length, ee = new Array(l); i < l; i++) {
13455 ee[i] = handlers[i].fn;
13456 }
13457
13458 return ee;
13459 };
13460
13461 /**
13462 * Return the number of listeners listening to a given event.
13463 *
13464 * @param {(String|Symbol)} event The event name.
13465 * @returns {Number} The number of listeners.
13466 * @public
13467 */
13468 EventEmitter.prototype.listenerCount = function listenerCount(event) {
13469 var evt = prefix ? prefix + event : event
13470 , listeners = this._events[evt];
13471
13472 if (!listeners) return 0;
13473 if (listeners.fn) return 1;
13474 return listeners.length;
13475 };
13476
13477 /**
13478 * Calls each of the listeners registered for a given event.
13479 *
13480 * @param {(String|Symbol)} event The event name.
13481 * @returns {Boolean} `true` if the event had listeners, else `false`.
13482 * @public
13483 */
13484 EventEmitter.prototype.emit = function emit(event, a1, a2, a3, a4, a5) {
13485 var evt = prefix ? prefix + event : event;
13486
13487 if (!this._events[evt]) return false;
13488
13489 var listeners = this._events[evt]
13490 , len = arguments.length
13491 , args
13492 , i;
13493
13494 if (listeners.fn) {
13495 if (listeners.once) this.removeListener(event, listeners.fn, undefined, true);
13496
13497 switch (len) {
13498 case 1: return listeners.fn.call(listeners.context), true;
13499 case 2: return listeners.fn.call(listeners.context, a1), true;
13500 case 3: return listeners.fn.call(listeners.context, a1, a2), true;
13501 case 4: return listeners.fn.call(listeners.context, a1, a2, a3), true;
13502 case 5: return listeners.fn.call(listeners.context, a1, a2, a3, a4), true;
13503 case 6: return listeners.fn.call(listeners.context, a1, a2, a3, a4, a5), true;
13504 }
13505
13506 for (i = 1, args = new Array(len -1); i < len; i++) {
13507 args[i - 1] = arguments[i];
13508 }
13509
13510 listeners.fn.apply(listeners.context, args);
13511 } else {
13512 var length = listeners.length
13513 , j;
13514
13515 for (i = 0; i < length; i++) {
13516 if (listeners[i].once) this.removeListener(event, listeners[i].fn, undefined, true);
13517
13518 switch (len) {
13519 case 1: listeners[i].fn.call(listeners[i].context); break;
13520 case 2: listeners[i].fn.call(listeners[i].context, a1); break;
13521 case 3: listeners[i].fn.call(listeners[i].context, a1, a2); break;
13522 case 4: listeners[i].fn.call(listeners[i].context, a1, a2, a3); break;
13523 default:
13524 if (!args) for (j = 1, args = new Array(len -1); j < len; j++) {
13525 args[j - 1] = arguments[j];
13526 }
13527
13528 listeners[i].fn.apply(listeners[i].context, args);
13529 }
13530 }
13531 }
13532
13533 return true;
13534 };
13535
13536 /**
13537 * Add a listener for a given event.
13538 *
13539 * @param {(String|Symbol)} event The event name.
13540 * @param {Function} fn The listener function.
13541 * @param {*} [context=this] The context to invoke the listener with.
13542 * @returns {EventEmitter} `this`.
13543 * @public
13544 */
13545 EventEmitter.prototype.on = function on(event, fn, context) {
13546 return addListener(this, event, fn, context, false);
13547 };
13548
13549 /**
13550 * Add a one-time listener for a given event.
13551 *
13552 * @param {(String|Symbol)} event The event name.
13553 * @param {Function} fn The listener function.
13554 * @param {*} [context=this] The context to invoke the listener with.
13555 * @returns {EventEmitter} `this`.
13556 * @public
13557 */
13558 EventEmitter.prototype.once = function once(event, fn, context) {
13559 return addListener(this, event, fn, context, true);
13560 };
13561
13562 /**
13563 * Remove the listeners of a given event.
13564 *
13565 * @param {(String|Symbol)} event The event name.
13566 * @param {Function} fn Only remove the listeners that match this function.
13567 * @param {*} context Only remove the listeners that have this context.
13568 * @param {Boolean} once Only remove one-time listeners.
13569 * @returns {EventEmitter} `this`.
13570 * @public
13571 */
13572 EventEmitter.prototype.removeListener = function removeListener(event, fn, context, once) {
13573 var evt = prefix ? prefix + event : event;
13574
13575 if (!this._events[evt]) return this;
13576 if (!fn) {
13577 clearEvent(this, evt);
13578 return this;
13579 }
13580
13581 var listeners = this._events[evt];
13582
13583 if (listeners.fn) {
13584 if (
13585 listeners.fn === fn &&
13586 (!once || listeners.once) &&
13587 (!context || listeners.context === context)
13588 ) {
13589 clearEvent(this, evt);
13590 }
13591 } else {
13592 for (var i = 0, events = [], length = listeners.length; i < length; i++) {
13593 if (
13594 listeners[i].fn !== fn ||
13595 (once && !listeners[i].once) ||
13596 (context && listeners[i].context !== context)
13597 ) {
13598 events.push(listeners[i]);
13599 }
13600 }
13601
13602 //
13603 // Reset the array, or remove it completely if we have no more listeners.
13604 //
13605 if (events.length) this._events[evt] = events.length === 1 ? events[0] : events;
13606 else clearEvent(this, evt);
13607 }
13608
13609 return this;
13610 };
13611
13612 /**
13613 * Remove all listeners, or those of the specified event.
13614 *
13615 * @param {(String|Symbol)} [event] The event name.
13616 * @returns {EventEmitter} `this`.
13617 * @public
13618 */
13619 EventEmitter.prototype.removeAllListeners = function removeAllListeners(event) {
13620 var evt;
13621
13622 if (event) {
13623 evt = prefix ? prefix + event : event;
13624 if (this._events[evt]) clearEvent(this, evt);
13625 } else {
13626 this._events = new Events();
13627 this._eventsCount = 0;
13628 }
13629
13630 return this;
13631 };
13632
13633 //
13634 // Alias methods names because people roll like that.
13635 //
13636 EventEmitter.prototype.off = EventEmitter.prototype.removeListener;
13637 EventEmitter.prototype.addListener = EventEmitter.prototype.on;
13638
13639 //
13640 // Expose the prefix.
13641 //
13642 EventEmitter.prefixed = prefix;
13643
13644 //
13645 // Allow `EventEmitter` to be imported as module namespace.
13646 //
13647 EventEmitter.EventEmitter = EventEmitter;
13648
13649 //
13650 // Expose the module.
13651 //
13652 {
13653 module.exports = EventEmitter;
13654 }
13655 });
13656
13657 var runtime_1 = createCommonjsModule(function (module) {
13658 /**
13659 * Copyright (c) 2014-present, Facebook, Inc.
13660 *
13661 * This source code is licensed under the MIT license found in the
13662 * LICENSE file in the root directory of this source tree.
13663 */
13664
13665 var runtime = (function (exports) {
13666
13667 var Op = Object.prototype;
13668 var hasOwn = Op.hasOwnProperty;
13669 var undefined$1; // More compressible than void 0.
13670 var $Symbol = typeof Symbol === "function" ? Symbol : {};
13671 var iteratorSymbol = $Symbol.iterator || "@@iterator";
13672 var asyncIteratorSymbol = $Symbol.asyncIterator || "@@asyncIterator";
13673 var toStringTagSymbol = $Symbol.toStringTag || "@@toStringTag";
13674
13675 function wrap(innerFn, outerFn, self, tryLocsList) {
13676 // If outerFn provided and outerFn.prototype is a Generator, then outerFn.prototype instanceof Generator.
13677 var protoGenerator = outerFn && outerFn.prototype instanceof Generator ? outerFn : Generator;
13678 var generator = Object.create(protoGenerator.prototype);
13679 var context = new Context(tryLocsList || []);
13680
13681 // The ._invoke method unifies the implementations of the .next,
13682 // .throw, and .return methods.
13683 generator._invoke = makeInvokeMethod(innerFn, self, context);
13684
13685 return generator;
13686 }
13687 exports.wrap = wrap;
13688
13689 // Try/catch helper to minimize deoptimizations. Returns a completion
13690 // record like context.tryEntries[i].completion. This interface could
13691 // have been (and was previously) designed to take a closure to be
13692 // invoked without arguments, but in all the cases we care about we
13693 // already have an existing method we want to call, so there's no need
13694 // to create a new function object. We can even get away with assuming
13695 // the method takes exactly one argument, since that happens to be true
13696 // in every case, so we don't have to touch the arguments object. The
13697 // only additional allocation required is the completion record, which
13698 // has a stable shape and so hopefully should be cheap to allocate.
13699 function tryCatch(fn, obj, arg) {
13700 try {
13701 return { type: "normal", arg: fn.call(obj, arg) };
13702 } catch (err) {
13703 return { type: "throw", arg: err };
13704 }
13705 }
13706
13707 var GenStateSuspendedStart = "suspendedStart";
13708 var GenStateSuspendedYield = "suspendedYield";
13709 var GenStateExecuting = "executing";
13710 var GenStateCompleted = "completed";
13711
13712 // Returning this object from the innerFn has the same effect as
13713 // breaking out of the dispatch switch statement.
13714 var ContinueSentinel = {};
13715
13716 // Dummy constructor functions that we use as the .constructor and
13717 // .constructor.prototype properties for functions that return Generator
13718 // objects. For full spec compliance, you may wish to configure your
13719 // minifier not to mangle the names of these two functions.
13720 function Generator() {}
13721 function GeneratorFunction() {}
13722 function GeneratorFunctionPrototype() {}
13723
13724 // This is a polyfill for %IteratorPrototype% for environments that
13725 // don't natively support it.
13726 var IteratorPrototype = {};
13727 IteratorPrototype[iteratorSymbol] = function () {
13728 return this;
13729 };
13730
13731 var getProto = Object.getPrototypeOf;
13732 var NativeIteratorPrototype = getProto && getProto(getProto(values([])));
13733 if (NativeIteratorPrototype &&
13734 NativeIteratorPrototype !== Op &&
13735 hasOwn.call(NativeIteratorPrototype, iteratorSymbol)) {
13736 // This environment has a native %IteratorPrototype%; use it instead
13737 // of the polyfill.
13738 IteratorPrototype = NativeIteratorPrototype;
13739 }
13740
13741 var Gp = GeneratorFunctionPrototype.prototype =
13742 Generator.prototype = Object.create(IteratorPrototype);
13743 GeneratorFunction.prototype = Gp.constructor = GeneratorFunctionPrototype;
13744 GeneratorFunctionPrototype.constructor = GeneratorFunction;
13745 GeneratorFunctionPrototype[toStringTagSymbol] =
13746 GeneratorFunction.displayName = "GeneratorFunction";
13747
13748 // Helper for defining the .next, .throw, and .return methods of the
13749 // Iterator interface in terms of a single ._invoke method.
13750 function defineIteratorMethods(prototype) {
13751 ["next", "throw", "return"].forEach(function(method) {
13752 prototype[method] = function(arg) {
13753 return this._invoke(method, arg);
13754 };
13755 });
13756 }
13757
13758 exports.isGeneratorFunction = function(genFun) {
13759 var ctor = typeof genFun === "function" && genFun.constructor;
13760 return ctor
13761 ? ctor === GeneratorFunction ||
13762 // For the native GeneratorFunction constructor, the best we can
13763 // do is to check its .name property.
13764 (ctor.displayName || ctor.name) === "GeneratorFunction"
13765 : false;
13766 };
13767
13768 exports.mark = function(genFun) {
13769 if (Object.setPrototypeOf) {
13770 Object.setPrototypeOf(genFun, GeneratorFunctionPrototype);
13771 } else {
13772 genFun.__proto__ = GeneratorFunctionPrototype;
13773 if (!(toStringTagSymbol in genFun)) {
13774 genFun[toStringTagSymbol] = "GeneratorFunction";
13775 }
13776 }
13777 genFun.prototype = Object.create(Gp);
13778 return genFun;
13779 };
13780
13781 // Within the body of any async function, `await x` is transformed to
13782 // `yield regeneratorRuntime.awrap(x)`, so that the runtime can test
13783 // `hasOwn.call(value, "__await")` to determine if the yielded value is
13784 // meant to be awaited.
13785 exports.awrap = function(arg) {
13786 return { __await: arg };
13787 };
13788
13789 function AsyncIterator(generator, PromiseImpl) {
13790 function invoke(method, arg, resolve, reject) {
13791 var record = tryCatch(generator[method], generator, arg);
13792 if (record.type === "throw") {
13793 reject(record.arg);
13794 } else {
13795 var result = record.arg;
13796 var value = result.value;
13797 if (value &&
13798 typeof value === "object" &&
13799 hasOwn.call(value, "__await")) {
13800 return PromiseImpl.resolve(value.__await).then(function(value) {
13801 invoke("next", value, resolve, reject);
13802 }, function(err) {
13803 invoke("throw", err, resolve, reject);
13804 });
13805 }
13806
13807 return PromiseImpl.resolve(value).then(function(unwrapped) {
13808 // When a yielded Promise is resolved, its final value becomes
13809 // the .value of the Promise<{value,done}> result for the
13810 // current iteration.
13811 result.value = unwrapped;
13812 resolve(result);
13813 }, function(error) {
13814 // If a rejected Promise was yielded, throw the rejection back
13815 // into the async generator function so it can be handled there.
13816 return invoke("throw", error, resolve, reject);
13817 });
13818 }
13819 }
13820
13821 var previousPromise;
13822
13823 function enqueue(method, arg) {
13824 function callInvokeWithMethodAndArg() {
13825 return new PromiseImpl(function(resolve, reject) {
13826 invoke(method, arg, resolve, reject);
13827 });
13828 }
13829
13830 return previousPromise =
13831 // If enqueue has been called before, then we want to wait until
13832 // all previous Promises have been resolved before calling invoke,
13833 // so that results are always delivered in the correct order. If
13834 // enqueue has not been called before, then it is important to
13835 // call invoke immediately, without waiting on a callback to fire,
13836 // so that the async generator function has the opportunity to do
13837 // any necessary setup in a predictable way. This predictability
13838 // is why the Promise constructor synchronously invokes its
13839 // executor callback, and why async functions synchronously
13840 // execute code before the first await. Since we implement simple
13841 // async functions in terms of async generators, it is especially
13842 // important to get this right, even though it requires care.
13843 previousPromise ? previousPromise.then(
13844 callInvokeWithMethodAndArg,
13845 // Avoid propagating failures to Promises returned by later
13846 // invocations of the iterator.
13847 callInvokeWithMethodAndArg
13848 ) : callInvokeWithMethodAndArg();
13849 }
13850
13851 // Define the unified helper method that is used to implement .next,
13852 // .throw, and .return (see defineIteratorMethods).
13853 this._invoke = enqueue;
13854 }
13855
13856 defineIteratorMethods(AsyncIterator.prototype);
13857 AsyncIterator.prototype[asyncIteratorSymbol] = function () {
13858 return this;
13859 };
13860 exports.AsyncIterator = AsyncIterator;
13861
13862 // Note that simple async functions are implemented on top of
13863 // AsyncIterator objects; they just return a Promise for the value of
13864 // the final result produced by the iterator.
13865 exports.async = function(innerFn, outerFn, self, tryLocsList, PromiseImpl) {
13866 if (PromiseImpl === void 0) PromiseImpl = Promise;
13867
13868 var iter = new AsyncIterator(
13869 wrap(innerFn, outerFn, self, tryLocsList),
13870 PromiseImpl
13871 );
13872
13873 return exports.isGeneratorFunction(outerFn)
13874 ? iter // If outerFn is a generator, return the full iterator.
13875 : iter.next().then(function(result) {
13876 return result.done ? result.value : iter.next();
13877 });
13878 };
13879
13880 function makeInvokeMethod(innerFn, self, context) {
13881 var state = GenStateSuspendedStart;
13882
13883 return function invoke(method, arg) {
13884 if (state === GenStateExecuting) {
13885 throw new Error("Generator is already running");
13886 }
13887
13888 if (state === GenStateCompleted) {
13889 if (method === "throw") {
13890 throw arg;
13891 }
13892
13893 // Be forgiving, per 25.3.3.3.3 of the spec:
13894 // https://people.mozilla.org/~jorendorff/es6-draft.html#sec-generatorresume
13895 return doneResult();
13896 }
13897
13898 context.method = method;
13899 context.arg = arg;
13900
13901 while (true) {
13902 var delegate = context.delegate;
13903 if (delegate) {
13904 var delegateResult = maybeInvokeDelegate(delegate, context);
13905 if (delegateResult) {
13906 if (delegateResult === ContinueSentinel) continue;
13907 return delegateResult;
13908 }
13909 }
13910
13911 if (context.method === "next") {
13912 // Setting context._sent for legacy support of Babel's
13913 // function.sent implementation.
13914 context.sent = context._sent = context.arg;
13915
13916 } else if (context.method === "throw") {
13917 if (state === GenStateSuspendedStart) {
13918 state = GenStateCompleted;
13919 throw context.arg;
13920 }
13921
13922 context.dispatchException(context.arg);
13923
13924 } else if (context.method === "return") {
13925 context.abrupt("return", context.arg);
13926 }
13927
13928 state = GenStateExecuting;
13929
13930 var record = tryCatch(innerFn, self, context);
13931 if (record.type === "normal") {
13932 // If an exception is thrown from innerFn, we leave state ===
13933 // GenStateExecuting and loop back for another invocation.
13934 state = context.done
13935 ? GenStateCompleted
13936 : GenStateSuspendedYield;
13937
13938 if (record.arg === ContinueSentinel) {
13939 continue;
13940 }
13941
13942 return {
13943 value: record.arg,
13944 done: context.done
13945 };
13946
13947 } else if (record.type === "throw") {
13948 state = GenStateCompleted;
13949 // Dispatch the exception by looping back around to the
13950 // context.dispatchException(context.arg) call above.
13951 context.method = "throw";
13952 context.arg = record.arg;
13953 }
13954 }
13955 };
13956 }
13957
13958 // Call delegate.iterator[context.method](context.arg) and handle the
13959 // result, either by returning a { value, done } result from the
13960 // delegate iterator, or by modifying context.method and context.arg,
13961 // setting context.delegate to null, and returning the ContinueSentinel.
13962 function maybeInvokeDelegate(delegate, context) {
13963 var method = delegate.iterator[context.method];
13964 if (method === undefined$1) {
13965 // A .throw or .return when the delegate iterator has no .throw
13966 // method always terminates the yield* loop.
13967 context.delegate = null;
13968
13969 if (context.method === "throw") {
13970 // Note: ["return"] must be used for ES3 parsing compatibility.
13971 if (delegate.iterator["return"]) {
13972 // If the delegate iterator has a return method, give it a
13973 // chance to clean up.
13974 context.method = "return";
13975 context.arg = undefined$1;
13976 maybeInvokeDelegate(delegate, context);
13977
13978 if (context.method === "throw") {
13979 // If maybeInvokeDelegate(context) changed context.method from
13980 // "return" to "throw", let that override the TypeError below.
13981 return ContinueSentinel;
13982 }
13983 }
13984
13985 context.method = "throw";
13986 context.arg = new TypeError(
13987 "The iterator does not provide a 'throw' method");
13988 }
13989
13990 return ContinueSentinel;
13991 }
13992
13993 var record = tryCatch(method, delegate.iterator, context.arg);
13994
13995 if (record.type === "throw") {
13996 context.method = "throw";
13997 context.arg = record.arg;
13998 context.delegate = null;
13999 return ContinueSentinel;
14000 }
14001
14002 var info = record.arg;
14003
14004 if (! info) {
14005 context.method = "throw";
14006 context.arg = new TypeError("iterator result is not an object");
14007 context.delegate = null;
14008 return ContinueSentinel;
14009 }
14010
14011 if (info.done) {
14012 // Assign the result of the finished delegate to the temporary
14013 // variable specified by delegate.resultName (see delegateYield).
14014 context[delegate.resultName] = info.value;
14015
14016 // Resume execution at the desired location (see delegateYield).
14017 context.next = delegate.nextLoc;
14018
14019 // If context.method was "throw" but the delegate handled the
14020 // exception, let the outer generator proceed normally. If
14021 // context.method was "next", forget context.arg since it has been
14022 // "consumed" by the delegate iterator. If context.method was
14023 // "return", allow the original .return call to continue in the
14024 // outer generator.
14025 if (context.method !== "return") {
14026 context.method = "next";
14027 context.arg = undefined$1;
14028 }
14029
14030 } else {
14031 // Re-yield the result returned by the delegate method.
14032 return info;
14033 }
14034
14035 // The delegate iterator is finished, so forget it and continue with
14036 // the outer generator.
14037 context.delegate = null;
14038 return ContinueSentinel;
14039 }
14040
14041 // Define Generator.prototype.{next,throw,return} in terms of the
14042 // unified ._invoke helper method.
14043 defineIteratorMethods(Gp);
14044
14045 Gp[toStringTagSymbol] = "Generator";
14046
14047 // A Generator should always return itself as the iterator object when the
14048 // @@iterator function is called on it. Some browsers' implementations of the
14049 // iterator prototype chain incorrectly implement this, causing the Generator
14050 // object to not be returned from this call. This ensures that doesn't happen.
14051 // See https://github.com/facebook/regenerator/issues/274 for more details.
14052 Gp[iteratorSymbol] = function() {
14053 return this;
14054 };
14055
14056 Gp.toString = function() {
14057 return "[object Generator]";
14058 };
14059
14060 function pushTryEntry(locs) {
14061 var entry = { tryLoc: locs[0] };
14062
14063 if (1 in locs) {
14064 entry.catchLoc = locs[1];
14065 }
14066
14067 if (2 in locs) {
14068 entry.finallyLoc = locs[2];
14069 entry.afterLoc = locs[3];
14070 }
14071
14072 this.tryEntries.push(entry);
14073 }
14074
14075 function resetTryEntry(entry) {
14076 var record = entry.completion || {};
14077 record.type = "normal";
14078 delete record.arg;
14079 entry.completion = record;
14080 }
14081
14082 function Context(tryLocsList) {
14083 // The root entry object (effectively a try statement without a catch
14084 // or a finally block) gives us a place to store values thrown from
14085 // locations where there is no enclosing try statement.
14086 this.tryEntries = [{ tryLoc: "root" }];
14087 tryLocsList.forEach(pushTryEntry, this);
14088 this.reset(true);
14089 }
14090
14091 exports.keys = function(object) {
14092 var keys = [];
14093 for (var key in object) {
14094 keys.push(key);
14095 }
14096 keys.reverse();
14097
14098 // Rather than returning an object with a next method, we keep
14099 // things simple and return the next function itself.
14100 return function next() {
14101 while (keys.length) {
14102 var key = keys.pop();
14103 if (key in object) {
14104 next.value = key;
14105 next.done = false;
14106 return next;
14107 }
14108 }
14109
14110 // To avoid creating an additional object, we just hang the .value
14111 // and .done properties off the next function object itself. This
14112 // also ensures that the minifier will not anonymize the function.
14113 next.done = true;
14114 return next;
14115 };
14116 };
14117
14118 function values(iterable) {
14119 if (iterable) {
14120 var iteratorMethod = iterable[iteratorSymbol];
14121 if (iteratorMethod) {
14122 return iteratorMethod.call(iterable);
14123 }
14124
14125 if (typeof iterable.next === "function") {
14126 return iterable;
14127 }
14128
14129 if (!isNaN(iterable.length)) {
14130 var i = -1, next = function next() {
14131 while (++i < iterable.length) {
14132 if (hasOwn.call(iterable, i)) {
14133 next.value = iterable[i];
14134 next.done = false;
14135 return next;
14136 }
14137 }
14138
14139 next.value = undefined$1;
14140 next.done = true;
14141
14142 return next;
14143 };
14144
14145 return next.next = next;
14146 }
14147 }
14148
14149 // Return an iterator with no values.
14150 return { next: doneResult };
14151 }
14152 exports.values = values;
14153
14154 function doneResult() {
14155 return { value: undefined$1, done: true };
14156 }
14157
14158 Context.prototype = {
14159 constructor: Context,
14160
14161 reset: function(skipTempReset) {
14162 this.prev = 0;
14163 this.next = 0;
14164 // Resetting context._sent for legacy support of Babel's
14165 // function.sent implementation.
14166 this.sent = this._sent = undefined$1;
14167 this.done = false;
14168 this.delegate = null;
14169
14170 this.method = "next";
14171 this.arg = undefined$1;
14172
14173 this.tryEntries.forEach(resetTryEntry);
14174
14175 if (!skipTempReset) {
14176 for (var name in this) {
14177 // Not sure about the optimal order of these conditions:
14178 if (name.charAt(0) === "t" &&
14179 hasOwn.call(this, name) &&
14180 !isNaN(+name.slice(1))) {
14181 this[name] = undefined$1;
14182 }
14183 }
14184 }
14185 },
14186
14187 stop: function() {
14188 this.done = true;
14189
14190 var rootEntry = this.tryEntries[0];
14191 var rootRecord = rootEntry.completion;
14192 if (rootRecord.type === "throw") {
14193 throw rootRecord.arg;
14194 }
14195
14196 return this.rval;
14197 },
14198
14199 dispatchException: function(exception) {
14200 if (this.done) {
14201 throw exception;
14202 }
14203
14204 var context = this;
14205 function handle(loc, caught) {
14206 record.type = "throw";
14207 record.arg = exception;
14208 context.next = loc;
14209
14210 if (caught) {
14211 // If the dispatched exception was caught by a catch block,
14212 // then let that catch block handle the exception normally.
14213 context.method = "next";
14214 context.arg = undefined$1;
14215 }
14216
14217 return !! caught;
14218 }
14219
14220 for (var i = this.tryEntries.length - 1; i >= 0; --i) {
14221 var entry = this.tryEntries[i];
14222 var record = entry.completion;
14223
14224 if (entry.tryLoc === "root") {
14225 // Exception thrown outside of any try block that could handle
14226 // it, so set the completion value of the entire function to
14227 // throw the exception.
14228 return handle("end");
14229 }
14230
14231 if (entry.tryLoc <= this.prev) {
14232 var hasCatch = hasOwn.call(entry, "catchLoc");
14233 var hasFinally = hasOwn.call(entry, "finallyLoc");
14234
14235 if (hasCatch && hasFinally) {
14236 if (this.prev < entry.catchLoc) {
14237 return handle(entry.catchLoc, true);
14238 } else if (this.prev < entry.finallyLoc) {
14239 return handle(entry.finallyLoc);
14240 }
14241
14242 } else if (hasCatch) {
14243 if (this.prev < entry.catchLoc) {
14244 return handle(entry.catchLoc, true);
14245 }
14246
14247 } else if (hasFinally) {
14248 if (this.prev < entry.finallyLoc) {
14249 return handle(entry.finallyLoc);
14250 }
14251
14252 } else {
14253 throw new Error("try statement without catch or finally");
14254 }
14255 }
14256 }
14257 },
14258
14259 abrupt: function(type, arg) {
14260 for (var i = this.tryEntries.length - 1; i >= 0; --i) {
14261 var entry = this.tryEntries[i];
14262 if (entry.tryLoc <= this.prev &&
14263 hasOwn.call(entry, "finallyLoc") &&
14264 this.prev < entry.finallyLoc) {
14265 var finallyEntry = entry;
14266 break;
14267 }
14268 }
14269
14270 if (finallyEntry &&
14271 (type === "break" ||
14272 type === "continue") &&
14273 finallyEntry.tryLoc <= arg &&
14274 arg <= finallyEntry.finallyLoc) {
14275 // Ignore the finally entry if control is not jumping to a
14276 // location outside the try/catch block.
14277 finallyEntry = null;
14278 }
14279
14280 var record = finallyEntry ? finallyEntry.completion : {};
14281 record.type = type;
14282 record.arg = arg;
14283
14284 if (finallyEntry) {
14285 this.method = "next";
14286 this.next = finallyEntry.finallyLoc;
14287 return ContinueSentinel;
14288 }
14289
14290 return this.complete(record);
14291 },
14292
14293 complete: function(record, afterLoc) {
14294 if (record.type === "throw") {
14295 throw record.arg;
14296 }
14297
14298 if (record.type === "break" ||
14299 record.type === "continue") {
14300 this.next = record.arg;
14301 } else if (record.type === "return") {
14302 this.rval = this.arg = record.arg;
14303 this.method = "return";
14304 this.next = "end";
14305 } else if (record.type === "normal" && afterLoc) {
14306 this.next = afterLoc;
14307 }
14308
14309 return ContinueSentinel;
14310 },
14311
14312 finish: function(finallyLoc) {
14313 for (var i = this.tryEntries.length - 1; i >= 0; --i) {
14314 var entry = this.tryEntries[i];
14315 if (entry.finallyLoc === finallyLoc) {
14316 this.complete(entry.completion, entry.afterLoc);
14317 resetTryEntry(entry);
14318 return ContinueSentinel;
14319 }
14320 }
14321 },
14322
14323 "catch": function(tryLoc) {
14324 for (var i = this.tryEntries.length - 1; i >= 0; --i) {
14325 var entry = this.tryEntries[i];
14326 if (entry.tryLoc === tryLoc) {
14327 var record = entry.completion;
14328 if (record.type === "throw") {
14329 var thrown = record.arg;
14330 resetTryEntry(entry);
14331 }
14332 return thrown;
14333 }
14334 }
14335
14336 // The context.catch method must only be called with a location
14337 // argument that corresponds to a known catch block.
14338 throw new Error("illegal catch attempt");
14339 },
14340
14341 delegateYield: function(iterable, resultName, nextLoc) {
14342 this.delegate = {
14343 iterator: values(iterable),
14344 resultName: resultName,
14345 nextLoc: nextLoc
14346 };
14347
14348 if (this.method === "next") {
14349 // Deliberately forget the last sent value so that we don't
14350 // accidentally pass it on to the delegate.
14351 this.arg = undefined$1;
14352 }
14353
14354 return ContinueSentinel;
14355 }
14356 };
14357
14358 // Regardless of whether this script is executing as a CommonJS module
14359 // or not, return the runtime object so that we can declare the variable
14360 // regeneratorRuntime in the outer scope, which allows this module to be
14361 // injected easily by `bin/regenerator --include-runtime script.js`.
14362 return exports;
14363
14364 }(
14365 // If this script is executing as a CommonJS module, use module.exports
14366 // as the regeneratorRuntime namespace. Otherwise create a new empty
14367 // object. Either way, the resulting object will be used to initialize
14368 // the regeneratorRuntime variable at the top of this file.
14369 module.exports
14370 ));
14371
14372 try {
14373 regeneratorRuntime = runtime;
14374 } catch (accidentalStrictMode) {
14375 // This module should not be running in strict mode, so the above
14376 // assignment should always work unless something is misconfigured. Just
14377 // in case runtime.js accidentally runs in strict mode, we can escape
14378 // strict mode using a global Function call. This could conceivably fail
14379 // if a Content Security Policy forbids using Function, but in that case
14380 // the proper solution is to fix the accidental strict mode problem. If
14381 // you've misconfigured your bundler to force strict mode and applied a
14382 // CSP to forbid Function, and you're not willing to fix either of those
14383 // problems, please detail your unique predicament in a GitHub issue.
14384 Function("r", "regeneratorRuntime = r")(runtime);
14385 }
14386 });
14387
14388 var regenerator = runtime_1;
14389
14390 function asyncGeneratorStep(gen, resolve, reject, _next, _throw, key, arg) {
14391 try {
14392 var info = gen[key](arg);
14393 var value = info.value;
14394 } catch (error) {
14395 reject(error);
14396 return;
14397 }
14398
14399 if (info.done) {
14400 resolve(value);
14401 } else {
14402 Promise.resolve(value).then(_next, _throw);
14403 }
14404 }
14405
14406 function _asyncToGenerator(fn) {
14407 return function () {
14408 var self = this,
14409 args = arguments;
14410 return new Promise(function (resolve, reject) {
14411 var gen = fn.apply(self, args);
14412
14413 function _next(value) {
14414 asyncGeneratorStep(gen, resolve, reject, _next, _throw, "next", value);
14415 }
14416
14417 function _throw(err) {
14418 asyncGeneratorStep(gen, resolve, reject, _next, _throw, "throw", err);
14419 }
14420
14421 _next(undefined);
14422 });
14423 };
14424 }
14425
14426 var asyncToGenerator = _asyncToGenerator;
14427
14428 function _arrayLikeToArray(arr, len) {
14429 if (len == null || len > arr.length) len = arr.length;
14430
14431 for (var i = 0, arr2 = new Array(len); i < len; i++) {
14432 arr2[i] = arr[i];
14433 }
14434
14435 return arr2;
14436 }
14437
14438 var arrayLikeToArray = _arrayLikeToArray;
14439
14440 function _arrayWithoutHoles$1(arr) {
14441 if (Array.isArray(arr)) return arrayLikeToArray(arr);
14442 }
14443
14444 var arrayWithoutHoles = _arrayWithoutHoles$1;
14445
14446 function _iterableToArray$1(iter) {
14447 if (typeof Symbol !== "undefined" && Symbol.iterator in Object(iter)) return Array.from(iter);
14448 }
14449
14450 var iterableToArray = _iterableToArray$1;
14451
14452 function _unsupportedIterableToArray(o, minLen) {
14453 if (!o) return;
14454 if (typeof o === "string") return arrayLikeToArray(o, minLen);
14455 var n = Object.prototype.toString.call(o).slice(8, -1);
14456 if (n === "Object" && o.constructor) n = o.constructor.name;
14457 if (n === "Map" || n === "Set") return Array.from(o);
14458 if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return arrayLikeToArray(o, minLen);
14459 }
14460
14461 var unsupportedIterableToArray = _unsupportedIterableToArray;
14462
14463 function _nonIterableSpread$1() {
14464 throw new TypeError("Invalid attempt to spread non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method.");
14465 }
14466
14467 var nonIterableSpread = _nonIterableSpread$1;
14468
14469 function _toConsumableArray$1(arr) {
14470 return arrayWithoutHoles(arr) || iterableToArray(arr) || unsupportedIterableToArray(arr) || nonIterableSpread();
14471 }
14472
14473 var toConsumableArray = _toConsumableArray$1;
14474
14475 function _objectWithoutPropertiesLoose(source, excluded) {
14476 if (source == null) return {};
14477 var target = {};
14478 var sourceKeys = Object.keys(source);
14479 var key, i;
14480
14481 for (i = 0; i < sourceKeys.length; i++) {
14482 key = sourceKeys[i];
14483 if (excluded.indexOf(key) >= 0) continue;
14484 target[key] = source[key];
14485 }
14486
14487 return target;
14488 }
14489
14490 var objectWithoutPropertiesLoose = _objectWithoutPropertiesLoose;
14491
14492 function _objectWithoutProperties(source, excluded) {
14493 if (source == null) return {};
14494 var target = objectWithoutPropertiesLoose(source, excluded);
14495 var key, i;
14496
14497 if (Object.getOwnPropertySymbols) {
14498 var sourceSymbolKeys = Object.getOwnPropertySymbols(source);
14499
14500 for (i = 0; i < sourceSymbolKeys.length; i++) {
14501 key = sourceSymbolKeys[i];
14502 if (excluded.indexOf(key) >= 0) continue;
14503 if (!Object.prototype.propertyIsEnumerable.call(source, key)) continue;
14504 target[key] = source[key];
14505 }
14506 }
14507
14508 return target;
14509 }
14510
14511 var objectWithoutProperties = _objectWithoutProperties;
14512
14513 function _assertThisInitialized(self) {
14514 if (self === void 0) {
14515 throw new ReferenceError("this hasn't been initialised - super() hasn't been called");
14516 }
14517
14518 return self;
14519 }
14520
14521 var assertThisInitialized = _assertThisInitialized;
14522
14523 function _inheritsLoose(subClass, superClass) {
14524 subClass.prototype = Object.create(superClass.prototype);
14525 subClass.prototype.constructor = subClass;
14526 subClass.__proto__ = superClass;
14527 }
14528
14529 var inheritsLoose = _inheritsLoose;
14530
14531 /**
14532 * Helpers.
14533 */
14534
14535 var s = 1000;
14536 var m = s * 60;
14537 var h = m * 60;
14538 var d = h * 24;
14539 var w = d * 7;
14540 var y = d * 365.25;
14541
14542 /**
14543 * Parse or format the given `val`.
14544 *
14545 * Options:
14546 *
14547 * - `long` verbose formatting [false]
14548 *
14549 * @param {String|Number} val
14550 * @param {Object} [options]
14551 * @throws {Error} throw an error if val is not a non-empty string or a number
14552 * @return {String|Number}
14553 * @api public
14554 */
14555
14556 var ms = function(val, options) {
14557 options = options || {};
14558 var type = typeof val;
14559 if (type === 'string' && val.length > 0) {
14560 return parse(val);
14561 } else if (type === 'number' && isNaN(val) === false) {
14562 return options.long ? fmtLong(val) : fmtShort(val);
14563 }
14564 throw new Error(
14565 'val is not a non-empty string or a valid number. val=' +
14566 JSON.stringify(val)
14567 );
14568 };
14569
14570 /**
14571 * Parse the given `str` and return milliseconds.
14572 *
14573 * @param {String} str
14574 * @return {Number}
14575 * @api private
14576 */
14577
14578 function parse(str) {
14579 str = String(str);
14580 if (str.length > 100) {
14581 return;
14582 }
14583 var match = /^((?:\d+)?\-?\d?\.?\d+) *(milliseconds?|msecs?|ms|seconds?|secs?|s|minutes?|mins?|m|hours?|hrs?|h|days?|d|weeks?|w|years?|yrs?|y)?$/i.exec(
14584 str
14585 );
14586 if (!match) {
14587 return;
14588 }
14589 var n = parseFloat(match[1]);
14590 var type = (match[2] || 'ms').toLowerCase();
14591 switch (type) {
14592 case 'years':
14593 case 'year':
14594 case 'yrs':
14595 case 'yr':
14596 case 'y':
14597 return n * y;
14598 case 'weeks':
14599 case 'week':
14600 case 'w':
14601 return n * w;
14602 case 'days':
14603 case 'day':
14604 case 'd':
14605 return n * d;
14606 case 'hours':
14607 case 'hour':
14608 case 'hrs':
14609 case 'hr':
14610 case 'h':
14611 return n * h;
14612 case 'minutes':
14613 case 'minute':
14614 case 'mins':
14615 case 'min':
14616 case 'm':
14617 return n * m;
14618 case 'seconds':
14619 case 'second':
14620 case 'secs':
14621 case 'sec':
14622 case 's':
14623 return n * s;
14624 case 'milliseconds':
14625 case 'millisecond':
14626 case 'msecs':
14627 case 'msec':
14628 case 'ms':
14629 return n;
14630 default:
14631 return undefined;
14632 }
14633 }
14634
14635 /**
14636 * Short format for `ms`.
14637 *
14638 * @param {Number} ms
14639 * @return {String}
14640 * @api private
14641 */
14642
14643 function fmtShort(ms) {
14644 var msAbs = Math.abs(ms);
14645 if (msAbs >= d) {
14646 return Math.round(ms / d) + 'd';
14647 }
14648 if (msAbs >= h) {
14649 return Math.round(ms / h) + 'h';
14650 }
14651 if (msAbs >= m) {
14652 return Math.round(ms / m) + 'm';
14653 }
14654 if (msAbs >= s) {
14655 return Math.round(ms / s) + 's';
14656 }
14657 return ms + 'ms';
14658 }
14659
14660 /**
14661 * Long format for `ms`.
14662 *
14663 * @param {Number} ms
14664 * @return {String}
14665 * @api private
14666 */
14667
14668 function fmtLong(ms) {
14669 var msAbs = Math.abs(ms);
14670 if (msAbs >= d) {
14671 return plural(ms, msAbs, d, 'day');
14672 }
14673 if (msAbs >= h) {
14674 return plural(ms, msAbs, h, 'hour');
14675 }
14676 if (msAbs >= m) {
14677 return plural(ms, msAbs, m, 'minute');
14678 }
14679 if (msAbs >= s) {
14680 return plural(ms, msAbs, s, 'second');
14681 }
14682 return ms + ' ms';
14683 }
14684
14685 /**
14686 * Pluralization helper.
14687 */
14688
14689 function plural(ms, msAbs, n, name) {
14690 var isPlural = msAbs >= n * 1.5;
14691 return Math.round(ms / n) + ' ' + name + (isPlural ? 's' : '');
14692 }
14693
14694 /**
14695 * This is the common logic for both the Node.js and web browser
14696 * implementations of `debug()`.
14697 */
14698 function setup(env) {
14699 createDebug.debug = createDebug;
14700 createDebug.default = createDebug;
14701 createDebug.coerce = coerce;
14702 createDebug.disable = disable;
14703 createDebug.enable = enable;
14704 createDebug.enabled = enabled;
14705 createDebug.humanize = ms;
14706 Object.keys(env).forEach(function (key) {
14707 createDebug[key] = env[key];
14708 });
14709 /**
14710 * Active `debug` instances.
14711 */
14712
14713 createDebug.instances = [];
14714 /**
14715 * The currently active debug mode names, and names to skip.
14716 */
14717
14718 createDebug.names = [];
14719 createDebug.skips = [];
14720 /**
14721 * Map of special "%n" handling functions, for the debug "format" argument.
14722 *
14723 * Valid key names are a single, lower or upper-case letter, i.e. "n" and "N".
14724 */
14725
14726 createDebug.formatters = {};
14727 /**
14728 * Selects a color for a debug namespace
14729 * @param {String} namespace The namespace string for the for the debug instance to be colored
14730 * @return {Number|String} An ANSI color code for the given namespace
14731 * @api private
14732 */
14733
14734 function selectColor(namespace) {
14735 var hash = 0;
14736
14737 for (var i = 0; i < namespace.length; i++) {
14738 hash = (hash << 5) - hash + namespace.charCodeAt(i);
14739 hash |= 0; // Convert to 32bit integer
14740 }
14741
14742 return createDebug.colors[Math.abs(hash) % createDebug.colors.length];
14743 }
14744
14745 createDebug.selectColor = selectColor;
14746 /**
14747 * Create a debugger with the given `namespace`.
14748 *
14749 * @param {String} namespace
14750 * @return {Function}
14751 * @api public
14752 */
14753
14754 function createDebug(namespace) {
14755 var prevTime;
14756
14757 function debug() {
14758 // Disabled?
14759 if (!debug.enabled) {
14760 return;
14761 }
14762
14763 for (var _len = arguments.length, args = new Array(_len), _key = 0; _key < _len; _key++) {
14764 args[_key] = arguments[_key];
14765 }
14766
14767 var self = debug; // Set `diff` timestamp
14768
14769 var curr = Number(new Date());
14770 var ms = curr - (prevTime || curr);
14771 self.diff = ms;
14772 self.prev = prevTime;
14773 self.curr = curr;
14774 prevTime = curr;
14775 args[0] = createDebug.coerce(args[0]);
14776
14777 if (typeof args[0] !== 'string') {
14778 // Anything else let's inspect with %O
14779 args.unshift('%O');
14780 } // Apply any `formatters` transformations
14781
14782
14783 var index = 0;
14784 args[0] = args[0].replace(/%([a-zA-Z%])/g, function (match, format) {
14785 // If we encounter an escaped % then don't increase the array index
14786 if (match === '%%') {
14787 return match;
14788 }
14789
14790 index++;
14791 var formatter = createDebug.formatters[format];
14792
14793 if (typeof formatter === 'function') {
14794 var val = args[index];
14795 match = formatter.call(self, val); // Now we need to remove `args[index]` since it's inlined in the `format`
14796
14797 args.splice(index, 1);
14798 index--;
14799 }
14800
14801 return match;
14802 }); // Apply env-specific formatting (colors, etc.)
14803
14804 createDebug.formatArgs.call(self, args);
14805 var logFn = self.log || createDebug.log;
14806 logFn.apply(self, args);
14807 }
14808
14809 debug.namespace = namespace;
14810 debug.enabled = createDebug.enabled(namespace);
14811 debug.useColors = createDebug.useColors();
14812 debug.color = selectColor(namespace);
14813 debug.destroy = destroy;
14814 debug.extend = extend; // Debug.formatArgs = formatArgs;
14815 // debug.rawLog = rawLog;
14816 // env-specific initialization logic for debug instances
14817
14818 if (typeof createDebug.init === 'function') {
14819 createDebug.init(debug);
14820 }
14821
14822 createDebug.instances.push(debug);
14823 return debug;
14824 }
14825
14826 function destroy() {
14827 var index = createDebug.instances.indexOf(this);
14828
14829 if (index !== -1) {
14830 createDebug.instances.splice(index, 1);
14831 return true;
14832 }
14833
14834 return false;
14835 }
14836
14837 function extend(namespace, delimiter) {
14838 return createDebug(this.namespace + (typeof delimiter === 'undefined' ? ':' : delimiter) + namespace);
14839 }
14840 /**
14841 * Enables a debug mode by namespaces. This can include modes
14842 * separated by a colon and wildcards.
14843 *
14844 * @param {String} namespaces
14845 * @api public
14846 */
14847
14848
14849 function enable(namespaces) {
14850 createDebug.save(namespaces);
14851 createDebug.names = [];
14852 createDebug.skips = [];
14853 var i;
14854 var split = (typeof namespaces === 'string' ? namespaces : '').split(/[\s,]+/);
14855 var len = split.length;
14856
14857 for (i = 0; i < len; i++) {
14858 if (!split[i]) {
14859 // ignore empty strings
14860 continue;
14861 }
14862
14863 namespaces = split[i].replace(/\*/g, '.*?');
14864
14865 if (namespaces[0] === '-') {
14866 createDebug.skips.push(new RegExp('^' + namespaces.substr(1) + '$'));
14867 } else {
14868 createDebug.names.push(new RegExp('^' + namespaces + '$'));
14869 }
14870 }
14871
14872 for (i = 0; i < createDebug.instances.length; i++) {
14873 var instance = createDebug.instances[i];
14874 instance.enabled = createDebug.enabled(instance.namespace);
14875 }
14876 }
14877 /**
14878 * Disable debug output.
14879 *
14880 * @api public
14881 */
14882
14883
14884 function disable() {
14885 createDebug.enable('');
14886 }
14887 /**
14888 * Returns true if the given mode name is enabled, false otherwise.
14889 *
14890 * @param {String} name
14891 * @return {Boolean}
14892 * @api public
14893 */
14894
14895
14896 function enabled(name) {
14897 if (name[name.length - 1] === '*') {
14898 return true;
14899 }
14900
14901 var i;
14902 var len;
14903
14904 for (i = 0, len = createDebug.skips.length; i < len; i++) {
14905 if (createDebug.skips[i].test(name)) {
14906 return false;
14907 }
14908 }
14909
14910 for (i = 0, len = createDebug.names.length; i < len; i++) {
14911 if (createDebug.names[i].test(name)) {
14912 return true;
14913 }
14914 }
14915
14916 return false;
14917 }
14918 /**
14919 * Coerce `val`.
14920 *
14921 * @param {Mixed} val
14922 * @return {Mixed}
14923 * @api private
14924 */
14925
14926
14927 function coerce(val) {
14928 if (val instanceof Error) {
14929 return val.stack || val.message;
14930 }
14931
14932 return val;
14933 }
14934
14935 createDebug.enable(createDebug.load());
14936 return createDebug;
14937 }
14938
14939 var common = setup;
14940
14941 var browser = createCommonjsModule(function (module, exports) {
14942
14943 function _typeof(obj) { if (typeof Symbol === "function" && typeof Symbol.iterator === "symbol") { _typeof = function _typeof(obj) { return typeof obj; }; } else { _typeof = function _typeof(obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; }; } return _typeof(obj); }
14944
14945 /* eslint-env browser */
14946
14947 /**
14948 * This is the web browser implementation of `debug()`.
14949 */
14950 exports.log = log;
14951 exports.formatArgs = formatArgs;
14952 exports.save = save;
14953 exports.load = load;
14954 exports.useColors = useColors;
14955 exports.storage = localstorage();
14956 /**
14957 * Colors.
14958 */
14959
14960 exports.colors = ['#0000CC', '#0000FF', '#0033CC', '#0033FF', '#0066CC', '#0066FF', '#0099CC', '#0099FF', '#00CC00', '#00CC33', '#00CC66', '#00CC99', '#00CCCC', '#00CCFF', '#3300CC', '#3300FF', '#3333CC', '#3333FF', '#3366CC', '#3366FF', '#3399CC', '#3399FF', '#33CC00', '#33CC33', '#33CC66', '#33CC99', '#33CCCC', '#33CCFF', '#6600CC', '#6600FF', '#6633CC', '#6633FF', '#66CC00', '#66CC33', '#9900CC', '#9900FF', '#9933CC', '#9933FF', '#99CC00', '#99CC33', '#CC0000', '#CC0033', '#CC0066', '#CC0099', '#CC00CC', '#CC00FF', '#CC3300', '#CC3333', '#CC3366', '#CC3399', '#CC33CC', '#CC33FF', '#CC6600', '#CC6633', '#CC9900', '#CC9933', '#CCCC00', '#CCCC33', '#FF0000', '#FF0033', '#FF0066', '#FF0099', '#FF00CC', '#FF00FF', '#FF3300', '#FF3333', '#FF3366', '#FF3399', '#FF33CC', '#FF33FF', '#FF6600', '#FF6633', '#FF9900', '#FF9933', '#FFCC00', '#FFCC33'];
14961 /**
14962 * Currently only WebKit-based Web Inspectors, Firefox >= v31,
14963 * and the Firebug extension (any Firefox version) are known
14964 * to support "%c" CSS customizations.
14965 *
14966 * TODO: add a `localStorage` variable to explicitly enable/disable colors
14967 */
14968 // eslint-disable-next-line complexity
14969
14970 function useColors() {
14971 // NB: In an Electron preload script, document will be defined but not fully
14972 // initialized. Since we know we're in Chrome, we'll just detect this case
14973 // explicitly
14974 if (typeof window !== 'undefined' && window.process && (window.process.type === 'renderer' || window.process.__nwjs)) {
14975 return true;
14976 } // Internet Explorer and Edge do not support colors.
14977
14978
14979 if (typeof navigator !== 'undefined' && navigator.userAgent && navigator.userAgent.toLowerCase().match(/(edge|trident)\/(\d+)/)) {
14980 return false;
14981 } // Is webkit? http://stackoverflow.com/a/16459606/376773
14982 // document is undefined in react-native: https://github.com/facebook/react-native/pull/1632
14983
14984
14985 return typeof document !== 'undefined' && document.documentElement && document.documentElement.style && document.documentElement.style.WebkitAppearance || // Is firebug? http://stackoverflow.com/a/398120/376773
14986 typeof window !== 'undefined' && window.console && (window.console.firebug || window.console.exception && window.console.table) || // Is firefox >= v31?
14987 // https://developer.mozilla.org/en-US/docs/Tools/Web_Console#Styling_messages
14988 typeof navigator !== 'undefined' && navigator.userAgent && navigator.userAgent.toLowerCase().match(/firefox\/(\d+)/) && parseInt(RegExp.$1, 10) >= 31 || // Double check webkit in userAgent just in case we are in a worker
14989 typeof navigator !== 'undefined' && navigator.userAgent && navigator.userAgent.toLowerCase().match(/applewebkit\/(\d+)/);
14990 }
14991 /**
14992 * Colorize log arguments if enabled.
14993 *
14994 * @api public
14995 */
14996
14997
14998 function formatArgs(args) {
14999 args[0] = (this.useColors ? '%c' : '') + this.namespace + (this.useColors ? ' %c' : ' ') + args[0] + (this.useColors ? '%c ' : ' ') + '+' + module.exports.humanize(this.diff);
15000
15001 if (!this.useColors) {
15002 return;
15003 }
15004
15005 var c = 'color: ' + this.color;
15006 args.splice(1, 0, c, 'color: inherit'); // The final "%c" is somewhat tricky, because there could be other
15007 // arguments passed either before or after the %c, so we need to
15008 // figure out the correct index to insert the CSS into
15009
15010 var index = 0;
15011 var lastC = 0;
15012 args[0].replace(/%[a-zA-Z%]/g, function (match) {
15013 if (match === '%%') {
15014 return;
15015 }
15016
15017 index++;
15018
15019 if (match === '%c') {
15020 // We only are interested in the *last* %c
15021 // (the user may have provided their own)
15022 lastC = index;
15023 }
15024 });
15025 args.splice(lastC, 0, c);
15026 }
15027 /**
15028 * Invokes `console.log()` when available.
15029 * No-op when `console.log` is not a "function".
15030 *
15031 * @api public
15032 */
15033
15034
15035 function log() {
15036 var _console;
15037
15038 // This hackery is required for IE8/9, where
15039 // the `console.log` function doesn't have 'apply'
15040 return (typeof console === "undefined" ? "undefined" : _typeof(console)) === 'object' && console.log && (_console = console).log.apply(_console, arguments);
15041 }
15042 /**
15043 * Save `namespaces`.
15044 *
15045 * @param {String} namespaces
15046 * @api private
15047 */
15048
15049
15050 function save(namespaces) {
15051 try {
15052 if (namespaces) {
15053 exports.storage.setItem('debug', namespaces);
15054 } else {
15055 exports.storage.removeItem('debug');
15056 }
15057 } catch (error) {// Swallow
15058 // XXX (@Qix-) should we be logging these?
15059 }
15060 }
15061 /**
15062 * Load `namespaces`.
15063 *
15064 * @return {String} returns the previously persisted debug modes
15065 * @api private
15066 */
15067
15068
15069 function load() {
15070 var r;
15071
15072 try {
15073 r = exports.storage.getItem('debug');
15074 } catch (error) {} // Swallow
15075 // XXX (@Qix-) should we be logging these?
15076 // If debug isn't set in LS, and we're in Electron, try to load $DEBUG
15077
15078
15079 if (!r && typeof process !== 'undefined' && 'env' in process) {
15080 r = process.env.DEBUG;
15081 }
15082
15083 return r;
15084 }
15085 /**
15086 * Localstorage attempts to return the localstorage.
15087 *
15088 * This is necessary because safari throws
15089 * when a user disables cookies/localstorage
15090 * and you attempt to access it.
15091 *
15092 * @return {LocalStorage}
15093 * @api private
15094 */
15095
15096
15097 function localstorage() {
15098 try {
15099 // TVMLKit (Apple TV JS Runtime) does not have a window object, just localStorage in the global context
15100 // The Browser also has localStorage in the global context.
15101 return localStorage;
15102 } catch (error) {// Swallow
15103 // XXX (@Qix-) should we be logging these?
15104 }
15105 }
15106
15107 module.exports = common(exports);
15108 var formatters = module.exports.formatters;
15109 /**
15110 * Map %j to `JSON.stringify()`, since no Web Inspectors do that by default.
15111 */
15112
15113 formatters.j = function (v) {
15114 try {
15115 return JSON.stringify(v);
15116 } catch (error) {
15117 return '[UnexpectedJSONParseError]: ' + error.message;
15118 }
15119 };
15120 });
15121 var browser_1 = browser.log;
15122 var browser_2 = browser.formatArgs;
15123 var browser_3 = browser.save;
15124 var browser_4 = browser.load;
15125 var browser_5 = browser.useColors;
15126 var browser_6 = browser.storage;
15127 var browser_7 = browser.colors;
15128
15129 /**
15130 * Copies the values of `source` to `array`.
15131 *
15132 * @private
15133 * @param {Array} source The array to copy values from.
15134 * @param {Array} [array=[]] The array to copy values to.
15135 * @returns {Array} Returns `array`.
15136 */
15137 function copyArray(source, array) {
15138 var index = -1,
15139 length = source.length;
15140
15141 array || (array = Array(length));
15142 while (++index < length) {
15143 array[index] = source[index];
15144 }
15145 return array;
15146 }
15147
15148 var _copyArray = copyArray;
15149
15150 /* Built-in method references for those with the same name as other `lodash` methods. */
15151 var nativeFloor = Math.floor,
15152 nativeRandom = Math.random;
15153
15154 /**
15155 * The base implementation of `_.random` without support for returning
15156 * floating-point numbers.
15157 *
15158 * @private
15159 * @param {number} lower The lower bound.
15160 * @param {number} upper The upper bound.
15161 * @returns {number} Returns the random number.
15162 */
15163 function baseRandom(lower, upper) {
15164 return lower + nativeFloor(nativeRandom() * (upper - lower + 1));
15165 }
15166
15167 var _baseRandom = baseRandom;
15168
15169 /**
15170 * A specialized version of `_.shuffle` which mutates and sets the size of `array`.
15171 *
15172 * @private
15173 * @param {Array} array The array to shuffle.
15174 * @param {number} [size=array.length] The size of `array`.
15175 * @returns {Array} Returns `array`.
15176 */
15177 function shuffleSelf(array, size) {
15178 var index = -1,
15179 length = array.length,
15180 lastIndex = length - 1;
15181
15182 size = size === undefined ? length : size;
15183 while (++index < size) {
15184 var rand = _baseRandom(index, lastIndex),
15185 value = array[rand];
15186
15187 array[rand] = array[index];
15188 array[index] = value;
15189 }
15190 array.length = size;
15191 return array;
15192 }
15193
15194 var _shuffleSelf = shuffleSelf;
15195
15196 /**
15197 * A specialized version of `_.shuffle` for arrays.
15198 *
15199 * @private
15200 * @param {Array} array The array to shuffle.
15201 * @returns {Array} Returns the new shuffled array.
15202 */
15203 function arrayShuffle(array) {
15204 return _shuffleSelf(_copyArray(array));
15205 }
15206
15207 var _arrayShuffle = arrayShuffle;
15208
15209 /**
15210 * A specialized version of `_.map` for arrays without support for iteratee
15211 * shorthands.
15212 *
15213 * @private
15214 * @param {Array} [array] The array to iterate over.
15215 * @param {Function} iteratee The function invoked per iteration.
15216 * @returns {Array} Returns the new mapped array.
15217 */
15218 function arrayMap(array, iteratee) {
15219 var index = -1,
15220 length = array == null ? 0 : array.length,
15221 result = Array(length);
15222
15223 while (++index < length) {
15224 result[index] = iteratee(array[index], index, array);
15225 }
15226 return result;
15227 }
15228
15229 var _arrayMap = arrayMap;
15230
15231 /**
15232 * The base implementation of `_.values` and `_.valuesIn` which creates an
15233 * array of `object` property values corresponding to the property names
15234 * of `props`.
15235 *
15236 * @private
15237 * @param {Object} object The object to query.
15238 * @param {Array} props The property names to get values for.
15239 * @returns {Object} Returns the array of property values.
15240 */
15241 function baseValues(object, props) {
15242 return _arrayMap(props, function(key) {
15243 return object[key];
15244 });
15245 }
15246
15247 var _baseValues = baseValues;
15248
15249 /**
15250 * The base implementation of `_.times` without support for iteratee shorthands
15251 * or max array length checks.
15252 *
15253 * @private
15254 * @param {number} n The number of times to invoke `iteratee`.
15255 * @param {Function} iteratee The function invoked per iteration.
15256 * @returns {Array} Returns the array of results.
15257 */
15258 function baseTimes(n, iteratee) {
15259 var index = -1,
15260 result = Array(n);
15261
15262 while (++index < n) {
15263 result[index] = iteratee(index);
15264 }
15265 return result;
15266 }
15267
15268 var _baseTimes = baseTimes;
15269
15270 /** Detect free variable `global` from Node.js. */
15271 var freeGlobal = typeof commonjsGlobal == 'object' && commonjsGlobal && commonjsGlobal.Object === Object && commonjsGlobal;
15272
15273 var _freeGlobal = freeGlobal;
15274
15275 /** Detect free variable `self`. */
15276 var freeSelf = typeof self == 'object' && self && self.Object === Object && self;
15277
15278 /** Used as a reference to the global object. */
15279 var root = _freeGlobal || freeSelf || Function('return this')();
15280
15281 var _root = root;
15282
15283 /** Built-in value references. */
15284 var Symbol$1 = _root.Symbol;
15285
15286 var _Symbol = Symbol$1;
15287
15288 /** Used for built-in method references. */
15289 var objectProto = Object.prototype;
15290
15291 /** Used to check objects for own properties. */
15292 var hasOwnProperty = objectProto.hasOwnProperty;
15293
15294 /**
15295 * Used to resolve the
15296 * [`toStringTag`](http://ecma-international.org/ecma-262/7.0/#sec-object.prototype.tostring)
15297 * of values.
15298 */
15299 var nativeObjectToString = objectProto.toString;
15300
15301 /** Built-in value references. */
15302 var symToStringTag = _Symbol ? _Symbol.toStringTag : undefined;
15303
15304 /**
15305 * A specialized version of `baseGetTag` which ignores `Symbol.toStringTag` values.
15306 *
15307 * @private
15308 * @param {*} value The value to query.
15309 * @returns {string} Returns the raw `toStringTag`.
15310 */
15311 function getRawTag(value) {
15312 var isOwn = hasOwnProperty.call(value, symToStringTag),
15313 tag = value[symToStringTag];
15314
15315 try {
15316 value[symToStringTag] = undefined;
15317 var unmasked = true;
15318 } catch (e) {}
15319
15320 var result = nativeObjectToString.call(value);
15321 if (unmasked) {
15322 if (isOwn) {
15323 value[symToStringTag] = tag;
15324 } else {
15325 delete value[symToStringTag];
15326 }
15327 }
15328 return result;
15329 }
15330
15331 var _getRawTag = getRawTag;
15332
15333 /** Used for built-in method references. */
15334 var objectProto$1 = Object.prototype;
15335
15336 /**
15337 * Used to resolve the
15338 * [`toStringTag`](http://ecma-international.org/ecma-262/7.0/#sec-object.prototype.tostring)
15339 * of values.
15340 */
15341 var nativeObjectToString$1 = objectProto$1.toString;
15342
15343 /**
15344 * Converts `value` to a string using `Object.prototype.toString`.
15345 *
15346 * @private
15347 * @param {*} value The value to convert.
15348 * @returns {string} Returns the converted string.
15349 */
15350 function objectToString(value) {
15351 return nativeObjectToString$1.call(value);
15352 }
15353
15354 var _objectToString = objectToString;
15355
15356 /** `Object#toString` result references. */
15357 var nullTag = '[object Null]',
15358 undefinedTag = '[object Undefined]';
15359
15360 /** Built-in value references. */
15361 var symToStringTag$1 = _Symbol ? _Symbol.toStringTag : undefined;
15362
15363 /**
15364 * The base implementation of `getTag` without fallbacks for buggy environments.
15365 *
15366 * @private
15367 * @param {*} value The value to query.
15368 * @returns {string} Returns the `toStringTag`.
15369 */
15370 function baseGetTag(value) {
15371 if (value == null) {
15372 return value === undefined ? undefinedTag : nullTag;
15373 }
15374 return (symToStringTag$1 && symToStringTag$1 in Object(value))
15375 ? _getRawTag(value)
15376 : _objectToString(value);
15377 }
15378
15379 var _baseGetTag = baseGetTag;
15380
15381 /**
15382 * Checks if `value` is object-like. A value is object-like if it's not `null`
15383 * and has a `typeof` result of "object".
15384 *
15385 * @static
15386 * @memberOf _
15387 * @since 4.0.0
15388 * @category Lang
15389 * @param {*} value The value to check.
15390 * @returns {boolean} Returns `true` if `value` is object-like, else `false`.
15391 * @example
15392 *
15393 * _.isObjectLike({});
15394 * // => true
15395 *
15396 * _.isObjectLike([1, 2, 3]);
15397 * // => true
15398 *
15399 * _.isObjectLike(_.noop);
15400 * // => false
15401 *
15402 * _.isObjectLike(null);
15403 * // => false
15404 */
15405 function isObjectLike(value) {
15406 return value != null && typeof value == 'object';
15407 }
15408
15409 var isObjectLike_1 = isObjectLike;
15410
15411 /** `Object#toString` result references. */
15412 var argsTag = '[object Arguments]';
15413
15414 /**
15415 * The base implementation of `_.isArguments`.
15416 *
15417 * @private
15418 * @param {*} value The value to check.
15419 * @returns {boolean} Returns `true` if `value` is an `arguments` object,
15420 */
15421 function baseIsArguments(value) {
15422 return isObjectLike_1(value) && _baseGetTag(value) == argsTag;
15423 }
15424
15425 var _baseIsArguments = baseIsArguments;
15426
15427 /** Used for built-in method references. */
15428 var objectProto$2 = Object.prototype;
15429
15430 /** Used to check objects for own properties. */
15431 var hasOwnProperty$1 = objectProto$2.hasOwnProperty;
15432
15433 /** Built-in value references. */
15434 var propertyIsEnumerable = objectProto$2.propertyIsEnumerable;
15435
15436 /**
15437 * Checks if `value` is likely an `arguments` object.
15438 *
15439 * @static
15440 * @memberOf _
15441 * @since 0.1.0
15442 * @category Lang
15443 * @param {*} value The value to check.
15444 * @returns {boolean} Returns `true` if `value` is an `arguments` object,
15445 * else `false`.
15446 * @example
15447 *
15448 * _.isArguments(function() { return arguments; }());
15449 * // => true
15450 *
15451 * _.isArguments([1, 2, 3]);
15452 * // => false
15453 */
15454 var isArguments = _baseIsArguments(function() { return arguments; }()) ? _baseIsArguments : function(value) {
15455 return isObjectLike_1(value) && hasOwnProperty$1.call(value, 'callee') &&
15456 !propertyIsEnumerable.call(value, 'callee');
15457 };
15458
15459 var isArguments_1 = isArguments;
15460
15461 /**
15462 * Checks if `value` is classified as an `Array` object.
15463 *
15464 * @static
15465 * @memberOf _
15466 * @since 0.1.0
15467 * @category Lang
15468 * @param {*} value The value to check.
15469 * @returns {boolean} Returns `true` if `value` is an array, else `false`.
15470 * @example
15471 *
15472 * _.isArray([1, 2, 3]);
15473 * // => true
15474 *
15475 * _.isArray(document.body.children);
15476 * // => false
15477 *
15478 * _.isArray('abc');
15479 * // => false
15480 *
15481 * _.isArray(_.noop);
15482 * // => false
15483 */
15484 var isArray = Array.isArray;
15485
15486 var isArray_1 = isArray;
15487
15488 /**
15489 * This method returns `false`.
15490 *
15491 * @static
15492 * @memberOf _
15493 * @since 4.13.0
15494 * @category Util
15495 * @returns {boolean} Returns `false`.
15496 * @example
15497 *
15498 * _.times(2, _.stubFalse);
15499 * // => [false, false]
15500 */
15501 function stubFalse() {
15502 return false;
15503 }
15504
15505 var stubFalse_1 = stubFalse;
15506
15507 var isBuffer_1 = createCommonjsModule(function (module, exports) {
15508 /** Detect free variable `exports`. */
15509 var freeExports = exports && !exports.nodeType && exports;
15510
15511 /** Detect free variable `module`. */
15512 var freeModule = freeExports && 'object' == 'object' && module && !module.nodeType && module;
15513
15514 /** Detect the popular CommonJS extension `module.exports`. */
15515 var moduleExports = freeModule && freeModule.exports === freeExports;
15516
15517 /** Built-in value references. */
15518 var Buffer = moduleExports ? _root.Buffer : undefined;
15519
15520 /* Built-in method references for those with the same name as other `lodash` methods. */
15521 var nativeIsBuffer = Buffer ? Buffer.isBuffer : undefined;
15522
15523 /**
15524 * Checks if `value` is a buffer.
15525 *
15526 * @static
15527 * @memberOf _
15528 * @since 4.3.0
15529 * @category Lang
15530 * @param {*} value The value to check.
15531 * @returns {boolean} Returns `true` if `value` is a buffer, else `false`.
15532 * @example
15533 *
15534 * _.isBuffer(new Buffer(2));
15535 * // => true
15536 *
15537 * _.isBuffer(new Uint8Array(2));
15538 * // => false
15539 */
15540 var isBuffer = nativeIsBuffer || stubFalse_1;
15541
15542 module.exports = isBuffer;
15543 });
15544
15545 /** Used as references for various `Number` constants. */
15546 var MAX_SAFE_INTEGER = 9007199254740991;
15547
15548 /** Used to detect unsigned integer values. */
15549 var reIsUint = /^(?:0|[1-9]\d*)$/;
15550
15551 /**
15552 * Checks if `value` is a valid array-like index.
15553 *
15554 * @private
15555 * @param {*} value The value to check.
15556 * @param {number} [length=MAX_SAFE_INTEGER] The upper bounds of a valid index.
15557 * @returns {boolean} Returns `true` if `value` is a valid index, else `false`.
15558 */
15559 function isIndex(value, length) {
15560 var type = typeof value;
15561 length = length == null ? MAX_SAFE_INTEGER : length;
15562
15563 return !!length &&
15564 (type == 'number' ||
15565 (type != 'symbol' && reIsUint.test(value))) &&
15566 (value > -1 && value % 1 == 0 && value < length);
15567 }
15568
15569 var _isIndex = isIndex;
15570
15571 /** Used as references for various `Number` constants. */
15572 var MAX_SAFE_INTEGER$1 = 9007199254740991;
15573
15574 /**
15575 * Checks if `value` is a valid array-like length.
15576 *
15577 * **Note:** This method is loosely based on
15578 * [`ToLength`](http://ecma-international.org/ecma-262/7.0/#sec-tolength).
15579 *
15580 * @static
15581 * @memberOf _
15582 * @since 4.0.0
15583 * @category Lang
15584 * @param {*} value The value to check.
15585 * @returns {boolean} Returns `true` if `value` is a valid length, else `false`.
15586 * @example
15587 *
15588 * _.isLength(3);
15589 * // => true
15590 *
15591 * _.isLength(Number.MIN_VALUE);
15592 * // => false
15593 *
15594 * _.isLength(Infinity);
15595 * // => false
15596 *
15597 * _.isLength('3');
15598 * // => false
15599 */
15600 function isLength(value) {
15601 return typeof value == 'number' &&
15602 value > -1 && value % 1 == 0 && value <= MAX_SAFE_INTEGER$1;
15603 }
15604
15605 var isLength_1 = isLength;
15606
15607 /** `Object#toString` result references. */
15608 var argsTag$1 = '[object Arguments]',
15609 arrayTag = '[object Array]',
15610 boolTag = '[object Boolean]',
15611 dateTag = '[object Date]',
15612 errorTag = '[object Error]',
15613 funcTag = '[object Function]',
15614 mapTag = '[object Map]',
15615 numberTag = '[object Number]',
15616 objectTag = '[object Object]',
15617 regexpTag = '[object RegExp]',
15618 setTag = '[object Set]',
15619 stringTag = '[object String]',
15620 weakMapTag = '[object WeakMap]';
15621
15622 var arrayBufferTag = '[object ArrayBuffer]',
15623 dataViewTag = '[object DataView]',
15624 float32Tag = '[object Float32Array]',
15625 float64Tag = '[object Float64Array]',
15626 int8Tag = '[object Int8Array]',
15627 int16Tag = '[object Int16Array]',
15628 int32Tag = '[object Int32Array]',
15629 uint8Tag = '[object Uint8Array]',
15630 uint8ClampedTag = '[object Uint8ClampedArray]',
15631 uint16Tag = '[object Uint16Array]',
15632 uint32Tag = '[object Uint32Array]';
15633
15634 /** Used to identify `toStringTag` values of typed arrays. */
15635 var typedArrayTags = {};
15636 typedArrayTags[float32Tag] = typedArrayTags[float64Tag] =
15637 typedArrayTags[int8Tag] = typedArrayTags[int16Tag] =
15638 typedArrayTags[int32Tag] = typedArrayTags[uint8Tag] =
15639 typedArrayTags[uint8ClampedTag] = typedArrayTags[uint16Tag] =
15640 typedArrayTags[uint32Tag] = true;
15641 typedArrayTags[argsTag$1] = typedArrayTags[arrayTag] =
15642 typedArrayTags[arrayBufferTag] = typedArrayTags[boolTag] =
15643 typedArrayTags[dataViewTag] = typedArrayTags[dateTag] =
15644 typedArrayTags[errorTag] = typedArrayTags[funcTag] =
15645 typedArrayTags[mapTag] = typedArrayTags[numberTag] =
15646 typedArrayTags[objectTag] = typedArrayTags[regexpTag] =
15647 typedArrayTags[setTag] = typedArrayTags[stringTag] =
15648 typedArrayTags[weakMapTag] = false;
15649
15650 /**
15651 * The base implementation of `_.isTypedArray` without Node.js optimizations.
15652 *
15653 * @private
15654 * @param {*} value The value to check.
15655 * @returns {boolean} Returns `true` if `value` is a typed array, else `false`.
15656 */
15657 function baseIsTypedArray(value) {
15658 return isObjectLike_1(value) &&
15659 isLength_1(value.length) && !!typedArrayTags[_baseGetTag(value)];
15660 }
15661
15662 var _baseIsTypedArray = baseIsTypedArray;
15663
15664 /**
15665 * The base implementation of `_.unary` without support for storing metadata.
15666 *
15667 * @private
15668 * @param {Function} func The function to cap arguments for.
15669 * @returns {Function} Returns the new capped function.
15670 */
15671 function baseUnary(func) {
15672 return function(value) {
15673 return func(value);
15674 };
15675 }
15676
15677 var _baseUnary = baseUnary;
15678
15679 var _nodeUtil = createCommonjsModule(function (module, exports) {
15680 /** Detect free variable `exports`. */
15681 var freeExports = exports && !exports.nodeType && exports;
15682
15683 /** Detect free variable `module`. */
15684 var freeModule = freeExports && 'object' == 'object' && module && !module.nodeType && module;
15685
15686 /** Detect the popular CommonJS extension `module.exports`. */
15687 var moduleExports = freeModule && freeModule.exports === freeExports;
15688
15689 /** Detect free variable `process` from Node.js. */
15690 var freeProcess = moduleExports && _freeGlobal.process;
15691
15692 /** Used to access faster Node.js helpers. */
15693 var nodeUtil = (function() {
15694 try {
15695 // Use `util.types` for Node.js 10+.
15696 var types = freeModule && freeModule.require && freeModule.require('util').types;
15697
15698 if (types) {
15699 return types;
15700 }
15701
15702 // Legacy `process.binding('util')` for Node.js < 10.
15703 return freeProcess && freeProcess.binding && freeProcess.binding('util');
15704 } catch (e) {}
15705 }());
15706
15707 module.exports = nodeUtil;
15708 });
15709
15710 /* Node.js helper references. */
15711 var nodeIsTypedArray = _nodeUtil && _nodeUtil.isTypedArray;
15712
15713 /**
15714 * Checks if `value` is classified as a typed array.
15715 *
15716 * @static
15717 * @memberOf _
15718 * @since 3.0.0
15719 * @category Lang
15720 * @param {*} value The value to check.
15721 * @returns {boolean} Returns `true` if `value` is a typed array, else `false`.
15722 * @example
15723 *
15724 * _.isTypedArray(new Uint8Array);
15725 * // => true
15726 *
15727 * _.isTypedArray([]);
15728 * // => false
15729 */
15730 var isTypedArray = nodeIsTypedArray ? _baseUnary(nodeIsTypedArray) : _baseIsTypedArray;
15731
15732 var isTypedArray_1 = isTypedArray;
15733
15734 /** Used for built-in method references. */
15735 var objectProto$3 = Object.prototype;
15736
15737 /** Used to check objects for own properties. */
15738 var hasOwnProperty$2 = objectProto$3.hasOwnProperty;
15739
15740 /**
15741 * Creates an array of the enumerable property names of the array-like `value`.
15742 *
15743 * @private
15744 * @param {*} value The value to query.
15745 * @param {boolean} inherited Specify returning inherited property names.
15746 * @returns {Array} Returns the array of property names.
15747 */
15748 function arrayLikeKeys(value, inherited) {
15749 var isArr = isArray_1(value),
15750 isArg = !isArr && isArguments_1(value),
15751 isBuff = !isArr && !isArg && isBuffer_1(value),
15752 isType = !isArr && !isArg && !isBuff && isTypedArray_1(value),
15753 skipIndexes = isArr || isArg || isBuff || isType,
15754 result = skipIndexes ? _baseTimes(value.length, String) : [],
15755 length = result.length;
15756
15757 for (var key in value) {
15758 if ((inherited || hasOwnProperty$2.call(value, key)) &&
15759 !(skipIndexes && (
15760 // Safari 9 has enumerable `arguments.length` in strict mode.
15761 key == 'length' ||
15762 // Node.js 0.10 has enumerable non-index properties on buffers.
15763 (isBuff && (key == 'offset' || key == 'parent')) ||
15764 // PhantomJS 2 has enumerable non-index properties on typed arrays.
15765 (isType && (key == 'buffer' || key == 'byteLength' || key == 'byteOffset')) ||
15766 // Skip index properties.
15767 _isIndex(key, length)
15768 ))) {
15769 result.push(key);
15770 }
15771 }
15772 return result;
15773 }
15774
15775 var _arrayLikeKeys = arrayLikeKeys;
15776
15777 /** Used for built-in method references. */
15778 var objectProto$4 = Object.prototype;
15779
15780 /**
15781 * Checks if `value` is likely a prototype object.
15782 *
15783 * @private
15784 * @param {*} value The value to check.
15785 * @returns {boolean} Returns `true` if `value` is a prototype, else `false`.
15786 */
15787 function isPrototype(value) {
15788 var Ctor = value && value.constructor,
15789 proto = (typeof Ctor == 'function' && Ctor.prototype) || objectProto$4;
15790
15791 return value === proto;
15792 }
15793
15794 var _isPrototype = isPrototype;
15795
15796 /**
15797 * Creates a unary function that invokes `func` with its argument transformed.
15798 *
15799 * @private
15800 * @param {Function} func The function to wrap.
15801 * @param {Function} transform The argument transform.
15802 * @returns {Function} Returns the new function.
15803 */
15804 function overArg(func, transform) {
15805 return function(arg) {
15806 return func(transform(arg));
15807 };
15808 }
15809
15810 var _overArg = overArg;
15811
15812 /* Built-in method references for those with the same name as other `lodash` methods. */
15813 var nativeKeys = _overArg(Object.keys, Object);
15814
15815 var _nativeKeys = nativeKeys;
15816
15817 /** Used for built-in method references. */
15818 var objectProto$5 = Object.prototype;
15819
15820 /** Used to check objects for own properties. */
15821 var hasOwnProperty$3 = objectProto$5.hasOwnProperty;
15822
15823 /**
15824 * The base implementation of `_.keys` which doesn't treat sparse arrays as dense.
15825 *
15826 * @private
15827 * @param {Object} object The object to query.
15828 * @returns {Array} Returns the array of property names.
15829 */
15830 function baseKeys(object) {
15831 if (!_isPrototype(object)) {
15832 return _nativeKeys(object);
15833 }
15834 var result = [];
15835 for (var key in Object(object)) {
15836 if (hasOwnProperty$3.call(object, key) && key != 'constructor') {
15837 result.push(key);
15838 }
15839 }
15840 return result;
15841 }
15842
15843 var _baseKeys = baseKeys;
15844
15845 /**
15846 * Checks if `value` is the
15847 * [language type](http://www.ecma-international.org/ecma-262/7.0/#sec-ecmascript-language-types)
15848 * of `Object`. (e.g. arrays, functions, objects, regexes, `new Number(0)`, and `new String('')`)
15849 *
15850 * @static
15851 * @memberOf _
15852 * @since 0.1.0
15853 * @category Lang
15854 * @param {*} value The value to check.
15855 * @returns {boolean} Returns `true` if `value` is an object, else `false`.
15856 * @example
15857 *
15858 * _.isObject({});
15859 * // => true
15860 *
15861 * _.isObject([1, 2, 3]);
15862 * // => true
15863 *
15864 * _.isObject(_.noop);
15865 * // => true
15866 *
15867 * _.isObject(null);
15868 * // => false
15869 */
15870 function isObject$1(value) {
15871 var type = typeof value;
15872 return value != null && (type == 'object' || type == 'function');
15873 }
15874
15875 var isObject_1$1 = isObject$1;
15876
15877 /** `Object#toString` result references. */
15878 var asyncTag = '[object AsyncFunction]',
15879 funcTag$1 = '[object Function]',
15880 genTag = '[object GeneratorFunction]',
15881 proxyTag = '[object Proxy]';
15882
15883 /**
15884 * Checks if `value` is classified as a `Function` object.
15885 *
15886 * @static
15887 * @memberOf _
15888 * @since 0.1.0
15889 * @category Lang
15890 * @param {*} value The value to check.
15891 * @returns {boolean} Returns `true` if `value` is a function, else `false`.
15892 * @example
15893 *
15894 * _.isFunction(_);
15895 * // => true
15896 *
15897 * _.isFunction(/abc/);
15898 * // => false
15899 */
15900 function isFunction(value) {
15901 if (!isObject_1$1(value)) {
15902 return false;
15903 }
15904 // The use of `Object#toString` avoids issues with the `typeof` operator
15905 // in Safari 9 which returns 'object' for typed arrays and other constructors.
15906 var tag = _baseGetTag(value);
15907 return tag == funcTag$1 || tag == genTag || tag == asyncTag || tag == proxyTag;
15908 }
15909
15910 var isFunction_1 = isFunction;
15911
15912 /**
15913 * Checks if `value` is array-like. A value is considered array-like if it's
15914 * not a function and has a `value.length` that's an integer greater than or
15915 * equal to `0` and less than or equal to `Number.MAX_SAFE_INTEGER`.
15916 *
15917 * @static
15918 * @memberOf _
15919 * @since 4.0.0
15920 * @category Lang
15921 * @param {*} value The value to check.
15922 * @returns {boolean} Returns `true` if `value` is array-like, else `false`.
15923 * @example
15924 *
15925 * _.isArrayLike([1, 2, 3]);
15926 * // => true
15927 *
15928 * _.isArrayLike(document.body.children);
15929 * // => true
15930 *
15931 * _.isArrayLike('abc');
15932 * // => true
15933 *
15934 * _.isArrayLike(_.noop);
15935 * // => false
15936 */
15937 function isArrayLike(value) {
15938 return value != null && isLength_1(value.length) && !isFunction_1(value);
15939 }
15940
15941 var isArrayLike_1 = isArrayLike;
15942
15943 /**
15944 * Creates an array of the own enumerable property names of `object`.
15945 *
15946 * **Note:** Non-object values are coerced to objects. See the
15947 * [ES spec](http://ecma-international.org/ecma-262/7.0/#sec-object.keys)
15948 * for more details.
15949 *
15950 * @static
15951 * @since 0.1.0
15952 * @memberOf _
15953 * @category Object
15954 * @param {Object} object The object to query.
15955 * @returns {Array} Returns the array of property names.
15956 * @example
15957 *
15958 * function Foo() {
15959 * this.a = 1;
15960 * this.b = 2;
15961 * }
15962 *
15963 * Foo.prototype.c = 3;
15964 *
15965 * _.keys(new Foo);
15966 * // => ['a', 'b'] (iteration order is not guaranteed)
15967 *
15968 * _.keys('hi');
15969 * // => ['0', '1']
15970 */
15971 function keys(object) {
15972 return isArrayLike_1(object) ? _arrayLikeKeys(object) : _baseKeys(object);
15973 }
15974
15975 var keys_1 = keys;
15976
15977 /**
15978 * Creates an array of the own enumerable string keyed property values of `object`.
15979 *
15980 * **Note:** Non-object values are coerced to objects.
15981 *
15982 * @static
15983 * @since 0.1.0
15984 * @memberOf _
15985 * @category Object
15986 * @param {Object} object The object to query.
15987 * @returns {Array} Returns the array of property values.
15988 * @example
15989 *
15990 * function Foo() {
15991 * this.a = 1;
15992 * this.b = 2;
15993 * }
15994 *
15995 * Foo.prototype.c = 3;
15996 *
15997 * _.values(new Foo);
15998 * // => [1, 2] (iteration order is not guaranteed)
15999 *
16000 * _.values('hi');
16001 * // => ['h', 'i']
16002 */
16003 function values(object) {
16004 return object == null ? [] : _baseValues(object, keys_1(object));
16005 }
16006
16007 var values_1 = values;
16008
16009 /**
16010 * The base implementation of `_.shuffle`.
16011 *
16012 * @private
16013 * @param {Array|Object} collection The collection to shuffle.
16014 * @returns {Array} Returns the new shuffled array.
16015 */
16016 function baseShuffle(collection) {
16017 return _shuffleSelf(values_1(collection));
16018 }
16019
16020 var _baseShuffle = baseShuffle;
16021
16022 /**
16023 * Creates an array of shuffled values, using a version of the
16024 * [Fisher-Yates shuffle](https://en.wikipedia.org/wiki/Fisher-Yates_shuffle).
16025 *
16026 * @static
16027 * @memberOf _
16028 * @since 0.1.0
16029 * @category Collection
16030 * @param {Array|Object} collection The collection to shuffle.
16031 * @returns {Array} Returns the new shuffled array.
16032 * @example
16033 *
16034 * _.shuffle([1, 2, 3, 4]);
16035 * // => [4, 1, 3, 2]
16036 */
16037 function shuffle(collection) {
16038 var func = isArray_1(collection) ? _arrayShuffle : _baseShuffle;
16039 return func(collection);
16040 }
16041
16042 var shuffle_1 = shuffle;
16043
16044 function _arrayWithHoles(arr) {
16045 if (Array.isArray(arr)) return arr;
16046 }
16047
16048 var arrayWithHoles = _arrayWithHoles;
16049
16050 function _nonIterableRest() {
16051 throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method.");
16052 }
16053
16054 var nonIterableRest = _nonIterableRest;
16055
16056 function _toArray(arr) {
16057 return arrayWithHoles(arr) || iterableToArray(arr) || unsupportedIterableToArray(arr) || nonIterableRest();
16058 }
16059
16060 var toArray = _toArray;
16061
16062 function _defineProperties(target, props) {
16063 for (var i = 0; i < props.length; i++) {
16064 var descriptor = props[i];
16065 descriptor.enumerable = descriptor.enumerable || false;
16066 descriptor.configurable = true;
16067 if ("value" in descriptor) descriptor.writable = true;
16068 Object.defineProperty(target, descriptor.key, descriptor);
16069 }
16070 }
16071
16072 function _createClass(Constructor, protoProps, staticProps) {
16073 if (protoProps) _defineProperties(Constructor.prototype, protoProps);
16074 if (staticProps) _defineProperties(Constructor, staticProps);
16075 return Constructor;
16076 }
16077
16078 var createClass = _createClass;
16079
16080 function _applyDecoratedDescriptor(target, property, decorators, descriptor, context) {
16081 var desc = {};
16082 Object.keys(descriptor).forEach(function (key) {
16083 desc[key] = descriptor[key];
16084 });
16085 desc.enumerable = !!desc.enumerable;
16086 desc.configurable = !!desc.configurable;
16087
16088 if ('value' in desc || desc.initializer) {
16089 desc.writable = true;
16090 }
16091
16092 desc = decorators.slice().reverse().reduce(function (desc, decorator) {
16093 return decorator(target, property, desc) || desc;
16094 }, desc);
16095
16096 if (context && desc.initializer !== void 0) {
16097 desc.value = desc.initializer ? desc.initializer.call(context) : void 0;
16098 desc.initializer = undefined;
16099 }
16100
16101 if (desc.initializer === void 0) {
16102 Object.defineProperty(target, property, desc);
16103 desc = null;
16104 }
16105
16106 return desc;
16107 }
16108
16109 var applyDecoratedDescriptor = _applyDecoratedDescriptor;
16110
16111 var stateMachine = createCommonjsModule(function (module, exports) {
16112 /*
16113
16114 Javascript State Machine Library - https://github.com/jakesgordon/javascript-state-machine
16115
16116 Copyright (c) 2012, 2013, 2014, 2015, Jake Gordon and contributors
16117 Released under the MIT license - https://github.com/jakesgordon/javascript-state-machine/blob/master/LICENSE
16118
16119 */
16120
16121 (function () {
16122
16123 var StateMachine = {
16124
16125 //---------------------------------------------------------------------------
16126
16127 VERSION: "2.4.0",
16128
16129 //---------------------------------------------------------------------------
16130
16131 Result: {
16132 SUCCEEDED: 1, // the event transitioned successfully from one state to another
16133 NOTRANSITION: 2, // the event was successfull but no state transition was necessary
16134 CANCELLED: 3, // the event was cancelled by the caller in a beforeEvent callback
16135 PENDING: 4 // the event is asynchronous and the caller is in control of when the transition occurs
16136 },
16137
16138 Error: {
16139 INVALID_TRANSITION: 100, // caller tried to fire an event that was innapropriate in the current state
16140 PENDING_TRANSITION: 200, // caller tried to fire an event while an async transition was still pending
16141 INVALID_CALLBACK: 300 // caller provided callback function threw an exception
16142 },
16143
16144 WILDCARD: '*',
16145 ASYNC: 'async',
16146
16147 //---------------------------------------------------------------------------
16148
16149 create: function(cfg, target) {
16150
16151 var initial = (typeof cfg.initial == 'string') ? { state: cfg.initial } : cfg.initial; // allow for a simple string, or an object with { state: 'foo', event: 'setup', defer: true|false }
16152 var terminal = cfg.terminal || cfg['final'];
16153 var fsm = target || cfg.target || {};
16154 var events = cfg.events || [];
16155 var callbacks = cfg.callbacks || {};
16156 var map = {}; // track state transitions allowed for an event { event: { from: [ to ] } }
16157 var transitions = {}; // track events allowed from a state { state: [ event ] }
16158
16159 var add = function(e) {
16160 var from = Array.isArray(e.from) ? e.from : (e.from ? [e.from] : [StateMachine.WILDCARD]); // allow 'wildcard' transition if 'from' is not specified
16161 map[e.name] = map[e.name] || {};
16162 for (var n = 0 ; n < from.length ; n++) {
16163 transitions[from[n]] = transitions[from[n]] || [];
16164 transitions[from[n]].push(e.name);
16165
16166 map[e.name][from[n]] = e.to || from[n]; // allow no-op transition if 'to' is not specified
16167 }
16168 if (e.to)
16169 transitions[e.to] = transitions[e.to] || [];
16170 };
16171
16172 if (initial) {
16173 initial.event = initial.event || 'startup';
16174 add({ name: initial.event, from: 'none', to: initial.state });
16175 }
16176
16177 for(var n = 0 ; n < events.length ; n++)
16178 add(events[n]);
16179
16180 for(var name in map) {
16181 if (map.hasOwnProperty(name))
16182 fsm[name] = StateMachine.buildEvent(name, map[name]);
16183 }
16184
16185 for(var name in callbacks) {
16186 if (callbacks.hasOwnProperty(name))
16187 fsm[name] = callbacks[name];
16188 }
16189
16190 fsm.current = 'none';
16191 fsm.is = function(state) { return Array.isArray(state) ? (state.indexOf(this.current) >= 0) : (this.current === state); };
16192 fsm.can = function(event) { return !this.transition && (map[event] !== undefined) && (map[event].hasOwnProperty(this.current) || map[event].hasOwnProperty(StateMachine.WILDCARD)); };
16193 fsm.cannot = function(event) { return !this.can(event); };
16194 fsm.transitions = function() { return (transitions[this.current] || []).concat(transitions[StateMachine.WILDCARD] || []); };
16195 fsm.isFinished = function() { return this.is(terminal); };
16196 fsm.error = cfg.error || function(name, from, to, args, error, msg, e) { throw e || msg; }; // default behavior when something unexpected happens is to throw an exception, but caller can override this behavior if desired (see github issue #3 and #17)
16197 fsm.states = function() { return Object.keys(transitions).sort() };
16198
16199 if (initial && !initial.defer)
16200 fsm[initial.event]();
16201
16202 return fsm;
16203
16204 },
16205
16206 //===========================================================================
16207
16208 doCallback: function(fsm, func, name, from, to, args) {
16209 if (func) {
16210 try {
16211 return func.apply(fsm, [name, from, to].concat(args));
16212 }
16213 catch(e) {
16214 return fsm.error(name, from, to, args, StateMachine.Error.INVALID_CALLBACK, "an exception occurred in a caller-provided callback function", e);
16215 }
16216 }
16217 },
16218
16219 beforeAnyEvent: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onbeforeevent'], name, from, to, args); },
16220 afterAnyEvent: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onafterevent'] || fsm['onevent'], name, from, to, args); },
16221 leaveAnyState: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onleavestate'], name, from, to, args); },
16222 enterAnyState: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onenterstate'] || fsm['onstate'], name, from, to, args); },
16223 changeState: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onchangestate'], name, from, to, args); },
16224
16225 beforeThisEvent: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onbefore' + name], name, from, to, args); },
16226 afterThisEvent: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onafter' + name] || fsm['on' + name], name, from, to, args); },
16227 leaveThisState: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onleave' + from], name, from, to, args); },
16228 enterThisState: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onenter' + to] || fsm['on' + to], name, from, to, args); },
16229
16230 beforeEvent: function(fsm, name, from, to, args) {
16231 if ((false === StateMachine.beforeThisEvent(fsm, name, from, to, args)) ||
16232 (false === StateMachine.beforeAnyEvent( fsm, name, from, to, args)))
16233 return false;
16234 },
16235
16236 afterEvent: function(fsm, name, from, to, args) {
16237 StateMachine.afterThisEvent(fsm, name, from, to, args);
16238 StateMachine.afterAnyEvent( fsm, name, from, to, args);
16239 },
16240
16241 leaveState: function(fsm, name, from, to, args) {
16242 var specific = StateMachine.leaveThisState(fsm, name, from, to, args),
16243 general = StateMachine.leaveAnyState( fsm, name, from, to, args);
16244 if ((false === specific) || (false === general))
16245 return false;
16246 else if ((StateMachine.ASYNC === specific) || (StateMachine.ASYNC === general))
16247 return StateMachine.ASYNC;
16248 },
16249
16250 enterState: function(fsm, name, from, to, args) {
16251 StateMachine.enterThisState(fsm, name, from, to, args);
16252 StateMachine.enterAnyState( fsm, name, from, to, args);
16253 },
16254
16255 //===========================================================================
16256
16257 buildEvent: function(name, map) {
16258 return function() {
16259
16260 var from = this.current;
16261 var to = map[from] || (map[StateMachine.WILDCARD] != StateMachine.WILDCARD ? map[StateMachine.WILDCARD] : from) || from;
16262 var args = Array.prototype.slice.call(arguments); // turn arguments into pure array
16263
16264 if (this.transition)
16265 return this.error(name, from, to, args, StateMachine.Error.PENDING_TRANSITION, "event " + name + " inappropriate because previous transition did not complete");
16266
16267 if (this.cannot(name))
16268 return this.error(name, from, to, args, StateMachine.Error.INVALID_TRANSITION, "event " + name + " inappropriate in current state " + this.current);
16269
16270 if (false === StateMachine.beforeEvent(this, name, from, to, args))
16271 return StateMachine.Result.CANCELLED;
16272
16273 if (from === to) {
16274 StateMachine.afterEvent(this, name, from, to, args);
16275 return StateMachine.Result.NOTRANSITION;
16276 }
16277
16278 // prepare a transition method for use EITHER lower down, or by caller if they want an async transition (indicated by an ASYNC return value from leaveState)
16279 var fsm = this;
16280 this.transition = function() {
16281 fsm.transition = null; // this method should only ever be called once
16282 fsm.current = to;
16283 StateMachine.enterState( fsm, name, from, to, args);
16284 StateMachine.changeState(fsm, name, from, to, args);
16285 StateMachine.afterEvent( fsm, name, from, to, args);
16286 return StateMachine.Result.SUCCEEDED;
16287 };
16288 this.transition.cancel = function() { // provide a way for caller to cancel async transition if desired (issue #22)
16289 fsm.transition = null;
16290 StateMachine.afterEvent(fsm, name, from, to, args);
16291 };
16292
16293 var leave = StateMachine.leaveState(this, name, from, to, args);
16294 if (false === leave) {
16295 this.transition = null;
16296 return StateMachine.Result.CANCELLED;
16297 }
16298 else if (StateMachine.ASYNC === leave) {
16299 return StateMachine.Result.PENDING;
16300 }
16301 else {
16302 if (this.transition) // need to check in case user manually called transition() but forgot to return StateMachine.ASYNC
16303 return this.transition();
16304 }
16305
16306 };
16307 }
16308
16309 }; // StateMachine
16310
16311 //===========================================================================
16312
16313 //======
16314 // NODE
16315 //======
16316 {
16317 if ( module.exports) {
16318 exports = module.exports = StateMachine;
16319 }
16320 exports.StateMachine = StateMachine;
16321 }
16322
16323 }());
16324 });
16325 var stateMachine_1 = stateMachine.StateMachine;
16326
16327 var adapters = {};
16328
16329 var getAdapter = function getAdapter(name) {
16330 var adapter = adapters[name];
16331
16332 if (adapter === undefined) {
16333 throw new Error("".concat(name, " adapter is not configured"));
16334 }
16335
16336 return adapter;
16337 };
16338 /**
16339 * 指定 Adapters
16340 * @function
16341 * @memberof module:leancloud-realtime
16342 * @param {Adapters} newAdapters Adapters 的类型请参考 {@link https://url.leanapp.cn/adapter-type-definitions @leancloud/adapter-types} 中的定义
16343 */
16344
16345
16346 var setAdapters = function setAdapters(newAdapters) {
16347 Object.assign(adapters, newAdapters);
16348 };
16349
16350 /** Built-in value references. */
16351 var getPrototype = _overArg(Object.getPrototypeOf, Object);
16352
16353 var _getPrototype = getPrototype;
16354
16355 /** `Object#toString` result references. */
16356 var objectTag$1 = '[object Object]';
16357
16358 /** Used for built-in method references. */
16359 var funcProto = Function.prototype,
16360 objectProto$6 = Object.prototype;
16361
16362 /** Used to resolve the decompiled source of functions. */
16363 var funcToString = funcProto.toString;
16364
16365 /** Used to check objects for own properties. */
16366 var hasOwnProperty$4 = objectProto$6.hasOwnProperty;
16367
16368 /** Used to infer the `Object` constructor. */
16369 var objectCtorString = funcToString.call(Object);
16370
16371 /**
16372 * Checks if `value` is a plain object, that is, an object created by the
16373 * `Object` constructor or one with a `[[Prototype]]` of `null`.
16374 *
16375 * @static
16376 * @memberOf _
16377 * @since 0.8.0
16378 * @category Lang
16379 * @param {*} value The value to check.
16380 * @returns {boolean} Returns `true` if `value` is a plain object, else `false`.
16381 * @example
16382 *
16383 * function Foo() {
16384 * this.a = 1;
16385 * }
16386 *
16387 * _.isPlainObject(new Foo);
16388 * // => false
16389 *
16390 * _.isPlainObject([1, 2, 3]);
16391 * // => false
16392 *
16393 * _.isPlainObject({ 'x': 0, 'y': 0 });
16394 * // => true
16395 *
16396 * _.isPlainObject(Object.create(null));
16397 * // => true
16398 */
16399 function isPlainObject(value) {
16400 if (!isObjectLike_1(value) || _baseGetTag(value) != objectTag$1) {
16401 return false;
16402 }
16403 var proto = _getPrototype(value);
16404 if (proto === null) {
16405 return true;
16406 }
16407 var Ctor = hasOwnProperty$4.call(proto, 'constructor') && proto.constructor;
16408 return typeof Ctor == 'function' && Ctor instanceof Ctor &&
16409 funcToString.call(Ctor) == objectCtorString;
16410 }
16411
16412 var isPlainObject_1 = isPlainObject;
16413
16414 /* eslint-disable */
16415 var global$1 = typeof global !== 'undefined' ? global : typeof window !== 'undefined' ? window : {};
16416
16417 var EXPIRED = Symbol('expired');
16418 var debug = browser('LC:Expirable');
16419
16420 var Expirable = /*#__PURE__*/function () {
16421 function Expirable(value, ttl) {
16422 this.originalValue = value;
16423
16424 if (typeof ttl === 'number') {
16425 this.expiredAt = Date.now() + ttl;
16426 }
16427 }
16428
16429 createClass(Expirable, [{
16430 key: "value",
16431 get: function get() {
16432 var expired = this.expiredAt && this.expiredAt <= Date.now();
16433 if (expired) debug("expired: ".concat(this.originalValue));
16434 return expired ? EXPIRED : this.originalValue;
16435 }
16436 }]);
16437
16438 return Expirable;
16439 }();
16440 Expirable.EXPIRED = EXPIRED;
16441
16442 var debug$1 = browser('LC:Cache');
16443
16444 var Cache = /*#__PURE__*/function () {
16445 function Cache() {
16446 var name = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : 'anonymous';
16447 this.name = name;
16448 this._map = {};
16449 }
16450
16451 var _proto = Cache.prototype;
16452
16453 _proto.get = function get(key) {
16454 var cache = this._map[key];
16455
16456 if (cache) {
16457 var value = cache.value;
16458
16459 if (value !== Expirable.EXPIRED) {
16460 debug$1('[%s] hit: %s', this.name, key);
16461 return value;
16462 }
16463
16464 delete this._map[key];
16465 }
16466
16467 debug$1("[".concat(this.name, "] missed: ").concat(key));
16468 return null;
16469 };
16470
16471 _proto.set = function set(key, value, ttl) {
16472 debug$1('[%s] set: %s %d', this.name, key, ttl);
16473 this._map[key] = new Expirable(value, ttl);
16474 };
16475
16476 return Cache;
16477 }();
16478
16479 function ownKeys(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); if (enumerableOnly) symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; }); keys.push.apply(keys, symbols); } return keys; }
16480
16481 function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i] != null ? arguments[i] : {}; if (i % 2) { ownKeys(Object(source), true).forEach(function (key) { defineProperty(target, key, source[key]); }); } else if (Object.getOwnPropertyDescriptors) { Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)); } else { ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } } return target; }
16482 /**
16483 * 调试日志控制器
16484 * @const
16485 * @memberof module:leancloud-realtime
16486 * @example
16487 * debug.enable(); // 启用调试日志
16488 * debug.disable(); // 关闭调试日志
16489 */
16490
16491 var debug$2 = {
16492 enable: function enable() {
16493 var namespaces = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : 'LC*';
16494 return browser.enable(namespaces);
16495 },
16496 disable: browser.disable
16497 };
16498 var tryAll = function tryAll(promiseConstructors) {
16499 var promise = new Promise(promiseConstructors[0]);
16500
16501 if (promiseConstructors.length === 1) {
16502 return promise;
16503 }
16504
16505 return promise["catch"](function () {
16506 return tryAll(promiseConstructors.slice(1));
16507 });
16508 }; // eslint-disable-next-line no-sequences
16509
16510 var tap = function tap(interceptor) {
16511 return function (value) {
16512 return interceptor(value), value;
16513 };
16514 };
16515 var finalize = function finalize(callback) {
16516 return [// eslint-disable-next-line no-sequences
16517 function (value) {
16518 return callback(), value;
16519 }, function (error) {
16520 callback();
16521 throw error;
16522 }];
16523 };
16524 /**
16525 * 将对象转换为 Date,支持 string、number、ProtoBuf Long 以及 LeanCloud 的 Date 类型,
16526 * 其他情况下(包括对象为 falsy)返回原值。
16527 * @private
16528 */
16529
16530 var decodeDate = function decodeDate(date) {
16531 if (!date) return date;
16532
16533 if (typeof date === 'string' || typeof date === 'number') {
16534 return new Date(date);
16535 }
16536
16537 if (date.__type === 'Date' && date.iso) {
16538 return new Date(date.iso);
16539 } // Long
16540
16541
16542 if (typeof date.toNumber === 'function') {
16543 return new Date(date.toNumber());
16544 }
16545
16546 return date;
16547 };
16548 /**
16549 * 获取 Date 的毫秒数,如果不是一个 Date 返回 undefined。
16550 * @private
16551 */
16552
16553 var getTime = function getTime(date) {
16554 return date && date.getTime ? date.getTime() : undefined;
16555 };
16556 /**
16557 * 解码对象中的 LeanCloud 数据结构。
16558 * 目前仅会处理 Date 类型。
16559 * @private
16560 */
16561
16562 var decode = function decode(value) {
16563 if (!value) return value;
16564
16565 if (value.__type === 'Date' && value.iso) {
16566 return new Date(value.iso);
16567 }
16568
16569 if (Array.isArray(value)) {
16570 return value.map(decode);
16571 }
16572
16573 if (isPlainObject_1(value)) {
16574 return Object.keys(value).reduce(function (result, key) {
16575 return _objectSpread(_objectSpread({}, result), {}, defineProperty({}, key, decode(value[key])));
16576 }, {});
16577 }
16578
16579 return value;
16580 };
16581 /**
16582 * 将对象中的特殊类型编码为 LeanCloud 数据结构。
16583 * 目前仅会处理 Date 类型。
16584 * @private
16585 */
16586
16587 var encode = function encode(value) {
16588 if (value instanceof Date) return {
16589 __type: 'Date',
16590 iso: value.toJSON()
16591 };
16592
16593 if (Array.isArray(value)) {
16594 return value.map(encode);
16595 }
16596
16597 if (isPlainObject_1(value)) {
16598 return Object.keys(value).reduce(function (result, key) {
16599 return _objectSpread(_objectSpread({}, result), {}, defineProperty({}, key, encode(value[key])));
16600 }, {});
16601 }
16602
16603 return value;
16604 };
16605 var keyRemap = function keyRemap(keymap, obj) {
16606 return Object.keys(obj).reduce(function (newObj, key) {
16607 var newKey = keymap[key] || key;
16608 return Object.assign(newObj, defineProperty({}, newKey, obj[key]));
16609 }, {});
16610 };
16611 var isIE10 = global$1.navigator && global$1.navigator.userAgent && global$1.navigator.userAgent.indexOf('MSIE 10.') !== -1;
16612 /* eslint-disable no-proto */
16613
16614 var getStaticProperty = function getStaticProperty(klass, property) {
16615 return klass[property] || (klass.__proto__ ? getStaticProperty(klass.__proto__, property) : undefined);
16616 };
16617 /* eslint-enable no-proto */
16618
16619 var union = function union(a, b) {
16620 return Array.from(new Set([].concat(toConsumableArray(a), toConsumableArray(b))));
16621 };
16622 var difference = function difference(a, b) {
16623 return Array.from(function (bSet) {
16624 return new Set(a.filter(function (x) {
16625 return !bSet.has(x);
16626 }));
16627 }(new Set(b)));
16628 };
16629 var map = new WeakMap(); // protected property helper
16630
16631 var internal = function internal(object) {
16632 if (!map.has(object)) {
16633 map.set(object, {});
16634 }
16635
16636 return map.get(object);
16637 };
16638 var compact = function compact(obj, filter) {
16639 if (!isPlainObject_1(obj)) return obj;
16640
16641 var object = _objectSpread({}, obj);
16642
16643 Object.keys(object).forEach(function (prop) {
16644 var value = object[prop];
16645
16646 if (value === filter) {
16647 delete object[prop];
16648 } else {
16649 object[prop] = compact(value, filter);
16650 }
16651 });
16652 return object;
16653 }; // debug utility
16654
16655 var removeNull = function removeNull(obj) {
16656 return compact(obj, null);
16657 };
16658
16659 var trim = function trim(message) {
16660 return removeNull(JSON.parse(JSON.stringify(message)));
16661 };
16662 var ensureArray = function ensureArray(target) {
16663 if (Array.isArray(target)) {
16664 return target;
16665 }
16666
16667 if (target === undefined || target === null) {
16668 return [];
16669 }
16670
16671 return [target];
16672 };
16673 var setValue = function setValue(target, key, value) {
16674 // '.' is not allowed in Class keys, escaping is not in concern now.
16675 var segs = key.split('.');
16676 var lastSeg = segs.pop();
16677 var currentTarget = target;
16678 segs.forEach(function (seg) {
16679 if (currentTarget[seg] === undefined) currentTarget[seg] = {};
16680 currentTarget = currentTarget[seg];
16681 });
16682 currentTarget[lastSeg] = value;
16683 return target;
16684 };
16685 var isWeapp = // eslint-disable-next-line no-undef
16686 (typeof wx === "undefined" ? "undefined" : _typeof_1(wx)) === 'object' && typeof wx.connectSocket === 'function'; // throttle decorator
16687
16688 var throttle = function throttle(wait) {
16689 return function (target, property, descriptor) {
16690 var callback = descriptor.value; // very naive, internal use only
16691
16692 if (callback.length) {
16693 throw new Error('throttled function should not accept any arguments');
16694 }
16695
16696 return _objectSpread(_objectSpread({}, descriptor), {}, {
16697 value: function value() {
16698 var _this = this;
16699
16700 var _internal = internal(this),
16701 throttleMeta = _internal.throttleMeta;
16702
16703 if (!throttleMeta) {
16704 throttleMeta = {};
16705 internal(this).throttleMeta = throttleMeta;
16706 }
16707
16708 var _throttleMeta = throttleMeta,
16709 propertyMeta = _throttleMeta[property];
16710
16711 if (!propertyMeta) {
16712 propertyMeta = {};
16713 throttleMeta[property] = propertyMeta;
16714 }
16715
16716 var _propertyMeta = propertyMeta,
16717 _propertyMeta$previou = _propertyMeta.previouseTimestamp,
16718 previouseTimestamp = _propertyMeta$previou === void 0 ? 0 : _propertyMeta$previou,
16719 timeout = _propertyMeta.timeout;
16720 var now = Date.now();
16721 var remainingTime = wait - (now - previouseTimestamp);
16722
16723 if (remainingTime <= 0) {
16724 throttleMeta[property].previouseTimestamp = now;
16725 callback.apply(this);
16726 } else if (!timeout) {
16727 propertyMeta.timeout = setTimeout(function () {
16728 propertyMeta.previouseTimestamp = Date.now();
16729 delete propertyMeta.timeout;
16730 callback.apply(_this);
16731 }, remainingTime);
16732 }
16733 }
16734 });
16735 };
16736 };
16737 var isCNApp = function isCNApp(appId) {
16738 return appId.slice(-9) !== '-MdYXbMMI';
16739 };
16740 var equalBuffer = function equalBuffer(buffer1, buffer2) {
16741 if (!buffer1 || !buffer2) return false;
16742 if (buffer1.byteLength !== buffer2.byteLength) return false;
16743 var a = new Uint8Array(buffer1);
16744 var b = new Uint8Array(buffer2);
16745 return !a.some(function (value, index) {
16746 return value !== b[index];
16747 });
16748 };
16749
16750 var _class;
16751
16752 function ownKeys$1(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); if (enumerableOnly) symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; }); keys.push.apply(keys, symbols); } return keys; }
16753
16754 function _objectSpread$1(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i] != null ? arguments[i] : {}; if (i % 2) { ownKeys$1(Object(source), true).forEach(function (key) { defineProperty(target, key, source[key]); }); } else if (Object.getOwnPropertyDescriptors) { Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)); } else { ownKeys$1(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } } return target; }
16755 var debug$3 = browser('LC:WebSocketPlus');
16756 var OPEN = 'open';
16757 var DISCONNECT = 'disconnect';
16758 var RECONNECT = 'reconnect';
16759 var RETRY = 'retry';
16760 var SCHEDULE = 'schedule';
16761 var OFFLINE = 'offline';
16762 var ONLINE = 'online';
16763 var ERROR = 'error';
16764 var MESSAGE = 'message';
16765 var HEARTBEAT_TIME = 180000;
16766 var TIMEOUT_TIME = 380000;
16767
16768 var DEFAULT_RETRY_STRATEGY = function DEFAULT_RETRY_STRATEGY(attempt) {
16769 return Math.min(1000 * Math.pow(2, attempt), 300000);
16770 };
16771
16772 var requireConnected = function requireConnected(target, name, descriptor) {
16773 return _objectSpread$1(_objectSpread$1({}, descriptor), {}, {
16774 value: function requireConnectedWrapper() {
16775 var _descriptor$value;
16776
16777 this.checkConnectionAvailability(name);
16778
16779 for (var _len = arguments.length, args = new Array(_len), _key = 0; _key < _len; _key++) {
16780 args[_key] = arguments[_key];
16781 }
16782
16783 return (_descriptor$value = descriptor.value).call.apply(_descriptor$value, [this].concat(args));
16784 }
16785 });
16786 };
16787
16788 var WebSocketPlus = (_class = /*#__PURE__*/function (_EventEmitter) {
16789 inheritsLoose(WebSocketPlus, _EventEmitter);
16790
16791 createClass(WebSocketPlus, [{
16792 key: "urls",
16793 get: function get() {
16794 return this._urls;
16795 },
16796 set: function set(urls) {
16797 this._urls = ensureArray(urls);
16798 }
16799 }]);
16800
16801 function WebSocketPlus(getUrls, protocol) {
16802 var _this;
16803
16804 _this = _EventEmitter.call(this) || this;
16805
16806 _this.init();
16807
16808 _this._protocol = protocol;
16809 Promise.resolve(typeof getUrls === 'function' ? getUrls() : getUrls).then(ensureArray).then(function (urls) {
16810 _this._urls = urls;
16811 return _this._open();
16812 }).then(function () {
16813 _this.__postponeTimeoutTimer = _this._postponeTimeoutTimer.bind(assertThisInitialized(_this));
16814
16815 if (global$1.addEventListener) {
16816 _this.__pause = function () {
16817 if (_this.can('pause')) _this.pause();
16818 };
16819
16820 _this.__resume = function () {
16821 if (_this.can('resume')) _this.resume();
16822 };
16823
16824 global$1.addEventListener('offline', _this.__pause);
16825 global$1.addEventListener('online', _this.__resume);
16826 }
16827
16828 _this.open();
16829 })["catch"](_this["throw"].bind(assertThisInitialized(_this)));
16830 return _this;
16831 }
16832
16833 var _proto = WebSocketPlus.prototype;
16834
16835 _proto._open = function _open() {
16836 var _this2 = this;
16837
16838 return this._createWs(this._urls, this._protocol).then(function (ws) {
16839 var _this2$_urls = toArray(_this2._urls),
16840 first = _this2$_urls[0],
16841 reset = _this2$_urls.slice(1);
16842
16843 _this2._urls = [].concat(toConsumableArray(reset), [first]);
16844 return ws;
16845 });
16846 };
16847
16848 _proto._createWs = function _createWs(urls, protocol) {
16849 var _this3 = this;
16850
16851 return tryAll(urls.map(function (url) {
16852 return function (resolve, reject) {
16853 debug$3("connect [".concat(url, "] ").concat(protocol));
16854 var WebSocket = getAdapter('WebSocket');
16855 var ws = protocol ? new WebSocket(url, protocol) : new WebSocket(url);
16856 ws.binaryType = _this3.binaryType || 'arraybuffer';
16857
16858 ws.onopen = function () {
16859 return resolve(ws);
16860 };
16861
16862 ws.onclose = function (error) {
16863 if (error instanceof Error) {
16864 return reject(error);
16865 } // in browser, error event is useless
16866
16867
16868 return reject(new Error("Failed to connect [".concat(url, "]")));
16869 };
16870
16871 ws.onerror = ws.onclose;
16872 };
16873 })).then(function (ws) {
16874 _this3._ws = ws;
16875 _this3._ws.onclose = _this3._handleClose.bind(_this3);
16876 _this3._ws.onmessage = _this3._handleMessage.bind(_this3);
16877 return ws;
16878 });
16879 };
16880
16881 _proto._destroyWs = function _destroyWs() {
16882 var ws = this._ws;
16883 if (!ws) return;
16884 ws.onopen = null;
16885 ws.onclose = null;
16886 ws.onerror = null;
16887 ws.onmessage = null;
16888 this._ws = null;
16889 ws.close();
16890 } // eslint-disable-next-line class-methods-use-this
16891 ;
16892
16893 _proto.onbeforeevent = function onbeforeevent(event, from, to) {
16894 for (var _len2 = arguments.length, payload = new Array(_len2 > 3 ? _len2 - 3 : 0), _key2 = 3; _key2 < _len2; _key2++) {
16895 payload[_key2 - 3] = arguments[_key2];
16896 }
16897
16898 debug$3("".concat(event, ": ").concat(from, " -> ").concat(to, " %o"), payload);
16899 };
16900
16901 _proto.onopen = function onopen() {
16902 this.emit(OPEN);
16903 };
16904
16905 _proto.onconnected = function onconnected() {
16906 this._startConnectionKeeper();
16907 };
16908
16909 _proto.onleaveconnected = function onleaveconnected(event, from, to) {
16910 this._stopConnectionKeeper();
16911
16912 this._destroyWs();
16913
16914 if (to === 'offline' || to === 'disconnected') {
16915 this.emit(DISCONNECT);
16916 }
16917 };
16918
16919 _proto.onpause = function onpause() {
16920 this.emit(OFFLINE);
16921 };
16922
16923 _proto.onbeforeresume = function onbeforeresume() {
16924 this.emit(ONLINE);
16925 };
16926
16927 _proto.onreconnect = function onreconnect() {
16928 this.emit(RECONNECT);
16929 };
16930
16931 _proto.ondisconnected = function ondisconnected(event, from, to) {
16932 var _this4 = this;
16933
16934 var attempt = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : 0;
16935 var delay = from === OFFLINE ? 0 : DEFAULT_RETRY_STRATEGY.call(null, attempt);
16936 debug$3("schedule attempt=".concat(attempt, " delay=").concat(delay));
16937 this.emit(SCHEDULE, attempt, delay);
16938
16939 if (this.__scheduledRetry) {
16940 clearTimeout(this.__scheduledRetry);
16941 }
16942
16943 this.__scheduledRetry = setTimeout(function () {
16944 if (_this4.is('disconnected')) {
16945 _this4.retry(attempt);
16946 }
16947 }, delay);
16948 };
16949
16950 _proto.onretry = function onretry(event, from, to) {
16951 var _this5 = this;
16952
16953 var attempt = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : 0;
16954 this.emit(RETRY, attempt);
16955
16956 this._open().then(function () {
16957 return _this5.can('reconnect') && _this5.reconnect();
16958 }, function () {
16959 return _this5.can('fail') && _this5.fail(attempt + 1);
16960 });
16961 };
16962
16963 _proto.onerror = function onerror(event, from, to, error) {
16964 this.emit(ERROR, error);
16965 };
16966
16967 _proto.onclose = function onclose() {
16968 if (global$1.removeEventListener) {
16969 if (this.__pause) global$1.removeEventListener('offline', this.__pause);
16970 if (this.__resume) global$1.removeEventListener('online', this.__resume);
16971 }
16972 };
16973
16974 _proto.checkConnectionAvailability = function checkConnectionAvailability() {
16975 var name = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : 'API';
16976
16977 if (!this.is('connected')) {
16978 var currentState = this.current;
16979 console.warn("".concat(name, " should not be called when the connection is ").concat(currentState));
16980
16981 if (this.is('disconnected') || this.is('reconnecting')) {
16982 console.warn('disconnect and reconnect event should be handled to avoid such calls.');
16983 }
16984
16985 throw new Error('Connection unavailable');
16986 }
16987 } // jsdoc-ignore-start
16988 ;
16989
16990 _proto. // jsdoc-ignore-end
16991 _ping = function _ping() {
16992 debug$3('ping');
16993
16994 try {
16995 this.ping();
16996 } catch (error) {
16997 console.warn("websocket ping error: ".concat(error.message));
16998 }
16999 };
17000
17001 _proto.ping = function ping() {
17002 if (this._ws.ping) {
17003 this._ws.ping();
17004 } else {
17005 console.warn("The WebSocket implement does not support sending ping frame.\n Override ping method to use application defined ping/pong mechanism.");
17006 }
17007 };
17008
17009 _proto._postponeTimeoutTimer = function _postponeTimeoutTimer() {
17010 var _this6 = this;
17011
17012 debug$3('_postponeTimeoutTimer');
17013
17014 this._clearTimeoutTimers();
17015
17016 this._timeoutTimer = setTimeout(function () {
17017 debug$3('timeout');
17018
17019 _this6.disconnect();
17020 }, TIMEOUT_TIME);
17021 };
17022
17023 _proto._clearTimeoutTimers = function _clearTimeoutTimers() {
17024 if (this._timeoutTimer) {
17025 clearTimeout(this._timeoutTimer);
17026 }
17027 };
17028
17029 _proto._startConnectionKeeper = function _startConnectionKeeper() {
17030 debug$3('start connection keeper');
17031 this._heartbeatTimer = setInterval(this._ping.bind(this), HEARTBEAT_TIME);
17032 var addListener = this._ws.addListener || this._ws.addEventListener;
17033
17034 if (!addListener) {
17035 debug$3('connection keeper disabled due to the lack of #addEventListener.');
17036 return;
17037 }
17038
17039 addListener.call(this._ws, 'message', this.__postponeTimeoutTimer);
17040 addListener.call(this._ws, 'pong', this.__postponeTimeoutTimer);
17041
17042 this._postponeTimeoutTimer();
17043 };
17044
17045 _proto._stopConnectionKeeper = function _stopConnectionKeeper() {
17046 debug$3('stop connection keeper'); // websockets/ws#489
17047
17048 var removeListener = this._ws.removeListener || this._ws.removeEventListener;
17049
17050 if (removeListener) {
17051 removeListener.call(this._ws, 'message', this.__postponeTimeoutTimer);
17052 removeListener.call(this._ws, 'pong', this.__postponeTimeoutTimer);
17053
17054 this._clearTimeoutTimers();
17055 }
17056
17057 if (this._heartbeatTimer) {
17058 clearInterval(this._heartbeatTimer);
17059 }
17060 };
17061
17062 _proto._handleClose = function _handleClose(event) {
17063 debug$3("ws closed [".concat(event.code, "] ").concat(event.reason)); // socket closed manually, ignore close event.
17064
17065 if (this.isFinished()) return;
17066 this.handleClose(event);
17067 };
17068
17069 _proto.handleClose = function handleClose() {
17070 // reconnect
17071 this.disconnect();
17072 } // jsdoc-ignore-start
17073 ;
17074
17075 _proto. // jsdoc-ignore-end
17076 send = function send(data) {
17077 debug$3('send', data);
17078
17079 this._ws.send(data);
17080 };
17081
17082 _proto._handleMessage = function _handleMessage(event) {
17083 debug$3('message', event.data);
17084 this.handleMessage(event.data);
17085 };
17086
17087 _proto.handleMessage = function handleMessage(message) {
17088 this.emit(MESSAGE, message);
17089 };
17090
17091 return WebSocketPlus;
17092 }(eventemitter3), (applyDecoratedDescriptor(_class.prototype, "_ping", [requireConnected], Object.getOwnPropertyDescriptor(_class.prototype, "_ping"), _class.prototype), applyDecoratedDescriptor(_class.prototype, "send", [requireConnected], Object.getOwnPropertyDescriptor(_class.prototype, "send"), _class.prototype)), _class);
17093 stateMachine.create({
17094 target: WebSocketPlus.prototype,
17095 initial: {
17096 state: 'initialized',
17097 event: 'init',
17098 defer: true
17099 },
17100 terminal: 'closed',
17101 events: [{
17102 name: 'open',
17103 from: 'initialized',
17104 to: 'connected'
17105 }, {
17106 name: 'disconnect',
17107 from: 'connected',
17108 to: 'disconnected'
17109 }, {
17110 name: 'retry',
17111 from: 'disconnected',
17112 to: 'reconnecting'
17113 }, {
17114 name: 'fail',
17115 from: 'reconnecting',
17116 to: 'disconnected'
17117 }, {
17118 name: 'reconnect',
17119 from: 'reconnecting',
17120 to: 'connected'
17121 }, {
17122 name: 'pause',
17123 from: ['connected', 'disconnected', 'reconnecting'],
17124 to: 'offline'
17125 }, {}, {
17126 name: 'resume',
17127 from: 'offline',
17128 to: 'disconnected'
17129 }, {
17130 name: 'close',
17131 from: ['connected', 'disconnected', 'reconnecting', 'offline'],
17132 to: 'closed'
17133 }, {
17134 name: 'throw',
17135 from: '*',
17136 to: 'error'
17137 }]
17138 });
17139
17140 var error = Object.freeze({
17141 1000: {
17142 name: 'CLOSE_NORMAL'
17143 },
17144 1006: {
17145 name: 'CLOSE_ABNORMAL'
17146 },
17147 4100: {
17148 name: 'APP_NOT_AVAILABLE',
17149 message: 'App not exists or realtime message service is disabled.'
17150 },
17151 4102: {
17152 name: 'SIGNATURE_FAILED',
17153 message: 'Login signature mismatch.'
17154 },
17155 4103: {
17156 name: 'INVALID_LOGIN',
17157 message: 'Malformed clientId.'
17158 },
17159 4105: {
17160 name: 'SESSION_REQUIRED',
17161 message: 'Message sent before session opened.'
17162 },
17163 4107: {
17164 name: 'READ_TIMEOUT'
17165 },
17166 4108: {
17167 name: 'LOGIN_TIMEOUT'
17168 },
17169 4109: {
17170 name: 'FRAME_TOO_LONG'
17171 },
17172 4110: {
17173 name: 'INVALID_ORIGIN',
17174 message: 'Access denied by domain whitelist.'
17175 },
17176 4111: {
17177 name: 'SESSION_CONFLICT'
17178 },
17179 4112: {
17180 name: 'SESSION_TOKEN_EXPIRED'
17181 },
17182 4113: {
17183 name: 'APP_QUOTA_EXCEEDED',
17184 message: 'The daily active users limit exceeded.'
17185 },
17186 4116: {
17187 name: 'MESSAGE_SENT_QUOTA_EXCEEDED',
17188 message: 'Command sent too fast.'
17189 },
17190 4200: {
17191 name: 'INTERNAL_ERROR',
17192 message: 'Internal error, please contact LeanCloud for support.'
17193 },
17194 4301: {
17195 name: 'CONVERSATION_API_FAILED',
17196 message: 'Upstream Conversatoin API failed, see error.detail for details.'
17197 },
17198 4302: {
17199 name: 'CONVERSATION_SIGNATURE_FAILED',
17200 message: 'Conversation action signature mismatch.'
17201 },
17202 4303: {
17203 name: 'CONVERSATION_NOT_FOUND'
17204 },
17205 4304: {
17206 name: 'CONVERSATION_FULL'
17207 },
17208 4305: {
17209 name: 'CONVERSATION_REJECTED_BY_APP',
17210 message: 'Conversation action rejected by hook.'
17211 },
17212 4306: {
17213 name: 'CONVERSATION_UPDATE_FAILED'
17214 },
17215 4307: {
17216 name: 'CONVERSATION_READ_ONLY'
17217 },
17218 4308: {
17219 name: 'CONVERSATION_NOT_ALLOWED'
17220 },
17221 4309: {
17222 name: 'CONVERSATION_UPDATE_REJECTED',
17223 message: 'Conversation update rejected because the client is not a member.'
17224 },
17225 4310: {
17226 name: 'CONVERSATION_QUERY_FAILED',
17227 message: 'Conversation query failed because it is too expansive.'
17228 },
17229 4311: {
17230 name: 'CONVERSATION_LOG_FAILED'
17231 },
17232 4312: {
17233 name: 'CONVERSATION_LOG_REJECTED',
17234 message: 'Message query rejected because the client is not a member of the conversation.'
17235 },
17236 4313: {
17237 name: 'SYSTEM_CONVERSATION_REQUIRED'
17238 },
17239 4314: {
17240 name: 'NORMAL_CONVERSATION_REQUIRED'
17241 },
17242 4315: {
17243 name: 'CONVERSATION_BLACKLISTED',
17244 message: 'Blacklisted in the conversation.'
17245 },
17246 4316: {
17247 name: 'TRANSIENT_CONVERSATION_REQUIRED'
17248 },
17249 4317: {
17250 name: 'CONVERSATION_MEMBERSHIP_REQUIRED'
17251 },
17252 4318: {
17253 name: 'CONVERSATION_API_QUOTA_EXCEEDED',
17254 message: 'LeanCloud API quota exceeded. You may upgrade your plan.'
17255 },
17256 4323: {
17257 name: 'TEMPORARY_CONVERSATION_EXPIRED',
17258 message: 'Temporary conversation expired or does not exist.'
17259 },
17260 4401: {
17261 name: 'INVALID_MESSAGING_TARGET',
17262 message: 'Conversation does not exist or client is not a member.'
17263 },
17264 4402: {
17265 name: 'MESSAGE_REJECTED_BY_APP',
17266 message: 'Message rejected by hook.'
17267 },
17268 4403: {
17269 name: 'MESSAGE_OWNERSHIP_REQUIRED'
17270 },
17271 4404: {
17272 name: 'MESSAGE_NOT_FOUND'
17273 },
17274 4405: {
17275 name: 'MESSAGE_UPDATE_REJECTED_BY_APP',
17276 message: 'Message update rejected by hook.'
17277 },
17278 4406: {
17279 name: 'MESSAGE_EDIT_DISABLED'
17280 },
17281 4407: {
17282 name: 'MESSAGE_RECALL_DISABLED'
17283 },
17284 5130: {
17285 name: 'OWNER_PROMOTION_NOT_ALLOWED',
17286 message: "Updating a member's role to owner is not allowed."
17287 }
17288 });
17289 var ErrorCode = Object.freeze(Object.keys(error).reduce(function (result, code) {
17290 return Object.assign(result, defineProperty({}, error[code].name, Number(code)));
17291 }, {}));
17292 var createError = function createError(_ref) {
17293 var code = _ref.code,
17294 reason = _ref.reason,
17295 appCode = _ref.appCode,
17296 detail = _ref.detail,
17297 errorMessage = _ref.error;
17298 var message = reason || detail || errorMessage;
17299 var name = reason;
17300
17301 if (!message && error[code]) {
17302 name = error[code].name;
17303 message = error[code].message || name;
17304 }
17305
17306 if (!message) {
17307 message = "Unknow Error: ".concat(code);
17308 }
17309
17310 var err = new Error(message);
17311 return Object.assign(err, {
17312 code: code,
17313 appCode: appCode,
17314 detail: detail,
17315 name: name
17316 });
17317 };
17318
17319 var debug$4 = browser('LC:Connection');
17320 var COMMAND_TIMEOUT = 20000;
17321 var EXPIRE = Symbol('expire');
17322
17323 var isIdempotentCommand = function isIdempotentCommand(command) {
17324 return !(command.cmd === CommandType.direct || command.cmd === CommandType.session && command.op === OpType.open || command.cmd === CommandType.conv && (command.op === OpType.start || command.op === OpType.update || command.op === OpType.members));
17325 };
17326
17327 var Connection = /*#__PURE__*/function (_WebSocketPlus) {
17328 inheritsLoose(Connection, _WebSocketPlus);
17329
17330 function Connection(getUrl, _ref) {
17331 var _this;
17332
17333 var format = _ref.format,
17334 version = _ref.version;
17335 debug$4('initializing Connection');
17336 var protocolString = "lc.".concat(format, ".").concat(version);
17337 _this = _WebSocketPlus.call(this, getUrl, protocolString) || this;
17338 _this._protocolFormat = format;
17339 _this._commands = {};
17340 _this._serialId = 0;
17341 return _this;
17342 }
17343
17344 var _proto = Connection.prototype;
17345
17346 _proto.send = /*#__PURE__*/function () {
17347 var _send = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee(command) {
17348 var _this2 = this;
17349
17350 var waitingForRespond,
17351 buffer,
17352 serialId,
17353 duplicatedCommand,
17354 message,
17355 promise,
17356 _args = arguments;
17357 return regenerator.wrap(function _callee$(_context) {
17358 while (1) {
17359 switch (_context.prev = _context.next) {
17360 case 0:
17361 waitingForRespond = _args.length > 1 && _args[1] !== undefined ? _args[1] : true;
17362
17363 if (!waitingForRespond) {
17364 _context.next = 11;
17365 break;
17366 }
17367
17368 if (!isIdempotentCommand(command)) {
17369 _context.next = 8;
17370 break;
17371 }
17372
17373 buffer = command.toArrayBuffer();
17374 duplicatedCommand = values_1(this._commands).find(function (_ref2) {
17375 var targetBuffer = _ref2.buffer,
17376 targetCommand = _ref2.command;
17377 return targetCommand.cmd === command.cmd && targetCommand.op === command.op && equalBuffer(targetBuffer, buffer);
17378 });
17379
17380 if (!duplicatedCommand) {
17381 _context.next = 8;
17382 break;
17383 }
17384
17385 console.warn("Duplicated command [cmd:".concat(command.cmd, " op:").concat(command.op, "] is throttled."));
17386 return _context.abrupt("return", duplicatedCommand.promise);
17387
17388 case 8:
17389 this._serialId += 1;
17390 serialId = this._serialId;
17391 command.i = serialId; // eslint-disable-line no-param-reassign
17392
17393 case 11:
17394 if (debug$4.enabled) debug$4('↑ %O sent', trim(command));
17395
17396 if (this._protocolFormat === 'proto2base64') {
17397 message = command.toBase64();
17398 } else if (command.toArrayBuffer) {
17399 message = command.toArrayBuffer();
17400 }
17401
17402 if (message) {
17403 _context.next = 15;
17404 break;
17405 }
17406
17407 throw new TypeError("".concat(command, " is not a GenericCommand"));
17408
17409 case 15:
17410 _WebSocketPlus.prototype.send.call(this, message);
17411
17412 if (waitingForRespond) {
17413 _context.next = 18;
17414 break;
17415 }
17416
17417 return _context.abrupt("return", undefined);
17418
17419 case 18:
17420 promise = new Promise(function (resolve, reject) {
17421 _this2._commands[serialId] = {
17422 command: command,
17423 buffer: buffer,
17424 resolve: resolve,
17425 reject: reject,
17426 timeout: setTimeout(function () {
17427 if (_this2._commands[serialId]) {
17428 if (debug$4.enabled) debug$4('✗ %O timeout', trim(command));
17429 reject(createError({
17430 error: "Command Timeout [cmd:".concat(command.cmd, " op:").concat(command.op, "]"),
17431 name: 'COMMAND_TIMEOUT'
17432 }));
17433 delete _this2._commands[serialId];
17434 }
17435 }, COMMAND_TIMEOUT)
17436 };
17437 });
17438 this._commands[serialId].promise = promise;
17439 return _context.abrupt("return", promise);
17440
17441 case 21:
17442 case "end":
17443 return _context.stop();
17444 }
17445 }
17446 }, _callee, this);
17447 }));
17448
17449 function send(_x) {
17450 return _send.apply(this, arguments);
17451 }
17452
17453 return send;
17454 }();
17455
17456 _proto.handleMessage = function handleMessage(msg) {
17457 var message;
17458
17459 try {
17460 message = GenericCommand.decode(msg);
17461 if (debug$4.enabled) debug$4('↓ %O received', trim(message));
17462 } catch (e) {
17463 console.warn('Decode message failed:', e.message, msg);
17464 return;
17465 }
17466
17467 var serialId = message.i;
17468
17469 if (serialId) {
17470 if (this._commands[serialId]) {
17471 clearTimeout(this._commands[serialId].timeout);
17472
17473 if (message.cmd === CommandType.error) {
17474 this._commands[serialId].reject(createError(message.errorMessage));
17475 } else {
17476 this._commands[serialId].resolve(message);
17477 }
17478
17479 delete this._commands[serialId];
17480 } else {
17481 console.warn("Unexpected command received with serialId [".concat(serialId, "],\n which have timed out or never been requested."));
17482 }
17483 } else {
17484 switch (message.cmd) {
17485 case CommandType.error:
17486 {
17487 this.emit(ERROR, createError(message.errorMessage));
17488 return;
17489 }
17490
17491 case CommandType.goaway:
17492 {
17493 this.emit(EXPIRE);
17494 return;
17495 }
17496
17497 default:
17498 {
17499 this.emit(MESSAGE, message);
17500 }
17501 }
17502 }
17503 };
17504
17505 _proto.ping = function ping() {
17506 return this.send(new GenericCommand({
17507 cmd: CommandType.echo
17508 }))["catch"](function (error) {
17509 return debug$4('ping failed:', error);
17510 });
17511 };
17512
17513 return Connection;
17514 }(WebSocketPlus);
17515
17516 var promiseTimeout = createCommonjsModule(function (module) {
17517 /**
17518 * Local reference to TimeoutError
17519 * @private
17520 */
17521
17522 var TimeoutError;
17523 /**
17524 * Rejects a promise with a {@link TimeoutError} if it does not settle within
17525 * the specified timeout.
17526 *
17527 * @param {Promise} promise The promise.
17528 * @param {number} timeoutMillis Number of milliseconds to wait on settling.
17529 * @returns {Promise} Either resolves/rejects with `promise`, or rejects with
17530 * `TimeoutError`, whichever settles first.
17531 */
17532
17533 var timeout = module.exports.timeout = function (promise, timeoutMillis) {
17534 var error = new TimeoutError(),
17535 timeout;
17536 return Promise.race([promise, new Promise(function (resolve, reject) {
17537 timeout = setTimeout(function () {
17538 reject(error);
17539 }, timeoutMillis);
17540 })]).then(function (v) {
17541 clearTimeout(timeout);
17542 return v;
17543 }, function (err) {
17544 clearTimeout(timeout);
17545 throw err;
17546 });
17547 };
17548 /**
17549 * Exception indicating that the timeout expired.
17550 */
17551
17552
17553 TimeoutError = module.exports.TimeoutError = function () {
17554 Error.call(this);
17555 this.stack = Error().stack;
17556 this.message = 'Timeout';
17557 };
17558
17559 TimeoutError.prototype = Object.create(Error.prototype);
17560 TimeoutError.prototype.name = "TimeoutError";
17561 });
17562 var promiseTimeout_1 = promiseTimeout.timeout;
17563 var promiseTimeout_2 = promiseTimeout.TimeoutError;
17564
17565 var debug$5 = browser('LC:request');
17566 var request = (function (_ref) {
17567 var _ref$method = _ref.method,
17568 method = _ref$method === void 0 ? 'GET' : _ref$method,
17569 _url = _ref.url,
17570 query = _ref.query,
17571 headers = _ref.headers,
17572 data = _ref.data,
17573 time = _ref.timeout;
17574 var url = _url;
17575
17576 if (query) {
17577 var queryString = Object.keys(query).map(function (key) {
17578 var value = query[key];
17579 if (value === undefined) return undefined;
17580 var v = isPlainObject_1(value) ? JSON.stringify(value) : value;
17581 return "".concat(encodeURIComponent(key), "=").concat(encodeURIComponent(v));
17582 }).filter(function (qs) {
17583 return qs;
17584 }).join('&');
17585 url = "".concat(url, "?").concat(queryString);
17586 }
17587
17588 debug$5('Req: %O %O %O', method, url, {
17589 headers: headers,
17590 data: data
17591 });
17592 var request = getAdapter('request');
17593 var promise = request(url, {
17594 method: method,
17595 headers: headers,
17596 data: data
17597 }).then(function (response) {
17598 if (response.ok === false) {
17599 var error = createError(response.data);
17600 error.response = response;
17601 throw error;
17602 }
17603
17604 debug$5('Res: %O %O %O', url, response.status, response.data);
17605 return response.data;
17606 })["catch"](function (error) {
17607 if (error.response) {
17608 debug$5('Error: %O %O %O', url, error.response.status, error.response.data);
17609 }
17610
17611 throw error;
17612 });
17613 return time ? promiseTimeout_1(promise, time) : promise;
17614 });
17615
17616 var checkType = function checkType(middleware) {
17617 return function (param) {
17618 var constructor = param.constructor;
17619 return Promise.resolve(param).then(middleware).then(tap(function (result) {
17620 if (result === undefined || result === null) {
17621 // eslint-disable-next-line max-len
17622 return console.warn("Middleware[".concat(middleware._pluginName || 'anonymous plugin', ":").concat(middleware.name || 'anonymous middleware', "] param/return types not match. It returns ").concat(result, " while a ").concat(param.constructor.name, " expected."));
17623 }
17624
17625 if (!(result instanceof constructor)) {
17626 // eslint-disable-next-line max-len
17627 return console.warn("Middleware[".concat(middleware._pluginName || 'anonymous plugin', ":").concat(middleware.name || 'anonymous middleware', "] param/return types not match. It returns a ").concat(result.constructor.name, " while a ").concat(param.constructor.name, " expected."));
17628 }
17629
17630 return 0;
17631 }));
17632 };
17633 };
17634
17635 var applyDecorators = function applyDecorators(decorators, target) {
17636 if (decorators) {
17637 decorators.forEach(function (decorator) {
17638 try {
17639 decorator(target);
17640 } catch (error) {
17641 if (decorator._pluginName) {
17642 error.message += "[".concat(decorator._pluginName, "]");
17643 }
17644
17645 throw error;
17646 }
17647 });
17648 }
17649 };
17650 var applyMiddlewares = function applyMiddlewares(middlewares) {
17651 return function (target) {
17652 return ensureArray(middlewares).reduce(function (previousPromise, middleware) {
17653 return previousPromise.then(checkType(middleware))["catch"](function (error) {
17654 if (middleware._pluginName) {
17655 // eslint-disable-next-line no-param-reassign
17656 error.message += "[".concat(middleware._pluginName, "]");
17657 }
17658
17659 throw error;
17660 });
17661 }, Promise.resolve(target));
17662 };
17663 };
17664 var applyDispatcher = function applyDispatcher(dispatchers, payload) {
17665 return ensureArray(dispatchers).reduce(function (resultPromise, dispatcher) {
17666 return resultPromise.then(function (shouldDispatch) {
17667 return shouldDispatch === false ? false : dispatcher.apply(void 0, toConsumableArray(payload));
17668 })["catch"](function (error) {
17669 if (dispatcher._pluginName) {
17670 // eslint-disable-next-line no-param-reassign
17671 error.message += "[".concat(dispatcher._pluginName, "]");
17672 }
17673
17674 throw error;
17675 });
17676 }, Promise.resolve(true));
17677 };
17678
17679 var version = "5.0.0-rc.7";
17680
17681 function ownKeys$2(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); if (enumerableOnly) symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; }); keys.push.apply(keys, symbols); } return keys; }
17682
17683 function _objectSpread$2(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i] != null ? arguments[i] : {}; if (i % 2) { ownKeys$2(Object(source), true).forEach(function (key) { defineProperty(target, key, source[key]); }); } else if (Object.getOwnPropertyDescriptors) { Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)); } else { ownKeys$2(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } } return target; }
17684 var debug$6 = browser('LC:Realtime');
17685 var routerCache = new Cache('push-router');
17686 var initializedApp = {};
17687
17688 var Realtime = /*#__PURE__*/function (_EventEmitter) {
17689 inheritsLoose(Realtime, _EventEmitter);
17690
17691 /**
17692 * @extends EventEmitter
17693 * @param {Object} options
17694 * @param {String} options.appId
17695 * @param {String} options.appKey (since 4.0.0)
17696 * @param {String|Object} [options.server] 指定服务器域名,中国节点应用此参数必填(since 4.0.0)
17697 * @param {Boolean} [options.noBinary=false] 设置 WebSocket 使用字符串格式收发消息(默认为二进制格式)。
17698 * 适用于 WebSocket 实现不支持二进制数据格式的情况
17699 * @param {Boolean} [options.ssl=true] 使用 wss 进行连接
17700 * @param {String|String[]} [options.RTMServers] 指定私有部署的 RTM 服务器地址(since 4.0.0)
17701 * @param {Plugin[]} [options.plugins] 加载插件(since 3.1.0)
17702 */
17703 function Realtime(_ref) {
17704 var _this2;
17705
17706 var plugins = _ref.plugins,
17707 options = objectWithoutProperties(_ref, ["plugins"]);
17708
17709 debug$6('initializing Realtime %s %O', version, options);
17710 _this2 = _EventEmitter.call(this) || this;
17711 var appId = options.appId;
17712
17713 if (typeof appId !== 'string') {
17714 throw new TypeError("appId [".concat(appId, "] is not a string"));
17715 }
17716
17717 if (initializedApp[appId]) {
17718 throw new Error("App [".concat(appId, "] is already initialized."));
17719 }
17720
17721 initializedApp[appId] = true;
17722
17723 if (typeof options.appKey !== 'string') {
17724 throw new TypeError("appKey [".concat(options.appKey, "] is not a string"));
17725 }
17726
17727 if (isCNApp(appId)) {
17728 if (!options.server) {
17729 throw new TypeError("server option is required for apps from CN region");
17730 }
17731 }
17732
17733 _this2._options = _objectSpread$2({
17734 appId: undefined,
17735 appKey: undefined,
17736 noBinary: false,
17737 ssl: true,
17738 RTMServerName: typeof process !== 'undefined' ? process.env.RTM_SERVER_NAME : undefined
17739 }, options);
17740 _this2._cache = new Cache('endpoints');
17741
17742 var _this = internal(assertThisInitialized(_this2));
17743
17744 _this.clients = new Set();
17745 _this.pendingClients = new Set();
17746 var mergedPlugins = [].concat(toConsumableArray(ensureArray(Realtime.__preRegisteredPlugins)), toConsumableArray(ensureArray(plugins)));
17747 debug$6('Using plugins %o', mergedPlugins.map(function (plugin) {
17748 return plugin.name;
17749 }));
17750 _this2._plugins = mergedPlugins.reduce(function (result, plugin) {
17751 Object.keys(plugin).forEach(function (hook) {
17752 if ({}.hasOwnProperty.call(plugin, hook) && hook !== 'name') {
17753 if (plugin.name) {
17754 ensureArray(plugin[hook]).forEach(function (value) {
17755 // eslint-disable-next-line no-param-reassign
17756 value._pluginName = plugin.name;
17757 });
17758 } // eslint-disable-next-line no-param-reassign
17759
17760
17761 result[hook] = ensureArray(result[hook]).concat(plugin[hook]);
17762 }
17763 });
17764 return result;
17765 }, {}); // onRealtimeCreate hook
17766
17767 applyDecorators(_this2._plugins.onRealtimeCreate, assertThisInitialized(_this2));
17768 return _this2;
17769 }
17770
17771 var _proto = Realtime.prototype;
17772
17773 _proto._request = /*#__PURE__*/function () {
17774 var _request2 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee(_ref2) {
17775 var method, _url, _ref2$version, version, path, query, headers, data, url, _this$_options, appId, server, _yield$this$construct, api;
17776
17777 return regenerator.wrap(function _callee$(_context) {
17778 while (1) {
17779 switch (_context.prev = _context.next) {
17780 case 0:
17781 method = _ref2.method, _url = _ref2.url, _ref2$version = _ref2.version, version = _ref2$version === void 0 ? '1.1' : _ref2$version, path = _ref2.path, query = _ref2.query, headers = _ref2.headers, data = _ref2.data;
17782 url = _url;
17783
17784 if (url) {
17785 _context.next = 9;
17786 break;
17787 }
17788
17789 _this$_options = this._options, appId = _this$_options.appId, server = _this$_options.server;
17790 _context.next = 6;
17791 return this.constructor._getServerUrls({
17792 appId: appId,
17793 server: server
17794 });
17795
17796 case 6:
17797 _yield$this$construct = _context.sent;
17798 api = _yield$this$construct.api;
17799 url = "".concat(api, "/").concat(version).concat(path);
17800
17801 case 9:
17802 return _context.abrupt("return", request({
17803 url: url,
17804 method: method,
17805 query: query,
17806 headers: _objectSpread$2({
17807 'X-LC-Id': this._options.appId,
17808 'X-LC-Key': this._options.appKey
17809 }, headers),
17810 data: data
17811 }));
17812
17813 case 10:
17814 case "end":
17815 return _context.stop();
17816 }
17817 }
17818 }, _callee, this);
17819 }));
17820
17821 function _request(_x) {
17822 return _request2.apply(this, arguments);
17823 }
17824
17825 return _request;
17826 }();
17827
17828 _proto._open = function _open() {
17829 var _this3 = this;
17830
17831 if (this._openPromise) return this._openPromise;
17832 var format = 'protobuf2';
17833
17834 if (this._options.noBinary) {
17835 // 不发送 binary data,fallback to base64 string
17836 format = 'proto2base64';
17837 }
17838
17839 var version = 3;
17840 var protocol = {
17841 format: format,
17842 version: version
17843 };
17844 this._openPromise = new Promise(function (resolve, reject) {
17845 debug$6('No connection established, create a new one.');
17846 var connection = new Connection(function () {
17847 return _this3._getRTMServers(_this3._options);
17848 }, protocol);
17849 connection.on(OPEN, function () {
17850 return resolve(connection);
17851 }).on(ERROR, function (error) {
17852 delete _this3._openPromise;
17853 reject(error);
17854 }).on(EXPIRE, /*#__PURE__*/asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee2() {
17855 return regenerator.wrap(function _callee2$(_context2) {
17856 while (1) {
17857 switch (_context2.prev = _context2.next) {
17858 case 0:
17859 debug$6('Connection expired. Refresh endpoints.');
17860
17861 _this3._cache.set('endpoints', null, 0);
17862
17863 _context2.next = 4;
17864 return _this3._getRTMServers(_this3._options);
17865
17866 case 4:
17867 connection.urls = _context2.sent;
17868 connection.disconnect();
17869
17870 case 6:
17871 case "end":
17872 return _context2.stop();
17873 }
17874 }
17875 }, _callee2);
17876 }))).on(MESSAGE, _this3._dispatchCommand.bind(_this3));
17877 /**
17878 * 连接断开。
17879 * 连接断开可能是因为 SDK 进入了离线状态(see {@link Realtime#event:OFFLINE}),或长时间没有收到服务器心跳。
17880 * 连接断开后所有的网络操作都会失败,请在连接断开后禁用相关的 UI 元素。
17881 * @event Realtime#DISCONNECT
17882 */
17883
17884 /**
17885 * 计划在一段时间后尝试重新连接
17886 * @event Realtime#SCHEDULE
17887 * @param {Number} attempt 尝试重连的次数
17888 * @param {Number} delay 延迟的毫秒数
17889 */
17890
17891 /**
17892 * 正在尝试重新连接
17893 * @event Realtime#RETRY
17894 * @param {Number} attempt 尝试重连的次数
17895 */
17896
17897 /**
17898 * 连接恢复正常。
17899 * 请重新启用在 {@link Realtime#event:DISCONNECT} 事件中禁用的相关 UI 元素
17900 * @event Realtime#RECONNECT
17901 */
17902
17903 /**
17904 * 客户端连接断开
17905 * @event IMClient#DISCONNECT
17906 * @see Realtime#event:DISCONNECT
17907 * @since 3.2.0
17908 */
17909
17910 /**
17911 * 计划在一段时间后尝试重新连接
17912 * @event IMClient#SCHEDULE
17913 * @param {Number} attempt 尝试重连的次数
17914 * @param {Number} delay 延迟的毫秒数
17915 * @since 3.2.0
17916 */
17917
17918 /**
17919 * 正在尝试重新连接
17920 * @event IMClient#RETRY
17921 * @param {Number} attempt 尝试重连的次数
17922 * @since 3.2.0
17923 */
17924
17925 /**
17926 * 客户端进入离线状态。
17927 * 这通常意味着网络已断开,或者 {@link Realtime#pause} 被调用
17928 * @event Realtime#OFFLINE
17929 * @since 3.4.0
17930 */
17931
17932 /**
17933 * 客户端恢复在线状态
17934 * 这通常意味着网络已恢复,或者 {@link Realtime#resume} 被调用
17935 * @event Realtime#ONLINE
17936 * @since 3.4.0
17937 */
17938
17939 /**
17940 * 进入离线状态。
17941 * 这通常意味着网络已断开,或者 {@link Realtime#pause} 被调用
17942 * @event IMClient#OFFLINE
17943 * @since 3.4.0
17944 */
17945
17946 /**
17947 * 恢复在线状态
17948 * 这通常意味着网络已恢复,或者 {@link Realtime#resume} 被调用
17949 * @event IMClient#ONLINE
17950 * @since 3.4.0
17951 */
17952 // event proxy
17953
17954 [DISCONNECT, RECONNECT, RETRY, SCHEDULE, OFFLINE, ONLINE].forEach(function (event) {
17955 return connection.on(event, function () {
17956 for (var _len = arguments.length, payload = new Array(_len), _key = 0; _key < _len; _key++) {
17957 payload[_key] = arguments[_key];
17958 }
17959
17960 debug$6("".concat(event, " event emitted. %o"), payload);
17961
17962 _this3.emit.apply(_this3, [event].concat(payload));
17963
17964 if (event !== RECONNECT) {
17965 internal(_this3).clients.forEach(function (client) {
17966 client.emit.apply(client, [event].concat(payload));
17967 });
17968 }
17969 });
17970 }); // override handleClose
17971
17972 connection.handleClose = function handleClose(event) {
17973 var isFatal = [ErrorCode.APP_NOT_AVAILABLE, ErrorCode.INVALID_LOGIN, ErrorCode.INVALID_ORIGIN].some(function (errorCode) {
17974 return errorCode === event.code;
17975 });
17976
17977 if (isFatal) {
17978 // in these cases, SDK should throw.
17979 this["throw"](createError(event));
17980 } else {
17981 // reconnect
17982 this.disconnect();
17983 }
17984 };
17985
17986 internal(_this3).connection = connection;
17987 });
17988 return this._openPromise;
17989 };
17990
17991 _proto._getRTMServers = /*#__PURE__*/function () {
17992 var _getRTMServers2 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee3(options) {
17993 var info, cachedEndPoints, _info, server, secondary, ttl;
17994
17995 return regenerator.wrap(function _callee3$(_context3) {
17996 while (1) {
17997 switch (_context3.prev = _context3.next) {
17998 case 0:
17999 if (!options.RTMServers) {
18000 _context3.next = 2;
18001 break;
18002 }
18003
18004 return _context3.abrupt("return", shuffle_1(ensureArray(options.RTMServers)));
18005
18006 case 2:
18007 cachedEndPoints = this._cache.get('endpoints');
18008
18009 if (!cachedEndPoints) {
18010 _context3.next = 7;
18011 break;
18012 }
18013
18014 info = cachedEndPoints;
18015 _context3.next = 14;
18016 break;
18017
18018 case 7:
18019 _context3.next = 9;
18020 return this.constructor._fetchRTMServers(options);
18021
18022 case 9:
18023 info = _context3.sent;
18024 _info = info, server = _info.server, secondary = _info.secondary, ttl = _info.ttl;
18025
18026 if (!(typeof server !== 'string' && typeof secondary !== 'string' && typeof ttl !== 'number')) {
18027 _context3.next = 13;
18028 break;
18029 }
18030
18031 throw new Error("malformed RTM route response: ".concat(JSON.stringify(info)));
18032
18033 case 13:
18034 this._cache.set('endpoints', info, info.ttl * 1000);
18035
18036 case 14:
18037 debug$6('endpoint info: %O', info);
18038 return _context3.abrupt("return", [info.server, info.secondary]);
18039
18040 case 16:
18041 case "end":
18042 return _context3.stop();
18043 }
18044 }
18045 }, _callee3, this);
18046 }));
18047
18048 function _getRTMServers(_x2) {
18049 return _getRTMServers2.apply(this, arguments);
18050 }
18051
18052 return _getRTMServers;
18053 }();
18054
18055 Realtime._getServerUrls = /*#__PURE__*/function () {
18056 var _getServerUrls2 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee4(_ref4) {
18057 var appId, server, cachedRouter, defaultProtocol;
18058 return regenerator.wrap(function _callee4$(_context4) {
18059 while (1) {
18060 switch (_context4.prev = _context4.next) {
18061 case 0:
18062 appId = _ref4.appId, server = _ref4.server;
18063 debug$6('fetch server urls');
18064
18065 if (!server) {
18066 _context4.next = 6;
18067 break;
18068 }
18069
18070 if (!(typeof server !== 'string')) {
18071 _context4.next = 5;
18072 break;
18073 }
18074
18075 return _context4.abrupt("return", server);
18076
18077 case 5:
18078 return _context4.abrupt("return", {
18079 RTMRouter: server,
18080 api: server
18081 });
18082
18083 case 6:
18084 cachedRouter = routerCache.get(appId);
18085
18086 if (!cachedRouter) {
18087 _context4.next = 9;
18088 break;
18089 }
18090
18091 return _context4.abrupt("return", cachedRouter);
18092
18093 case 9:
18094 defaultProtocol = 'https://';
18095 return _context4.abrupt("return", request({
18096 url: 'https://app-router.com/2/route',
18097 query: {
18098 appId: appId
18099 },
18100 timeout: 20000
18101 }).then(tap(debug$6)).then(function (_ref5) {
18102 var RTMRouterServer = _ref5.rtm_router_server,
18103 APIServer = _ref5.api_server,
18104 _ref5$ttl = _ref5.ttl,
18105 ttl = _ref5$ttl === void 0 ? 3600 : _ref5$ttl;
18106
18107 if (!RTMRouterServer) {
18108 throw new Error('rtm router not exists');
18109 }
18110
18111 var serverUrls = {
18112 RTMRouter: "".concat(defaultProtocol).concat(RTMRouterServer),
18113 api: "".concat(defaultProtocol).concat(APIServer)
18114 };
18115 routerCache.set(appId, serverUrls, ttl * 1000);
18116 return serverUrls;
18117 })["catch"](function () {
18118 var id = appId.slice(0, 8).toLowerCase();
18119 var domain = 'lncldglobal.com';
18120 return {
18121 RTMRouter: "".concat(defaultProtocol).concat(id, ".rtm.").concat(domain),
18122 api: "".concat(defaultProtocol).concat(id, ".api.").concat(domain)
18123 };
18124 }));
18125
18126 case 11:
18127 case "end":
18128 return _context4.stop();
18129 }
18130 }
18131 }, _callee4);
18132 }));
18133
18134 function _getServerUrls(_x3) {
18135 return _getServerUrls2.apply(this, arguments);
18136 }
18137
18138 return _getServerUrls;
18139 }();
18140
18141 Realtime._fetchRTMServers = function _fetchRTMServers(_ref6) {
18142 var appId = _ref6.appId,
18143 ssl = _ref6.ssl,
18144 server = _ref6.server,
18145 RTMServerName = _ref6.RTMServerName;
18146 debug$6('fetch endpoint info');
18147 return this._getServerUrls({
18148 appId: appId,
18149 server: server
18150 }).then(tap(debug$6)).then(function (_ref7) {
18151 var RTMRouter = _ref7.RTMRouter;
18152 return request({
18153 url: "".concat(RTMRouter, "/v1/route"),
18154 query: {
18155 appId: appId,
18156 secure: ssl,
18157 features: isWeapp ? 'wechat' : undefined,
18158 server: RTMServerName,
18159 _t: Date.now()
18160 },
18161 timeout: 20000
18162 }).then(tap(debug$6));
18163 });
18164 };
18165
18166 _proto._close = function _close() {
18167 if (this._openPromise) {
18168 this._openPromise.then(function (connection) {
18169 return connection.close();
18170 });
18171 }
18172
18173 delete this._openPromise;
18174 }
18175 /**
18176 * 手动进行重连。
18177 * SDK 在网络出现异常时会自动按照一定的时间间隔尝试重连,调用该方法会立即尝试重连并重置重连尝试计数器。
18178 * 只能在 `SCHEDULE` 事件之后,`RETRY` 事件之前调用,如果当前网络正常或者正在进行重连,调用该方法会抛异常。
18179 */
18180 ;
18181
18182 _proto.retry = function retry() {
18183 var _internal = internal(this),
18184 connection = _internal.connection;
18185
18186 if (!connection) {
18187 throw new Error('no connection established');
18188 }
18189
18190 if (connection.cannot('retry')) {
18191 throw new Error("retrying not allowed when not disconnected. the connection is now ".concat(connection.current));
18192 }
18193
18194 return connection.retry();
18195 }
18196 /**
18197 * 暂停,使 SDK 进入离线状态。
18198 * 你可以在网络断开、应用进入后台等时刻调用该方法让 SDK 进入离线状态,离线状态下不会尝试重连。
18199 * 在浏览器中 SDK 会自动监听网络变化,因此无需手动调用该方法。
18200 *
18201 * @since 3.4.0
18202 * @see Realtime#event:OFFLINE
18203 */
18204 ;
18205
18206 _proto.pause = function pause() {
18207 // 这个方法常常在网络断开、进入后台时被调用,此时 connection 可能没有建立或者已经 close。
18208 // 因此不像 retry,这个方法应该尽可能 loose
18209 var _internal2 = internal(this),
18210 connection = _internal2.connection;
18211
18212 if (!connection) return;
18213 if (connection.can('pause')) connection.pause();
18214 }
18215 /**
18216 * 恢复在线状态。
18217 * 你可以在网络恢复、应用回到前台等时刻调用该方法让 SDK 恢复在线状态,恢复在线状态后 SDK 会开始尝试重连。
18218 *
18219 * @since 3.4.0
18220 * @see Realtime#event:ONLINE
18221 */
18222 ;
18223
18224 _proto.resume = function resume() {
18225 // 与 pause 一样,这个方法应该尽可能 loose
18226 var _internal3 = internal(this),
18227 connection = _internal3.connection;
18228
18229 if (!connection) return;
18230 if (connection.can('resume')) connection.resume();
18231 };
18232
18233 _proto._registerPending = function _registerPending(value) {
18234 internal(this).pendingClients.add(value);
18235 };
18236
18237 _proto._deregisterPending = function _deregisterPending(client) {
18238 internal(this).pendingClients["delete"](client);
18239 };
18240
18241 _proto._register = function _register(client) {
18242 internal(this).clients.add(client);
18243 };
18244
18245 _proto._deregister = function _deregister(client) {
18246 var _this = internal(this);
18247
18248 _this.clients["delete"](client);
18249
18250 if (_this.clients.size + _this.pendingClients.size === 0) {
18251 this._close();
18252 }
18253 };
18254
18255 _proto._dispatchCommand = function _dispatchCommand(command) {
18256 return applyDispatcher(this._plugins.beforeCommandDispatch, [command, this]).then(function (shouldDispatch) {
18257 // no plugin handled this command
18258 if (shouldDispatch) return debug$6('[WARN] Unexpected message received: %O', trim(command));
18259 return false;
18260 });
18261 };
18262
18263 return Realtime;
18264 }(eventemitter3); // For test purpose only
18265
18266 var polyfilledPromise = Promise;
18267
18268 var rngBrowser = createCommonjsModule(function (module) {
18269 // Unique ID creation requires a high quality random # generator. In the
18270 // browser this is a little complicated due to unknown quality of Math.random()
18271 // and inconsistent support for the `crypto` API. We do the best we can via
18272 // feature-detection
18273
18274 // getRandomValues needs to be invoked in a context where "this" is a Crypto
18275 // implementation. Also, find the complete implementation of crypto on IE11.
18276 var getRandomValues = (typeof(crypto) != 'undefined' && crypto.getRandomValues && crypto.getRandomValues.bind(crypto)) ||
18277 (typeof(msCrypto) != 'undefined' && typeof window.msCrypto.getRandomValues == 'function' && msCrypto.getRandomValues.bind(msCrypto));
18278
18279 if (getRandomValues) {
18280 // WHATWG crypto RNG - http://wiki.whatwg.org/wiki/Crypto
18281 var rnds8 = new Uint8Array(16); // eslint-disable-line no-undef
18282
18283 module.exports = function whatwgRNG() {
18284 getRandomValues(rnds8);
18285 return rnds8;
18286 };
18287 } else {
18288 // Math.random()-based (RNG)
18289 //
18290 // If all else fails, use Math.random(). It's fast, but is of unspecified
18291 // quality.
18292 var rnds = new Array(16);
18293
18294 module.exports = function mathRNG() {
18295 for (var i = 0, r; i < 16; i++) {
18296 if ((i & 0x03) === 0) r = Math.random() * 0x100000000;
18297 rnds[i] = r >>> ((i & 0x03) << 3) & 0xff;
18298 }
18299
18300 return rnds;
18301 };
18302 }
18303 });
18304
18305 /**
18306 * Convert array of 16 byte values to UUID string format of the form:
18307 * XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX
18308 */
18309 var byteToHex = [];
18310 for (var i = 0; i < 256; ++i) {
18311 byteToHex[i] = (i + 0x100).toString(16).substr(1);
18312 }
18313
18314 function bytesToUuid(buf, offset) {
18315 var i = offset || 0;
18316 var bth = byteToHex;
18317 // join used to fix memory issue caused by concatenation: https://bugs.chromium.org/p/v8/issues/detail?id=3175#c4
18318 return ([bth[buf[i++]], bth[buf[i++]],
18319 bth[buf[i++]], bth[buf[i++]], '-',
18320 bth[buf[i++]], bth[buf[i++]], '-',
18321 bth[buf[i++]], bth[buf[i++]], '-',
18322 bth[buf[i++]], bth[buf[i++]], '-',
18323 bth[buf[i++]], bth[buf[i++]],
18324 bth[buf[i++]], bth[buf[i++]],
18325 bth[buf[i++]], bth[buf[i++]]]).join('');
18326 }
18327
18328 var bytesToUuid_1 = bytesToUuid;
18329
18330 function v4(options, buf, offset) {
18331 var i = buf && offset || 0;
18332
18333 if (typeof(options) == 'string') {
18334 buf = options === 'binary' ? new Array(16) : null;
18335 options = null;
18336 }
18337 options = options || {};
18338
18339 var rnds = options.random || (options.rng || rngBrowser)();
18340
18341 // Per 4.4, set bits for version and `clock_seq_hi_and_reserved`
18342 rnds[6] = (rnds[6] & 0x0f) | 0x40;
18343 rnds[8] = (rnds[8] & 0x3f) | 0x80;
18344
18345 // Copy bytes to buffer, if provided
18346 if (buf) {
18347 for (var ii = 0; ii < 16; ++ii) {
18348 buf[i + ii] = rnds[ii];
18349 }
18350 }
18351
18352 return buf || bytesToUuid_1(rnds);
18353 }
18354
18355 var v4_1 = v4;
18356
18357 function _iterableToArrayLimit(arr, i) {
18358 if (typeof Symbol === "undefined" || !(Symbol.iterator in Object(arr))) return;
18359 var _arr = [];
18360 var _n = true;
18361 var _d = false;
18362 var _e = undefined;
18363
18364 try {
18365 for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) {
18366 _arr.push(_s.value);
18367
18368 if (i && _arr.length === i) break;
18369 }
18370 } catch (err) {
18371 _d = true;
18372 _e = err;
18373 } finally {
18374 try {
18375 if (!_n && _i["return"] != null) _i["return"]();
18376 } finally {
18377 if (_d) throw _e;
18378 }
18379 }
18380
18381 return _arr;
18382 }
18383
18384 var iterableToArrayLimit = _iterableToArrayLimit;
18385
18386 function _slicedToArray(arr, i) {
18387 return arrayWithHoles(arr) || iterableToArrayLimit(arr, i) || unsupportedIterableToArray(arr, i) || nonIterableRest();
18388 }
18389
18390 var slicedToArray = _slicedToArray;
18391
18392 var base64Arraybuffer = createCommonjsModule(function (module, exports) {
18393 /*
18394 * base64-arraybuffer
18395 * https://github.com/niklasvh/base64-arraybuffer
18396 *
18397 * Copyright (c) 2012 Niklas von Hertzen
18398 * Licensed under the MIT license.
18399 */
18400 (function(){
18401
18402 var chars = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
18403
18404 // Use a lookup table to find the index.
18405 var lookup = new Uint8Array(256);
18406 for (var i = 0; i < chars.length; i++) {
18407 lookup[chars.charCodeAt(i)] = i;
18408 }
18409
18410 exports.encode = function(arraybuffer) {
18411 var bytes = new Uint8Array(arraybuffer),
18412 i, len = bytes.length, base64 = "";
18413
18414 for (i = 0; i < len; i+=3) {
18415 base64 += chars[bytes[i] >> 2];
18416 base64 += chars[((bytes[i] & 3) << 4) | (bytes[i + 1] >> 4)];
18417 base64 += chars[((bytes[i + 1] & 15) << 2) | (bytes[i + 2] >> 6)];
18418 base64 += chars[bytes[i + 2] & 63];
18419 }
18420
18421 if ((len % 3) === 2) {
18422 base64 = base64.substring(0, base64.length - 1) + "=";
18423 } else if (len % 3 === 1) {
18424 base64 = base64.substring(0, base64.length - 2) + "==";
18425 }
18426
18427 return base64;
18428 };
18429
18430 exports.decode = function(base64) {
18431 var bufferLength = base64.length * 0.75,
18432 len = base64.length, i, p = 0,
18433 encoded1, encoded2, encoded3, encoded4;
18434
18435 if (base64[base64.length - 1] === "=") {
18436 bufferLength--;
18437 if (base64[base64.length - 2] === "=") {
18438 bufferLength--;
18439 }
18440 }
18441
18442 var arraybuffer = new ArrayBuffer(bufferLength),
18443 bytes = new Uint8Array(arraybuffer);
18444
18445 for (i = 0; i < len; i+=4) {
18446 encoded1 = lookup[base64.charCodeAt(i)];
18447 encoded2 = lookup[base64.charCodeAt(i+1)];
18448 encoded3 = lookup[base64.charCodeAt(i+2)];
18449 encoded4 = lookup[base64.charCodeAt(i+3)];
18450
18451 bytes[p++] = (encoded1 << 2) | (encoded2 >> 4);
18452 bytes[p++] = ((encoded2 & 15) << 4) | (encoded3 >> 2);
18453 bytes[p++] = ((encoded3 & 3) << 6) | (encoded4 & 63);
18454 }
18455
18456 return arraybuffer;
18457 };
18458 })();
18459 });
18460 var base64Arraybuffer_1 = base64Arraybuffer.encode;
18461 var base64Arraybuffer_2 = base64Arraybuffer.decode;
18462
18463 /**
18464 * Removes all key-value entries from the list cache.
18465 *
18466 * @private
18467 * @name clear
18468 * @memberOf ListCache
18469 */
18470 function listCacheClear() {
18471 this.__data__ = [];
18472 this.size = 0;
18473 }
18474
18475 var _listCacheClear = listCacheClear;
18476
18477 /**
18478 * Performs a
18479 * [`SameValueZero`](http://ecma-international.org/ecma-262/7.0/#sec-samevaluezero)
18480 * comparison between two values to determine if they are equivalent.
18481 *
18482 * @static
18483 * @memberOf _
18484 * @since 4.0.0
18485 * @category Lang
18486 * @param {*} value The value to compare.
18487 * @param {*} other The other value to compare.
18488 * @returns {boolean} Returns `true` if the values are equivalent, else `false`.
18489 * @example
18490 *
18491 * var object = { 'a': 1 };
18492 * var other = { 'a': 1 };
18493 *
18494 * _.eq(object, object);
18495 * // => true
18496 *
18497 * _.eq(object, other);
18498 * // => false
18499 *
18500 * _.eq('a', 'a');
18501 * // => true
18502 *
18503 * _.eq('a', Object('a'));
18504 * // => false
18505 *
18506 * _.eq(NaN, NaN);
18507 * // => true
18508 */
18509 function eq(value, other) {
18510 return value === other || (value !== value && other !== other);
18511 }
18512
18513 var eq_1 = eq;
18514
18515 /**
18516 * Gets the index at which the `key` is found in `array` of key-value pairs.
18517 *
18518 * @private
18519 * @param {Array} array The array to inspect.
18520 * @param {*} key The key to search for.
18521 * @returns {number} Returns the index of the matched value, else `-1`.
18522 */
18523 function assocIndexOf(array, key) {
18524 var length = array.length;
18525 while (length--) {
18526 if (eq_1(array[length][0], key)) {
18527 return length;
18528 }
18529 }
18530 return -1;
18531 }
18532
18533 var _assocIndexOf = assocIndexOf;
18534
18535 /** Used for built-in method references. */
18536 var arrayProto = Array.prototype;
18537
18538 /** Built-in value references. */
18539 var splice = arrayProto.splice;
18540
18541 /**
18542 * Removes `key` and its value from the list cache.
18543 *
18544 * @private
18545 * @name delete
18546 * @memberOf ListCache
18547 * @param {string} key The key of the value to remove.
18548 * @returns {boolean} Returns `true` if the entry was removed, else `false`.
18549 */
18550 function listCacheDelete(key) {
18551 var data = this.__data__,
18552 index = _assocIndexOf(data, key);
18553
18554 if (index < 0) {
18555 return false;
18556 }
18557 var lastIndex = data.length - 1;
18558 if (index == lastIndex) {
18559 data.pop();
18560 } else {
18561 splice.call(data, index, 1);
18562 }
18563 --this.size;
18564 return true;
18565 }
18566
18567 var _listCacheDelete = listCacheDelete;
18568
18569 /**
18570 * Gets the list cache value for `key`.
18571 *
18572 * @private
18573 * @name get
18574 * @memberOf ListCache
18575 * @param {string} key The key of the value to get.
18576 * @returns {*} Returns the entry value.
18577 */
18578 function listCacheGet(key) {
18579 var data = this.__data__,
18580 index = _assocIndexOf(data, key);
18581
18582 return index < 0 ? undefined : data[index][1];
18583 }
18584
18585 var _listCacheGet = listCacheGet;
18586
18587 /**
18588 * Checks if a list cache value for `key` exists.
18589 *
18590 * @private
18591 * @name has
18592 * @memberOf ListCache
18593 * @param {string} key The key of the entry to check.
18594 * @returns {boolean} Returns `true` if an entry for `key` exists, else `false`.
18595 */
18596 function listCacheHas(key) {
18597 return _assocIndexOf(this.__data__, key) > -1;
18598 }
18599
18600 var _listCacheHas = listCacheHas;
18601
18602 /**
18603 * Sets the list cache `key` to `value`.
18604 *
18605 * @private
18606 * @name set
18607 * @memberOf ListCache
18608 * @param {string} key The key of the value to set.
18609 * @param {*} value The value to set.
18610 * @returns {Object} Returns the list cache instance.
18611 */
18612 function listCacheSet(key, value) {
18613 var data = this.__data__,
18614 index = _assocIndexOf(data, key);
18615
18616 if (index < 0) {
18617 ++this.size;
18618 data.push([key, value]);
18619 } else {
18620 data[index][1] = value;
18621 }
18622 return this;
18623 }
18624
18625 var _listCacheSet = listCacheSet;
18626
18627 /**
18628 * Creates an list cache object.
18629 *
18630 * @private
18631 * @constructor
18632 * @param {Array} [entries] The key-value pairs to cache.
18633 */
18634 function ListCache(entries) {
18635 var index = -1,
18636 length = entries == null ? 0 : entries.length;
18637
18638 this.clear();
18639 while (++index < length) {
18640 var entry = entries[index];
18641 this.set(entry[0], entry[1]);
18642 }
18643 }
18644
18645 // Add methods to `ListCache`.
18646 ListCache.prototype.clear = _listCacheClear;
18647 ListCache.prototype['delete'] = _listCacheDelete;
18648 ListCache.prototype.get = _listCacheGet;
18649 ListCache.prototype.has = _listCacheHas;
18650 ListCache.prototype.set = _listCacheSet;
18651
18652 var _ListCache = ListCache;
18653
18654 /**
18655 * Removes all key-value entries from the stack.
18656 *
18657 * @private
18658 * @name clear
18659 * @memberOf Stack
18660 */
18661 function stackClear() {
18662 this.__data__ = new _ListCache;
18663 this.size = 0;
18664 }
18665
18666 var _stackClear = stackClear;
18667
18668 /**
18669 * Removes `key` and its value from the stack.
18670 *
18671 * @private
18672 * @name delete
18673 * @memberOf Stack
18674 * @param {string} key The key of the value to remove.
18675 * @returns {boolean} Returns `true` if the entry was removed, else `false`.
18676 */
18677 function stackDelete(key) {
18678 var data = this.__data__,
18679 result = data['delete'](key);
18680
18681 this.size = data.size;
18682 return result;
18683 }
18684
18685 var _stackDelete = stackDelete;
18686
18687 /**
18688 * Gets the stack value for `key`.
18689 *
18690 * @private
18691 * @name get
18692 * @memberOf Stack
18693 * @param {string} key The key of the value to get.
18694 * @returns {*} Returns the entry value.
18695 */
18696 function stackGet(key) {
18697 return this.__data__.get(key);
18698 }
18699
18700 var _stackGet = stackGet;
18701
18702 /**
18703 * Checks if a stack value for `key` exists.
18704 *
18705 * @private
18706 * @name has
18707 * @memberOf Stack
18708 * @param {string} key The key of the entry to check.
18709 * @returns {boolean} Returns `true` if an entry for `key` exists, else `false`.
18710 */
18711 function stackHas(key) {
18712 return this.__data__.has(key);
18713 }
18714
18715 var _stackHas = stackHas;
18716
18717 /** Used to detect overreaching core-js shims. */
18718 var coreJsData = _root['__core-js_shared__'];
18719
18720 var _coreJsData = coreJsData;
18721
18722 /** Used to detect methods masquerading as native. */
18723 var maskSrcKey = (function() {
18724 var uid = /[^.]+$/.exec(_coreJsData && _coreJsData.keys && _coreJsData.keys.IE_PROTO || '');
18725 return uid ? ('Symbol(src)_1.' + uid) : '';
18726 }());
18727
18728 /**
18729 * Checks if `func` has its source masked.
18730 *
18731 * @private
18732 * @param {Function} func The function to check.
18733 * @returns {boolean} Returns `true` if `func` is masked, else `false`.
18734 */
18735 function isMasked(func) {
18736 return !!maskSrcKey && (maskSrcKey in func);
18737 }
18738
18739 var _isMasked = isMasked;
18740
18741 /** Used for built-in method references. */
18742 var funcProto$1 = Function.prototype;
18743
18744 /** Used to resolve the decompiled source of functions. */
18745 var funcToString$1 = funcProto$1.toString;
18746
18747 /**
18748 * Converts `func` to its source code.
18749 *
18750 * @private
18751 * @param {Function} func The function to convert.
18752 * @returns {string} Returns the source code.
18753 */
18754 function toSource(func) {
18755 if (func != null) {
18756 try {
18757 return funcToString$1.call(func);
18758 } catch (e) {}
18759 try {
18760 return (func + '');
18761 } catch (e) {}
18762 }
18763 return '';
18764 }
18765
18766 var _toSource = toSource;
18767
18768 /**
18769 * Used to match `RegExp`
18770 * [syntax characters](http://ecma-international.org/ecma-262/7.0/#sec-patterns).
18771 */
18772 var reRegExpChar = /[\\^$.*+?()[\]{}|]/g;
18773
18774 /** Used to detect host constructors (Safari). */
18775 var reIsHostCtor = /^\[object .+?Constructor\]$/;
18776
18777 /** Used for built-in method references. */
18778 var funcProto$2 = Function.prototype,
18779 objectProto$7 = Object.prototype;
18780
18781 /** Used to resolve the decompiled source of functions. */
18782 var funcToString$2 = funcProto$2.toString;
18783
18784 /** Used to check objects for own properties. */
18785 var hasOwnProperty$5 = objectProto$7.hasOwnProperty;
18786
18787 /** Used to detect if a method is native. */
18788 var reIsNative = RegExp('^' +
18789 funcToString$2.call(hasOwnProperty$5).replace(reRegExpChar, '\\$&')
18790 .replace(/hasOwnProperty|(function).*?(?=\\\()| for .+?(?=\\\])/g, '$1.*?') + '$'
18791 );
18792
18793 /**
18794 * The base implementation of `_.isNative` without bad shim checks.
18795 *
18796 * @private
18797 * @param {*} value The value to check.
18798 * @returns {boolean} Returns `true` if `value` is a native function,
18799 * else `false`.
18800 */
18801 function baseIsNative(value) {
18802 if (!isObject_1$1(value) || _isMasked(value)) {
18803 return false;
18804 }
18805 var pattern = isFunction_1(value) ? reIsNative : reIsHostCtor;
18806 return pattern.test(_toSource(value));
18807 }
18808
18809 var _baseIsNative = baseIsNative;
18810
18811 /**
18812 * Gets the value at `key` of `object`.
18813 *
18814 * @private
18815 * @param {Object} [object] The object to query.
18816 * @param {string} key The key of the property to get.
18817 * @returns {*} Returns the property value.
18818 */
18819 function getValue(object, key) {
18820 return object == null ? undefined : object[key];
18821 }
18822
18823 var _getValue = getValue;
18824
18825 /**
18826 * Gets the native function at `key` of `object`.
18827 *
18828 * @private
18829 * @param {Object} object The object to query.
18830 * @param {string} key The key of the method to get.
18831 * @returns {*} Returns the function if it's native, else `undefined`.
18832 */
18833 function getNative(object, key) {
18834 var value = _getValue(object, key);
18835 return _baseIsNative(value) ? value : undefined;
18836 }
18837
18838 var _getNative = getNative;
18839
18840 /* Built-in method references that are verified to be native. */
18841 var Map = _getNative(_root, 'Map');
18842
18843 var _Map = Map;
18844
18845 /* Built-in method references that are verified to be native. */
18846 var nativeCreate = _getNative(Object, 'create');
18847
18848 var _nativeCreate = nativeCreate;
18849
18850 /**
18851 * Removes all key-value entries from the hash.
18852 *
18853 * @private
18854 * @name clear
18855 * @memberOf Hash
18856 */
18857 function hashClear() {
18858 this.__data__ = _nativeCreate ? _nativeCreate(null) : {};
18859 this.size = 0;
18860 }
18861
18862 var _hashClear = hashClear;
18863
18864 /**
18865 * Removes `key` and its value from the hash.
18866 *
18867 * @private
18868 * @name delete
18869 * @memberOf Hash
18870 * @param {Object} hash The hash to modify.
18871 * @param {string} key The key of the value to remove.
18872 * @returns {boolean} Returns `true` if the entry was removed, else `false`.
18873 */
18874 function hashDelete(key) {
18875 var result = this.has(key) && delete this.__data__[key];
18876 this.size -= result ? 1 : 0;
18877 return result;
18878 }
18879
18880 var _hashDelete = hashDelete;
18881
18882 /** Used to stand-in for `undefined` hash values. */
18883 var HASH_UNDEFINED = '__lodash_hash_undefined__';
18884
18885 /** Used for built-in method references. */
18886 var objectProto$8 = Object.prototype;
18887
18888 /** Used to check objects for own properties. */
18889 var hasOwnProperty$6 = objectProto$8.hasOwnProperty;
18890
18891 /**
18892 * Gets the hash value for `key`.
18893 *
18894 * @private
18895 * @name get
18896 * @memberOf Hash
18897 * @param {string} key The key of the value to get.
18898 * @returns {*} Returns the entry value.
18899 */
18900 function hashGet(key) {
18901 var data = this.__data__;
18902 if (_nativeCreate) {
18903 var result = data[key];
18904 return result === HASH_UNDEFINED ? undefined : result;
18905 }
18906 return hasOwnProperty$6.call(data, key) ? data[key] : undefined;
18907 }
18908
18909 var _hashGet = hashGet;
18910
18911 /** Used for built-in method references. */
18912 var objectProto$9 = Object.prototype;
18913
18914 /** Used to check objects for own properties. */
18915 var hasOwnProperty$7 = objectProto$9.hasOwnProperty;
18916
18917 /**
18918 * Checks if a hash value for `key` exists.
18919 *
18920 * @private
18921 * @name has
18922 * @memberOf Hash
18923 * @param {string} key The key of the entry to check.
18924 * @returns {boolean} Returns `true` if an entry for `key` exists, else `false`.
18925 */
18926 function hashHas(key) {
18927 var data = this.__data__;
18928 return _nativeCreate ? (data[key] !== undefined) : hasOwnProperty$7.call(data, key);
18929 }
18930
18931 var _hashHas = hashHas;
18932
18933 /** Used to stand-in for `undefined` hash values. */
18934 var HASH_UNDEFINED$1 = '__lodash_hash_undefined__';
18935
18936 /**
18937 * Sets the hash `key` to `value`.
18938 *
18939 * @private
18940 * @name set
18941 * @memberOf Hash
18942 * @param {string} key The key of the value to set.
18943 * @param {*} value The value to set.
18944 * @returns {Object} Returns the hash instance.
18945 */
18946 function hashSet(key, value) {
18947 var data = this.__data__;
18948 this.size += this.has(key) ? 0 : 1;
18949 data[key] = (_nativeCreate && value === undefined) ? HASH_UNDEFINED$1 : value;
18950 return this;
18951 }
18952
18953 var _hashSet = hashSet;
18954
18955 /**
18956 * Creates a hash object.
18957 *
18958 * @private
18959 * @constructor
18960 * @param {Array} [entries] The key-value pairs to cache.
18961 */
18962 function Hash(entries) {
18963 var index = -1,
18964 length = entries == null ? 0 : entries.length;
18965
18966 this.clear();
18967 while (++index < length) {
18968 var entry = entries[index];
18969 this.set(entry[0], entry[1]);
18970 }
18971 }
18972
18973 // Add methods to `Hash`.
18974 Hash.prototype.clear = _hashClear;
18975 Hash.prototype['delete'] = _hashDelete;
18976 Hash.prototype.get = _hashGet;
18977 Hash.prototype.has = _hashHas;
18978 Hash.prototype.set = _hashSet;
18979
18980 var _Hash = Hash;
18981
18982 /**
18983 * Removes all key-value entries from the map.
18984 *
18985 * @private
18986 * @name clear
18987 * @memberOf MapCache
18988 */
18989 function mapCacheClear() {
18990 this.size = 0;
18991 this.__data__ = {
18992 'hash': new _Hash,
18993 'map': new (_Map || _ListCache),
18994 'string': new _Hash
18995 };
18996 }
18997
18998 var _mapCacheClear = mapCacheClear;
18999
19000 /**
19001 * Checks if `value` is suitable for use as unique object key.
19002 *
19003 * @private
19004 * @param {*} value The value to check.
19005 * @returns {boolean} Returns `true` if `value` is suitable, else `false`.
19006 */
19007 function isKeyable(value) {
19008 var type = typeof value;
19009 return (type == 'string' || type == 'number' || type == 'symbol' || type == 'boolean')
19010 ? (value !== '__proto__')
19011 : (value === null);
19012 }
19013
19014 var _isKeyable = isKeyable;
19015
19016 /**
19017 * Gets the data for `map`.
19018 *
19019 * @private
19020 * @param {Object} map The map to query.
19021 * @param {string} key The reference key.
19022 * @returns {*} Returns the map data.
19023 */
19024 function getMapData(map, key) {
19025 var data = map.__data__;
19026 return _isKeyable(key)
19027 ? data[typeof key == 'string' ? 'string' : 'hash']
19028 : data.map;
19029 }
19030
19031 var _getMapData = getMapData;
19032
19033 /**
19034 * Removes `key` and its value from the map.
19035 *
19036 * @private
19037 * @name delete
19038 * @memberOf MapCache
19039 * @param {string} key The key of the value to remove.
19040 * @returns {boolean} Returns `true` if the entry was removed, else `false`.
19041 */
19042 function mapCacheDelete(key) {
19043 var result = _getMapData(this, key)['delete'](key);
19044 this.size -= result ? 1 : 0;
19045 return result;
19046 }
19047
19048 var _mapCacheDelete = mapCacheDelete;
19049
19050 /**
19051 * Gets the map value for `key`.
19052 *
19053 * @private
19054 * @name get
19055 * @memberOf MapCache
19056 * @param {string} key The key of the value to get.
19057 * @returns {*} Returns the entry value.
19058 */
19059 function mapCacheGet(key) {
19060 return _getMapData(this, key).get(key);
19061 }
19062
19063 var _mapCacheGet = mapCacheGet;
19064
19065 /**
19066 * Checks if a map value for `key` exists.
19067 *
19068 * @private
19069 * @name has
19070 * @memberOf MapCache
19071 * @param {string} key The key of the entry to check.
19072 * @returns {boolean} Returns `true` if an entry for `key` exists, else `false`.
19073 */
19074 function mapCacheHas(key) {
19075 return _getMapData(this, key).has(key);
19076 }
19077
19078 var _mapCacheHas = mapCacheHas;
19079
19080 /**
19081 * Sets the map `key` to `value`.
19082 *
19083 * @private
19084 * @name set
19085 * @memberOf MapCache
19086 * @param {string} key The key of the value to set.
19087 * @param {*} value The value to set.
19088 * @returns {Object} Returns the map cache instance.
19089 */
19090 function mapCacheSet(key, value) {
19091 var data = _getMapData(this, key),
19092 size = data.size;
19093
19094 data.set(key, value);
19095 this.size += data.size == size ? 0 : 1;
19096 return this;
19097 }
19098
19099 var _mapCacheSet = mapCacheSet;
19100
19101 /**
19102 * Creates a map cache object to store key-value pairs.
19103 *
19104 * @private
19105 * @constructor
19106 * @param {Array} [entries] The key-value pairs to cache.
19107 */
19108 function MapCache(entries) {
19109 var index = -1,
19110 length = entries == null ? 0 : entries.length;
19111
19112 this.clear();
19113 while (++index < length) {
19114 var entry = entries[index];
19115 this.set(entry[0], entry[1]);
19116 }
19117 }
19118
19119 // Add methods to `MapCache`.
19120 MapCache.prototype.clear = _mapCacheClear;
19121 MapCache.prototype['delete'] = _mapCacheDelete;
19122 MapCache.prototype.get = _mapCacheGet;
19123 MapCache.prototype.has = _mapCacheHas;
19124 MapCache.prototype.set = _mapCacheSet;
19125
19126 var _MapCache = MapCache;
19127
19128 /** Used as the size to enable large array optimizations. */
19129 var LARGE_ARRAY_SIZE = 200;
19130
19131 /**
19132 * Sets the stack `key` to `value`.
19133 *
19134 * @private
19135 * @name set
19136 * @memberOf Stack
19137 * @param {string} key The key of the value to set.
19138 * @param {*} value The value to set.
19139 * @returns {Object} Returns the stack cache instance.
19140 */
19141 function stackSet(key, value) {
19142 var data = this.__data__;
19143 if (data instanceof _ListCache) {
19144 var pairs = data.__data__;
19145 if (!_Map || (pairs.length < LARGE_ARRAY_SIZE - 1)) {
19146 pairs.push([key, value]);
19147 this.size = ++data.size;
19148 return this;
19149 }
19150 data = this.__data__ = new _MapCache(pairs);
19151 }
19152 data.set(key, value);
19153 this.size = data.size;
19154 return this;
19155 }
19156
19157 var _stackSet = stackSet;
19158
19159 /**
19160 * Creates a stack cache object to store key-value pairs.
19161 *
19162 * @private
19163 * @constructor
19164 * @param {Array} [entries] The key-value pairs to cache.
19165 */
19166 function Stack(entries) {
19167 var data = this.__data__ = new _ListCache(entries);
19168 this.size = data.size;
19169 }
19170
19171 // Add methods to `Stack`.
19172 Stack.prototype.clear = _stackClear;
19173 Stack.prototype['delete'] = _stackDelete;
19174 Stack.prototype.get = _stackGet;
19175 Stack.prototype.has = _stackHas;
19176 Stack.prototype.set = _stackSet;
19177
19178 var _Stack = Stack;
19179
19180 /** Used to stand-in for `undefined` hash values. */
19181 var HASH_UNDEFINED$2 = '__lodash_hash_undefined__';
19182
19183 /**
19184 * Adds `value` to the array cache.
19185 *
19186 * @private
19187 * @name add
19188 * @memberOf SetCache
19189 * @alias push
19190 * @param {*} value The value to cache.
19191 * @returns {Object} Returns the cache instance.
19192 */
19193 function setCacheAdd(value) {
19194 this.__data__.set(value, HASH_UNDEFINED$2);
19195 return this;
19196 }
19197
19198 var _setCacheAdd = setCacheAdd;
19199
19200 /**
19201 * Checks if `value` is in the array cache.
19202 *
19203 * @private
19204 * @name has
19205 * @memberOf SetCache
19206 * @param {*} value The value to search for.
19207 * @returns {number} Returns `true` if `value` is found, else `false`.
19208 */
19209 function setCacheHas(value) {
19210 return this.__data__.has(value);
19211 }
19212
19213 var _setCacheHas = setCacheHas;
19214
19215 /**
19216 *
19217 * Creates an array cache object to store unique values.
19218 *
19219 * @private
19220 * @constructor
19221 * @param {Array} [values] The values to cache.
19222 */
19223 function SetCache(values) {
19224 var index = -1,
19225 length = values == null ? 0 : values.length;
19226
19227 this.__data__ = new _MapCache;
19228 while (++index < length) {
19229 this.add(values[index]);
19230 }
19231 }
19232
19233 // Add methods to `SetCache`.
19234 SetCache.prototype.add = SetCache.prototype.push = _setCacheAdd;
19235 SetCache.prototype.has = _setCacheHas;
19236
19237 var _SetCache = SetCache;
19238
19239 /**
19240 * A specialized version of `_.some` for arrays without support for iteratee
19241 * shorthands.
19242 *
19243 * @private
19244 * @param {Array} [array] The array to iterate over.
19245 * @param {Function} predicate The function invoked per iteration.
19246 * @returns {boolean} Returns `true` if any element passes the predicate check,
19247 * else `false`.
19248 */
19249 function arraySome(array, predicate) {
19250 var index = -1,
19251 length = array == null ? 0 : array.length;
19252
19253 while (++index < length) {
19254 if (predicate(array[index], index, array)) {
19255 return true;
19256 }
19257 }
19258 return false;
19259 }
19260
19261 var _arraySome = arraySome;
19262
19263 /**
19264 * Checks if a `cache` value for `key` exists.
19265 *
19266 * @private
19267 * @param {Object} cache The cache to query.
19268 * @param {string} key The key of the entry to check.
19269 * @returns {boolean} Returns `true` if an entry for `key` exists, else `false`.
19270 */
19271 function cacheHas(cache, key) {
19272 return cache.has(key);
19273 }
19274
19275 var _cacheHas = cacheHas;
19276
19277 /** Used to compose bitmasks for value comparisons. */
19278 var COMPARE_PARTIAL_FLAG = 1,
19279 COMPARE_UNORDERED_FLAG = 2;
19280
19281 /**
19282 * A specialized version of `baseIsEqualDeep` for arrays with support for
19283 * partial deep comparisons.
19284 *
19285 * @private
19286 * @param {Array} array The array to compare.
19287 * @param {Array} other The other array to compare.
19288 * @param {number} bitmask The bitmask flags. See `baseIsEqual` for more details.
19289 * @param {Function} customizer The function to customize comparisons.
19290 * @param {Function} equalFunc The function to determine equivalents of values.
19291 * @param {Object} stack Tracks traversed `array` and `other` objects.
19292 * @returns {boolean} Returns `true` if the arrays are equivalent, else `false`.
19293 */
19294 function equalArrays(array, other, bitmask, customizer, equalFunc, stack) {
19295 var isPartial = bitmask & COMPARE_PARTIAL_FLAG,
19296 arrLength = array.length,
19297 othLength = other.length;
19298
19299 if (arrLength != othLength && !(isPartial && othLength > arrLength)) {
19300 return false;
19301 }
19302 // Check that cyclic values are equal.
19303 var arrStacked = stack.get(array);
19304 var othStacked = stack.get(other);
19305 if (arrStacked && othStacked) {
19306 return arrStacked == other && othStacked == array;
19307 }
19308 var index = -1,
19309 result = true,
19310 seen = (bitmask & COMPARE_UNORDERED_FLAG) ? new _SetCache : undefined;
19311
19312 stack.set(array, other);
19313 stack.set(other, array);
19314
19315 // Ignore non-index properties.
19316 while (++index < arrLength) {
19317 var arrValue = array[index],
19318 othValue = other[index];
19319
19320 if (customizer) {
19321 var compared = isPartial
19322 ? customizer(othValue, arrValue, index, other, array, stack)
19323 : customizer(arrValue, othValue, index, array, other, stack);
19324 }
19325 if (compared !== undefined) {
19326 if (compared) {
19327 continue;
19328 }
19329 result = false;
19330 break;
19331 }
19332 // Recursively compare arrays (susceptible to call stack limits).
19333 if (seen) {
19334 if (!_arraySome(other, function(othValue, othIndex) {
19335 if (!_cacheHas(seen, othIndex) &&
19336 (arrValue === othValue || equalFunc(arrValue, othValue, bitmask, customizer, stack))) {
19337 return seen.push(othIndex);
19338 }
19339 })) {
19340 result = false;
19341 break;
19342 }
19343 } else if (!(
19344 arrValue === othValue ||
19345 equalFunc(arrValue, othValue, bitmask, customizer, stack)
19346 )) {
19347 result = false;
19348 break;
19349 }
19350 }
19351 stack['delete'](array);
19352 stack['delete'](other);
19353 return result;
19354 }
19355
19356 var _equalArrays = equalArrays;
19357
19358 /** Built-in value references. */
19359 var Uint8Array$1 = _root.Uint8Array;
19360
19361 var _Uint8Array = Uint8Array$1;
19362
19363 /**
19364 * Converts `map` to its key-value pairs.
19365 *
19366 * @private
19367 * @param {Object} map The map to convert.
19368 * @returns {Array} Returns the key-value pairs.
19369 */
19370 function mapToArray(map) {
19371 var index = -1,
19372 result = Array(map.size);
19373
19374 map.forEach(function(value, key) {
19375 result[++index] = [key, value];
19376 });
19377 return result;
19378 }
19379
19380 var _mapToArray = mapToArray;
19381
19382 /**
19383 * Converts `set` to an array of its values.
19384 *
19385 * @private
19386 * @param {Object} set The set to convert.
19387 * @returns {Array} Returns the values.
19388 */
19389 function setToArray(set) {
19390 var index = -1,
19391 result = Array(set.size);
19392
19393 set.forEach(function(value) {
19394 result[++index] = value;
19395 });
19396 return result;
19397 }
19398
19399 var _setToArray = setToArray;
19400
19401 /** Used to compose bitmasks for value comparisons. */
19402 var COMPARE_PARTIAL_FLAG$1 = 1,
19403 COMPARE_UNORDERED_FLAG$1 = 2;
19404
19405 /** `Object#toString` result references. */
19406 var boolTag$1 = '[object Boolean]',
19407 dateTag$1 = '[object Date]',
19408 errorTag$1 = '[object Error]',
19409 mapTag$1 = '[object Map]',
19410 numberTag$1 = '[object Number]',
19411 regexpTag$1 = '[object RegExp]',
19412 setTag$1 = '[object Set]',
19413 stringTag$1 = '[object String]',
19414 symbolTag = '[object Symbol]';
19415
19416 var arrayBufferTag$1 = '[object ArrayBuffer]',
19417 dataViewTag$1 = '[object DataView]';
19418
19419 /** Used to convert symbols to primitives and strings. */
19420 var symbolProto = _Symbol ? _Symbol.prototype : undefined,
19421 symbolValueOf = symbolProto ? symbolProto.valueOf : undefined;
19422
19423 /**
19424 * A specialized version of `baseIsEqualDeep` for comparing objects of
19425 * the same `toStringTag`.
19426 *
19427 * **Note:** This function only supports comparing values with tags of
19428 * `Boolean`, `Date`, `Error`, `Number`, `RegExp`, or `String`.
19429 *
19430 * @private
19431 * @param {Object} object The object to compare.
19432 * @param {Object} other The other object to compare.
19433 * @param {string} tag The `toStringTag` of the objects to compare.
19434 * @param {number} bitmask The bitmask flags. See `baseIsEqual` for more details.
19435 * @param {Function} customizer The function to customize comparisons.
19436 * @param {Function} equalFunc The function to determine equivalents of values.
19437 * @param {Object} stack Tracks traversed `object` and `other` objects.
19438 * @returns {boolean} Returns `true` if the objects are equivalent, else `false`.
19439 */
19440 function equalByTag(object, other, tag, bitmask, customizer, equalFunc, stack) {
19441 switch (tag) {
19442 case dataViewTag$1:
19443 if ((object.byteLength != other.byteLength) ||
19444 (object.byteOffset != other.byteOffset)) {
19445 return false;
19446 }
19447 object = object.buffer;
19448 other = other.buffer;
19449
19450 case arrayBufferTag$1:
19451 if ((object.byteLength != other.byteLength) ||
19452 !equalFunc(new _Uint8Array(object), new _Uint8Array(other))) {
19453 return false;
19454 }
19455 return true;
19456
19457 case boolTag$1:
19458 case dateTag$1:
19459 case numberTag$1:
19460 // Coerce booleans to `1` or `0` and dates to milliseconds.
19461 // Invalid dates are coerced to `NaN`.
19462 return eq_1(+object, +other);
19463
19464 case errorTag$1:
19465 return object.name == other.name && object.message == other.message;
19466
19467 case regexpTag$1:
19468 case stringTag$1:
19469 // Coerce regexes to strings and treat strings, primitives and objects,
19470 // as equal. See http://www.ecma-international.org/ecma-262/7.0/#sec-regexp.prototype.tostring
19471 // for more details.
19472 return object == (other + '');
19473
19474 case mapTag$1:
19475 var convert = _mapToArray;
19476
19477 case setTag$1:
19478 var isPartial = bitmask & COMPARE_PARTIAL_FLAG$1;
19479 convert || (convert = _setToArray);
19480
19481 if (object.size != other.size && !isPartial) {
19482 return false;
19483 }
19484 // Assume cyclic values are equal.
19485 var stacked = stack.get(object);
19486 if (stacked) {
19487 return stacked == other;
19488 }
19489 bitmask |= COMPARE_UNORDERED_FLAG$1;
19490
19491 // Recursively compare objects (susceptible to call stack limits).
19492 stack.set(object, other);
19493 var result = _equalArrays(convert(object), convert(other), bitmask, customizer, equalFunc, stack);
19494 stack['delete'](object);
19495 return result;
19496
19497 case symbolTag:
19498 if (symbolValueOf) {
19499 return symbolValueOf.call(object) == symbolValueOf.call(other);
19500 }
19501 }
19502 return false;
19503 }
19504
19505 var _equalByTag = equalByTag;
19506
19507 /**
19508 * Appends the elements of `values` to `array`.
19509 *
19510 * @private
19511 * @param {Array} array The array to modify.
19512 * @param {Array} values The values to append.
19513 * @returns {Array} Returns `array`.
19514 */
19515 function arrayPush(array, values) {
19516 var index = -1,
19517 length = values.length,
19518 offset = array.length;
19519
19520 while (++index < length) {
19521 array[offset + index] = values[index];
19522 }
19523 return array;
19524 }
19525
19526 var _arrayPush = arrayPush;
19527
19528 /**
19529 * The base implementation of `getAllKeys` and `getAllKeysIn` which uses
19530 * `keysFunc` and `symbolsFunc` to get the enumerable property names and
19531 * symbols of `object`.
19532 *
19533 * @private
19534 * @param {Object} object The object to query.
19535 * @param {Function} keysFunc The function to get the keys of `object`.
19536 * @param {Function} symbolsFunc The function to get the symbols of `object`.
19537 * @returns {Array} Returns the array of property names and symbols.
19538 */
19539 function baseGetAllKeys(object, keysFunc, symbolsFunc) {
19540 var result = keysFunc(object);
19541 return isArray_1(object) ? result : _arrayPush(result, symbolsFunc(object));
19542 }
19543
19544 var _baseGetAllKeys = baseGetAllKeys;
19545
19546 /**
19547 * A specialized version of `_.filter` for arrays without support for
19548 * iteratee shorthands.
19549 *
19550 * @private
19551 * @param {Array} [array] The array to iterate over.
19552 * @param {Function} predicate The function invoked per iteration.
19553 * @returns {Array} Returns the new filtered array.
19554 */
19555 function arrayFilter(array, predicate) {
19556 var index = -1,
19557 length = array == null ? 0 : array.length,
19558 resIndex = 0,
19559 result = [];
19560
19561 while (++index < length) {
19562 var value = array[index];
19563 if (predicate(value, index, array)) {
19564 result[resIndex++] = value;
19565 }
19566 }
19567 return result;
19568 }
19569
19570 var _arrayFilter = arrayFilter;
19571
19572 /**
19573 * This method returns a new empty array.
19574 *
19575 * @static
19576 * @memberOf _
19577 * @since 4.13.0
19578 * @category Util
19579 * @returns {Array} Returns the new empty array.
19580 * @example
19581 *
19582 * var arrays = _.times(2, _.stubArray);
19583 *
19584 * console.log(arrays);
19585 * // => [[], []]
19586 *
19587 * console.log(arrays[0] === arrays[1]);
19588 * // => false
19589 */
19590 function stubArray() {
19591 return [];
19592 }
19593
19594 var stubArray_1 = stubArray;
19595
19596 /** Used for built-in method references. */
19597 var objectProto$a = Object.prototype;
19598
19599 /** Built-in value references. */
19600 var propertyIsEnumerable$1 = objectProto$a.propertyIsEnumerable;
19601
19602 /* Built-in method references for those with the same name as other `lodash` methods. */
19603 var nativeGetSymbols = Object.getOwnPropertySymbols;
19604
19605 /**
19606 * Creates an array of the own enumerable symbols of `object`.
19607 *
19608 * @private
19609 * @param {Object} object The object to query.
19610 * @returns {Array} Returns the array of symbols.
19611 */
19612 var getSymbols = !nativeGetSymbols ? stubArray_1 : function(object) {
19613 if (object == null) {
19614 return [];
19615 }
19616 object = Object(object);
19617 return _arrayFilter(nativeGetSymbols(object), function(symbol) {
19618 return propertyIsEnumerable$1.call(object, symbol);
19619 });
19620 };
19621
19622 var _getSymbols = getSymbols;
19623
19624 /**
19625 * Creates an array of own enumerable property names and symbols of `object`.
19626 *
19627 * @private
19628 * @param {Object} object The object to query.
19629 * @returns {Array} Returns the array of property names and symbols.
19630 */
19631 function getAllKeys(object) {
19632 return _baseGetAllKeys(object, keys_1, _getSymbols);
19633 }
19634
19635 var _getAllKeys = getAllKeys;
19636
19637 /** Used to compose bitmasks for value comparisons. */
19638 var COMPARE_PARTIAL_FLAG$2 = 1;
19639
19640 /** Used for built-in method references. */
19641 var objectProto$b = Object.prototype;
19642
19643 /** Used to check objects for own properties. */
19644 var hasOwnProperty$8 = objectProto$b.hasOwnProperty;
19645
19646 /**
19647 * A specialized version of `baseIsEqualDeep` for objects with support for
19648 * partial deep comparisons.
19649 *
19650 * @private
19651 * @param {Object} object The object to compare.
19652 * @param {Object} other The other object to compare.
19653 * @param {number} bitmask The bitmask flags. See `baseIsEqual` for more details.
19654 * @param {Function} customizer The function to customize comparisons.
19655 * @param {Function} equalFunc The function to determine equivalents of values.
19656 * @param {Object} stack Tracks traversed `object` and `other` objects.
19657 * @returns {boolean} Returns `true` if the objects are equivalent, else `false`.
19658 */
19659 function equalObjects(object, other, bitmask, customizer, equalFunc, stack) {
19660 var isPartial = bitmask & COMPARE_PARTIAL_FLAG$2,
19661 objProps = _getAllKeys(object),
19662 objLength = objProps.length,
19663 othProps = _getAllKeys(other),
19664 othLength = othProps.length;
19665
19666 if (objLength != othLength && !isPartial) {
19667 return false;
19668 }
19669 var index = objLength;
19670 while (index--) {
19671 var key = objProps[index];
19672 if (!(isPartial ? key in other : hasOwnProperty$8.call(other, key))) {
19673 return false;
19674 }
19675 }
19676 // Check that cyclic values are equal.
19677 var objStacked = stack.get(object);
19678 var othStacked = stack.get(other);
19679 if (objStacked && othStacked) {
19680 return objStacked == other && othStacked == object;
19681 }
19682 var result = true;
19683 stack.set(object, other);
19684 stack.set(other, object);
19685
19686 var skipCtor = isPartial;
19687 while (++index < objLength) {
19688 key = objProps[index];
19689 var objValue = object[key],
19690 othValue = other[key];
19691
19692 if (customizer) {
19693 var compared = isPartial
19694 ? customizer(othValue, objValue, key, other, object, stack)
19695 : customizer(objValue, othValue, key, object, other, stack);
19696 }
19697 // Recursively compare objects (susceptible to call stack limits).
19698 if (!(compared === undefined
19699 ? (objValue === othValue || equalFunc(objValue, othValue, bitmask, customizer, stack))
19700 : compared
19701 )) {
19702 result = false;
19703 break;
19704 }
19705 skipCtor || (skipCtor = key == 'constructor');
19706 }
19707 if (result && !skipCtor) {
19708 var objCtor = object.constructor,
19709 othCtor = other.constructor;
19710
19711 // Non `Object` object instances with different constructors are not equal.
19712 if (objCtor != othCtor &&
19713 ('constructor' in object && 'constructor' in other) &&
19714 !(typeof objCtor == 'function' && objCtor instanceof objCtor &&
19715 typeof othCtor == 'function' && othCtor instanceof othCtor)) {
19716 result = false;
19717 }
19718 }
19719 stack['delete'](object);
19720 stack['delete'](other);
19721 return result;
19722 }
19723
19724 var _equalObjects = equalObjects;
19725
19726 /* Built-in method references that are verified to be native. */
19727 var DataView = _getNative(_root, 'DataView');
19728
19729 var _DataView = DataView;
19730
19731 /* Built-in method references that are verified to be native. */
19732 var Promise$1 = _getNative(_root, 'Promise');
19733
19734 var _Promise = Promise$1;
19735
19736 /* Built-in method references that are verified to be native. */
19737 var Set$1 = _getNative(_root, 'Set');
19738
19739 var _Set = Set$1;
19740
19741 /* Built-in method references that are verified to be native. */
19742 var WeakMap$1 = _getNative(_root, 'WeakMap');
19743
19744 var _WeakMap = WeakMap$1;
19745
19746 /** `Object#toString` result references. */
19747 var mapTag$2 = '[object Map]',
19748 objectTag$2 = '[object Object]',
19749 promiseTag = '[object Promise]',
19750 setTag$2 = '[object Set]',
19751 weakMapTag$1 = '[object WeakMap]';
19752
19753 var dataViewTag$2 = '[object DataView]';
19754
19755 /** Used to detect maps, sets, and weakmaps. */
19756 var dataViewCtorString = _toSource(_DataView),
19757 mapCtorString = _toSource(_Map),
19758 promiseCtorString = _toSource(_Promise),
19759 setCtorString = _toSource(_Set),
19760 weakMapCtorString = _toSource(_WeakMap);
19761
19762 /**
19763 * Gets the `toStringTag` of `value`.
19764 *
19765 * @private
19766 * @param {*} value The value to query.
19767 * @returns {string} Returns the `toStringTag`.
19768 */
19769 var getTag = _baseGetTag;
19770
19771 // Fallback for data views, maps, sets, and weak maps in IE 11 and promises in Node.js < 6.
19772 if ((_DataView && getTag(new _DataView(new ArrayBuffer(1))) != dataViewTag$2) ||
19773 (_Map && getTag(new _Map) != mapTag$2) ||
19774 (_Promise && getTag(_Promise.resolve()) != promiseTag) ||
19775 (_Set && getTag(new _Set) != setTag$2) ||
19776 (_WeakMap && getTag(new _WeakMap) != weakMapTag$1)) {
19777 getTag = function(value) {
19778 var result = _baseGetTag(value),
19779 Ctor = result == objectTag$2 ? value.constructor : undefined,
19780 ctorString = Ctor ? _toSource(Ctor) : '';
19781
19782 if (ctorString) {
19783 switch (ctorString) {
19784 case dataViewCtorString: return dataViewTag$2;
19785 case mapCtorString: return mapTag$2;
19786 case promiseCtorString: return promiseTag;
19787 case setCtorString: return setTag$2;
19788 case weakMapCtorString: return weakMapTag$1;
19789 }
19790 }
19791 return result;
19792 };
19793 }
19794
19795 var _getTag = getTag;
19796
19797 /** Used to compose bitmasks for value comparisons. */
19798 var COMPARE_PARTIAL_FLAG$3 = 1;
19799
19800 /** `Object#toString` result references. */
19801 var argsTag$2 = '[object Arguments]',
19802 arrayTag$1 = '[object Array]',
19803 objectTag$3 = '[object Object]';
19804
19805 /** Used for built-in method references. */
19806 var objectProto$c = Object.prototype;
19807
19808 /** Used to check objects for own properties. */
19809 var hasOwnProperty$9 = objectProto$c.hasOwnProperty;
19810
19811 /**
19812 * A specialized version of `baseIsEqual` for arrays and objects which performs
19813 * deep comparisons and tracks traversed objects enabling objects with circular
19814 * references to be compared.
19815 *
19816 * @private
19817 * @param {Object} object The object to compare.
19818 * @param {Object} other The other object to compare.
19819 * @param {number} bitmask The bitmask flags. See `baseIsEqual` for more details.
19820 * @param {Function} customizer The function to customize comparisons.
19821 * @param {Function} equalFunc The function to determine equivalents of values.
19822 * @param {Object} [stack] Tracks traversed `object` and `other` objects.
19823 * @returns {boolean} Returns `true` if the objects are equivalent, else `false`.
19824 */
19825 function baseIsEqualDeep(object, other, bitmask, customizer, equalFunc, stack) {
19826 var objIsArr = isArray_1(object),
19827 othIsArr = isArray_1(other),
19828 objTag = objIsArr ? arrayTag$1 : _getTag(object),
19829 othTag = othIsArr ? arrayTag$1 : _getTag(other);
19830
19831 objTag = objTag == argsTag$2 ? objectTag$3 : objTag;
19832 othTag = othTag == argsTag$2 ? objectTag$3 : othTag;
19833
19834 var objIsObj = objTag == objectTag$3,
19835 othIsObj = othTag == objectTag$3,
19836 isSameTag = objTag == othTag;
19837
19838 if (isSameTag && isBuffer_1(object)) {
19839 if (!isBuffer_1(other)) {
19840 return false;
19841 }
19842 objIsArr = true;
19843 objIsObj = false;
19844 }
19845 if (isSameTag && !objIsObj) {
19846 stack || (stack = new _Stack);
19847 return (objIsArr || isTypedArray_1(object))
19848 ? _equalArrays(object, other, bitmask, customizer, equalFunc, stack)
19849 : _equalByTag(object, other, objTag, bitmask, customizer, equalFunc, stack);
19850 }
19851 if (!(bitmask & COMPARE_PARTIAL_FLAG$3)) {
19852 var objIsWrapped = objIsObj && hasOwnProperty$9.call(object, '__wrapped__'),
19853 othIsWrapped = othIsObj && hasOwnProperty$9.call(other, '__wrapped__');
19854
19855 if (objIsWrapped || othIsWrapped) {
19856 var objUnwrapped = objIsWrapped ? object.value() : object,
19857 othUnwrapped = othIsWrapped ? other.value() : other;
19858
19859 stack || (stack = new _Stack);
19860 return equalFunc(objUnwrapped, othUnwrapped, bitmask, customizer, stack);
19861 }
19862 }
19863 if (!isSameTag) {
19864 return false;
19865 }
19866 stack || (stack = new _Stack);
19867 return _equalObjects(object, other, bitmask, customizer, equalFunc, stack);
19868 }
19869
19870 var _baseIsEqualDeep = baseIsEqualDeep;
19871
19872 /**
19873 * The base implementation of `_.isEqual` which supports partial comparisons
19874 * and tracks traversed objects.
19875 *
19876 * @private
19877 * @param {*} value The value to compare.
19878 * @param {*} other The other value to compare.
19879 * @param {boolean} bitmask The bitmask flags.
19880 * 1 - Unordered comparison
19881 * 2 - Partial comparison
19882 * @param {Function} [customizer] The function to customize comparisons.
19883 * @param {Object} [stack] Tracks traversed `value` and `other` objects.
19884 * @returns {boolean} Returns `true` if the values are equivalent, else `false`.
19885 */
19886 function baseIsEqual(value, other, bitmask, customizer, stack) {
19887 if (value === other) {
19888 return true;
19889 }
19890 if (value == null || other == null || (!isObjectLike_1(value) && !isObjectLike_1(other))) {
19891 return value !== value && other !== other;
19892 }
19893 return _baseIsEqualDeep(value, other, bitmask, customizer, baseIsEqual, stack);
19894 }
19895
19896 var _baseIsEqual = baseIsEqual;
19897
19898 /** Used to compose bitmasks for value comparisons. */
19899 var COMPARE_PARTIAL_FLAG$4 = 1,
19900 COMPARE_UNORDERED_FLAG$2 = 2;
19901
19902 /**
19903 * The base implementation of `_.isMatch` without support for iteratee shorthands.
19904 *
19905 * @private
19906 * @param {Object} object The object to inspect.
19907 * @param {Object} source The object of property values to match.
19908 * @param {Array} matchData The property names, values, and compare flags to match.
19909 * @param {Function} [customizer] The function to customize comparisons.
19910 * @returns {boolean} Returns `true` if `object` is a match, else `false`.
19911 */
19912 function baseIsMatch(object, source, matchData, customizer) {
19913 var index = matchData.length,
19914 length = index,
19915 noCustomizer = !customizer;
19916
19917 if (object == null) {
19918 return !length;
19919 }
19920 object = Object(object);
19921 while (index--) {
19922 var data = matchData[index];
19923 if ((noCustomizer && data[2])
19924 ? data[1] !== object[data[0]]
19925 : !(data[0] in object)
19926 ) {
19927 return false;
19928 }
19929 }
19930 while (++index < length) {
19931 data = matchData[index];
19932 var key = data[0],
19933 objValue = object[key],
19934 srcValue = data[1];
19935
19936 if (noCustomizer && data[2]) {
19937 if (objValue === undefined && !(key in object)) {
19938 return false;
19939 }
19940 } else {
19941 var stack = new _Stack;
19942 if (customizer) {
19943 var result = customizer(objValue, srcValue, key, object, source, stack);
19944 }
19945 if (!(result === undefined
19946 ? _baseIsEqual(srcValue, objValue, COMPARE_PARTIAL_FLAG$4 | COMPARE_UNORDERED_FLAG$2, customizer, stack)
19947 : result
19948 )) {
19949 return false;
19950 }
19951 }
19952 }
19953 return true;
19954 }
19955
19956 var _baseIsMatch = baseIsMatch;
19957
19958 /**
19959 * Checks if `value` is suitable for strict equality comparisons, i.e. `===`.
19960 *
19961 * @private
19962 * @param {*} value The value to check.
19963 * @returns {boolean} Returns `true` if `value` if suitable for strict
19964 * equality comparisons, else `false`.
19965 */
19966 function isStrictComparable(value) {
19967 return value === value && !isObject_1$1(value);
19968 }
19969
19970 var _isStrictComparable = isStrictComparable;
19971
19972 /**
19973 * Gets the property names, values, and compare flags of `object`.
19974 *
19975 * @private
19976 * @param {Object} object The object to query.
19977 * @returns {Array} Returns the match data of `object`.
19978 */
19979 function getMatchData(object) {
19980 var result = keys_1(object),
19981 length = result.length;
19982
19983 while (length--) {
19984 var key = result[length],
19985 value = object[key];
19986
19987 result[length] = [key, value, _isStrictComparable(value)];
19988 }
19989 return result;
19990 }
19991
19992 var _getMatchData = getMatchData;
19993
19994 /**
19995 * A specialized version of `matchesProperty` for source values suitable
19996 * for strict equality comparisons, i.e. `===`.
19997 *
19998 * @private
19999 * @param {string} key The key of the property to get.
20000 * @param {*} srcValue The value to match.
20001 * @returns {Function} Returns the new spec function.
20002 */
20003 function matchesStrictComparable(key, srcValue) {
20004 return function(object) {
20005 if (object == null) {
20006 return false;
20007 }
20008 return object[key] === srcValue &&
20009 (srcValue !== undefined || (key in Object(object)));
20010 };
20011 }
20012
20013 var _matchesStrictComparable = matchesStrictComparable;
20014
20015 /**
20016 * The base implementation of `_.matches` which doesn't clone `source`.
20017 *
20018 * @private
20019 * @param {Object} source The object of property values to match.
20020 * @returns {Function} Returns the new spec function.
20021 */
20022 function baseMatches(source) {
20023 var matchData = _getMatchData(source);
20024 if (matchData.length == 1 && matchData[0][2]) {
20025 return _matchesStrictComparable(matchData[0][0], matchData[0][1]);
20026 }
20027 return function(object) {
20028 return object === source || _baseIsMatch(object, source, matchData);
20029 };
20030 }
20031
20032 var _baseMatches = baseMatches;
20033
20034 /** `Object#toString` result references. */
20035 var symbolTag$1 = '[object Symbol]';
20036
20037 /**
20038 * Checks if `value` is classified as a `Symbol` primitive or object.
20039 *
20040 * @static
20041 * @memberOf _
20042 * @since 4.0.0
20043 * @category Lang
20044 * @param {*} value The value to check.
20045 * @returns {boolean} Returns `true` if `value` is a symbol, else `false`.
20046 * @example
20047 *
20048 * _.isSymbol(Symbol.iterator);
20049 * // => true
20050 *
20051 * _.isSymbol('abc');
20052 * // => false
20053 */
20054 function isSymbol(value) {
20055 return typeof value == 'symbol' ||
20056 (isObjectLike_1(value) && _baseGetTag(value) == symbolTag$1);
20057 }
20058
20059 var isSymbol_1 = isSymbol;
20060
20061 /** Used to match property names within property paths. */
20062 var reIsDeepProp = /\.|\[(?:[^[\]]*|(["'])(?:(?!\1)[^\\]|\\.)*?\1)\]/,
20063 reIsPlainProp = /^\w*$/;
20064
20065 /**
20066 * Checks if `value` is a property name and not a property path.
20067 *
20068 * @private
20069 * @param {*} value The value to check.
20070 * @param {Object} [object] The object to query keys on.
20071 * @returns {boolean} Returns `true` if `value` is a property name, else `false`.
20072 */
20073 function isKey(value, object) {
20074 if (isArray_1(value)) {
20075 return false;
20076 }
20077 var type = typeof value;
20078 if (type == 'number' || type == 'symbol' || type == 'boolean' ||
20079 value == null || isSymbol_1(value)) {
20080 return true;
20081 }
20082 return reIsPlainProp.test(value) || !reIsDeepProp.test(value) ||
20083 (object != null && value in Object(object));
20084 }
20085
20086 var _isKey = isKey;
20087
20088 /** Error message constants. */
20089 var FUNC_ERROR_TEXT = 'Expected a function';
20090
20091 /**
20092 * Creates a function that memoizes the result of `func`. If `resolver` is
20093 * provided, it determines the cache key for storing the result based on the
20094 * arguments provided to the memoized function. By default, the first argument
20095 * provided to the memoized function is used as the map cache key. The `func`
20096 * is invoked with the `this` binding of the memoized function.
20097 *
20098 * **Note:** The cache is exposed as the `cache` property on the memoized
20099 * function. Its creation may be customized by replacing the `_.memoize.Cache`
20100 * constructor with one whose instances implement the
20101 * [`Map`](http://ecma-international.org/ecma-262/7.0/#sec-properties-of-the-map-prototype-object)
20102 * method interface of `clear`, `delete`, `get`, `has`, and `set`.
20103 *
20104 * @static
20105 * @memberOf _
20106 * @since 0.1.0
20107 * @category Function
20108 * @param {Function} func The function to have its output memoized.
20109 * @param {Function} [resolver] The function to resolve the cache key.
20110 * @returns {Function} Returns the new memoized function.
20111 * @example
20112 *
20113 * var object = { 'a': 1, 'b': 2 };
20114 * var other = { 'c': 3, 'd': 4 };
20115 *
20116 * var values = _.memoize(_.values);
20117 * values(object);
20118 * // => [1, 2]
20119 *
20120 * values(other);
20121 * // => [3, 4]
20122 *
20123 * object.a = 2;
20124 * values(object);
20125 * // => [1, 2]
20126 *
20127 * // Modify the result cache.
20128 * values.cache.set(object, ['a', 'b']);
20129 * values(object);
20130 * // => ['a', 'b']
20131 *
20132 * // Replace `_.memoize.Cache`.
20133 * _.memoize.Cache = WeakMap;
20134 */
20135 function memoize(func, resolver) {
20136 if (typeof func != 'function' || (resolver != null && typeof resolver != 'function')) {
20137 throw new TypeError(FUNC_ERROR_TEXT);
20138 }
20139 var memoized = function() {
20140 var args = arguments,
20141 key = resolver ? resolver.apply(this, args) : args[0],
20142 cache = memoized.cache;
20143
20144 if (cache.has(key)) {
20145 return cache.get(key);
20146 }
20147 var result = func.apply(this, args);
20148 memoized.cache = cache.set(key, result) || cache;
20149 return result;
20150 };
20151 memoized.cache = new (memoize.Cache || _MapCache);
20152 return memoized;
20153 }
20154
20155 // Expose `MapCache`.
20156 memoize.Cache = _MapCache;
20157
20158 var memoize_1 = memoize;
20159
20160 /** Used as the maximum memoize cache size. */
20161 var MAX_MEMOIZE_SIZE = 500;
20162
20163 /**
20164 * A specialized version of `_.memoize` which clears the memoized function's
20165 * cache when it exceeds `MAX_MEMOIZE_SIZE`.
20166 *
20167 * @private
20168 * @param {Function} func The function to have its output memoized.
20169 * @returns {Function} Returns the new memoized function.
20170 */
20171 function memoizeCapped(func) {
20172 var result = memoize_1(func, function(key) {
20173 if (cache.size === MAX_MEMOIZE_SIZE) {
20174 cache.clear();
20175 }
20176 return key;
20177 });
20178
20179 var cache = result.cache;
20180 return result;
20181 }
20182
20183 var _memoizeCapped = memoizeCapped;
20184
20185 /** Used to match property names within property paths. */
20186 var rePropName = /[^.[\]]+|\[(?:(-?\d+(?:\.\d+)?)|(["'])((?:(?!\2)[^\\]|\\.)*?)\2)\]|(?=(?:\.|\[\])(?:\.|\[\]|$))/g;
20187
20188 /** Used to match backslashes in property paths. */
20189 var reEscapeChar = /\\(\\)?/g;
20190
20191 /**
20192 * Converts `string` to a property path array.
20193 *
20194 * @private
20195 * @param {string} string The string to convert.
20196 * @returns {Array} Returns the property path array.
20197 */
20198 var stringToPath = _memoizeCapped(function(string) {
20199 var result = [];
20200 if (string.charCodeAt(0) === 46 /* . */) {
20201 result.push('');
20202 }
20203 string.replace(rePropName, function(match, number, quote, subString) {
20204 result.push(quote ? subString.replace(reEscapeChar, '$1') : (number || match));
20205 });
20206 return result;
20207 });
20208
20209 var _stringToPath = stringToPath;
20210
20211 /** Used as references for various `Number` constants. */
20212 var INFINITY = 1 / 0;
20213
20214 /** Used to convert symbols to primitives and strings. */
20215 var symbolProto$1 = _Symbol ? _Symbol.prototype : undefined,
20216 symbolToString = symbolProto$1 ? symbolProto$1.toString : undefined;
20217
20218 /**
20219 * The base implementation of `_.toString` which doesn't convert nullish
20220 * values to empty strings.
20221 *
20222 * @private
20223 * @param {*} value The value to process.
20224 * @returns {string} Returns the string.
20225 */
20226 function baseToString(value) {
20227 // Exit early for strings to avoid a performance hit in some environments.
20228 if (typeof value == 'string') {
20229 return value;
20230 }
20231 if (isArray_1(value)) {
20232 // Recursively convert values (susceptible to call stack limits).
20233 return _arrayMap(value, baseToString) + '';
20234 }
20235 if (isSymbol_1(value)) {
20236 return symbolToString ? symbolToString.call(value) : '';
20237 }
20238 var result = (value + '');
20239 return (result == '0' && (1 / value) == -INFINITY) ? '-0' : result;
20240 }
20241
20242 var _baseToString = baseToString;
20243
20244 /**
20245 * Converts `value` to a string. An empty string is returned for `null`
20246 * and `undefined` values. The sign of `-0` is preserved.
20247 *
20248 * @static
20249 * @memberOf _
20250 * @since 4.0.0
20251 * @category Lang
20252 * @param {*} value The value to convert.
20253 * @returns {string} Returns the converted string.
20254 * @example
20255 *
20256 * _.toString(null);
20257 * // => ''
20258 *
20259 * _.toString(-0);
20260 * // => '-0'
20261 *
20262 * _.toString([1, 2, 3]);
20263 * // => '1,2,3'
20264 */
20265 function toString(value) {
20266 return value == null ? '' : _baseToString(value);
20267 }
20268
20269 var toString_1 = toString;
20270
20271 /**
20272 * Casts `value` to a path array if it's not one.
20273 *
20274 * @private
20275 * @param {*} value The value to inspect.
20276 * @param {Object} [object] The object to query keys on.
20277 * @returns {Array} Returns the cast property path array.
20278 */
20279 function castPath(value, object) {
20280 if (isArray_1(value)) {
20281 return value;
20282 }
20283 return _isKey(value, object) ? [value] : _stringToPath(toString_1(value));
20284 }
20285
20286 var _castPath = castPath;
20287
20288 /** Used as references for various `Number` constants. */
20289 var INFINITY$1 = 1 / 0;
20290
20291 /**
20292 * Converts `value` to a string key if it's not a string or symbol.
20293 *
20294 * @private
20295 * @param {*} value The value to inspect.
20296 * @returns {string|symbol} Returns the key.
20297 */
20298 function toKey(value) {
20299 if (typeof value == 'string' || isSymbol_1(value)) {
20300 return value;
20301 }
20302 var result = (value + '');
20303 return (result == '0' && (1 / value) == -INFINITY$1) ? '-0' : result;
20304 }
20305
20306 var _toKey = toKey;
20307
20308 /**
20309 * The base implementation of `_.get` without support for default values.
20310 *
20311 * @private
20312 * @param {Object} object The object to query.
20313 * @param {Array|string} path The path of the property to get.
20314 * @returns {*} Returns the resolved value.
20315 */
20316 function baseGet(object, path) {
20317 path = _castPath(path, object);
20318
20319 var index = 0,
20320 length = path.length;
20321
20322 while (object != null && index < length) {
20323 object = object[_toKey(path[index++])];
20324 }
20325 return (index && index == length) ? object : undefined;
20326 }
20327
20328 var _baseGet = baseGet;
20329
20330 /**
20331 * Gets the value at `path` of `object`. If the resolved value is
20332 * `undefined`, the `defaultValue` is returned in its place.
20333 *
20334 * @static
20335 * @memberOf _
20336 * @since 3.7.0
20337 * @category Object
20338 * @param {Object} object The object to query.
20339 * @param {Array|string} path The path of the property to get.
20340 * @param {*} [defaultValue] The value returned for `undefined` resolved values.
20341 * @returns {*} Returns the resolved value.
20342 * @example
20343 *
20344 * var object = { 'a': [{ 'b': { 'c': 3 } }] };
20345 *
20346 * _.get(object, 'a[0].b.c');
20347 * // => 3
20348 *
20349 * _.get(object, ['a', '0', 'b', 'c']);
20350 * // => 3
20351 *
20352 * _.get(object, 'a.b.c', 'default');
20353 * // => 'default'
20354 */
20355 function get(object, path, defaultValue) {
20356 var result = object == null ? undefined : _baseGet(object, path);
20357 return result === undefined ? defaultValue : result;
20358 }
20359
20360 var get_1 = get;
20361
20362 /**
20363 * The base implementation of `_.hasIn` without support for deep paths.
20364 *
20365 * @private
20366 * @param {Object} [object] The object to query.
20367 * @param {Array|string} key The key to check.
20368 * @returns {boolean} Returns `true` if `key` exists, else `false`.
20369 */
20370 function baseHasIn(object, key) {
20371 return object != null && key in Object(object);
20372 }
20373
20374 var _baseHasIn = baseHasIn;
20375
20376 /**
20377 * Checks if `path` exists on `object`.
20378 *
20379 * @private
20380 * @param {Object} object The object to query.
20381 * @param {Array|string} path The path to check.
20382 * @param {Function} hasFunc The function to check properties.
20383 * @returns {boolean} Returns `true` if `path` exists, else `false`.
20384 */
20385 function hasPath(object, path, hasFunc) {
20386 path = _castPath(path, object);
20387
20388 var index = -1,
20389 length = path.length,
20390 result = false;
20391
20392 while (++index < length) {
20393 var key = _toKey(path[index]);
20394 if (!(result = object != null && hasFunc(object, key))) {
20395 break;
20396 }
20397 object = object[key];
20398 }
20399 if (result || ++index != length) {
20400 return result;
20401 }
20402 length = object == null ? 0 : object.length;
20403 return !!length && isLength_1(length) && _isIndex(key, length) &&
20404 (isArray_1(object) || isArguments_1(object));
20405 }
20406
20407 var _hasPath = hasPath;
20408
20409 /**
20410 * Checks if `path` is a direct or inherited property of `object`.
20411 *
20412 * @static
20413 * @memberOf _
20414 * @since 4.0.0
20415 * @category Object
20416 * @param {Object} object The object to query.
20417 * @param {Array|string} path The path to check.
20418 * @returns {boolean} Returns `true` if `path` exists, else `false`.
20419 * @example
20420 *
20421 * var object = _.create({ 'a': _.create({ 'b': 2 }) });
20422 *
20423 * _.hasIn(object, 'a');
20424 * // => true
20425 *
20426 * _.hasIn(object, 'a.b');
20427 * // => true
20428 *
20429 * _.hasIn(object, ['a', 'b']);
20430 * // => true
20431 *
20432 * _.hasIn(object, 'b');
20433 * // => false
20434 */
20435 function hasIn(object, path) {
20436 return object != null && _hasPath(object, path, _baseHasIn);
20437 }
20438
20439 var hasIn_1 = hasIn;
20440
20441 /** Used to compose bitmasks for value comparisons. */
20442 var COMPARE_PARTIAL_FLAG$5 = 1,
20443 COMPARE_UNORDERED_FLAG$3 = 2;
20444
20445 /**
20446 * The base implementation of `_.matchesProperty` which doesn't clone `srcValue`.
20447 *
20448 * @private
20449 * @param {string} path The path of the property to get.
20450 * @param {*} srcValue The value to match.
20451 * @returns {Function} Returns the new spec function.
20452 */
20453 function baseMatchesProperty(path, srcValue) {
20454 if (_isKey(path) && _isStrictComparable(srcValue)) {
20455 return _matchesStrictComparable(_toKey(path), srcValue);
20456 }
20457 return function(object) {
20458 var objValue = get_1(object, path);
20459 return (objValue === undefined && objValue === srcValue)
20460 ? hasIn_1(object, path)
20461 : _baseIsEqual(srcValue, objValue, COMPARE_PARTIAL_FLAG$5 | COMPARE_UNORDERED_FLAG$3);
20462 };
20463 }
20464
20465 var _baseMatchesProperty = baseMatchesProperty;
20466
20467 /**
20468 * This method returns the first argument it receives.
20469 *
20470 * @static
20471 * @since 0.1.0
20472 * @memberOf _
20473 * @category Util
20474 * @param {*} value Any value.
20475 * @returns {*} Returns `value`.
20476 * @example
20477 *
20478 * var object = { 'a': 1 };
20479 *
20480 * console.log(_.identity(object) === object);
20481 * // => true
20482 */
20483 function identity(value) {
20484 return value;
20485 }
20486
20487 var identity_1 = identity;
20488
20489 /**
20490 * The base implementation of `_.property` without support for deep paths.
20491 *
20492 * @private
20493 * @param {string} key The key of the property to get.
20494 * @returns {Function} Returns the new accessor function.
20495 */
20496 function baseProperty(key) {
20497 return function(object) {
20498 return object == null ? undefined : object[key];
20499 };
20500 }
20501
20502 var _baseProperty = baseProperty;
20503
20504 /**
20505 * A specialized version of `baseProperty` which supports deep paths.
20506 *
20507 * @private
20508 * @param {Array|string} path The path of the property to get.
20509 * @returns {Function} Returns the new accessor function.
20510 */
20511 function basePropertyDeep(path) {
20512 return function(object) {
20513 return _baseGet(object, path);
20514 };
20515 }
20516
20517 var _basePropertyDeep = basePropertyDeep;
20518
20519 /**
20520 * Creates a function that returns the value at `path` of a given object.
20521 *
20522 * @static
20523 * @memberOf _
20524 * @since 2.4.0
20525 * @category Util
20526 * @param {Array|string} path The path of the property to get.
20527 * @returns {Function} Returns the new accessor function.
20528 * @example
20529 *
20530 * var objects = [
20531 * { 'a': { 'b': 2 } },
20532 * { 'a': { 'b': 1 } }
20533 * ];
20534 *
20535 * _.map(objects, _.property('a.b'));
20536 * // => [2, 1]
20537 *
20538 * _.map(_.sortBy(objects, _.property(['a', 'b'])), 'a.b');
20539 * // => [1, 2]
20540 */
20541 function property(path) {
20542 return _isKey(path) ? _baseProperty(_toKey(path)) : _basePropertyDeep(path);
20543 }
20544
20545 var property_1 = property;
20546
20547 /**
20548 * The base implementation of `_.iteratee`.
20549 *
20550 * @private
20551 * @param {*} [value=_.identity] The value to convert to an iteratee.
20552 * @returns {Function} Returns the iteratee.
20553 */
20554 function baseIteratee(value) {
20555 // Don't store the `typeof` result in a variable to avoid a JIT bug in Safari 9.
20556 // See https://bugs.webkit.org/show_bug.cgi?id=156034 for more details.
20557 if (typeof value == 'function') {
20558 return value;
20559 }
20560 if (value == null) {
20561 return identity_1;
20562 }
20563 if (typeof value == 'object') {
20564 return isArray_1(value)
20565 ? _baseMatchesProperty(value[0], value[1])
20566 : _baseMatches(value);
20567 }
20568 return property_1(value);
20569 }
20570
20571 var _baseIteratee = baseIteratee;
20572
20573 /**
20574 * Gets the last element of `array`.
20575 *
20576 * @static
20577 * @memberOf _
20578 * @since 0.1.0
20579 * @category Array
20580 * @param {Array} array The array to query.
20581 * @returns {*} Returns the last element of `array`.
20582 * @example
20583 *
20584 * _.last([1, 2, 3]);
20585 * // => 3
20586 */
20587 function last(array) {
20588 var length = array == null ? 0 : array.length;
20589 return length ? array[length - 1] : undefined;
20590 }
20591
20592 var last_1 = last;
20593
20594 /**
20595 * The base implementation of `_.slice` without an iteratee call guard.
20596 *
20597 * @private
20598 * @param {Array} array The array to slice.
20599 * @param {number} [start=0] The start position.
20600 * @param {number} [end=array.length] The end position.
20601 * @returns {Array} Returns the slice of `array`.
20602 */
20603 function baseSlice(array, start, end) {
20604 var index = -1,
20605 length = array.length;
20606
20607 if (start < 0) {
20608 start = -start > length ? 0 : (length + start);
20609 }
20610 end = end > length ? length : end;
20611 if (end < 0) {
20612 end += length;
20613 }
20614 length = start > end ? 0 : ((end - start) >>> 0);
20615 start >>>= 0;
20616
20617 var result = Array(length);
20618 while (++index < length) {
20619 result[index] = array[index + start];
20620 }
20621 return result;
20622 }
20623
20624 var _baseSlice = baseSlice;
20625
20626 /**
20627 * Gets the parent value at `path` of `object`.
20628 *
20629 * @private
20630 * @param {Object} object The object to query.
20631 * @param {Array} path The path to get the parent value of.
20632 * @returns {*} Returns the parent value.
20633 */
20634 function parent(object, path) {
20635 return path.length < 2 ? object : _baseGet(object, _baseSlice(path, 0, -1));
20636 }
20637
20638 var _parent = parent;
20639
20640 /**
20641 * The base implementation of `_.unset`.
20642 *
20643 * @private
20644 * @param {Object} object The object to modify.
20645 * @param {Array|string} path The property path to unset.
20646 * @returns {boolean} Returns `true` if the property is deleted, else `false`.
20647 */
20648 function baseUnset(object, path) {
20649 path = _castPath(path, object);
20650 object = _parent(object, path);
20651 return object == null || delete object[_toKey(last_1(path))];
20652 }
20653
20654 var _baseUnset = baseUnset;
20655
20656 /** Used for built-in method references. */
20657 var arrayProto$1 = Array.prototype;
20658
20659 /** Built-in value references. */
20660 var splice$1 = arrayProto$1.splice;
20661
20662 /**
20663 * The base implementation of `_.pullAt` without support for individual
20664 * indexes or capturing the removed elements.
20665 *
20666 * @private
20667 * @param {Array} array The array to modify.
20668 * @param {number[]} indexes The indexes of elements to remove.
20669 * @returns {Array} Returns `array`.
20670 */
20671 function basePullAt(array, indexes) {
20672 var length = array ? indexes.length : 0,
20673 lastIndex = length - 1;
20674
20675 while (length--) {
20676 var index = indexes[length];
20677 if (length == lastIndex || index !== previous) {
20678 var previous = index;
20679 if (_isIndex(index)) {
20680 splice$1.call(array, index, 1);
20681 } else {
20682 _baseUnset(array, index);
20683 }
20684 }
20685 }
20686 return array;
20687 }
20688
20689 var _basePullAt = basePullAt;
20690
20691 /**
20692 * Removes all elements from `array` that `predicate` returns truthy for
20693 * and returns an array of the removed elements. The predicate is invoked
20694 * with three arguments: (value, index, array).
20695 *
20696 * **Note:** Unlike `_.filter`, this method mutates `array`. Use `_.pull`
20697 * to pull elements from an array by value.
20698 *
20699 * @static
20700 * @memberOf _
20701 * @since 2.0.0
20702 * @category Array
20703 * @param {Array} array The array to modify.
20704 * @param {Function} [predicate=_.identity] The function invoked per iteration.
20705 * @returns {Array} Returns the new array of removed elements.
20706 * @example
20707 *
20708 * var array = [1, 2, 3, 4];
20709 * var evens = _.remove(array, function(n) {
20710 * return n % 2 == 0;
20711 * });
20712 *
20713 * console.log(array);
20714 * // => [1, 3]
20715 *
20716 * console.log(evens);
20717 * // => [2, 4]
20718 */
20719 function remove(array, predicate) {
20720 var result = [];
20721 if (!(array && array.length)) {
20722 return result;
20723 }
20724 var index = -1,
20725 indexes = [],
20726 length = array.length;
20727
20728 predicate = _baseIteratee(predicate);
20729 while (++index < length) {
20730 var value = array[index];
20731 if (predicate(value, index, array)) {
20732 result.push(value);
20733 indexes.push(index);
20734 }
20735 }
20736 _basePullAt(array, indexes);
20737 return result;
20738 }
20739
20740 var remove_1 = remove;
20741
20742 /** `Object#toString` result references. */
20743 var mapTag$3 = '[object Map]',
20744 setTag$3 = '[object Set]';
20745
20746 /** Used for built-in method references. */
20747 var objectProto$d = Object.prototype;
20748
20749 /** Used to check objects for own properties. */
20750 var hasOwnProperty$a = objectProto$d.hasOwnProperty;
20751
20752 /**
20753 * Checks if `value` is an empty object, collection, map, or set.
20754 *
20755 * Objects are considered empty if they have no own enumerable string keyed
20756 * properties.
20757 *
20758 * Array-like values such as `arguments` objects, arrays, buffers, strings, or
20759 * jQuery-like collections are considered empty if they have a `length` of `0`.
20760 * Similarly, maps and sets are considered empty if they have a `size` of `0`.
20761 *
20762 * @static
20763 * @memberOf _
20764 * @since 0.1.0
20765 * @category Lang
20766 * @param {*} value The value to check.
20767 * @returns {boolean} Returns `true` if `value` is empty, else `false`.
20768 * @example
20769 *
20770 * _.isEmpty(null);
20771 * // => true
20772 *
20773 * _.isEmpty(true);
20774 * // => true
20775 *
20776 * _.isEmpty(1);
20777 * // => true
20778 *
20779 * _.isEmpty([1, 2, 3]);
20780 * // => false
20781 *
20782 * _.isEmpty({ 'a': 1 });
20783 * // => false
20784 */
20785 function isEmpty(value) {
20786 if (value == null) {
20787 return true;
20788 }
20789 if (isArrayLike_1(value) &&
20790 (isArray_1(value) || typeof value == 'string' || typeof value.splice == 'function' ||
20791 isBuffer_1(value) || isTypedArray_1(value) || isArguments_1(value))) {
20792 return !value.length;
20793 }
20794 var tag = _getTag(value);
20795 if (tag == mapTag$3 || tag == setTag$3) {
20796 return !value.size;
20797 }
20798 if (_isPrototype(value)) {
20799 return !_baseKeys(value).length;
20800 }
20801 for (var key in value) {
20802 if (hasOwnProperty$a.call(value, key)) {
20803 return false;
20804 }
20805 }
20806 return true;
20807 }
20808
20809 var isEmpty_1 = isEmpty;
20810
20811 /**
20812 * A specialized version of `_.forEach` for arrays without support for
20813 * iteratee shorthands.
20814 *
20815 * @private
20816 * @param {Array} [array] The array to iterate over.
20817 * @param {Function} iteratee The function invoked per iteration.
20818 * @returns {Array} Returns `array`.
20819 */
20820 function arrayEach(array, iteratee) {
20821 var index = -1,
20822 length = array == null ? 0 : array.length;
20823
20824 while (++index < length) {
20825 if (iteratee(array[index], index, array) === false) {
20826 break;
20827 }
20828 }
20829 return array;
20830 }
20831
20832 var _arrayEach = arrayEach;
20833
20834 var defineProperty$1 = (function() {
20835 try {
20836 var func = _getNative(Object, 'defineProperty');
20837 func({}, '', {});
20838 return func;
20839 } catch (e) {}
20840 }());
20841
20842 var _defineProperty$1 = defineProperty$1;
20843
20844 /**
20845 * The base implementation of `assignValue` and `assignMergeValue` without
20846 * value checks.
20847 *
20848 * @private
20849 * @param {Object} object The object to modify.
20850 * @param {string} key The key of the property to assign.
20851 * @param {*} value The value to assign.
20852 */
20853 function baseAssignValue(object, key, value) {
20854 if (key == '__proto__' && _defineProperty$1) {
20855 _defineProperty$1(object, key, {
20856 'configurable': true,
20857 'enumerable': true,
20858 'value': value,
20859 'writable': true
20860 });
20861 } else {
20862 object[key] = value;
20863 }
20864 }
20865
20866 var _baseAssignValue = baseAssignValue;
20867
20868 /** Used for built-in method references. */
20869 var objectProto$e = Object.prototype;
20870
20871 /** Used to check objects for own properties. */
20872 var hasOwnProperty$b = objectProto$e.hasOwnProperty;
20873
20874 /**
20875 * Assigns `value` to `key` of `object` if the existing value is not equivalent
20876 * using [`SameValueZero`](http://ecma-international.org/ecma-262/7.0/#sec-samevaluezero)
20877 * for equality comparisons.
20878 *
20879 * @private
20880 * @param {Object} object The object to modify.
20881 * @param {string} key The key of the property to assign.
20882 * @param {*} value The value to assign.
20883 */
20884 function assignValue(object, key, value) {
20885 var objValue = object[key];
20886 if (!(hasOwnProperty$b.call(object, key) && eq_1(objValue, value)) ||
20887 (value === undefined && !(key in object))) {
20888 _baseAssignValue(object, key, value);
20889 }
20890 }
20891
20892 var _assignValue = assignValue;
20893
20894 /**
20895 * Copies properties of `source` to `object`.
20896 *
20897 * @private
20898 * @param {Object} source The object to copy properties from.
20899 * @param {Array} props The property identifiers to copy.
20900 * @param {Object} [object={}] The object to copy properties to.
20901 * @param {Function} [customizer] The function to customize copied values.
20902 * @returns {Object} Returns `object`.
20903 */
20904 function copyObject(source, props, object, customizer) {
20905 var isNew = !object;
20906 object || (object = {});
20907
20908 var index = -1,
20909 length = props.length;
20910
20911 while (++index < length) {
20912 var key = props[index];
20913
20914 var newValue = customizer
20915 ? customizer(object[key], source[key], key, object, source)
20916 : undefined;
20917
20918 if (newValue === undefined) {
20919 newValue = source[key];
20920 }
20921 if (isNew) {
20922 _baseAssignValue(object, key, newValue);
20923 } else {
20924 _assignValue(object, key, newValue);
20925 }
20926 }
20927 return object;
20928 }
20929
20930 var _copyObject = copyObject;
20931
20932 /**
20933 * The base implementation of `_.assign` without support for multiple sources
20934 * or `customizer` functions.
20935 *
20936 * @private
20937 * @param {Object} object The destination object.
20938 * @param {Object} source The source object.
20939 * @returns {Object} Returns `object`.
20940 */
20941 function baseAssign(object, source) {
20942 return object && _copyObject(source, keys_1(source), object);
20943 }
20944
20945 var _baseAssign = baseAssign;
20946
20947 /**
20948 * This function is like
20949 * [`Object.keys`](http://ecma-international.org/ecma-262/7.0/#sec-object.keys)
20950 * except that it includes inherited enumerable properties.
20951 *
20952 * @private
20953 * @param {Object} object The object to query.
20954 * @returns {Array} Returns the array of property names.
20955 */
20956 function nativeKeysIn(object) {
20957 var result = [];
20958 if (object != null) {
20959 for (var key in Object(object)) {
20960 result.push(key);
20961 }
20962 }
20963 return result;
20964 }
20965
20966 var _nativeKeysIn = nativeKeysIn;
20967
20968 /** Used for built-in method references. */
20969 var objectProto$f = Object.prototype;
20970
20971 /** Used to check objects for own properties. */
20972 var hasOwnProperty$c = objectProto$f.hasOwnProperty;
20973
20974 /**
20975 * The base implementation of `_.keysIn` which doesn't treat sparse arrays as dense.
20976 *
20977 * @private
20978 * @param {Object} object The object to query.
20979 * @returns {Array} Returns the array of property names.
20980 */
20981 function baseKeysIn(object) {
20982 if (!isObject_1$1(object)) {
20983 return _nativeKeysIn(object);
20984 }
20985 var isProto = _isPrototype(object),
20986 result = [];
20987
20988 for (var key in object) {
20989 if (!(key == 'constructor' && (isProto || !hasOwnProperty$c.call(object, key)))) {
20990 result.push(key);
20991 }
20992 }
20993 return result;
20994 }
20995
20996 var _baseKeysIn = baseKeysIn;
20997
20998 /**
20999 * Creates an array of the own and inherited enumerable property names of `object`.
21000 *
21001 * **Note:** Non-object values are coerced to objects.
21002 *
21003 * @static
21004 * @memberOf _
21005 * @since 3.0.0
21006 * @category Object
21007 * @param {Object} object The object to query.
21008 * @returns {Array} Returns the array of property names.
21009 * @example
21010 *
21011 * function Foo() {
21012 * this.a = 1;
21013 * this.b = 2;
21014 * }
21015 *
21016 * Foo.prototype.c = 3;
21017 *
21018 * _.keysIn(new Foo);
21019 * // => ['a', 'b', 'c'] (iteration order is not guaranteed)
21020 */
21021 function keysIn(object) {
21022 return isArrayLike_1(object) ? _arrayLikeKeys(object, true) : _baseKeysIn(object);
21023 }
21024
21025 var keysIn_1 = keysIn;
21026
21027 /**
21028 * The base implementation of `_.assignIn` without support for multiple sources
21029 * or `customizer` functions.
21030 *
21031 * @private
21032 * @param {Object} object The destination object.
21033 * @param {Object} source The source object.
21034 * @returns {Object} Returns `object`.
21035 */
21036 function baseAssignIn(object, source) {
21037 return object && _copyObject(source, keysIn_1(source), object);
21038 }
21039
21040 var _baseAssignIn = baseAssignIn;
21041
21042 var _cloneBuffer = createCommonjsModule(function (module, exports) {
21043 /** Detect free variable `exports`. */
21044 var freeExports = exports && !exports.nodeType && exports;
21045
21046 /** Detect free variable `module`. */
21047 var freeModule = freeExports && 'object' == 'object' && module && !module.nodeType && module;
21048
21049 /** Detect the popular CommonJS extension `module.exports`. */
21050 var moduleExports = freeModule && freeModule.exports === freeExports;
21051
21052 /** Built-in value references. */
21053 var Buffer = moduleExports ? _root.Buffer : undefined,
21054 allocUnsafe = Buffer ? Buffer.allocUnsafe : undefined;
21055
21056 /**
21057 * Creates a clone of `buffer`.
21058 *
21059 * @private
21060 * @param {Buffer} buffer The buffer to clone.
21061 * @param {boolean} [isDeep] Specify a deep clone.
21062 * @returns {Buffer} Returns the cloned buffer.
21063 */
21064 function cloneBuffer(buffer, isDeep) {
21065 if (isDeep) {
21066 return buffer.slice();
21067 }
21068 var length = buffer.length,
21069 result = allocUnsafe ? allocUnsafe(length) : new buffer.constructor(length);
21070
21071 buffer.copy(result);
21072 return result;
21073 }
21074
21075 module.exports = cloneBuffer;
21076 });
21077
21078 /**
21079 * Copies own symbols of `source` to `object`.
21080 *
21081 * @private
21082 * @param {Object} source The object to copy symbols from.
21083 * @param {Object} [object={}] The object to copy symbols to.
21084 * @returns {Object} Returns `object`.
21085 */
21086 function copySymbols(source, object) {
21087 return _copyObject(source, _getSymbols(source), object);
21088 }
21089
21090 var _copySymbols = copySymbols;
21091
21092 /* Built-in method references for those with the same name as other `lodash` methods. */
21093 var nativeGetSymbols$1 = Object.getOwnPropertySymbols;
21094
21095 /**
21096 * Creates an array of the own and inherited enumerable symbols of `object`.
21097 *
21098 * @private
21099 * @param {Object} object The object to query.
21100 * @returns {Array} Returns the array of symbols.
21101 */
21102 var getSymbolsIn = !nativeGetSymbols$1 ? stubArray_1 : function(object) {
21103 var result = [];
21104 while (object) {
21105 _arrayPush(result, _getSymbols(object));
21106 object = _getPrototype(object);
21107 }
21108 return result;
21109 };
21110
21111 var _getSymbolsIn = getSymbolsIn;
21112
21113 /**
21114 * Copies own and inherited symbols of `source` to `object`.
21115 *
21116 * @private
21117 * @param {Object} source The object to copy symbols from.
21118 * @param {Object} [object={}] The object to copy symbols to.
21119 * @returns {Object} Returns `object`.
21120 */
21121 function copySymbolsIn(source, object) {
21122 return _copyObject(source, _getSymbolsIn(source), object);
21123 }
21124
21125 var _copySymbolsIn = copySymbolsIn;
21126
21127 /**
21128 * Creates an array of own and inherited enumerable property names and
21129 * symbols of `object`.
21130 *
21131 * @private
21132 * @param {Object} object The object to query.
21133 * @returns {Array} Returns the array of property names and symbols.
21134 */
21135 function getAllKeysIn(object) {
21136 return _baseGetAllKeys(object, keysIn_1, _getSymbolsIn);
21137 }
21138
21139 var _getAllKeysIn = getAllKeysIn;
21140
21141 /** Used for built-in method references. */
21142 var objectProto$g = Object.prototype;
21143
21144 /** Used to check objects for own properties. */
21145 var hasOwnProperty$d = objectProto$g.hasOwnProperty;
21146
21147 /**
21148 * Initializes an array clone.
21149 *
21150 * @private
21151 * @param {Array} array The array to clone.
21152 * @returns {Array} Returns the initialized clone.
21153 */
21154 function initCloneArray(array) {
21155 var length = array.length,
21156 result = new array.constructor(length);
21157
21158 // Add properties assigned by `RegExp#exec`.
21159 if (length && typeof array[0] == 'string' && hasOwnProperty$d.call(array, 'index')) {
21160 result.index = array.index;
21161 result.input = array.input;
21162 }
21163 return result;
21164 }
21165
21166 var _initCloneArray = initCloneArray;
21167
21168 /**
21169 * Creates a clone of `arrayBuffer`.
21170 *
21171 * @private
21172 * @param {ArrayBuffer} arrayBuffer The array buffer to clone.
21173 * @returns {ArrayBuffer} Returns the cloned array buffer.
21174 */
21175 function cloneArrayBuffer(arrayBuffer) {
21176 var result = new arrayBuffer.constructor(arrayBuffer.byteLength);
21177 new _Uint8Array(result).set(new _Uint8Array(arrayBuffer));
21178 return result;
21179 }
21180
21181 var _cloneArrayBuffer = cloneArrayBuffer;
21182
21183 /**
21184 * Creates a clone of `dataView`.
21185 *
21186 * @private
21187 * @param {Object} dataView The data view to clone.
21188 * @param {boolean} [isDeep] Specify a deep clone.
21189 * @returns {Object} Returns the cloned data view.
21190 */
21191 function cloneDataView(dataView, isDeep) {
21192 var buffer = isDeep ? _cloneArrayBuffer(dataView.buffer) : dataView.buffer;
21193 return new dataView.constructor(buffer, dataView.byteOffset, dataView.byteLength);
21194 }
21195
21196 var _cloneDataView = cloneDataView;
21197
21198 /** Used to match `RegExp` flags from their coerced string values. */
21199 var reFlags = /\w*$/;
21200
21201 /**
21202 * Creates a clone of `regexp`.
21203 *
21204 * @private
21205 * @param {Object} regexp The regexp to clone.
21206 * @returns {Object} Returns the cloned regexp.
21207 */
21208 function cloneRegExp(regexp) {
21209 var result = new regexp.constructor(regexp.source, reFlags.exec(regexp));
21210 result.lastIndex = regexp.lastIndex;
21211 return result;
21212 }
21213
21214 var _cloneRegExp = cloneRegExp;
21215
21216 /** Used to convert symbols to primitives and strings. */
21217 var symbolProto$2 = _Symbol ? _Symbol.prototype : undefined,
21218 symbolValueOf$1 = symbolProto$2 ? symbolProto$2.valueOf : undefined;
21219
21220 /**
21221 * Creates a clone of the `symbol` object.
21222 *
21223 * @private
21224 * @param {Object} symbol The symbol object to clone.
21225 * @returns {Object} Returns the cloned symbol object.
21226 */
21227 function cloneSymbol(symbol) {
21228 return symbolValueOf$1 ? Object(symbolValueOf$1.call(symbol)) : {};
21229 }
21230
21231 var _cloneSymbol = cloneSymbol;
21232
21233 /**
21234 * Creates a clone of `typedArray`.
21235 *
21236 * @private
21237 * @param {Object} typedArray The typed array to clone.
21238 * @param {boolean} [isDeep] Specify a deep clone.
21239 * @returns {Object} Returns the cloned typed array.
21240 */
21241 function cloneTypedArray(typedArray, isDeep) {
21242 var buffer = isDeep ? _cloneArrayBuffer(typedArray.buffer) : typedArray.buffer;
21243 return new typedArray.constructor(buffer, typedArray.byteOffset, typedArray.length);
21244 }
21245
21246 var _cloneTypedArray = cloneTypedArray;
21247
21248 /** `Object#toString` result references. */
21249 var boolTag$2 = '[object Boolean]',
21250 dateTag$2 = '[object Date]',
21251 mapTag$4 = '[object Map]',
21252 numberTag$2 = '[object Number]',
21253 regexpTag$2 = '[object RegExp]',
21254 setTag$4 = '[object Set]',
21255 stringTag$2 = '[object String]',
21256 symbolTag$2 = '[object Symbol]';
21257
21258 var arrayBufferTag$2 = '[object ArrayBuffer]',
21259 dataViewTag$3 = '[object DataView]',
21260 float32Tag$1 = '[object Float32Array]',
21261 float64Tag$1 = '[object Float64Array]',
21262 int8Tag$1 = '[object Int8Array]',
21263 int16Tag$1 = '[object Int16Array]',
21264 int32Tag$1 = '[object Int32Array]',
21265 uint8Tag$1 = '[object Uint8Array]',
21266 uint8ClampedTag$1 = '[object Uint8ClampedArray]',
21267 uint16Tag$1 = '[object Uint16Array]',
21268 uint32Tag$1 = '[object Uint32Array]';
21269
21270 /**
21271 * Initializes an object clone based on its `toStringTag`.
21272 *
21273 * **Note:** This function only supports cloning values with tags of
21274 * `Boolean`, `Date`, `Error`, `Map`, `Number`, `RegExp`, `Set`, or `String`.
21275 *
21276 * @private
21277 * @param {Object} object The object to clone.
21278 * @param {string} tag The `toStringTag` of the object to clone.
21279 * @param {boolean} [isDeep] Specify a deep clone.
21280 * @returns {Object} Returns the initialized clone.
21281 */
21282 function initCloneByTag(object, tag, isDeep) {
21283 var Ctor = object.constructor;
21284 switch (tag) {
21285 case arrayBufferTag$2:
21286 return _cloneArrayBuffer(object);
21287
21288 case boolTag$2:
21289 case dateTag$2:
21290 return new Ctor(+object);
21291
21292 case dataViewTag$3:
21293 return _cloneDataView(object, isDeep);
21294
21295 case float32Tag$1: case float64Tag$1:
21296 case int8Tag$1: case int16Tag$1: case int32Tag$1:
21297 case uint8Tag$1: case uint8ClampedTag$1: case uint16Tag$1: case uint32Tag$1:
21298 return _cloneTypedArray(object, isDeep);
21299
21300 case mapTag$4:
21301 return new Ctor;
21302
21303 case numberTag$2:
21304 case stringTag$2:
21305 return new Ctor(object);
21306
21307 case regexpTag$2:
21308 return _cloneRegExp(object);
21309
21310 case setTag$4:
21311 return new Ctor;
21312
21313 case symbolTag$2:
21314 return _cloneSymbol(object);
21315 }
21316 }
21317
21318 var _initCloneByTag = initCloneByTag;
21319
21320 /** Built-in value references. */
21321 var objectCreate = Object.create;
21322
21323 /**
21324 * The base implementation of `_.create` without support for assigning
21325 * properties to the created object.
21326 *
21327 * @private
21328 * @param {Object} proto The object to inherit from.
21329 * @returns {Object} Returns the new object.
21330 */
21331 var baseCreate = (function() {
21332 function object() {}
21333 return function(proto) {
21334 if (!isObject_1$1(proto)) {
21335 return {};
21336 }
21337 if (objectCreate) {
21338 return objectCreate(proto);
21339 }
21340 object.prototype = proto;
21341 var result = new object;
21342 object.prototype = undefined;
21343 return result;
21344 };
21345 }());
21346
21347 var _baseCreate = baseCreate;
21348
21349 /**
21350 * Initializes an object clone.
21351 *
21352 * @private
21353 * @param {Object} object The object to clone.
21354 * @returns {Object} Returns the initialized clone.
21355 */
21356 function initCloneObject(object) {
21357 return (typeof object.constructor == 'function' && !_isPrototype(object))
21358 ? _baseCreate(_getPrototype(object))
21359 : {};
21360 }
21361
21362 var _initCloneObject = initCloneObject;
21363
21364 /** `Object#toString` result references. */
21365 var mapTag$5 = '[object Map]';
21366
21367 /**
21368 * The base implementation of `_.isMap` without Node.js optimizations.
21369 *
21370 * @private
21371 * @param {*} value The value to check.
21372 * @returns {boolean} Returns `true` if `value` is a map, else `false`.
21373 */
21374 function baseIsMap(value) {
21375 return isObjectLike_1(value) && _getTag(value) == mapTag$5;
21376 }
21377
21378 var _baseIsMap = baseIsMap;
21379
21380 /* Node.js helper references. */
21381 var nodeIsMap = _nodeUtil && _nodeUtil.isMap;
21382
21383 /**
21384 * Checks if `value` is classified as a `Map` object.
21385 *
21386 * @static
21387 * @memberOf _
21388 * @since 4.3.0
21389 * @category Lang
21390 * @param {*} value The value to check.
21391 * @returns {boolean} Returns `true` if `value` is a map, else `false`.
21392 * @example
21393 *
21394 * _.isMap(new Map);
21395 * // => true
21396 *
21397 * _.isMap(new WeakMap);
21398 * // => false
21399 */
21400 var isMap = nodeIsMap ? _baseUnary(nodeIsMap) : _baseIsMap;
21401
21402 var isMap_1 = isMap;
21403
21404 /** `Object#toString` result references. */
21405 var setTag$5 = '[object Set]';
21406
21407 /**
21408 * The base implementation of `_.isSet` without Node.js optimizations.
21409 *
21410 * @private
21411 * @param {*} value The value to check.
21412 * @returns {boolean} Returns `true` if `value` is a set, else `false`.
21413 */
21414 function baseIsSet(value) {
21415 return isObjectLike_1(value) && _getTag(value) == setTag$5;
21416 }
21417
21418 var _baseIsSet = baseIsSet;
21419
21420 /* Node.js helper references. */
21421 var nodeIsSet = _nodeUtil && _nodeUtil.isSet;
21422
21423 /**
21424 * Checks if `value` is classified as a `Set` object.
21425 *
21426 * @static
21427 * @memberOf _
21428 * @since 4.3.0
21429 * @category Lang
21430 * @param {*} value The value to check.
21431 * @returns {boolean} Returns `true` if `value` is a set, else `false`.
21432 * @example
21433 *
21434 * _.isSet(new Set);
21435 * // => true
21436 *
21437 * _.isSet(new WeakSet);
21438 * // => false
21439 */
21440 var isSet = nodeIsSet ? _baseUnary(nodeIsSet) : _baseIsSet;
21441
21442 var isSet_1 = isSet;
21443
21444 /** Used to compose bitmasks for cloning. */
21445 var CLONE_DEEP_FLAG = 1,
21446 CLONE_FLAT_FLAG = 2,
21447 CLONE_SYMBOLS_FLAG = 4;
21448
21449 /** `Object#toString` result references. */
21450 var argsTag$3 = '[object Arguments]',
21451 arrayTag$2 = '[object Array]',
21452 boolTag$3 = '[object Boolean]',
21453 dateTag$3 = '[object Date]',
21454 errorTag$2 = '[object Error]',
21455 funcTag$2 = '[object Function]',
21456 genTag$1 = '[object GeneratorFunction]',
21457 mapTag$6 = '[object Map]',
21458 numberTag$3 = '[object Number]',
21459 objectTag$4 = '[object Object]',
21460 regexpTag$3 = '[object RegExp]',
21461 setTag$6 = '[object Set]',
21462 stringTag$3 = '[object String]',
21463 symbolTag$3 = '[object Symbol]',
21464 weakMapTag$2 = '[object WeakMap]';
21465
21466 var arrayBufferTag$3 = '[object ArrayBuffer]',
21467 dataViewTag$4 = '[object DataView]',
21468 float32Tag$2 = '[object Float32Array]',
21469 float64Tag$2 = '[object Float64Array]',
21470 int8Tag$2 = '[object Int8Array]',
21471 int16Tag$2 = '[object Int16Array]',
21472 int32Tag$2 = '[object Int32Array]',
21473 uint8Tag$2 = '[object Uint8Array]',
21474 uint8ClampedTag$2 = '[object Uint8ClampedArray]',
21475 uint16Tag$2 = '[object Uint16Array]',
21476 uint32Tag$2 = '[object Uint32Array]';
21477
21478 /** Used to identify `toStringTag` values supported by `_.clone`. */
21479 var cloneableTags = {};
21480 cloneableTags[argsTag$3] = cloneableTags[arrayTag$2] =
21481 cloneableTags[arrayBufferTag$3] = cloneableTags[dataViewTag$4] =
21482 cloneableTags[boolTag$3] = cloneableTags[dateTag$3] =
21483 cloneableTags[float32Tag$2] = cloneableTags[float64Tag$2] =
21484 cloneableTags[int8Tag$2] = cloneableTags[int16Tag$2] =
21485 cloneableTags[int32Tag$2] = cloneableTags[mapTag$6] =
21486 cloneableTags[numberTag$3] = cloneableTags[objectTag$4] =
21487 cloneableTags[regexpTag$3] = cloneableTags[setTag$6] =
21488 cloneableTags[stringTag$3] = cloneableTags[symbolTag$3] =
21489 cloneableTags[uint8Tag$2] = cloneableTags[uint8ClampedTag$2] =
21490 cloneableTags[uint16Tag$2] = cloneableTags[uint32Tag$2] = true;
21491 cloneableTags[errorTag$2] = cloneableTags[funcTag$2] =
21492 cloneableTags[weakMapTag$2] = false;
21493
21494 /**
21495 * The base implementation of `_.clone` and `_.cloneDeep` which tracks
21496 * traversed objects.
21497 *
21498 * @private
21499 * @param {*} value The value to clone.
21500 * @param {boolean} bitmask The bitmask flags.
21501 * 1 - Deep clone
21502 * 2 - Flatten inherited properties
21503 * 4 - Clone symbols
21504 * @param {Function} [customizer] The function to customize cloning.
21505 * @param {string} [key] The key of `value`.
21506 * @param {Object} [object] The parent object of `value`.
21507 * @param {Object} [stack] Tracks traversed objects and their clone counterparts.
21508 * @returns {*} Returns the cloned value.
21509 */
21510 function baseClone(value, bitmask, customizer, key, object, stack) {
21511 var result,
21512 isDeep = bitmask & CLONE_DEEP_FLAG,
21513 isFlat = bitmask & CLONE_FLAT_FLAG,
21514 isFull = bitmask & CLONE_SYMBOLS_FLAG;
21515
21516 if (customizer) {
21517 result = object ? customizer(value, key, object, stack) : customizer(value);
21518 }
21519 if (result !== undefined) {
21520 return result;
21521 }
21522 if (!isObject_1$1(value)) {
21523 return value;
21524 }
21525 var isArr = isArray_1(value);
21526 if (isArr) {
21527 result = _initCloneArray(value);
21528 if (!isDeep) {
21529 return _copyArray(value, result);
21530 }
21531 } else {
21532 var tag = _getTag(value),
21533 isFunc = tag == funcTag$2 || tag == genTag$1;
21534
21535 if (isBuffer_1(value)) {
21536 return _cloneBuffer(value, isDeep);
21537 }
21538 if (tag == objectTag$4 || tag == argsTag$3 || (isFunc && !object)) {
21539 result = (isFlat || isFunc) ? {} : _initCloneObject(value);
21540 if (!isDeep) {
21541 return isFlat
21542 ? _copySymbolsIn(value, _baseAssignIn(result, value))
21543 : _copySymbols(value, _baseAssign(result, value));
21544 }
21545 } else {
21546 if (!cloneableTags[tag]) {
21547 return object ? value : {};
21548 }
21549 result = _initCloneByTag(value, tag, isDeep);
21550 }
21551 }
21552 // Check for circular references and return its corresponding clone.
21553 stack || (stack = new _Stack);
21554 var stacked = stack.get(value);
21555 if (stacked) {
21556 return stacked;
21557 }
21558 stack.set(value, result);
21559
21560 if (isSet_1(value)) {
21561 value.forEach(function(subValue) {
21562 result.add(baseClone(subValue, bitmask, customizer, subValue, value, stack));
21563 });
21564 } else if (isMap_1(value)) {
21565 value.forEach(function(subValue, key) {
21566 result.set(key, baseClone(subValue, bitmask, customizer, key, value, stack));
21567 });
21568 }
21569
21570 var keysFunc = isFull
21571 ? (isFlat ? _getAllKeysIn : _getAllKeys)
21572 : (isFlat ? keysIn_1 : keys_1);
21573
21574 var props = isArr ? undefined : keysFunc(value);
21575 _arrayEach(props || value, function(subValue, key) {
21576 if (props) {
21577 key = subValue;
21578 subValue = value[key];
21579 }
21580 // Recursively populate clone (susceptible to call stack limits).
21581 _assignValue(result, key, baseClone(subValue, bitmask, customizer, key, value, stack));
21582 });
21583 return result;
21584 }
21585
21586 var _baseClone = baseClone;
21587
21588 /** Used to compose bitmasks for cloning. */
21589 var CLONE_DEEP_FLAG$1 = 1,
21590 CLONE_SYMBOLS_FLAG$1 = 4;
21591
21592 /**
21593 * This method is like `_.clone` except that it recursively clones `value`.
21594 *
21595 * @static
21596 * @memberOf _
21597 * @since 1.0.0
21598 * @category Lang
21599 * @param {*} value The value to recursively clone.
21600 * @returns {*} Returns the deep cloned value.
21601 * @see _.clone
21602 * @example
21603 *
21604 * var objects = [{ 'a': 1 }, { 'b': 2 }];
21605 *
21606 * var deep = _.cloneDeep(objects);
21607 * console.log(deep[0] === objects[0]);
21608 * // => false
21609 */
21610 function cloneDeep(value) {
21611 return _baseClone(value, CLONE_DEEP_FLAG$1 | CLONE_SYMBOLS_FLAG$1);
21612 }
21613
21614 var cloneDeep_1 = cloneDeep;
21615
21616 /**
21617 * Creates a `_.find` or `_.findLast` function.
21618 *
21619 * @private
21620 * @param {Function} findIndexFunc The function to find the collection index.
21621 * @returns {Function} Returns the new find function.
21622 */
21623 function createFind(findIndexFunc) {
21624 return function(collection, predicate, fromIndex) {
21625 var iterable = Object(collection);
21626 if (!isArrayLike_1(collection)) {
21627 var iteratee = _baseIteratee(predicate);
21628 collection = keys_1(collection);
21629 predicate = function(key) { return iteratee(iterable[key], key, iterable); };
21630 }
21631 var index = findIndexFunc(collection, predicate, fromIndex);
21632 return index > -1 ? iterable[iteratee ? collection[index] : index] : undefined;
21633 };
21634 }
21635
21636 var _createFind = createFind;
21637
21638 /**
21639 * The base implementation of `_.findIndex` and `_.findLastIndex` without
21640 * support for iteratee shorthands.
21641 *
21642 * @private
21643 * @param {Array} array The array to inspect.
21644 * @param {Function} predicate The function invoked per iteration.
21645 * @param {number} fromIndex The index to search from.
21646 * @param {boolean} [fromRight] Specify iterating from right to left.
21647 * @returns {number} Returns the index of the matched value, else `-1`.
21648 */
21649 function baseFindIndex(array, predicate, fromIndex, fromRight) {
21650 var length = array.length,
21651 index = fromIndex + (fromRight ? 1 : -1);
21652
21653 while ((fromRight ? index-- : ++index < length)) {
21654 if (predicate(array[index], index, array)) {
21655 return index;
21656 }
21657 }
21658 return -1;
21659 }
21660
21661 var _baseFindIndex = baseFindIndex;
21662
21663 /** Used to match a single whitespace character. */
21664 var reWhitespace = /\s/;
21665
21666 /**
21667 * Used by `_.trim` and `_.trimEnd` to get the index of the last non-whitespace
21668 * character of `string`.
21669 *
21670 * @private
21671 * @param {string} string The string to inspect.
21672 * @returns {number} Returns the index of the last non-whitespace character.
21673 */
21674 function trimmedEndIndex(string) {
21675 var index = string.length;
21676
21677 while (index-- && reWhitespace.test(string.charAt(index))) {}
21678 return index;
21679 }
21680
21681 var _trimmedEndIndex = trimmedEndIndex;
21682
21683 /** Used to match leading whitespace. */
21684 var reTrimStart = /^\s+/;
21685
21686 /**
21687 * The base implementation of `_.trim`.
21688 *
21689 * @private
21690 * @param {string} string The string to trim.
21691 * @returns {string} Returns the trimmed string.
21692 */
21693 function baseTrim(string) {
21694 return string
21695 ? string.slice(0, _trimmedEndIndex(string) + 1).replace(reTrimStart, '')
21696 : string;
21697 }
21698
21699 var _baseTrim = baseTrim;
21700
21701 /** Used as references for various `Number` constants. */
21702 var NAN = 0 / 0;
21703
21704 /** Used to detect bad signed hexadecimal string values. */
21705 var reIsBadHex = /^[-+]0x[0-9a-f]+$/i;
21706
21707 /** Used to detect binary string values. */
21708 var reIsBinary = /^0b[01]+$/i;
21709
21710 /** Used to detect octal string values. */
21711 var reIsOctal = /^0o[0-7]+$/i;
21712
21713 /** Built-in method references without a dependency on `root`. */
21714 var freeParseInt = parseInt;
21715
21716 /**
21717 * Converts `value` to a number.
21718 *
21719 * @static
21720 * @memberOf _
21721 * @since 4.0.0
21722 * @category Lang
21723 * @param {*} value The value to process.
21724 * @returns {number} Returns the number.
21725 * @example
21726 *
21727 * _.toNumber(3.2);
21728 * // => 3.2
21729 *
21730 * _.toNumber(Number.MIN_VALUE);
21731 * // => 5e-324
21732 *
21733 * _.toNumber(Infinity);
21734 * // => Infinity
21735 *
21736 * _.toNumber('3.2');
21737 * // => 3.2
21738 */
21739 function toNumber(value) {
21740 if (typeof value == 'number') {
21741 return value;
21742 }
21743 if (isSymbol_1(value)) {
21744 return NAN;
21745 }
21746 if (isObject_1$1(value)) {
21747 var other = typeof value.valueOf == 'function' ? value.valueOf() : value;
21748 value = isObject_1$1(other) ? (other + '') : other;
21749 }
21750 if (typeof value != 'string') {
21751 return value === 0 ? value : +value;
21752 }
21753 value = _baseTrim(value);
21754 var isBinary = reIsBinary.test(value);
21755 return (isBinary || reIsOctal.test(value))
21756 ? freeParseInt(value.slice(2), isBinary ? 2 : 8)
21757 : (reIsBadHex.test(value) ? NAN : +value);
21758 }
21759
21760 var toNumber_1 = toNumber;
21761
21762 /** Used as references for various `Number` constants. */
21763 var INFINITY$2 = 1 / 0,
21764 MAX_INTEGER = 1.7976931348623157e+308;
21765
21766 /**
21767 * Converts `value` to a finite number.
21768 *
21769 * @static
21770 * @memberOf _
21771 * @since 4.12.0
21772 * @category Lang
21773 * @param {*} value The value to convert.
21774 * @returns {number} Returns the converted number.
21775 * @example
21776 *
21777 * _.toFinite(3.2);
21778 * // => 3.2
21779 *
21780 * _.toFinite(Number.MIN_VALUE);
21781 * // => 5e-324
21782 *
21783 * _.toFinite(Infinity);
21784 * // => 1.7976931348623157e+308
21785 *
21786 * _.toFinite('3.2');
21787 * // => 3.2
21788 */
21789 function toFinite(value) {
21790 if (!value) {
21791 return value === 0 ? value : 0;
21792 }
21793 value = toNumber_1(value);
21794 if (value === INFINITY$2 || value === -INFINITY$2) {
21795 var sign = (value < 0 ? -1 : 1);
21796 return sign * MAX_INTEGER;
21797 }
21798 return value === value ? value : 0;
21799 }
21800
21801 var toFinite_1 = toFinite;
21802
21803 /**
21804 * Converts `value` to an integer.
21805 *
21806 * **Note:** This method is loosely based on
21807 * [`ToInteger`](http://www.ecma-international.org/ecma-262/7.0/#sec-tointeger).
21808 *
21809 * @static
21810 * @memberOf _
21811 * @since 4.0.0
21812 * @category Lang
21813 * @param {*} value The value to convert.
21814 * @returns {number} Returns the converted integer.
21815 * @example
21816 *
21817 * _.toInteger(3.2);
21818 * // => 3
21819 *
21820 * _.toInteger(Number.MIN_VALUE);
21821 * // => 0
21822 *
21823 * _.toInteger(Infinity);
21824 * // => 1.7976931348623157e+308
21825 *
21826 * _.toInteger('3.2');
21827 * // => 3
21828 */
21829 function toInteger(value) {
21830 var result = toFinite_1(value),
21831 remainder = result % 1;
21832
21833 return result === result ? (remainder ? result - remainder : result) : 0;
21834 }
21835
21836 var toInteger_1 = toInteger;
21837
21838 /* Built-in method references for those with the same name as other `lodash` methods. */
21839 var nativeMax = Math.max;
21840
21841 /**
21842 * This method is like `_.find` except that it returns the index of the first
21843 * element `predicate` returns truthy for instead of the element itself.
21844 *
21845 * @static
21846 * @memberOf _
21847 * @since 1.1.0
21848 * @category Array
21849 * @param {Array} array The array to inspect.
21850 * @param {Function} [predicate=_.identity] The function invoked per iteration.
21851 * @param {number} [fromIndex=0] The index to search from.
21852 * @returns {number} Returns the index of the found element, else `-1`.
21853 * @example
21854 *
21855 * var users = [
21856 * { 'user': 'barney', 'active': false },
21857 * { 'user': 'fred', 'active': false },
21858 * { 'user': 'pebbles', 'active': true }
21859 * ];
21860 *
21861 * _.findIndex(users, function(o) { return o.user == 'barney'; });
21862 * // => 0
21863 *
21864 * // The `_.matches` iteratee shorthand.
21865 * _.findIndex(users, { 'user': 'fred', 'active': false });
21866 * // => 1
21867 *
21868 * // The `_.matchesProperty` iteratee shorthand.
21869 * _.findIndex(users, ['active', false]);
21870 * // => 0
21871 *
21872 * // The `_.property` iteratee shorthand.
21873 * _.findIndex(users, 'active');
21874 * // => 2
21875 */
21876 function findIndex(array, predicate, fromIndex) {
21877 var length = array == null ? 0 : array.length;
21878 if (!length) {
21879 return -1;
21880 }
21881 var index = fromIndex == null ? 0 : toInteger_1(fromIndex);
21882 if (index < 0) {
21883 index = nativeMax(length + index, 0);
21884 }
21885 return _baseFindIndex(array, _baseIteratee(predicate), index);
21886 }
21887
21888 var findIndex_1 = findIndex;
21889
21890 /**
21891 * Iterates over elements of `collection`, returning the first element
21892 * `predicate` returns truthy for. The predicate is invoked with three
21893 * arguments: (value, index|key, collection).
21894 *
21895 * @static
21896 * @memberOf _
21897 * @since 0.1.0
21898 * @category Collection
21899 * @param {Array|Object} collection The collection to inspect.
21900 * @param {Function} [predicate=_.identity] The function invoked per iteration.
21901 * @param {number} [fromIndex=0] The index to search from.
21902 * @returns {*} Returns the matched element, else `undefined`.
21903 * @example
21904 *
21905 * var users = [
21906 * { 'user': 'barney', 'age': 36, 'active': true },
21907 * { 'user': 'fred', 'age': 40, 'active': false },
21908 * { 'user': 'pebbles', 'age': 1, 'active': true }
21909 * ];
21910 *
21911 * _.find(users, function(o) { return o.age < 40; });
21912 * // => object for 'barney'
21913 *
21914 * // The `_.matches` iteratee shorthand.
21915 * _.find(users, { 'age': 1, 'active': true });
21916 * // => object for 'pebbles'
21917 *
21918 * // The `_.matchesProperty` iteratee shorthand.
21919 * _.find(users, ['active', false]);
21920 * // => object for 'fred'
21921 *
21922 * // The `_.property` iteratee shorthand.
21923 * _.find(users, 'active');
21924 * // => object for 'barney'
21925 */
21926 var find = _createFind(findIndex_1);
21927
21928 var find_1 = find;
21929
21930 // IMClient
21931 var UNREAD_MESSAGES_COUNT_UPDATE = 'unreadmessagescountupdate';
21932 var CLOSE = 'close';
21933 var CONFLICT = 'conflict';
21934 var CONVERSATION_INFO_UPDATED = 'conversationinfoupdated';
21935 var UNHANDLED_MESSAGE = 'unhandledmessage'; // shared
21936
21937 var INVITED = 'invited';
21938 var KICKED = 'kicked';
21939 var MEMBERS_JOINED = 'membersjoined';
21940 var MEMBERS_LEFT = 'membersleft';
21941 var MEMBER_INFO_UPDATED = 'memberinfoupdated';
21942 var BLOCKED = 'blocked';
21943 var UNBLOCKED = 'unblocked';
21944 var MEMBERS_BLOCKED = 'membersblocked';
21945 var MEMBERS_UNBLOCKED = 'membersunblocked';
21946 var MUTED = 'muted';
21947 var UNMUTED = 'unmuted';
21948 var MEMBERS_MUTED = 'membersmuted';
21949 var MEMBERS_UNMUTED = 'membersunmuted';
21950 var MESSAGE$1 = 'message';
21951 var MESSAGE_RECALL = 'messagerecall';
21952 var MESSAGE_UPDATE = 'messageupdate'; // Conversation
21953
21954 var LAST_DELIVERED_AT_UPDATE = 'lastdeliveredatupdate';
21955 var LAST_READ_AT_UPDATE = 'lastreadatupdate';
21956 var INFO_UPDATED = 'infoupdated';
21957
21958 var IMEvent = /*#__PURE__*/Object.freeze({
21959 __proto__: null,
21960 UNREAD_MESSAGES_COUNT_UPDATE: UNREAD_MESSAGES_COUNT_UPDATE,
21961 CLOSE: CLOSE,
21962 CONFLICT: CONFLICT,
21963 CONVERSATION_INFO_UPDATED: CONVERSATION_INFO_UPDATED,
21964 UNHANDLED_MESSAGE: UNHANDLED_MESSAGE,
21965 INVITED: INVITED,
21966 KICKED: KICKED,
21967 MEMBERS_JOINED: MEMBERS_JOINED,
21968 MEMBERS_LEFT: MEMBERS_LEFT,
21969 MEMBER_INFO_UPDATED: MEMBER_INFO_UPDATED,
21970 BLOCKED: BLOCKED,
21971 UNBLOCKED: UNBLOCKED,
21972 MEMBERS_BLOCKED: MEMBERS_BLOCKED,
21973 MEMBERS_UNBLOCKED: MEMBERS_UNBLOCKED,
21974 MUTED: MUTED,
21975 UNMUTED: UNMUTED,
21976 MEMBERS_MUTED: MEMBERS_MUTED,
21977 MEMBERS_UNMUTED: MEMBERS_UNMUTED,
21978 MESSAGE: MESSAGE$1,
21979 MESSAGE_RECALL: MESSAGE_RECALL,
21980 MESSAGE_UPDATE: MESSAGE_UPDATE,
21981 LAST_DELIVERED_AT_UPDATE: LAST_DELIVERED_AT_UPDATE,
21982 LAST_READ_AT_UPDATE: LAST_READ_AT_UPDATE,
21983 INFO_UPDATED: INFO_UPDATED
21984 });
21985
21986 var _rMessageStatus;
21987
21988 function ownKeys$3(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); if (enumerableOnly) symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; }); keys.push.apply(keys, symbols); } return keys; }
21989
21990 function _objectSpread$3(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i] != null ? arguments[i] : {}; if (i % 2) { ownKeys$3(Object(source), true).forEach(function (key) { defineProperty(target, key, source[key]); }); } else if (Object.getOwnPropertyDescriptors) { Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)); } else { ownKeys$3(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } } return target; }
21991 /**
21992 * 消息状态枚举
21993 * @enum {Symbol}
21994 * @since 3.2.0
21995 * @memberof module:leancloud-realtime
21996 */
21997
21998 var MessageStatus = {
21999 /** 初始状态、未知状态 */
22000 NONE: Symbol('none'),
22001
22002 /** 正在发送 */
22003 SENDING: Symbol('sending'),
22004
22005 /** 已发送 */
22006 SENT: Symbol('sent'),
22007
22008 /** 已送达 */
22009 DELIVERED: Symbol('delivered'),
22010
22011 /** 发送失败 */
22012 FAILED: Symbol('failed')
22013 };
22014 Object.freeze(MessageStatus);
22015 var rMessageStatus = (_rMessageStatus = {}, defineProperty(_rMessageStatus, MessageStatus.NONE, true), defineProperty(_rMessageStatus, MessageStatus.SENDING, true), defineProperty(_rMessageStatus, MessageStatus.SENT, true), defineProperty(_rMessageStatus, MessageStatus.DELIVERED, true), defineProperty(_rMessageStatus, MessageStatus.READ, true), defineProperty(_rMessageStatus, MessageStatus.FAILED, true), _rMessageStatus);
22016
22017 var Message = /*#__PURE__*/function () {
22018 /**
22019 * @implements AVMessage
22020 * @param {Object|String|ArrayBuffer} content 消息内容
22021 */
22022 function Message(content) {
22023 Object.assign(this, {
22024 content: content
22025 }, {
22026 /**
22027 * @type {String}
22028 * @memberof Message#
22029 */
22030 id: v4_1(),
22031
22032 /**
22033 * 消息所在的 conversation id
22034 * @memberof Message#
22035 * @type {String?}
22036 */
22037 cid: null,
22038
22039 /**
22040 * 消息发送时间
22041 * @memberof Message#
22042 * @type {Date}
22043 */
22044 timestamp: new Date(),
22045
22046 /**
22047 * 消息发送者
22048 * @memberof Message#
22049 * @type {String}
22050 */
22051 from: undefined,
22052
22053 /**
22054 * 消息提及的用户
22055 * @since 4.0.0
22056 * @memberof Message#
22057 * @type {String[]}
22058 */
22059 mentionList: [],
22060
22061 /**
22062 * 消息是否提及了所有人
22063 * @since 4.0.0
22064 * @memberof Message#
22065 * @type {Boolean}
22066 */
22067 mentionedAll: false,
22068 _mentioned: false
22069 });
22070
22071 this._setStatus(MessageStatus.NONE);
22072 }
22073 /**
22074 * 将当前消息的内容序列化为 JSON 对象
22075 * @private
22076 * @return {Object}
22077 */
22078
22079
22080 var _proto = Message.prototype;
22081
22082 _proto.getPayload = function getPayload() {
22083 return this.content;
22084 };
22085
22086 _proto._toJSON = function _toJSON() {
22087 var id = this.id,
22088 cid = this.cid,
22089 from = this.from,
22090 timestamp = this.timestamp,
22091 deliveredAt = this.deliveredAt,
22092 updatedAt = this.updatedAt,
22093 mentionList = this.mentionList,
22094 mentionedAll = this.mentionedAll,
22095 mentioned = this.mentioned;
22096 return {
22097 id: id,
22098 cid: cid,
22099 from: from,
22100 timestamp: timestamp,
22101 deliveredAt: deliveredAt,
22102 updatedAt: updatedAt,
22103 mentionList: mentionList,
22104 mentionedAll: mentionedAll,
22105 mentioned: mentioned
22106 };
22107 }
22108 /**
22109 * 返回 JSON 格式的消息
22110 * @return {Object} 返回值是一个 plain Object
22111 */
22112 ;
22113
22114 _proto.toJSON = function toJSON() {
22115 return _objectSpread$3(_objectSpread$3({}, this._toJSON()), {}, {
22116 data: this.content
22117 });
22118 }
22119 /**
22120 * 返回 JSON 格式的消息,与 toJSON 不同的是,该对象包含了完整的信息,可以通过 {@link IMClient#parseMessage} 反序列化。
22121 * @return {Object} 返回值是一个 plain Object
22122 * @since 4.0.0
22123 */
22124 ;
22125
22126 _proto.toFullJSON = function toFullJSON() {
22127 var content = this.content,
22128 id = this.id,
22129 cid = this.cid,
22130 from = this.from,
22131 timestamp = this.timestamp,
22132 deliveredAt = this.deliveredAt,
22133 _updatedAt = this._updatedAt,
22134 mentionList = this.mentionList,
22135 mentionedAll = this.mentionedAll;
22136 return {
22137 data: content,
22138 id: id,
22139 cid: cid,
22140 from: from,
22141 timestamp: getTime(timestamp),
22142 deliveredAt: getTime(deliveredAt),
22143 updatedAt: getTime(_updatedAt),
22144 mentionList: mentionList,
22145 mentionedAll: mentionedAll
22146 };
22147 }
22148 /**
22149 * 消息状态,值为 {@link module:leancloud-realtime.MessageStatus} 之一
22150 * @type {Symbol}
22151 * @readonly
22152 * @since 3.2.0
22153 */
22154 ;
22155
22156 _proto._setStatus = function _setStatus(status) {
22157 if (!rMessageStatus[status]) {
22158 throw new Error('Invalid message status');
22159 }
22160
22161 this._status = status;
22162 };
22163
22164 _proto._updateMentioned = function _updateMentioned(client) {
22165 this._mentioned = this.from !== client && (this.mentionedAll || this.mentionList.indexOf(client) > -1);
22166 }
22167 /**
22168 * 获取提及用户列表
22169 * @since 4.0.0
22170 * @return {String[]} 提及用户的 id 列表
22171 */
22172 ;
22173
22174 _proto.getMentionList = function getMentionList() {
22175 return this.mentionList;
22176 }
22177 /**
22178 * 设置提及用户列表
22179 * @since 4.0.0
22180 * @param {String[]} clients 提及用户的 id 列表
22181 * @return {this} self
22182 */
22183 ;
22184
22185 _proto.setMentionList = function setMentionList(clients) {
22186 this.mentionList = ensureArray(clients);
22187 return this;
22188 }
22189 /**
22190 * 设置是否提及所有人
22191 * @since 4.0.0
22192 * @param {Boolean} [value=true]
22193 * @return {this} self
22194 */
22195 ;
22196
22197 _proto.mentionAll = function mentionAll() {
22198 var value = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : true;
22199 this.mentionedAll = Boolean(value);
22200 return this;
22201 }
22202 /**
22203 * 判断给定的内容是否是有效的 Message,
22204 * 该方法始终返回 true
22205 * @private
22206 * @returns {Boolean}
22207 * @implements AVMessage.validate
22208 */
22209 ;
22210
22211 Message.validate = function validate() {
22212 return true;
22213 }
22214 /**
22215 * 解析处理消息内容
22216 * <pre>
22217 * 如果子类提供了 message,返回该 message
22218 * 如果没有提供,将 json 作为 content 实例化一个 Message
22219 * @private
22220 * @param {Object} json json 格式的消息内容
22221 * @param {Message} message 子类提供的 message
22222 * @return {Message}
22223 * @implements AVMessage.parse
22224 */
22225 ;
22226
22227 Message.parse = function parse(json, message) {
22228 return message || new this(json);
22229 };
22230
22231 createClass(Message, [{
22232 key: "status",
22233 get: function get() {
22234 return this._status;
22235 }
22236 }, {
22237 key: "timestamp",
22238 get: function get() {
22239 return this._timestamp;
22240 },
22241 set: function set(value) {
22242 this._timestamp = decodeDate(value);
22243 }
22244 /**
22245 * 消息送达时间
22246 * @type {?Date}
22247 */
22248
22249 }, {
22250 key: "deliveredAt",
22251 get: function get() {
22252 return this._deliveredAt;
22253 },
22254 set: function set(value) {
22255 this._deliveredAt = decodeDate(value);
22256 }
22257 /**
22258 * 消息修改或撤回时间,可以通过比较其与消息的 timestamp 是否相等判断消息是否被修改过或撤回过。
22259 * @type {Date}
22260 * @since 3.5.0
22261 */
22262
22263 }, {
22264 key: "updatedAt",
22265 get: function get() {
22266 return this._updatedAt || this.timestamp;
22267 },
22268 set: function set(value) {
22269 this._updatedAt = decodeDate(value);
22270 }
22271 /**
22272 * 当前用户是否在该消息中被提及
22273 * @type {Boolean}
22274 * @readonly
22275 * @since 4.0.0
22276 */
22277
22278 }, {
22279 key: "mentioned",
22280 get: function get() {
22281 return this._mentioned;
22282 }
22283 }]);
22284
22285 return Message;
22286 }();
22287
22288 /* eslint-disable no-param-reassign */
22289
22290 var messageType = function messageType(type) {
22291 if (typeof type !== 'number') {
22292 throw new TypeError("".concat(type, " is not a Number"));
22293 }
22294
22295 return function (target) {
22296 target.TYPE = type;
22297
22298 target.validate = function (json) {
22299 return json._lctype === type;
22300 };
22301
22302 target.prototype._getType = function () {
22303 return {
22304 _lctype: type
22305 };
22306 };
22307 };
22308 }; // documented in ../plugin-im.js
22309
22310 var messageField = function messageField(fields) {
22311 if (typeof fields !== 'string') {
22312 if (!Array.isArray(fields)) {
22313 throw new TypeError("".concat(fields, " is not an Array"));
22314 } else if (fields.some(function (value) {
22315 return typeof value !== 'string';
22316 })) {
22317 throw new TypeError('fields contains non-string typed member');
22318 }
22319 }
22320
22321 return function (target) {
22322 // IE10 Hack:
22323 // static properties in IE10 will not be inherited from super
22324 // search for parse method and assign it manually
22325 var originalCustomFields = isIE10 ? getStaticProperty(target, '_customFields') : target._customFields;
22326 originalCustomFields = Array.isArray(originalCustomFields) ? originalCustomFields : [];
22327 target._customFields = originalCustomFields.concat(fields);
22328 };
22329 }; // IE10 Hack:
22330 // static properties in IE10 will not be inherited from super
22331 // search for parse method and assign it manually
22332
22333 var IE10Compatible = function IE10Compatible(target) {
22334 if (isIE10) {
22335 target.parse = getStaticProperty(target, 'parse');
22336 }
22337 };
22338
22339 var _dec, _class$1;
22340
22341 function ownKeys$4(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); if (enumerableOnly) symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; }); keys.push.apply(keys, symbols); } return keys; }
22342
22343 function _objectSpread$4(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i] != null ? arguments[i] : {}; if (i % 2) { ownKeys$4(Object(source), true).forEach(function (key) { defineProperty(target, key, source[key]); }); } else if (Object.getOwnPropertyDescriptors) { Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)); } else { ownKeys$4(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } } return target; }
22344
22345 var // jsdoc-ignore-end
22346
22347 /**
22348 * 所有内置的富媒体消息均继承自本类
22349 * @extends Message
22350 */
22351 TypedMessage = (_dec = messageField(['_lctext', '_lcattrs']), _dec(_class$1 = /*#__PURE__*/function (_Message) {
22352 inheritsLoose(TypedMessage, _Message);
22353
22354 function TypedMessage() {
22355 return _Message.apply(this, arguments) || this;
22356 }
22357
22358 var _proto = TypedMessage.prototype;
22359
22360 /**
22361 * @param {String} text
22362 * @return {this} self
22363 */
22364 _proto.setText = function setText(text) {
22365 this._lctext = text;
22366 return this;
22367 }
22368 /**
22369 * @return {String}
22370 */
22371 ;
22372
22373 _proto.getText = function getText() {
22374 return this._lctext;
22375 }
22376 /**
22377 * @param {Object} attributes
22378 * @return {this} self
22379 */
22380 ;
22381
22382 _proto.setAttributes = function setAttributes(attributes) {
22383 this._lcattrs = attributes;
22384 return this;
22385 }
22386 /**
22387 * @return {Object}
22388 */
22389 ;
22390
22391 _proto.getAttributes = function getAttributes() {
22392 return this._lcattrs;
22393 };
22394
22395 _proto._getCustomFields = function _getCustomFields() {
22396 var _this = this;
22397
22398 var fields = Array.isArray(this.constructor._customFields) ? this.constructor._customFields : [];
22399 return fields.reduce(function (result, field) {
22400 if (typeof field !== 'string') return result;
22401 result[field] = _this[field]; // eslint-disable-line no-param-reassign
22402
22403 return result;
22404 }, {});
22405 }
22406 /* eslint-disable class-methods-use-this */
22407 ;
22408
22409 _proto._getType = function _getType() {
22410 throw new Error('not implemented');
22411 }
22412 /* eslint-enable class-methods-use-this */
22413 ;
22414
22415 _proto.getPayload = function getPayload() {
22416 return compact(_objectSpread$4(_objectSpread$4({
22417 _lctext: this.getText(),
22418 _lcattrs: this.getAttributes()
22419 }, this._getCustomFields()), this._getType()));
22420 };
22421
22422 _proto.toJSON = function toJSON() {
22423 var type = this.type,
22424 text = this.text,
22425 attributes = this.attributes,
22426 summary = this.summary;
22427 return _objectSpread$4(_objectSpread$4({}, _Message.prototype._toJSON.call(this)), {}, {
22428 type: type,
22429 text: text,
22430 attributes: attributes,
22431 summary: summary
22432 });
22433 };
22434
22435 _proto.toFullJSON = function toFullJSON() {
22436 return _objectSpread$4(_objectSpread$4({}, _Message.prototype.toFullJSON.call(this)), {}, {
22437 data: this.getPayload()
22438 });
22439 }
22440 /**
22441 * 解析处理消息内容
22442 * <pre>
22443 * 为给定的 message 设置 text 与 attributes 属性,返回该 message
22444 * 如果子类没有提供 message,new this()
22445 * @protected
22446 * @param {Object} json json 格式的消息内容
22447 * @param {TypedMessage} message 子类提供的 message
22448 * @return {TypedMessage}
22449 * @implements AVMessage.parse
22450 */
22451 ;
22452
22453 TypedMessage.parse = function parse(json) {
22454 var message = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : new this();
22455 message.content = json; // eslint-disable-line no-param-reassign
22456
22457 var customFields = isIE10 ? getStaticProperty(message.constructor, '_customFields') : message.constructor._customFields;
22458 var fields = Array.isArray(customFields) ? customFields : [];
22459 fields = fields.reduce(function (result, field) {
22460 if (typeof field !== 'string') return result;
22461 result[field] = json[field]; // eslint-disable-line no-param-reassign
22462
22463 return result;
22464 }, {});
22465 Object.assign(message, fields);
22466 return _Message.parse.call(this, json, message);
22467 };
22468
22469 createClass(TypedMessage, [{
22470 key: "type",
22471
22472 /**
22473 * @type {Number}
22474 * @readonly
22475 */
22476 get: function get() {
22477 return this.constructor.TYPE;
22478 }
22479 /** @type {String} */
22480
22481 }, {
22482 key: "text",
22483 set: function set(text) {
22484 return this.setText(text);
22485 },
22486 get: function get() {
22487 return this.getText();
22488 }
22489 /** @type {Object} */
22490
22491 }, {
22492 key: "attributes",
22493 set: function set(attributes) {
22494 return this.setAttributes(attributes);
22495 },
22496 get: function get() {
22497 return this.getAttributes();
22498 }
22499 /**
22500 * 在客户端需要以文本形式展示该消息时显示的文案,
22501 * 如 <code>[红包] 新春快乐</code>。
22502 * 默认值为消息的 text。
22503 * @type {String}
22504 * @readonly
22505 */
22506
22507 }, {
22508 key: "summary",
22509 get: function get() {
22510 return this.text;
22511 }
22512 }]);
22513
22514 return TypedMessage;
22515 }(Message)) || _class$1);
22516
22517 var _dec$1, _class$2;
22518
22519 var // jsdoc-ignore-end
22520
22521 /**
22522 * 已撤回类型消息,当消息被撤回时,SDK 会使用该类型的消息替代原始消息
22523 * @extends TypedMessage
22524 */
22525 RecalledMessage = (_dec$1 = messageType(-127), _dec$1(_class$2 = IE10Compatible(_class$2 = /*#__PURE__*/function (_TypedMessage) {
22526 inheritsLoose(RecalledMessage, _TypedMessage);
22527
22528 function RecalledMessage() {
22529 return _TypedMessage.apply(this, arguments) || this;
22530 }
22531
22532 createClass(RecalledMessage, [{
22533 key: "summary",
22534
22535 /**
22536 * 在客户端需要以文本形式展示该消息时显示的文案,值为 <code>[该消息已撤回]</code>
22537 * @type {String}
22538 * @readonly
22539 */
22540 // eslint-disable-next-line class-methods-use-this
22541 get: function get() {
22542 return '[该消息已撤回]';
22543 }
22544 }]);
22545
22546 return RecalledMessage;
22547 }(TypedMessage)) || _class$2) || _class$2);
22548
22549 function ownKeys$5(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); if (enumerableOnly) symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; }); keys.push.apply(keys, symbols); } return keys; }
22550
22551 function _objectSpread$5(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i] != null ? arguments[i] : {}; if (i % 2) { ownKeys$5(Object(source), true).forEach(function (key) { defineProperty(target, key, source[key]); }); } else if (Object.getOwnPropertyDescriptors) { Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)); } else { ownKeys$5(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } } return target; }
22552 var debug$7 = browser('LC:Conversation');
22553
22554 var serializeMessage = function serializeMessage(message) {
22555 var content = message.getPayload();
22556 var msg;
22557 var binaryMsg;
22558
22559 if (content instanceof ArrayBuffer) {
22560 binaryMsg = content;
22561 } else if (typeof content !== 'string') {
22562 msg = JSON.stringify(content);
22563 } else {
22564 msg = content;
22565 }
22566
22567 return {
22568 msg: msg,
22569 binaryMsg: binaryMsg
22570 };
22571 };
22572
22573 var _LogsCommand$QueryDir = LogsCommand.QueryDirection,
22574 NEW = _LogsCommand$QueryDir.NEW,
22575 OLD = _LogsCommand$QueryDir.OLD;
22576 /**
22577 * 历史消息查询方向枚举
22578 * @enum {Number}
22579 * @since 4.0.0
22580 * @memberof module:leancloud-realtime
22581 */
22582
22583 var MessageQueryDirection = {
22584 /** 从后向前 */
22585 NEW_TO_OLD: OLD,
22586
22587 /** 从前向后 */
22588 OLD_TO_NEW: NEW
22589 };
22590 Object.freeze(MessageQueryDirection);
22591
22592 var ConversationBase = /*#__PURE__*/function (_EventEmitter) {
22593 inheritsLoose(ConversationBase, _EventEmitter);
22594
22595 /**
22596 * @extends EventEmitter
22597 * @private
22598 * @abstract
22599 */
22600 function ConversationBase(_ref, client) {
22601 var _this;
22602
22603 var id = _ref.id,
22604 lastMessageAt = _ref.lastMessageAt,
22605 lastMessage = _ref.lastMessage,
22606 lastDeliveredAt = _ref.lastDeliveredAt,
22607 lastReadAt = _ref.lastReadAt,
22608 _ref$unreadMessagesCo = _ref.unreadMessagesCount,
22609 unreadMessagesCount = _ref$unreadMessagesCo === void 0 ? 0 : _ref$unreadMessagesCo,
22610 _ref$members = _ref.members,
22611 members = _ref$members === void 0 ? [] : _ref$members,
22612 _ref$mentioned = _ref.mentioned,
22613 mentioned = _ref$mentioned === void 0 ? false : _ref$mentioned,
22614 properties = objectWithoutProperties(_ref, ["id", "lastMessageAt", "lastMessage", "lastDeliveredAt", "lastReadAt", "unreadMessagesCount", "members", "mentioned"]);
22615
22616 _this = _EventEmitter.call(this) || this;
22617 Object.assign(assertThisInitialized(_this), _objectSpread$5({
22618 /**
22619 * 对话 id,对应 _Conversation 表中的 objectId
22620 * @memberof ConversationBase#
22621 * @type {String}
22622 */
22623 id: id,
22624
22625 /**
22626 * 最后一条消息时间
22627 * @memberof ConversationBase#
22628 * @type {?Date}
22629 */
22630 lastMessageAt: lastMessageAt,
22631
22632 /**
22633 * 最后一条消息
22634 * @memberof ConversationBase#
22635 * @type {?Message}
22636 */
22637 lastMessage: lastMessage,
22638
22639 /**
22640 * 参与该对话的用户列表
22641 * @memberof ConversationBase#
22642 * @type {String[]}
22643 */
22644 members: members
22645 }, properties));
22646 _this.members = Array.from(new Set(_this.members));
22647 Object.assign(internal(assertThisInitialized(_this)), {
22648 messagesWaitingForReceipt: {},
22649 lastDeliveredAt: lastDeliveredAt,
22650 lastReadAt: lastReadAt,
22651 unreadMessagesCount: unreadMessagesCount,
22652 mentioned: mentioned
22653 });
22654 _this._client = client;
22655
22656 if (debug$7.enabled) {
22657 values_1(IMEvent).forEach(function (event) {
22658 return _this.on(event, function () {
22659 for (var _len = arguments.length, payload = new Array(_len), _key = 0; _key < _len; _key++) {
22660 payload[_key] = arguments[_key];
22661 }
22662
22663 return _this._debug("".concat(event, " event emitted. %o"), payload);
22664 });
22665 });
22666 } // onConversationCreate hook
22667
22668
22669 applyDecorators(_this._client._plugins.onConversationCreate, assertThisInitialized(_this));
22670 return _this;
22671 }
22672 /**
22673 * 当前用户是否在该对话的未读消息中被提及
22674 * @type {Boolean}
22675 * @since 4.0.0
22676 */
22677
22678
22679 var _proto = ConversationBase.prototype;
22680
22681 _proto._setUnreadMessagesMentioned = function _setUnreadMessagesMentioned(value) {
22682 internal(this).unreadMessagesMentioned = Boolean(value);
22683 };
22684
22685 _proto._setLastDeliveredAt = function _setLastDeliveredAt(value) {
22686 var date = decodeDate(value);
22687
22688 if (!(date < internal(this).lastDeliveredAt)) {
22689 internal(this).lastDeliveredAt = date;
22690 /**
22691 * 最后消息送达时间更新
22692 * @event ConversationBase#LAST_DELIVERED_AT_UPDATE
22693 * @since 3.4.0
22694 */
22695
22696 this.emit(LAST_DELIVERED_AT_UPDATE);
22697 }
22698 }
22699 /**
22700 * 最后消息被阅读时间,常用来实现发送消息的「已读」标记,可通过 {@link Conversation#fetchReceiptTimestamps} 获取或更新该属性
22701 * @type {?Date}
22702 * @since 3.4.0
22703 */
22704 ;
22705
22706 _proto._setLastReadAt = function _setLastReadAt(value) {
22707 var date = decodeDate(value);
22708
22709 if (!(date < internal(this).lastReadAt)) {
22710 internal(this).lastReadAt = date;
22711 /**
22712 * 最后消息被阅读时间更新
22713 * @event ConversationBase#LAST_READ_AT_UPDATE
22714 * @since 3.4.0
22715 */
22716
22717 this.emit(LAST_READ_AT_UPDATE);
22718 }
22719 }
22720 /**
22721 * 返回 JSON 格式的对话,与 toJSON 不同的是,该对象包含了完整的信息,可以通过 {@link IMClient#parseConversation} 反序列化。
22722 * @return {Object} 返回值是一个 plain Object
22723 * @since 4.0.0
22724 */
22725 ;
22726
22727 _proto.toFullJSON = function toFullJSON() {
22728 var id = this.id,
22729 members = this.members,
22730 lastMessageAt = this.lastMessageAt,
22731 lastDeliveredAt = this.lastDeliveredAt,
22732 lastReadAt = this.lastReadAt,
22733 lastMessage = this.lastMessage,
22734 unreadMessagesCount = this.unreadMessagesCount;
22735 return {
22736 id: id,
22737 members: members,
22738 lastMessageAt: getTime(lastMessageAt),
22739 lastDeliveredAt: getTime(lastDeliveredAt),
22740 lastReadAt: getTime(lastReadAt),
22741 lastMessage: lastMessage ? lastMessage.toFullJSON() : undefined,
22742 unreadMessagesCount: unreadMessagesCount
22743 };
22744 }
22745 /**
22746 * 返回 JSON 格式的对话
22747 * @return {Object} 返回值是一个 plain Object
22748 * @since 4.0.0
22749 */
22750 ;
22751
22752 _proto.toJSON = function toJSON() {
22753 var id = this.id,
22754 members = this.members,
22755 lastMessageAt = this.lastMessageAt,
22756 lastDeliveredAt = this.lastDeliveredAt,
22757 lastReadAt = this.lastReadAt,
22758 lastMessage = this.lastMessage,
22759 unreadMessagesCount = this.unreadMessagesCount,
22760 unreadMessagesMentioned = this.unreadMessagesMentioned;
22761 return {
22762 id: id,
22763 members: members,
22764 lastMessageAt: lastMessageAt,
22765 lastDeliveredAt: lastDeliveredAt,
22766 lastReadAt: lastReadAt,
22767 lastMessage: lastMessage ? lastMessage.toJSON() : undefined,
22768 unreadMessagesCount: unreadMessagesCount,
22769 unreadMessagesMentioned: unreadMessagesMentioned
22770 };
22771 };
22772
22773 _proto._debug = function _debug() {
22774 for (var _len2 = arguments.length, params = new Array(_len2), _key2 = 0; _key2 < _len2; _key2++) {
22775 params[_key2] = arguments[_key2];
22776 }
22777
22778 debug$7.apply(void 0, params.concat(["[".concat(this.id, "]")]));
22779 };
22780
22781 _proto._send = function _send(command) {
22782 var _this$_client;
22783
22784 /* eslint-disable no-param-reassign */
22785 if (command.cmd === null) {
22786 command.cmd = 'conv';
22787 }
22788
22789 if (command.cmd === 'conv' && command.convMessage === null) {
22790 command.convMessage = new ConvCommand();
22791 }
22792
22793 if (command.convMessage && command.convMessage.cid === null) {
22794 command.convMessage.cid = this.id;
22795 }
22796 /* eslint-enable no-param-reassign */
22797
22798
22799 for (var _len3 = arguments.length, args = new Array(_len3 > 1 ? _len3 - 1 : 0), _key3 = 1; _key3 < _len3; _key3++) {
22800 args[_key3 - 1] = arguments[_key3];
22801 }
22802
22803 return (_this$_client = this._client)._send.apply(_this$_client, [command].concat(args));
22804 }
22805 /**
22806 * 发送消息
22807 * @param {Message} message 消息,Message 及其子类的实例
22808 * @param {Object} [options] since v3.3.0,发送选项
22809 * @param {Boolean} [options.transient] since v3.3.1,是否作为暂态消息发送
22810 * @param {Boolean} [options.receipt] 是否需要回执,仅在普通对话中有效
22811 * @param {Boolean} [options.will] since v3.4.0,是否指定该消息作为「掉线消息」发送,
22812 * 「掉线消息」会延迟到当前用户掉线后发送,常用来实现「下线通知」功能
22813 * @param {MessagePriority} [options.priority] 消息优先级,仅在暂态对话中有效,
22814 * see: {@link module:leancloud-realtime.MessagePriority MessagePriority}
22815 * @param {Object} [options.pushData] 消息对应的离线推送内容,如果消息接收方不在线,会推送指定的内容。其结构说明参见: {@link https://url.leanapp.cn/pushData 推送消息内容}
22816 * @return {Promise.<Message>} 发送的消息
22817 */
22818 ;
22819
22820 _proto.send =
22821 /*#__PURE__*/
22822 function () {
22823 var _send2 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee(message, options) {
22824 var _message$constructor$, _transient, receipt, priority, pushData, will, _serializeMessage, msg, binaryMsg, command, resCommand, _resCommand$ackMessag, uid, t, code, reason, appCode;
22825
22826 return regenerator.wrap(function _callee$(_context) {
22827 while (1) {
22828 switch (_context.prev = _context.next) {
22829 case 0:
22830 this._debug(message, 'send');
22831
22832 if (message instanceof Message) {
22833 _context.next = 3;
22834 break;
22835 }
22836
22837 throw new TypeError("".concat(message, " is not a Message"));
22838
22839 case 3:
22840 _message$constructor$ = _objectSpread$5(_objectSpread$5(_objectSpread$5({}, message.constructor.sendOptions), typeof message.constructor.getSendOptions === 'function' ? message.constructor.getSendOptions(message) : {}), options), _transient = _message$constructor$["transient"], receipt = _message$constructor$.receipt, priority = _message$constructor$.priority, pushData = _message$constructor$.pushData, will = _message$constructor$.will;
22841
22842 if (receipt) {
22843 if (this["transient"]) {
22844 console.warn('receipt option is ignored as the conversation is transient.');
22845 } else if (_transient) {
22846 console.warn('receipt option is ignored as the message is sent transiently.');
22847 } else if (this.members.length > 2) {
22848 console.warn('receipt option is recommended to be used in one-on-one conversation.'); // eslint-disable-line max-len
22849 }
22850 }
22851
22852 if (priority && !this["transient"]) {
22853 console.warn('priority option is ignored as the conversation is not transient.');
22854 }
22855
22856 Object.assign(message, {
22857 cid: this.id,
22858 from: this._client.id
22859 });
22860
22861 message._setStatus(MessageStatus.SENDING);
22862
22863 _serializeMessage = serializeMessage(message), msg = _serializeMessage.msg, binaryMsg = _serializeMessage.binaryMsg;
22864 command = new GenericCommand({
22865 cmd: 'direct',
22866 directMessage: new DirectCommand({
22867 msg: msg,
22868 binaryMsg: binaryMsg,
22869 cid: this.id,
22870 r: receipt,
22871 "transient": _transient,
22872 dt: message.id,
22873 pushData: JSON.stringify(pushData),
22874 will: will,
22875 mentionPids: message.mentionList,
22876 mentionAll: message.mentionedAll
22877 }),
22878 priority: priority
22879 });
22880 _context.prev = 10;
22881 _context.next = 13;
22882 return this._send(command);
22883
22884 case 13:
22885 resCommand = _context.sent;
22886 _resCommand$ackMessag = resCommand.ackMessage, uid = _resCommand$ackMessag.uid, t = _resCommand$ackMessag.t, code = _resCommand$ackMessag.code, reason = _resCommand$ackMessag.reason, appCode = _resCommand$ackMessag.appCode;
22887
22888 if (!(code !== null)) {
22889 _context.next = 17;
22890 break;
22891 }
22892
22893 throw createError({
22894 code: code,
22895 reason: reason,
22896 appCode: appCode
22897 });
22898
22899 case 17:
22900 Object.assign(message, {
22901 id: uid,
22902 timestamp: t
22903 });
22904
22905 if (!_transient) {
22906 this.lastMessage = message;
22907 this.lastMessageAt = message.timestamp;
22908 }
22909
22910 message._setStatus(MessageStatus.SENT);
22911
22912 if (receipt) {
22913 internal(this).messagesWaitingForReceipt[message.id] = message;
22914 }
22915
22916 return _context.abrupt("return", message);
22917
22918 case 24:
22919 _context.prev = 24;
22920 _context.t0 = _context["catch"](10);
22921
22922 message._setStatus(MessageStatus.FAILED);
22923
22924 throw _context.t0;
22925
22926 case 28:
22927 case "end":
22928 return _context.stop();
22929 }
22930 }
22931 }, _callee, this, [[10, 24]]);
22932 }));
22933
22934 function send(_x, _x2) {
22935 return _send2.apply(this, arguments);
22936 }
22937
22938 return send;
22939 }();
22940
22941 _proto._update = /*#__PURE__*/function () {
22942 var _update2 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee2(message, newMessage, recall) {
22943 var msg, binaryMsg, content, id, cid, timestamp, from, _status;
22944
22945 return regenerator.wrap(function _callee2$(_context2) {
22946 while (1) {
22947 switch (_context2.prev = _context2.next) {
22948 case 0:
22949 this._debug('patch %O %O %O', message, newMessage, recall);
22950
22951 if (!(message instanceof Message)) {
22952 _context2.next = 8;
22953 break;
22954 }
22955
22956 if (!(message.from !== this._client.id)) {
22957 _context2.next = 4;
22958 break;
22959 }
22960
22961 throw new Error('Updating message from others is not allowed');
22962
22963 case 4:
22964 if (!(message.status !== MessageStatus.SENT && message.status !== MessageStatus.DELIVERED)) {
22965 _context2.next = 6;
22966 break;
22967 }
22968
22969 throw new Error('Message is not sent');
22970
22971 case 6:
22972 _context2.next = 10;
22973 break;
22974
22975 case 8:
22976 if (message.id && message.timestamp) {
22977 _context2.next = 10;
22978 break;
22979 }
22980
22981 throw new TypeError("".concat(message, " is not a Message"));
22982
22983 case 10:
22984 if (!recall) {
22985 content = serializeMessage(newMessage);
22986 msg = content.msg;
22987 binaryMsg = content.binaryMsg;
22988 }
22989
22990 _context2.next = 13;
22991 return this._send(new GenericCommand({
22992 cmd: CommandType.patch,
22993 op: OpType.modify,
22994 patchMessage: new PatchCommand({
22995 patches: [new PatchItem({
22996 cid: this.id,
22997 mid: message.id,
22998 timestamp: Number(message.timestamp),
22999 recall: recall,
23000 data: msg,
23001 binaryMsg: binaryMsg,
23002 mentionPids: newMessage.mentionList,
23003 mentionAll: newMessage.mentionedAll
23004 })],
23005 lastPatchTime: this._client._lastPatchTime
23006 })
23007 }));
23008
23009 case 13:
23010 id = message.id, cid = message.cid, timestamp = message.timestamp, from = message.from, _status = message._status;
23011 Object.assign(newMessage, {
23012 id: id,
23013 cid: cid,
23014 timestamp: timestamp,
23015 from: from,
23016 _status: _status
23017 });
23018
23019 if (this.lastMessage && this.lastMessage.id === newMessage.id) {
23020 this.lastMessage = newMessage;
23021 }
23022
23023 return _context2.abrupt("return", newMessage);
23024
23025 case 17:
23026 case "end":
23027 return _context2.stop();
23028 }
23029 }
23030 }, _callee2, this);
23031 }));
23032
23033 function _update(_x3, _x4, _x5) {
23034 return _update2.apply(this, arguments);
23035 }
23036
23037 return _update;
23038 }()
23039 /**
23040 * 获取对话人数,或暂态对话的在线人数
23041 * @return {Promise.<Number>}
23042 */
23043 ;
23044
23045 _proto.count =
23046 /*#__PURE__*/
23047 function () {
23048 var _count = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee3() {
23049 var resCommand;
23050 return regenerator.wrap(function _callee3$(_context3) {
23051 while (1) {
23052 switch (_context3.prev = _context3.next) {
23053 case 0:
23054 this._debug('count');
23055
23056 _context3.next = 3;
23057 return this._send(new GenericCommand({
23058 op: 'count'
23059 }));
23060
23061 case 3:
23062 resCommand = _context3.sent;
23063 return _context3.abrupt("return", resCommand.convMessage.count);
23064
23065 case 5:
23066 case "end":
23067 return _context3.stop();
23068 }
23069 }
23070 }, _callee3, this);
23071 }));
23072
23073 function count() {
23074 return _count.apply(this, arguments);
23075 }
23076
23077 return count;
23078 }()
23079 /**
23080 * 应用增加成员的操作,产生副作用
23081 * @param {string[]} members
23082 * @abstract
23083 * @private
23084 */
23085 ;
23086
23087 _proto._addMembers = function _addMembers() {}
23088 /**
23089 * 应用减少成员的操作,产生副作用
23090 * @param {string[]} members
23091 * @abstract
23092 * @private
23093 */
23094 ;
23095
23096 _proto._removeMembers = function _removeMembers() {}
23097 /**
23098 * 修改已发送的消息
23099 * @param {AVMessage} message 要修改的消息,该消息必须是由当前用户发送的。也可以提供一个包含消息 {id, timestamp} 的对象
23100 * @param {AVMessage} newMessage 新的消息
23101 * @return {Promise.<AVMessage>} 更新后的消息
23102 */
23103 ;
23104
23105 _proto.update =
23106 /*#__PURE__*/
23107 function () {
23108 var _update3 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee4(message, newMessage) {
23109 return regenerator.wrap(function _callee4$(_context4) {
23110 while (1) {
23111 switch (_context4.prev = _context4.next) {
23112 case 0:
23113 if (newMessage instanceof Message) {
23114 _context4.next = 2;
23115 break;
23116 }
23117
23118 throw new TypeError("".concat(newMessage, " is not a Message"));
23119
23120 case 2:
23121 return _context4.abrupt("return", this._update(message, newMessage, false));
23122
23123 case 3:
23124 case "end":
23125 return _context4.stop();
23126 }
23127 }
23128 }, _callee4, this);
23129 }));
23130
23131 function update(_x6, _x7) {
23132 return _update3.apply(this, arguments);
23133 }
23134
23135 return update;
23136 }()
23137 /**
23138 * 撤回已发送的消息
23139 * @param {AVMessage} message 要撤回的消息,该消息必须是由当前用户发送的。也可以提供一个包含消息 {id, timestamp} 的对象
23140 * @return {Promise.<RecalledMessage>} 一条已撤回的消息
23141 */
23142 ;
23143
23144 _proto.recall =
23145 /*#__PURE__*/
23146 function () {
23147 var _recall = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee5(message) {
23148 return regenerator.wrap(function _callee5$(_context5) {
23149 while (1) {
23150 switch (_context5.prev = _context5.next) {
23151 case 0:
23152 return _context5.abrupt("return", this._update(message, new RecalledMessage(), true));
23153
23154 case 1:
23155 case "end":
23156 return _context5.stop();
23157 }
23158 }
23159 }, _callee5, this);
23160 }));
23161
23162 function recall(_x8) {
23163 return _recall.apply(this, arguments);
23164 }
23165
23166 return recall;
23167 }()
23168 /**
23169 * 查询消息记录
23170 * 如果仅需实现消息向前记录翻页查询需求,建议使用 {@link Conversation#createMessagesIterator}。
23171 * 不论何种方向,获得的消息都是按照时间升序排列的。
23172 * startClosed 与 endClosed 用于指定查询区间的开闭。
23173 *
23174 * @param {Object} [options]
23175 * @param {Number} [options.limit] 限制查询结果的数量,目前服务端默认为 20
23176 * @param {Number} [options.type] 指定查询的富媒体消息类型,不指定则查询所有消息。
23177 * @param {MessageQueryDirection} [options.direction] 查询的方向。
23178 * 在不指定的情况下如果 startTime 大于 endTime,则为从新到旧查询,可以实现加载聊天记录等场景。
23179 * 如果 startTime 小于 endTime,则为从旧到新查询,可以实现弹幕等场景。
23180 * @param {Date} [options.startTime] 从该时间开始查询,不传则从当前时间开始查询
23181 * @param {String} [options.startMessageId] 从该消息之前开始查询,需要与 startTime 同时使用,为防止某时刻有重复消息
23182 * @param {Boolean}[options.startClosed] 指定查询范围是否包括开始的时间点,默认不包括
23183 * @param {Date} [options.endTime] 查询到该时间为止,不传则查询最早消息为止
23184 * @param {String} [options.endMessageId] 查询到该消息为止,需要与 endTime 同时使用,为防止某时刻有重复消息
23185 * @param {Boolean}[options.endClosed] 指定查询范围是否包括结束的时间点,默认不包括
23186 *
23187 * @param {Date} [options.beforeTime] DEPRECATED: 使用 startTime 代替。限制查询结果为小于该时间之前的消息,不传则为当前时间
23188 * @param {String} [options.beforeMessageId] DEPRECATED: 使用 startMessageId 代替。
23189 * 限制查询结果为该消息之前的消息,需要与 beforeTime 同时使用,为防止某时刻有重复消息
23190 * @param {Date} [options.afterTime] DEPRECATED: 使用 endTime 代替。限制查询结果为大于该时间之前的消息
23191 * @param {String} [options.afterMessageId] DEPRECATED: 使用 endMessageId 代替。
23192 * 限制查询结果为该消息之后的消息,需要与 afterTime 同时使用,为防止某时刻有重复消息
23193 * @return {Promise.<Message[]>} 消息列表
23194 */
23195 ;
23196
23197 _proto.queryMessages =
23198 /*#__PURE__*/
23199 function () {
23200 var _queryMessages = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee7() {
23201 var _this2 = this;
23202
23203 var options,
23204 beforeTime,
23205 beforeMessageId,
23206 afterTime,
23207 afterMessageId,
23208 limit,
23209 direction,
23210 type,
23211 startTime,
23212 startMessageId,
23213 startClosed,
23214 endTime,
23215 endMessageId,
23216 endClosed,
23217 conditions,
23218 resCommand,
23219 _args7 = arguments;
23220 return regenerator.wrap(function _callee7$(_context7) {
23221 while (1) {
23222 switch (_context7.prev = _context7.next) {
23223 case 0:
23224 options = _args7.length > 0 && _args7[0] !== undefined ? _args7[0] : {};
23225
23226 this._debug('query messages %O', options);
23227
23228 beforeTime = options.beforeTime, beforeMessageId = options.beforeMessageId, afterTime = options.afterTime, afterMessageId = options.afterMessageId, limit = options.limit, direction = options.direction, type = options.type, startTime = options.startTime, startMessageId = options.startMessageId, startClosed = options.startClosed, endTime = options.endTime, endMessageId = options.endMessageId, endClosed = options.endClosed;
23229
23230 if (!(beforeMessageId || beforeTime || afterMessageId || afterTime)) {
23231 _context7.next = 6;
23232 break;
23233 }
23234
23235 console.warn('DEPRECATION: queryMessages options beforeTime, beforeMessageId, afterTime and afterMessageId are deprecated in favor of startTime, startMessageId, endTime and endMessageId.');
23236 return _context7.abrupt("return", this.queryMessages({
23237 startTime: beforeTime,
23238 startMessageId: beforeMessageId,
23239 endTime: afterTime,
23240 endMessageId: afterMessageId,
23241 limit: limit
23242 }));
23243
23244 case 6:
23245 if (!(startMessageId && !startTime)) {
23246 _context7.next = 8;
23247 break;
23248 }
23249
23250 throw new Error('query option startMessageId must be used with option startTime');
23251
23252 case 8:
23253 if (!(endMessageId && !endTime)) {
23254 _context7.next = 10;
23255 break;
23256 }
23257
23258 throw new Error('query option endMessageId must be used with option endTime');
23259
23260 case 10:
23261 conditions = {
23262 t: startTime,
23263 mid: startMessageId,
23264 tIncluded: startClosed,
23265 tt: endTime,
23266 tmid: endMessageId,
23267 ttIncluded: endClosed,
23268 l: limit,
23269 lctype: type
23270 };
23271
23272 if (conditions.t instanceof Date) {
23273 conditions.t = conditions.t.getTime();
23274 }
23275
23276 if (conditions.tt instanceof Date) {
23277 conditions.tt = conditions.tt.getTime();
23278 }
23279
23280 if (direction !== undefined) {
23281 conditions.direction = direction;
23282 } else if (conditions.tt > conditions.t) {
23283 conditions.direction = MessageQueryDirection.OLD_TO_NEW;
23284 }
23285
23286 _context7.next = 16;
23287 return this._send(new GenericCommand({
23288 cmd: 'logs',
23289 logsMessage: new LogsCommand(Object.assign(conditions, {
23290 cid: this.id
23291 }))
23292 }));
23293
23294 case 16:
23295 resCommand = _context7.sent;
23296 return _context7.abrupt("return", Promise.all(resCommand.logsMessage.logs.map( /*#__PURE__*/function () {
23297 var _ref3 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee6(_ref2) {
23298 var msgId, timestamp, patchTimestamp, from, ackAt, readAt, data, mentionAll, mentionPids, bin, messageData, message, status;
23299 return regenerator.wrap(function _callee6$(_context6) {
23300 while (1) {
23301 switch (_context6.prev = _context6.next) {
23302 case 0:
23303 msgId = _ref2.msgId, timestamp = _ref2.timestamp, patchTimestamp = _ref2.patchTimestamp, from = _ref2.from, ackAt = _ref2.ackAt, readAt = _ref2.readAt, data = _ref2.data, mentionAll = _ref2.mentionAll, mentionPids = _ref2.mentionPids, bin = _ref2.bin;
23304 messageData = {
23305 data: data,
23306 bin: bin,
23307 id: msgId,
23308 cid: _this2.id,
23309 timestamp: timestamp,
23310 from: from,
23311 deliveredAt: ackAt,
23312 updatedAt: patchTimestamp,
23313 mentionList: mentionPids,
23314 mentionedAll: mentionAll
23315 };
23316 _context6.next = 4;
23317 return _this2._client.parseMessage(messageData);
23318
23319 case 4:
23320 message = _context6.sent;
23321 status = MessageStatus.SENT;
23322
23323 if (_this2.members.length === 2) {
23324 if (ackAt) status = MessageStatus.DELIVERED;
23325 if (ackAt) _this2._setLastDeliveredAt(ackAt);
23326 if (readAt) _this2._setLastReadAt(readAt);
23327 }
23328
23329 message._setStatus(status);
23330
23331 return _context6.abrupt("return", message);
23332
23333 case 9:
23334 case "end":
23335 return _context6.stop();
23336 }
23337 }
23338 }, _callee6);
23339 }));
23340
23341 return function (_x9) {
23342 return _ref3.apply(this, arguments);
23343 };
23344 }())));
23345
23346 case 18:
23347 case "end":
23348 return _context7.stop();
23349 }
23350 }
23351 }, _callee7, this);
23352 }));
23353
23354 function queryMessages() {
23355 return _queryMessages.apply(this, arguments);
23356 }
23357
23358 return queryMessages;
23359 }()
23360 /**
23361 * 获取消息翻页迭代器
23362 * @param {Object} [options]
23363 * @param {Date} [options.beforeTime] 限制起始查询结果为小于该时间之前的消息,不传则为当前时间
23364 * @param {String} [options.beforeMessageId] 限制起始查询结果为该消息之前的消息,需要与 beforeTime 同时使用,为防止某时刻有重复消息
23365 * @param {Number} [options.limit] 限制每页查询结果的数量,目前服务端默认为 20
23366 * @return {AsyncIterater.<Promise.<IteratorResult<Message[]>>>} [AsyncIterator]{@link https://github.com/tc39/proposal-async-iteration},调用其 next 方法返回获取下一页消息的 Promise
23367 * @example
23368 * var messageIterator = conversation.createMessagesIterator({ limit: 10 });
23369 * messageIterator.next().then(function(result) {
23370 * // result: {
23371 * // value: [message1, ..., message10],
23372 * // done: false,
23373 * // }
23374 * });
23375 * messageIterator.next().then(function(result) {
23376 * // result: {
23377 * // value: [message11, ..., message20],
23378 * // done: false,
23379 * // }
23380 * });
23381 * messageIterator.next().then(function(result) {
23382 * // No more messages
23383 * // result: { value: [], done: true }
23384 * });
23385 */
23386 ;
23387
23388 _proto.createMessagesIterator = function createMessagesIterator() {
23389 var _this3 = this;
23390
23391 var _ref4 = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {},
23392 beforeTime = _ref4.beforeTime,
23393 beforeMessageId = _ref4.beforeMessageId,
23394 limit = _ref4.limit;
23395
23396 var promise;
23397 return {
23398 next: function next() {
23399 if (promise === undefined) {
23400 // first call
23401 promise = _this3.queryMessages({
23402 limit: limit,
23403 startTime: beforeTime,
23404 startMessageId: beforeMessageId
23405 });
23406 } else {
23407 promise = promise.then(function (prevMessages) {
23408 if (prevMessages.length === 0 || prevMessages.length < limit) {
23409 // no more messages
23410 return [];
23411 }
23412
23413 return _this3.queryMessages({
23414 startTime: prevMessages[0].timestamp,
23415 startMessageId: prevMessages[0].id,
23416 limit: limit
23417 });
23418 });
23419 }
23420
23421 return promise.then(function (value) {
23422 return {
23423 value: Array.from(value),
23424 done: value.length === 0 || value.length < limit
23425 };
23426 });
23427 }
23428 };
23429 }
23430 /**
23431 * 将该会话标记为已读
23432 * @return {Promise.<this>} self
23433 */
23434 ;
23435
23436 _proto.read =
23437 /*#__PURE__*/
23438 function () {
23439 var _read = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee8() {
23440 var client;
23441 return regenerator.wrap(function _callee8$(_context8) {
23442 while (1) {
23443 switch (_context8.prev = _context8.next) {
23444 case 0:
23445 this.unreadMessagesCount = 0;
23446
23447 this._setUnreadMessagesMentioned(false); // 跳过暂态会话
23448
23449
23450 if (!this["transient"]) {
23451 _context8.next = 4;
23452 break;
23453 }
23454
23455 return _context8.abrupt("return", this);
23456
23457 case 4:
23458 client = this._client;
23459
23460 if (!internal(client).readConversationsBuffer) {
23461 internal(client).readConversationsBuffer = new Set();
23462 }
23463
23464 internal(client).readConversationsBuffer.add(this);
23465
23466 client._doSendRead();
23467
23468 return _context8.abrupt("return", this);
23469
23470 case 9:
23471 case "end":
23472 return _context8.stop();
23473 }
23474 }
23475 }, _callee8, this);
23476 }));
23477
23478 function read() {
23479 return _read.apply(this, arguments);
23480 }
23481
23482 return read;
23483 }();
23484
23485 _proto._handleReceipt = function _handleReceipt(_ref5) {
23486 var messageId = _ref5.messageId,
23487 timestamp = _ref5.timestamp,
23488 read = _ref5.read;
23489
23490 if (read) {
23491 this._setLastReadAt(timestamp);
23492 } else {
23493 this._setLastDeliveredAt(timestamp);
23494 }
23495
23496 var _internal = internal(this),
23497 messagesWaitingForReceipt = _internal.messagesWaitingForReceipt;
23498
23499 var message = messagesWaitingForReceipt[messageId];
23500 if (!message) return;
23501
23502 message._setStatus(MessageStatus.DELIVERED);
23503
23504 message.deliveredAt = timestamp;
23505 delete messagesWaitingForReceipt[messageId];
23506 }
23507 /**
23508 * 更新对话的最新回执时间戳(lastDeliveredAt、lastReadAt)
23509 * @since 3.4.0
23510 * @return {Promise.<this>} this
23511 */
23512 ;
23513
23514 _proto.fetchReceiptTimestamps =
23515 /*#__PURE__*/
23516 function () {
23517 var _fetchReceiptTimestamps = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee9() {
23518 var _yield$this$_send, _yield$this$_send$con, maxReadTimestamp, maxAckTimestamp;
23519
23520 return regenerator.wrap(function _callee9$(_context9) {
23521 while (1) {
23522 switch (_context9.prev = _context9.next) {
23523 case 0:
23524 if (!(this["transient"] || this.system)) {
23525 _context9.next = 2;
23526 break;
23527 }
23528
23529 return _context9.abrupt("return", this);
23530
23531 case 2:
23532 _context9.next = 4;
23533 return this._send(new GenericCommand({
23534 op: 'max_read'
23535 }));
23536
23537 case 4:
23538 _yield$this$_send = _context9.sent;
23539 _yield$this$_send$con = _yield$this$_send.convMessage;
23540 maxReadTimestamp = _yield$this$_send$con.maxReadTimestamp;
23541 maxAckTimestamp = _yield$this$_send$con.maxAckTimestamp;
23542
23543 this._setLastDeliveredAt(maxAckTimestamp);
23544
23545 this._setLastReadAt(maxReadTimestamp);
23546
23547 return _context9.abrupt("return", this);
23548
23549 case 11:
23550 case "end":
23551 return _context9.stop();
23552 }
23553 }
23554 }, _callee9, this);
23555 }));
23556
23557 function fetchReceiptTimestamps() {
23558 return _fetchReceiptTimestamps.apply(this, arguments);
23559 }
23560
23561 return fetchReceiptTimestamps;
23562 }();
23563
23564 _proto._fetchAllReceiptTimestamps = function _fetchAllReceiptTimestamps() {
23565 // 暂态/系统会话不支持回执
23566 if (this["transient"] || this.system) return this;
23567 var convMessage = new ConvCommand({
23568 queryAllMembers: true
23569 });
23570 return this._send(new GenericCommand({
23571 op: 'max_read',
23572 convMessage: convMessage
23573 })).then(function (_ref6) {
23574 var maxReadTuples = _ref6.convMessage.maxReadTuples;
23575 return maxReadTuples.filter(function (maxReadTuple) {
23576 return maxReadTuple.maxAckTimestamp || maxReadTuple.maxReadTimestamp;
23577 }).map(function (_ref7) {
23578 var pid = _ref7.pid,
23579 maxAckTimestamp = _ref7.maxAckTimestamp,
23580 maxReadTimestamp = _ref7.maxReadTimestamp;
23581 return {
23582 pid: pid,
23583 lastDeliveredAt: decodeDate(maxAckTimestamp),
23584 lastReadAt: decodeDate(maxReadTimestamp)
23585 };
23586 });
23587 });
23588 };
23589
23590 createClass(ConversationBase, [{
23591 key: "unreadMessagesMentioned",
23592 get: function get() {
23593 return internal(this).unreadMessagesMentioned;
23594 }
23595 }, {
23596 key: "unreadMessagesCount",
23597 set: function set(value) {
23598 if (value !== this.unreadMessagesCount) {
23599 internal(this).unreadMessagesCount = value;
23600
23601 this._client.emit(UNREAD_MESSAGES_COUNT_UPDATE, [this]);
23602 }
23603 }
23604 /**
23605 * 当前用户在该对话的未读消息数
23606 * @type {Number}
23607 */
23608 ,
23609 get: function get() {
23610 return internal(this).unreadMessagesCount;
23611 }
23612 }, {
23613 key: "lastMessageAt",
23614 set: function set(value) {
23615 var time = decodeDate(value);
23616 if (time <= this._lastMessageAt) return;
23617 this._lastMessageAt = time;
23618 },
23619 get: function get() {
23620 return this._lastMessageAt;
23621 }
23622 /**
23623 * 最后消息送达时间,常用来实现消息的「已送达」标记,可通过 {@link Conversation#fetchReceiptTimestamps} 获取或更新该属性
23624 * @type {?Date}
23625 * @since 3.4.0
23626 */
23627
23628 }, {
23629 key: "lastDeliveredAt",
23630 get: function get() {
23631 if (this.members.length !== 2) return null;
23632 return internal(this).lastDeliveredAt;
23633 }
23634 }, {
23635 key: "lastReadAt",
23636 get: function get() {
23637 if (this.members.length !== 2) return null;
23638 return internal(this).lastReadAt;
23639 }
23640 }]);
23641
23642 return ConversationBase;
23643 }(eventemitter3);
23644
23645 var debug$8 = browser('LC:SignatureFactoryRunner');
23646
23647 function _validateSignature() {
23648 var signatureResult = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {};
23649 var signature = signatureResult.signature,
23650 timestamp = signatureResult.timestamp,
23651 nonce = signatureResult.nonce;
23652
23653 if (typeof signature !== 'string' || typeof timestamp !== 'number' || typeof nonce !== 'string') {
23654 throw new Error('malformed signature');
23655 }
23656
23657 return {
23658 signature: signature,
23659 timestamp: timestamp,
23660 nonce: nonce
23661 };
23662 }
23663
23664 var runSignatureFactory = (function (signatureFactory, params) {
23665 return Promise.resolve().then(function () {
23666 debug$8('call signatureFactory with %O', params);
23667 return signatureFactory.apply(void 0, toConsumableArray(params));
23668 }).then(tap(function (signatureResult) {
23669 return debug$8('sign result %O', signatureResult);
23670 }), function (error) {
23671 // eslint-disable-next-line no-param-reassign
23672 error.message = "sign error: ".concat(error.message);
23673 debug$8(error);
23674 throw error;
23675 }).then(_validateSignature);
23676 });
23677
23678 function ownKeys$6(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); if (enumerableOnly) symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; }); keys.push.apply(keys, symbols); } return keys; }
23679
23680 function _objectSpread$6(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i] != null ? arguments[i] : {}; if (i % 2) { ownKeys$6(Object(source), true).forEach(function (key) { defineProperty(target, key, source[key]); }); } else if (Object.getOwnPropertyDescriptors) { Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)); } else { ownKeys$6(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } } return target; }
23681 /**
23682 * 部分失败异常
23683 * @typedef OperationFailureError
23684 * @type {Error}
23685 * @property {string} message 异常信息
23686 * @property {string[]} clientIds 因为该原因失败的 client id 列表
23687 * @property {number} [code] 错误码
23688 * @property {string} [detail] 详细信息
23689 */
23690
23691 /**
23692 * 部分成功的结果
23693 * @typedef PartiallySuccess
23694 * @type {Object}
23695 * @property {string[]} successfulClientIds 成功的 client id 列表
23696 * @property {OperationFailureError[]} failures 失败的异常列表
23697 */
23698
23699 /**
23700 * 分页查询结果
23701 * @typedef PagedResults
23702 * @type {Object}
23703 * @property {T[]} results 查询结果
23704 * @property {string} [next] 存在表示还有更多结果,在下次查询中带上可实现翻页。
23705 */
23706
23707 var createPartiallySuccess = function createPartiallySuccess(_ref) {
23708 var allowedPids = _ref.allowedPids,
23709 failedPids = _ref.failedPids;
23710 return {
23711 successfulClientIds: allowedPids,
23712 failures: failedPids.map(function (_ref2) {
23713 var pids = _ref2.pids,
23714 error = objectWithoutProperties(_ref2, ["pids"]);
23715
23716 return Object.assign(createError(error), {
23717 clientIds: pids
23718 });
23719 })
23720 };
23721 };
23722 /**
23723 * @extends ConversationBase
23724 * @private
23725 * @abstract
23726 */
23727
23728
23729 var PersistentConversation = /*#__PURE__*/function (_ConversationBase) {
23730 inheritsLoose(PersistentConversation, _ConversationBase);
23731
23732 function PersistentConversation(data, _ref3, client) {
23733 var _this;
23734
23735 var creator = _ref3.creator,
23736 createdAt = _ref3.createdAt,
23737 updatedAt = _ref3.updatedAt,
23738 _ref3$transient = _ref3["transient"],
23739 _transient = _ref3$transient === void 0 ? false : _ref3$transient,
23740 _ref3$system = _ref3.system,
23741 system = _ref3$system === void 0 ? false : _ref3$system,
23742 _ref3$muted = _ref3.muted,
23743 muted = _ref3$muted === void 0 ? false : _ref3$muted,
23744 _ref3$mutedMembers = _ref3.mutedMembers,
23745 mutedMembers = _ref3$mutedMembers === void 0 ? [] : _ref3$mutedMembers,
23746 attributes = objectWithoutProperties(_ref3, ["creator", "createdAt", "updatedAt", "transient", "system", "muted", "mutedMembers"]);
23747
23748 _this = _ConversationBase.call(this, _objectSpread$6(_objectSpread$6({}, data), {}, {
23749 /**
23750 * 对话创建者
23751 * @memberof PersistentConversation#
23752 * @type {String}
23753 */
23754 creator: creator,
23755
23756 /**
23757 * 对话创建时间
23758 * @memberof PersistentConversation#
23759 * @type {Date}
23760 */
23761 createdAt: createdAt,
23762
23763 /**
23764 * 对话更新时间
23765 * @memberof PersistentConversation#
23766 * @type {Date}
23767 */
23768 updatedAt: updatedAt,
23769
23770 /**
23771 * 对该对话设置了静音的用户列表
23772 * @memberof PersistentConversation#
23773 * @type {?String[]}
23774 */
23775 mutedMembers: mutedMembers,
23776
23777 /**
23778 * 暂态对话标记
23779 * @memberof PersistentConversation#
23780 * @type {Boolean}
23781 */
23782 "transient": _transient,
23783
23784 /**
23785 * 系统对话标记
23786 * @memberof PersistentConversation#
23787 * @type {Boolean}
23788 * @since 3.3.0
23789 */
23790 system: system,
23791
23792 /**
23793 * 当前用户静音该对话标记
23794 * @memberof PersistentConversation#
23795 * @type {Boolean}
23796 */
23797 muted: muted,
23798 _attributes: attributes
23799 }), client) || this;
23800
23801 _this._reset();
23802
23803 return _this;
23804 }
23805
23806 var _proto = PersistentConversation.prototype;
23807
23808 /**
23809 * 获取对话的自定义属性
23810 * @since 3.2.0
23811 * @param {String} key key 属性的键名,'x' 对应 Conversation 表中的 x 列
23812 * @return {Any} 属性的值
23813 */
23814 _proto.get = function get(key) {
23815 return get_1(internal(this).currentAttributes, key);
23816 }
23817 /**
23818 * 设置对话的自定义属性
23819 * @since 3.2.0
23820 * @param {String} key 属性的键名,'x' 对应 Conversation 表中的 x 列,支持使用 'x.y.z' 来修改对象的部分字段。
23821 * @param {Any} value 属性的值
23822 * @return {this} self
23823 * @example
23824 *
23825 * // 设置对话的 color 属性
23826 * conversation.set('color', {
23827 * text: '#000',
23828 * background: '#DDD',
23829 * });
23830 * // 设置对话的 color.text 属性
23831 * conversation.set('color.text', '#333');
23832 */
23833 ;
23834
23835 _proto.set = function set(key, value) {
23836 this._debug("set [".concat(key, "]: ").concat(value));
23837
23838 var _internal = internal(this),
23839 pendingAttributes = _internal.pendingAttributes;
23840
23841 var pendingKeys = Object.keys(pendingAttributes); // suppose pendingAttributes = { 'a.b': {} }
23842 // set 'a' or 'a.b': delete 'a.b'
23843
23844 var re = new RegExp("^".concat(key));
23845 var childKeys = pendingKeys.filter(re.test.bind(re));
23846 childKeys.forEach(function (k) {
23847 delete pendingAttributes[k];
23848 });
23849
23850 if (childKeys.length) {
23851 pendingAttributes[key] = value;
23852 } else {
23853 // set 'a.c': nothing to do
23854 // set 'a.b.c.d': assign c: { d: {} } to 'a.b'
23855 var parentKey = find_1(pendingKeys, function (k) {
23856 return key.indexOf(k) === 0;
23857 }); // 'a.b'
23858
23859 if (parentKey) {
23860 setValue(pendingAttributes[parentKey], key.slice(parentKey.length + 1), value);
23861 } else {
23862 pendingAttributes[key] = value;
23863 }
23864 }
23865
23866 this._buildCurrentAttributes();
23867
23868 return this;
23869 };
23870
23871 _proto._buildCurrentAttributes = function _buildCurrentAttributes() {
23872 var _internal2 = internal(this),
23873 pendingAttributes = _internal2.pendingAttributes;
23874
23875 internal(this).currentAttributes = Object.keys(pendingAttributes).reduce(function (target, k) {
23876 return setValue(target, k, pendingAttributes[k]);
23877 }, cloneDeep_1(this._attributes));
23878 };
23879
23880 _proto._updateServerAttributes = function _updateServerAttributes(attributes) {
23881 var _this2 = this;
23882
23883 Object.keys(attributes).forEach(function (key) {
23884 return setValue(_this2._attributes, key, attributes[key]);
23885 });
23886
23887 this._buildCurrentAttributes();
23888 };
23889
23890 _proto._reset = function _reset() {
23891 Object.assign(internal(this), {
23892 pendingAttributes: {},
23893 currentAttributes: this._attributes
23894 });
23895 }
23896 /**
23897 * 保存当前对话的属性至服务器
23898 * @return {Promise.<this>} self
23899 */
23900 ;
23901
23902 _proto.save =
23903 /*#__PURE__*/
23904 function () {
23905 var _save = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee() {
23906 var attr, convMessage, resCommand;
23907 return regenerator.wrap(function _callee$(_context) {
23908 while (1) {
23909 switch (_context.prev = _context.next) {
23910 case 0:
23911 this._debug('save');
23912
23913 attr = internal(this).pendingAttributes;
23914
23915 if (!isEmpty_1(attr)) {
23916 _context.next = 5;
23917 break;
23918 }
23919
23920 this._debug('nothing touched, resolve with self');
23921
23922 return _context.abrupt("return", this);
23923
23924 case 5:
23925 this._debug('attr: %O', attr);
23926
23927 convMessage = new ConvCommand({
23928 attr: new JsonObjectMessage({
23929 data: JSON.stringify(encode(attr))
23930 })
23931 });
23932 _context.next = 9;
23933 return this._send(new GenericCommand({
23934 op: 'update',
23935 convMessage: convMessage
23936 }));
23937
23938 case 9:
23939 resCommand = _context.sent;
23940 this.updatedAt = resCommand.convMessage.udate;
23941 this._attributes = internal(this).currentAttributes;
23942 internal(this).pendingAttributes = {};
23943 return _context.abrupt("return", this);
23944
23945 case 14:
23946 case "end":
23947 return _context.stop();
23948 }
23949 }
23950 }, _callee, this);
23951 }));
23952
23953 function save() {
23954 return _save.apply(this, arguments);
23955 }
23956
23957 return save;
23958 }()
23959 /**
23960 * 从服务器更新对话的属性
23961 * @return {Promise.<this>} self
23962 */
23963 ;
23964
23965 _proto.fetch =
23966 /*#__PURE__*/
23967 function () {
23968 var _fetch = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee2() {
23969 var query;
23970 return regenerator.wrap(function _callee2$(_context2) {
23971 while (1) {
23972 switch (_context2.prev = _context2.next) {
23973 case 0:
23974 query = this._client.getQuery().equalTo('objectId', this.id);
23975 _context2.next = 3;
23976 return query.find();
23977
23978 case 3:
23979 return _context2.abrupt("return", this);
23980
23981 case 4:
23982 case "end":
23983 return _context2.stop();
23984 }
23985 }
23986 }, _callee2, this);
23987 }));
23988
23989 function fetch() {
23990 return _fetch.apply(this, arguments);
23991 }
23992
23993 return fetch;
23994 }()
23995 /**
23996 * 静音,客户端拒绝收到服务器端的离线推送通知
23997 * @return {Promise.<this>} self
23998 */
23999 ;
24000
24001 _proto.mute =
24002 /*#__PURE__*/
24003 function () {
24004 var _mute = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee3() {
24005 return regenerator.wrap(function _callee3$(_context3) {
24006 while (1) {
24007 switch (_context3.prev = _context3.next) {
24008 case 0:
24009 this._debug('mute');
24010
24011 _context3.next = 3;
24012 return this._send(new GenericCommand({
24013 op: 'mute'
24014 }));
24015
24016 case 3:
24017 if (!this["transient"]) {
24018 this.muted = true;
24019 this.mutedMembers = union(this.mutedMembers, [this._client.id]);
24020 }
24021
24022 return _context3.abrupt("return", this);
24023
24024 case 5:
24025 case "end":
24026 return _context3.stop();
24027 }
24028 }
24029 }, _callee3, this);
24030 }));
24031
24032 function mute() {
24033 return _mute.apply(this, arguments);
24034 }
24035
24036 return mute;
24037 }()
24038 /**
24039 * 取消静音
24040 * @return {Promise.<this>} self
24041 */
24042 ;
24043
24044 _proto.unmute =
24045 /*#__PURE__*/
24046 function () {
24047 var _unmute = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee4() {
24048 return regenerator.wrap(function _callee4$(_context4) {
24049 while (1) {
24050 switch (_context4.prev = _context4.next) {
24051 case 0:
24052 this._debug('unmute');
24053
24054 _context4.next = 3;
24055 return this._send(new GenericCommand({
24056 op: 'unmute'
24057 }));
24058
24059 case 3:
24060 if (!this["transient"]) {
24061 this.muted = false;
24062 this.mutedMembers = difference(this.mutedMembers, [this._client.id]);
24063 }
24064
24065 return _context4.abrupt("return", this);
24066
24067 case 5:
24068 case "end":
24069 return _context4.stop();
24070 }
24071 }
24072 }, _callee4, this);
24073 }));
24074
24075 function unmute() {
24076 return _unmute.apply(this, arguments);
24077 }
24078
24079 return unmute;
24080 }();
24081
24082 _proto._appendConversationSignature = /*#__PURE__*/function () {
24083 var _appendConversationSignature2 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee5(command, action, clientIds) {
24084 var params, signatureResult;
24085 return regenerator.wrap(function _callee5$(_context5) {
24086 while (1) {
24087 switch (_context5.prev = _context5.next) {
24088 case 0:
24089 if (!this._client.options.conversationSignatureFactory) {
24090 _context5.next = 6;
24091 break;
24092 }
24093
24094 params = [this.id, this._client.id, clientIds.sort(), action];
24095 _context5.next = 4;
24096 return runSignatureFactory(this._client.options.conversationSignatureFactory, params);
24097
24098 case 4:
24099 signatureResult = _context5.sent;
24100 Object.assign(command.convMessage, keyRemap({
24101 signature: 's',
24102 timestamp: 't',
24103 nonce: 'n'
24104 }, signatureResult));
24105
24106 case 6:
24107 case "end":
24108 return _context5.stop();
24109 }
24110 }
24111 }, _callee5, this);
24112 }));
24113
24114 function _appendConversationSignature(_x, _x2, _x3) {
24115 return _appendConversationSignature2.apply(this, arguments);
24116 }
24117
24118 return _appendConversationSignature;
24119 }();
24120
24121 _proto._appendBlacklistSignature = /*#__PURE__*/function () {
24122 var _appendBlacklistSignature2 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee6(command, action, clientIds) {
24123 var params, signatureResult;
24124 return regenerator.wrap(function _callee6$(_context6) {
24125 while (1) {
24126 switch (_context6.prev = _context6.next) {
24127 case 0:
24128 if (!this._client.options.blacklistSignatureFactory) {
24129 _context6.next = 6;
24130 break;
24131 }
24132
24133 params = [this.id, this._client.id, clientIds.sort(), action];
24134 _context6.next = 4;
24135 return runSignatureFactory(this._client.options.blacklistSignatureFactory, params);
24136
24137 case 4:
24138 signatureResult = _context6.sent;
24139 Object.assign(command.blacklistMessage, keyRemap({
24140 signature: 's',
24141 timestamp: 't',
24142 nonce: 'n'
24143 }, signatureResult));
24144
24145 case 6:
24146 case "end":
24147 return _context6.stop();
24148 }
24149 }
24150 }, _callee6, this);
24151 }));
24152
24153 function _appendBlacklistSignature(_x4, _x5, _x6) {
24154 return _appendBlacklistSignature2.apply(this, arguments);
24155 }
24156
24157 return _appendBlacklistSignature;
24158 }()
24159 /**
24160 * 增加成员
24161 * @param {String|String[]} clientIds 新增成员 client id
24162 * @return {Promise.<PartiallySuccess>} 部分成功结果,包含了成功的 id 列表、失败原因与对应的 id 列表
24163 */
24164 ;
24165
24166 _proto.add =
24167 /*#__PURE__*/
24168 function () {
24169 var _add = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee7(clientIds) {
24170 var command, _yield$this$_send, convMessage, allowedPids;
24171
24172 return regenerator.wrap(function _callee7$(_context7) {
24173 while (1) {
24174 switch (_context7.prev = _context7.next) {
24175 case 0:
24176 this._debug('add', clientIds);
24177
24178 if (typeof clientIds === 'string') {
24179 clientIds = [clientIds]; // eslint-disable-line no-param-reassign
24180 }
24181
24182 command = new GenericCommand({
24183 op: 'add',
24184 convMessage: new ConvCommand({
24185 m: clientIds
24186 })
24187 });
24188 _context7.next = 5;
24189 return this._appendConversationSignature(command, 'invite', clientIds);
24190
24191 case 5:
24192 _context7.next = 7;
24193 return this._send(command);
24194
24195 case 7:
24196 _yield$this$_send = _context7.sent;
24197 convMessage = _yield$this$_send.convMessage;
24198 allowedPids = _yield$this$_send.convMessage.allowedPids;
24199
24200 this._addMembers(allowedPids);
24201
24202 return _context7.abrupt("return", createPartiallySuccess(convMessage));
24203
24204 case 12:
24205 case "end":
24206 return _context7.stop();
24207 }
24208 }
24209 }, _callee7, this);
24210 }));
24211
24212 function add(_x7) {
24213 return _add.apply(this, arguments);
24214 }
24215
24216 return add;
24217 }()
24218 /**
24219 * 剔除成员
24220 * @param {String|String[]} clientIds 成员 client id
24221 * @return {Promise.<PartiallySuccess>} 部分成功结果,包含了成功的 id 列表、失败原因与对应的 id 列表
24222 */
24223 ;
24224
24225 _proto.remove =
24226 /*#__PURE__*/
24227 function () {
24228 var _remove = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee8(clientIds) {
24229 var command, _yield$this$_send2, convMessage, allowedPids;
24230
24231 return regenerator.wrap(function _callee8$(_context8) {
24232 while (1) {
24233 switch (_context8.prev = _context8.next) {
24234 case 0:
24235 this._debug('remove', clientIds);
24236
24237 if (typeof clientIds === 'string') {
24238 clientIds = [clientIds]; // eslint-disable-line no-param-reassign
24239 }
24240
24241 command = new GenericCommand({
24242 op: 'remove',
24243 convMessage: new ConvCommand({
24244 m: clientIds
24245 })
24246 });
24247 _context8.next = 5;
24248 return this._appendConversationSignature(command, 'kick', clientIds);
24249
24250 case 5:
24251 _context8.next = 7;
24252 return this._send(command);
24253
24254 case 7:
24255 _yield$this$_send2 = _context8.sent;
24256 convMessage = _yield$this$_send2.convMessage;
24257 allowedPids = _yield$this$_send2.convMessage.allowedPids;
24258
24259 this._removeMembers(allowedPids);
24260
24261 return _context8.abrupt("return", createPartiallySuccess(convMessage));
24262
24263 case 12:
24264 case "end":
24265 return _context8.stop();
24266 }
24267 }
24268 }, _callee8, this);
24269 }));
24270
24271 function remove(_x8) {
24272 return _remove.apply(this, arguments);
24273 }
24274
24275 return remove;
24276 }()
24277 /**
24278 * (当前用户)加入该对话
24279 * @return {Promise.<this>} self
24280 */
24281 ;
24282
24283 _proto.join =
24284 /*#__PURE__*/
24285 function () {
24286 var _join = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee9() {
24287 var _this3 = this;
24288
24289 return regenerator.wrap(function _callee9$(_context9) {
24290 while (1) {
24291 switch (_context9.prev = _context9.next) {
24292 case 0:
24293 this._debug('join');
24294
24295 return _context9.abrupt("return", this.add(this._client.id).then(function (_ref4) {
24296 var failures = _ref4.failures;
24297 if (failures[0]) throw failures[0];
24298 return _this3;
24299 }));
24300
24301 case 2:
24302 case "end":
24303 return _context9.stop();
24304 }
24305 }
24306 }, _callee9, this);
24307 }));
24308
24309 function join() {
24310 return _join.apply(this, arguments);
24311 }
24312
24313 return join;
24314 }()
24315 /**
24316 * (当前用户)退出该对话
24317 * @return {Promise.<this>} self
24318 */
24319 ;
24320
24321 _proto.quit =
24322 /*#__PURE__*/
24323 function () {
24324 var _quit = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee10() {
24325 var _this4 = this;
24326
24327 return regenerator.wrap(function _callee10$(_context10) {
24328 while (1) {
24329 switch (_context10.prev = _context10.next) {
24330 case 0:
24331 this._debug('quit');
24332
24333 return _context10.abrupt("return", this.remove(this._client.id).then(function (_ref5) {
24334 var failures = _ref5.failures;
24335 if (failures[0]) throw failures[0];
24336 return _this4;
24337 }));
24338
24339 case 2:
24340 case "end":
24341 return _context10.stop();
24342 }
24343 }
24344 }, _callee10, this);
24345 }));
24346
24347 function quit() {
24348 return _quit.apply(this, arguments);
24349 }
24350
24351 return quit;
24352 }()
24353 /**
24354 * 在该对话中禁言成员
24355 * @param {String|String[]} clientIds 成员 client id
24356 * @return {Promise.<PartiallySuccess>} 部分成功结果,包含了成功的 id 列表、失败原因与对应的 id 列表
24357 */
24358 ;
24359
24360 _proto.muteMembers =
24361 /*#__PURE__*/
24362 function () {
24363 var _muteMembers = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee11(clientIds) {
24364 var command, _yield$this$_send3, convMessage;
24365
24366 return regenerator.wrap(function _callee11$(_context11) {
24367 while (1) {
24368 switch (_context11.prev = _context11.next) {
24369 case 0:
24370 this._debug('mute', clientIds);
24371
24372 clientIds = ensureArray(clientIds); // eslint-disable-line no-param-reassign
24373
24374 command = new GenericCommand({
24375 op: OpType.add_shutup,
24376 convMessage: new ConvCommand({
24377 m: clientIds
24378 })
24379 });
24380 _context11.next = 5;
24381 return this._send(command);
24382
24383 case 5:
24384 _yield$this$_send3 = _context11.sent;
24385 convMessage = _yield$this$_send3.convMessage;
24386 return _context11.abrupt("return", createPartiallySuccess(convMessage));
24387
24388 case 8:
24389 case "end":
24390 return _context11.stop();
24391 }
24392 }
24393 }, _callee11, this);
24394 }));
24395
24396 function muteMembers(_x9) {
24397 return _muteMembers.apply(this, arguments);
24398 }
24399
24400 return muteMembers;
24401 }()
24402 /**
24403 * 在该对话中解除成员禁言
24404 * @param {String|String[]} clientIds 成员 client id
24405 * @return {Promise.<PartiallySuccess>} 部分成功结果,包含了成功的 id 列表、失败原因与对应的 id 列表
24406 */
24407 ;
24408
24409 _proto.unmuteMembers =
24410 /*#__PURE__*/
24411 function () {
24412 var _unmuteMembers = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee12(clientIds) {
24413 var command, _yield$this$_send4, convMessage;
24414
24415 return regenerator.wrap(function _callee12$(_context12) {
24416 while (1) {
24417 switch (_context12.prev = _context12.next) {
24418 case 0:
24419 this._debug('unmute', clientIds);
24420
24421 clientIds = ensureArray(clientIds); // eslint-disable-line no-param-reassign
24422
24423 command = new GenericCommand({
24424 op: OpType.remove_shutup,
24425 convMessage: new ConvCommand({
24426 m: clientIds
24427 })
24428 });
24429 _context12.next = 5;
24430 return this._send(command);
24431
24432 case 5:
24433 _yield$this$_send4 = _context12.sent;
24434 convMessage = _yield$this$_send4.convMessage;
24435 return _context12.abrupt("return", createPartiallySuccess(convMessage));
24436
24437 case 8:
24438 case "end":
24439 return _context12.stop();
24440 }
24441 }
24442 }, _callee12, this);
24443 }));
24444
24445 function unmuteMembers(_x10) {
24446 return _unmuteMembers.apply(this, arguments);
24447 }
24448
24449 return unmuteMembers;
24450 }()
24451 /**
24452 * 查询该对话禁言成员列表
24453 * @param {Object} [options]
24454 * @param {Number} [options.limit] 返回的成员数量,服务器默认值 10
24455 * @param {String} [options.next] 从指定 next 开始查询,与 limit 一起使用可以完成翻页。
24456 * @return {PagedResults.<string>} 查询结果。其中的 cureser 存在表示还有更多结果。
24457 */
24458 ;
24459
24460 _proto.queryMutedMembers =
24461 /*#__PURE__*/
24462 function () {
24463 var _queryMutedMembers = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee13() {
24464 var _ref6,
24465 limit,
24466 next,
24467 command,
24468 _yield$this$_send5,
24469 _yield$this$_send5$co,
24470 m,
24471 newNext,
24472 _args13 = arguments;
24473
24474 return regenerator.wrap(function _callee13$(_context13) {
24475 while (1) {
24476 switch (_context13.prev = _context13.next) {
24477 case 0:
24478 _ref6 = _args13.length > 0 && _args13[0] !== undefined ? _args13[0] : {}, limit = _ref6.limit, next = _ref6.next;
24479
24480 this._debug('query muted: limit %O, next: %O', limit, next);
24481
24482 command = new GenericCommand({
24483 op: OpType.query_shutup,
24484 convMessage: new ConvCommand({
24485 limit: limit,
24486 next: next
24487 })
24488 });
24489 _context13.next = 5;
24490 return this._send(command);
24491
24492 case 5:
24493 _yield$this$_send5 = _context13.sent;
24494 _yield$this$_send5$co = _yield$this$_send5.convMessage;
24495 m = _yield$this$_send5$co.m;
24496 newNext = _yield$this$_send5$co.next;
24497 return _context13.abrupt("return", {
24498 results: m,
24499 next: newNext
24500 });
24501
24502 case 10:
24503 case "end":
24504 return _context13.stop();
24505 }
24506 }
24507 }, _callee13, this);
24508 }));
24509
24510 function queryMutedMembers() {
24511 return _queryMutedMembers.apply(this, arguments);
24512 }
24513
24514 return queryMutedMembers;
24515 }()
24516 /**
24517 * 将用户加入该对话黑名单
24518 * @param {String|String[]} clientIds 成员 client id
24519 * @return {Promise.<PartiallySuccess>} 部分成功结果,包含了成功的 id 列表、失败原因与对应的 id 列表
24520 */
24521 ;
24522
24523 _proto.blockMembers =
24524 /*#__PURE__*/
24525 function () {
24526 var _blockMembers = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee14(clientIds) {
24527 var command, _yield$this$_send6, blacklistMessage;
24528
24529 return regenerator.wrap(function _callee14$(_context14) {
24530 while (1) {
24531 switch (_context14.prev = _context14.next) {
24532 case 0:
24533 this._debug('block', clientIds);
24534
24535 clientIds = ensureArray(clientIds); // eslint-disable-line no-param-reassign
24536
24537 command = new GenericCommand({
24538 cmd: 'blacklist',
24539 op: OpType.block,
24540 blacklistMessage: new BlacklistCommand({
24541 srcCid: this.id,
24542 toPids: clientIds
24543 })
24544 });
24545 _context14.next = 5;
24546 return this._appendBlacklistSignature(command, 'conversation-block-clients', clientIds);
24547
24548 case 5:
24549 _context14.next = 7;
24550 return this._send(command);
24551
24552 case 7:
24553 _yield$this$_send6 = _context14.sent;
24554 blacklistMessage = _yield$this$_send6.blacklistMessage;
24555 return _context14.abrupt("return", createPartiallySuccess(blacklistMessage));
24556
24557 case 10:
24558 case "end":
24559 return _context14.stop();
24560 }
24561 }
24562 }, _callee14, this);
24563 }));
24564
24565 function blockMembers(_x11) {
24566 return _blockMembers.apply(this, arguments);
24567 }
24568
24569 return blockMembers;
24570 }()
24571 /**
24572 * 将用户移出该对话黑名单
24573 * @param {String|String[]} clientIds 成员 client id
24574 * @return {Promise.<PartiallySuccess>} 部分成功结果,包含了成功的 id 列表、失败原因与对应的 id 列表
24575 */
24576 ;
24577
24578 _proto.unblockMembers =
24579 /*#__PURE__*/
24580 function () {
24581 var _unblockMembers = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee15(clientIds) {
24582 var command, _yield$this$_send7, blacklistMessage;
24583
24584 return regenerator.wrap(function _callee15$(_context15) {
24585 while (1) {
24586 switch (_context15.prev = _context15.next) {
24587 case 0:
24588 this._debug('unblock', clientIds);
24589
24590 clientIds = ensureArray(clientIds); // eslint-disable-line no-param-reassign
24591
24592 command = new GenericCommand({
24593 cmd: 'blacklist',
24594 op: OpType.unblock,
24595 blacklistMessage: new BlacklistCommand({
24596 srcCid: this.id,
24597 toPids: clientIds
24598 })
24599 });
24600 _context15.next = 5;
24601 return this._appendBlacklistSignature(command, 'conversation-unblock-clients', clientIds);
24602
24603 case 5:
24604 _context15.next = 7;
24605 return this._send(command);
24606
24607 case 7:
24608 _yield$this$_send7 = _context15.sent;
24609 blacklistMessage = _yield$this$_send7.blacklistMessage;
24610 return _context15.abrupt("return", createPartiallySuccess(blacklistMessage));
24611
24612 case 10:
24613 case "end":
24614 return _context15.stop();
24615 }
24616 }
24617 }, _callee15, this);
24618 }));
24619
24620 function unblockMembers(_x12) {
24621 return _unblockMembers.apply(this, arguments);
24622 }
24623
24624 return unblockMembers;
24625 }()
24626 /**
24627 * 查询该对话黑名单
24628 * @param {Object} [options]
24629 * @param {Number} [options.limit] 返回的成员数量,服务器默认值 10
24630 * @param {String} [options.next] 从指定 next 开始查询,与 limit 一起使用可以完成翻页
24631 * @return {PagedResults.<string>} 查询结果。其中的 cureser 存在表示还有更多结果。
24632 */
24633 ;
24634
24635 _proto.queryBlockedMembers =
24636 /*#__PURE__*/
24637 function () {
24638 var _queryBlockedMembers = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee16() {
24639 var _ref7,
24640 limit,
24641 next,
24642 command,
24643 _yield$this$_send8,
24644 _yield$this$_send8$bl,
24645 blockedPids,
24646 newNext,
24647 _args16 = arguments;
24648
24649 return regenerator.wrap(function _callee16$(_context16) {
24650 while (1) {
24651 switch (_context16.prev = _context16.next) {
24652 case 0:
24653 _ref7 = _args16.length > 0 && _args16[0] !== undefined ? _args16[0] : {}, limit = _ref7.limit, next = _ref7.next;
24654
24655 this._debug('query blocked: limit %O, next: %O', limit, next);
24656
24657 command = new GenericCommand({
24658 cmd: 'blacklist',
24659 op: OpType.query,
24660 blacklistMessage: new BlacklistCommand({
24661 srcCid: this.id,
24662 limit: limit,
24663 next: next
24664 })
24665 });
24666 _context16.next = 5;
24667 return this._send(command);
24668
24669 case 5:
24670 _yield$this$_send8 = _context16.sent;
24671 _yield$this$_send8$bl = _yield$this$_send8.blacklistMessage;
24672 blockedPids = _yield$this$_send8$bl.blockedPids;
24673 newNext = _yield$this$_send8$bl.next;
24674 return _context16.abrupt("return", {
24675 results: blockedPids,
24676 next: newNext
24677 });
24678
24679 case 10:
24680 case "end":
24681 return _context16.stop();
24682 }
24683 }
24684 }, _callee16, this);
24685 }));
24686
24687 function queryBlockedMembers() {
24688 return _queryBlockedMembers.apply(this, arguments);
24689 }
24690
24691 return queryBlockedMembers;
24692 }();
24693
24694 _proto.toFullJSON = function toFullJSON() {
24695 var creator = this.creator,
24696 system = this.system,
24697 _transient2 = this["transient"],
24698 createdAt = this.createdAt,
24699 updatedAt = this.updatedAt,
24700 _attributes = this._attributes;
24701 return _objectSpread$6(_objectSpread$6({}, _ConversationBase.prototype.toFullJSON.call(this)), {}, {
24702 creator: creator,
24703 system: system,
24704 "transient": _transient2,
24705 createdAt: getTime(createdAt),
24706 updatedAt: getTime(updatedAt)
24707 }, _attributes);
24708 };
24709
24710 _proto.toJSON = function toJSON() {
24711 var creator = this.creator,
24712 system = this.system,
24713 _transient3 = this["transient"],
24714 muted = this.muted,
24715 mutedMembers = this.mutedMembers,
24716 createdAt = this.createdAt,
24717 updatedAt = this.updatedAt,
24718 _attributes = this._attributes;
24719 return _objectSpread$6(_objectSpread$6({}, _ConversationBase.prototype.toJSON.call(this)), {}, {
24720 creator: creator,
24721 system: system,
24722 "transient": _transient3,
24723 muted: muted,
24724 mutedMembers: mutedMembers,
24725 createdAt: createdAt,
24726 updatedAt: updatedAt
24727 }, _attributes);
24728 };
24729
24730 createClass(PersistentConversation, [{
24731 key: "createdAt",
24732 set: function set(value) {
24733 this._createdAt = decodeDate(value);
24734 },
24735 get: function get() {
24736 return this._createdAt;
24737 }
24738 }, {
24739 key: "updatedAt",
24740 set: function set(value) {
24741 this._updatedAt = decodeDate(value);
24742 },
24743 get: function get() {
24744 return this._updatedAt;
24745 }
24746 /**
24747 * 对话名字,对应 _Conversation 表中的 name
24748 * @type {String}
24749 */
24750
24751 }, {
24752 key: "name",
24753 get: function get() {
24754 return this.get('name');
24755 },
24756 set: function set(value) {
24757 this.set('name', value);
24758 }
24759 }]);
24760
24761 return PersistentConversation;
24762 }(ConversationBase);
24763
24764 /**
24765 * 对话成员角色枚举
24766 * @enum {String}
24767 * @since 4.0.0
24768 * @memberof module:leancloud-realtime
24769 */
24770
24771 var ConversationMemberRole = {
24772 /** 所有者 */
24773 OWNER: 'Owner',
24774
24775 /** 管理员 */
24776 MANAGER: 'Manager',
24777
24778 /** 成员 */
24779 MEMBER: 'Member'
24780 };
24781 Object.freeze(ConversationMemberRole);
24782
24783 var ConversationMemberInfo = /*#__PURE__*/function () {
24784 /**
24785 * 对话成员属性,保存了成员与某个对话相关的属性,对应 _ConversationMemberInfo 表
24786 * @since 4.0.0
24787 */
24788 function ConversationMemberInfo(_ref) {
24789 var conversation = _ref.conversation,
24790 memberId = _ref.memberId,
24791 role = _ref.role;
24792 if (!conversation) throw new Error('conversation requried');
24793 if (!memberId) throw new Error('memberId requried');
24794 Object.assign(internal(this), {
24795 conversation: conversation,
24796 memberId: memberId,
24797 role: role
24798 });
24799 }
24800 /**
24801 * 对话 Id
24802 * @type {String}
24803 * @readonly
24804 */
24805
24806
24807 var _proto = ConversationMemberInfo.prototype;
24808
24809 _proto.toJSON = function toJSON() {
24810 var conversationId = this.conversationId,
24811 memberId = this.memberId,
24812 role = this.role,
24813 isOwner = this.isOwner;
24814 return {
24815 conversationId: conversationId,
24816 memberId: memberId,
24817 role: role,
24818 isOwner: isOwner
24819 };
24820 };
24821
24822 createClass(ConversationMemberInfo, [{
24823 key: "conversationId",
24824 get: function get() {
24825 return internal(this).conversation.id;
24826 }
24827 /**
24828 * 成员 Id
24829 * @type {String}
24830 * @readonly
24831 */
24832
24833 }, {
24834 key: "memberId",
24835 get: function get() {
24836 return internal(this).memberId;
24837 }
24838 /**
24839 * 角色
24840 * @type {module:leancloud-realtime.ConversationMemberRole | String}
24841 * @readonly
24842 */
24843
24844 }, {
24845 key: "role",
24846 get: function get() {
24847 if (this.isOwner) return ConversationMemberRole.OWNER;
24848 return internal(this).role;
24849 }
24850 /**
24851 * 是否是管理员
24852 * @type {Boolean}
24853 * @readonly
24854 */
24855
24856 }, {
24857 key: "isOwner",
24858 get: function get() {
24859 return this.memberId === internal(this).conversation.creator;
24860 }
24861 }]);
24862
24863 return ConversationMemberInfo;
24864 }();
24865
24866 /**
24867 * 普通对话
24868 *
24869 * 无法直接实例化,请使用 {@link IMClient#createConversation} 创建新的普通对话。
24870 * @extends PersistentConversation
24871 * @public
24872 */
24873
24874 var Conversation = /*#__PURE__*/function (_PersistentConversati) {
24875 inheritsLoose(Conversation, _PersistentConversati);
24876
24877 function Conversation() {
24878 return _PersistentConversati.apply(this, arguments) || this;
24879 }
24880
24881 var _proto = Conversation.prototype;
24882
24883 _proto._addMembers = function _addMembers(members) {
24884 var _this = this;
24885
24886 _PersistentConversati.prototype._addMembers.call(this, members);
24887
24888 this.members = union(this.members, members);
24889
24890 var _internal = internal(this),
24891 memberInfoMap = _internal.memberInfoMap;
24892
24893 if (!memberInfoMap) return;
24894 members.forEach(function (memberId) {
24895 memberInfoMap[memberId] = memberInfoMap[memberId] || new ConversationMemberInfo({
24896 conversation: _this,
24897 memberId: memberId,
24898 role: ConversationMemberRole.MEMBER
24899 });
24900 });
24901 };
24902
24903 _proto._removeMembers = function _removeMembers(members) {
24904 _PersistentConversati.prototype._removeMembers.call(this, members);
24905
24906 this.members = difference(this.members, members);
24907
24908 var _internal2 = internal(this),
24909 memberInfoMap = _internal2.memberInfoMap;
24910
24911 if (!memberInfoMap) return;
24912 members.forEach(function (memberId) {
24913 delete memberInfoMap[memberId];
24914 });
24915 };
24916
24917 _proto._fetchAllMemberInfo = /*#__PURE__*/function () {
24918 var _fetchAllMemberInfo2 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee() {
24919 var _this2 = this;
24920
24921 var response, memberInfos, memberInfoMap;
24922 return regenerator.wrap(function _callee$(_context) {
24923 while (1) {
24924 switch (_context.prev = _context.next) {
24925 case 0:
24926 _context.next = 2;
24927 return this._client._requestWithSessionToken({
24928 method: 'GET',
24929 path: '/classes/_ConversationMemberInfo',
24930 query: {
24931 where: {
24932 cid: this.id
24933 }
24934 }
24935 });
24936
24937 case 2:
24938 response = _context.sent;
24939 memberInfos = response.results.map(function (info) {
24940 return new ConversationMemberInfo({
24941 conversation: _this2,
24942 memberId: info.clientId,
24943 role: info.role
24944 });
24945 });
24946 memberInfoMap = {};
24947 memberInfos.forEach(function (memberInfo) {
24948 memberInfoMap[memberInfo.memberId] = memberInfo;
24949 });
24950 this.members.forEach(function (memberId) {
24951 memberInfoMap[memberId] = memberInfoMap[memberId] || new ConversationMemberInfo({
24952 conversation: _this2,
24953 memberId: memberId,
24954 role: ConversationMemberRole.MEMBER
24955 });
24956 });
24957 internal(this).memberInfoMap = memberInfoMap;
24958 return _context.abrupt("return", memberInfoMap);
24959
24960 case 9:
24961 case "end":
24962 return _context.stop();
24963 }
24964 }
24965 }, _callee, this);
24966 }));
24967
24968 function _fetchAllMemberInfo() {
24969 return _fetchAllMemberInfo2.apply(this, arguments);
24970 }
24971
24972 return _fetchAllMemberInfo;
24973 }()
24974 /**
24975 * 获取所有成员的对话属性
24976 * @since 4.0.0
24977 * @return {Promise.<ConversationMemberInfo[]>} 所有成员的对话属性列表
24978 */
24979 ;
24980
24981 _proto.getAllMemberInfo =
24982 /*#__PURE__*/
24983 function () {
24984 var _getAllMemberInfo = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee2() {
24985 var _ref,
24986 _ref$noCache,
24987 noCache,
24988 _internal3,
24989 memberInfoMap,
24990 _args2 = arguments;
24991
24992 return regenerator.wrap(function _callee2$(_context2) {
24993 while (1) {
24994 switch (_context2.prev = _context2.next) {
24995 case 0:
24996 _ref = _args2.length > 0 && _args2[0] !== undefined ? _args2[0] : {}, _ref$noCache = _ref.noCache, noCache = _ref$noCache === void 0 ? false : _ref$noCache;
24997 _internal3 = internal(this), memberInfoMap = _internal3.memberInfoMap;
24998
24999 if (!(!memberInfoMap || noCache)) {
25000 _context2.next = 6;
25001 break;
25002 }
25003
25004 _context2.next = 5;
25005 return this._fetchAllMemberInfo();
25006
25007 case 5:
25008 memberInfoMap = _context2.sent;
25009
25010 case 6:
25011 return _context2.abrupt("return", this.members.map(function (memberId) {
25012 return memberInfoMap[memberId];
25013 }));
25014
25015 case 7:
25016 case "end":
25017 return _context2.stop();
25018 }
25019 }
25020 }, _callee2, this);
25021 }));
25022
25023 function getAllMemberInfo() {
25024 return _getAllMemberInfo.apply(this, arguments);
25025 }
25026
25027 return getAllMemberInfo;
25028 }()
25029 /**
25030 * 获取指定成员的对话属性
25031 * @since 4.0.0
25032 * @param {String} memberId 成员 Id
25033 * @return {Promise.<ConversationMemberInfo>} 指定成员的对话属性
25034 */
25035 ;
25036
25037 _proto.getMemberInfo =
25038 /*#__PURE__*/
25039 function () {
25040 var _getMemberInfo = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee3(memberId) {
25041 var _internal4, memberInfoMap;
25042
25043 return regenerator.wrap(function _callee3$(_context3) {
25044 while (1) {
25045 switch (_context3.prev = _context3.next) {
25046 case 0:
25047 if (!(this.members.indexOf(memberId) === -1)) {
25048 _context3.next = 2;
25049 break;
25050 }
25051
25052 throw new Error("".concat(memberId, " is not the mumber of conversation[").concat(this.id, "]"));
25053
25054 case 2:
25055 _internal4 = internal(this), memberInfoMap = _internal4.memberInfoMap;
25056
25057 if (memberInfoMap && memberInfoMap[memberId]) {
25058 _context3.next = 6;
25059 break;
25060 }
25061
25062 _context3.next = 6;
25063 return this.getAllMemberInfo();
25064
25065 case 6:
25066 return _context3.abrupt("return", internal(this).memberInfoMap[memberId]);
25067
25068 case 7:
25069 case "end":
25070 return _context3.stop();
25071 }
25072 }
25073 }, _callee3, this);
25074 }));
25075
25076 function getMemberInfo(_x) {
25077 return _getMemberInfo.apply(this, arguments);
25078 }
25079
25080 return getMemberInfo;
25081 }()
25082 /**
25083 * 更新指定用户的角色
25084 * @since 4.0.0
25085 * @param {String} memberId 成员 Id
25086 * @param {module:leancloud-realtime.ConversationMemberRole | String} role 角色
25087 * @return {Promise.<this>} self
25088 */
25089 ;
25090
25091 _proto.updateMemberRole =
25092 /*#__PURE__*/
25093 function () {
25094 var _updateMemberRole = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee4(memberId, role) {
25095 var _internal5, memberInfos;
25096
25097 return regenerator.wrap(function _callee4$(_context4) {
25098 while (1) {
25099 switch (_context4.prev = _context4.next) {
25100 case 0:
25101 this._debug('update member role');
25102
25103 if (!(role === ConversationMemberRole.OWNER)) {
25104 _context4.next = 3;
25105 break;
25106 }
25107
25108 throw createError({
25109 code: ErrorCode.OWNER_PROMOTION_NOT_ALLOWED
25110 });
25111
25112 case 3:
25113 _context4.next = 5;
25114 return this._send(new GenericCommand({
25115 op: OpType.member_info_update,
25116 convMessage: new ConvCommand({
25117 targetClientId: memberId,
25118 info: new ConvMemberInfo({
25119 pid: memberId,
25120 role: role
25121 })
25122 })
25123 }));
25124
25125 case 5:
25126 _internal5 = internal(this), memberInfos = _internal5.memberInfos;
25127
25128 if (memberInfos && memberInfos[memberId]) {
25129 internal(memberInfos[memberId]).role = role;
25130 }
25131
25132 return _context4.abrupt("return", this);
25133
25134 case 8:
25135 case "end":
25136 return _context4.stop();
25137 }
25138 }
25139 }, _callee4, this);
25140 }));
25141
25142 function updateMemberRole(_x2, _x3) {
25143 return _updateMemberRole.apply(this, arguments);
25144 }
25145
25146 return updateMemberRole;
25147 }();
25148
25149 return Conversation;
25150 }(PersistentConversation);
25151
25152 /**
25153 * 聊天室。
25154 *
25155 * 无法直接实例化,请使用 {@link IMClient#createChatRoom} 创建新的聊天室。
25156 * @since 4.0.0
25157 * @extends PersistentConversation
25158 * @public
25159 */
25160
25161 var ChatRoom = /*#__PURE__*/function (_PersistentConversati) {
25162 inheritsLoose(ChatRoom, _PersistentConversati);
25163
25164 function ChatRoom() {
25165 return _PersistentConversati.apply(this, arguments) || this;
25166 }
25167
25168 return ChatRoom;
25169 }(PersistentConversation);
25170
25171 /**
25172 * 服务号。
25173 *
25174 * 服务号不支持在客户端创建。
25175 * @since 4.0.0
25176 * @extends PersistentConversation
25177 * @public
25178 */
25179
25180 var ServiceConversation = /*#__PURE__*/function (_PersistentConversati) {
25181 inheritsLoose(ServiceConversation, _PersistentConversati);
25182
25183 function ServiceConversation() {
25184 return _PersistentConversati.apply(this, arguments) || this;
25185 }
25186
25187 var _proto = ServiceConversation.prototype;
25188
25189 /**
25190 * 订阅该服务号
25191 * @return {Promise.<this>} self
25192 */
25193 _proto.subscribe =
25194 /*#__PURE__*/
25195 function () {
25196 var _subscribe = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee() {
25197 return regenerator.wrap(function _callee$(_context) {
25198 while (1) {
25199 switch (_context.prev = _context.next) {
25200 case 0:
25201 return _context.abrupt("return", this.join());
25202
25203 case 1:
25204 case "end":
25205 return _context.stop();
25206 }
25207 }
25208 }, _callee, this);
25209 }));
25210
25211 function subscribe() {
25212 return _subscribe.apply(this, arguments);
25213 }
25214
25215 return subscribe;
25216 }()
25217 /**
25218 * 退订该服务号
25219 * @return {Promise.<this>} self
25220 */
25221 ;
25222
25223 _proto.unsubscribe =
25224 /*#__PURE__*/
25225 function () {
25226 var _unsubscribe = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee2() {
25227 return regenerator.wrap(function _callee2$(_context2) {
25228 while (1) {
25229 switch (_context2.prev = _context2.next) {
25230 case 0:
25231 return _context2.abrupt("return", this.quit());
25232
25233 case 1:
25234 case "end":
25235 return _context2.stop();
25236 }
25237 }
25238 }, _callee2, this);
25239 }));
25240
25241 function unsubscribe() {
25242 return _unsubscribe.apply(this, arguments);
25243 }
25244
25245 return unsubscribe;
25246 }();
25247
25248 return ServiceConversation;
25249 }(PersistentConversation);
25250
25251 function ownKeys$7(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); if (enumerableOnly) symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; }); keys.push.apply(keys, symbols); } return keys; }
25252
25253 function _objectSpread$7(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i] != null ? arguments[i] : {}; if (i % 2) { ownKeys$7(Object(source), true).forEach(function (key) { defineProperty(target, key, source[key]); }); } else if (Object.getOwnPropertyDescriptors) { Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)); } else { ownKeys$7(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } } return target; }
25254
25255 var transformNotFoundError = function transformNotFoundError(error) {
25256 return error.code === ErrorCode.CONVERSATION_NOT_FOUND ? createError({
25257 code: ErrorCode.TEMPORARY_CONVERSATION_EXPIRED
25258 }) : error;
25259 };
25260 /**
25261 * 临时对话
25262 * @since 4.0.0
25263 * @extends ConversationBase
25264 * @public
25265 */
25266
25267
25268 var TemporaryConversation = /*#__PURE__*/function (_ConversationBase) {
25269 inheritsLoose(TemporaryConversation, _ConversationBase);
25270
25271 /**
25272 * 无法直接实例化,请使用 {@link IMClient#createTemporaryConversation} 创建新的临时对话。
25273 */
25274 function TemporaryConversation(data, _ref, client) {
25275 var expiredAt = _ref.expiredAt;
25276 return _ConversationBase.call(this, _objectSpread$7(_objectSpread$7({}, data), {}, {
25277 expiredAt: expiredAt
25278 }), client) || this;
25279 }
25280 /**
25281 * 对话失效时间
25282 * @type {Date}
25283 */
25284
25285
25286 var _proto = TemporaryConversation.prototype;
25287
25288 _proto._send = /*#__PURE__*/function () {
25289 var _send2 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee() {
25290 var _ConversationBase$pro,
25291 _len,
25292 args,
25293 _key,
25294 _args = arguments;
25295
25296 return regenerator.wrap(function _callee$(_context) {
25297 while (1) {
25298 switch (_context.prev = _context.next) {
25299 case 0:
25300 if (!this.expired) {
25301 _context.next = 2;
25302 break;
25303 }
25304
25305 throw createError({
25306 code: ErrorCode.TEMPORARY_CONVERSATION_EXPIRED
25307 });
25308
25309 case 2:
25310 _context.prev = 2;
25311
25312 for (_len = _args.length, args = new Array(_len), _key = 0; _key < _len; _key++) {
25313 args[_key] = _args[_key];
25314 }
25315
25316 _context.next = 6;
25317 return (_ConversationBase$pro = _ConversationBase.prototype._send).call.apply(_ConversationBase$pro, [this].concat(args));
25318
25319 case 6:
25320 return _context.abrupt("return", _context.sent);
25321
25322 case 9:
25323 _context.prev = 9;
25324 _context.t0 = _context["catch"](2);
25325 throw transformNotFoundError(_context.t0);
25326
25327 case 12:
25328 case "end":
25329 return _context.stop();
25330 }
25331 }
25332 }, _callee, this, [[2, 9]]);
25333 }));
25334
25335 function _send() {
25336 return _send2.apply(this, arguments);
25337 }
25338
25339 return _send;
25340 }();
25341
25342 _proto.send = /*#__PURE__*/function () {
25343 var _send3 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee2() {
25344 var _ConversationBase$pro2,
25345 _len2,
25346 args,
25347 _key2,
25348 _args2 = arguments;
25349
25350 return regenerator.wrap(function _callee2$(_context2) {
25351 while (1) {
25352 switch (_context2.prev = _context2.next) {
25353 case 0:
25354 _context2.prev = 0;
25355
25356 for (_len2 = _args2.length, args = new Array(_len2), _key2 = 0; _key2 < _len2; _key2++) {
25357 args[_key2] = _args2[_key2];
25358 }
25359
25360 _context2.next = 4;
25361 return (_ConversationBase$pro2 = _ConversationBase.prototype.send).call.apply(_ConversationBase$pro2, [this].concat(args));
25362
25363 case 4:
25364 return _context2.abrupt("return", _context2.sent);
25365
25366 case 7:
25367 _context2.prev = 7;
25368 _context2.t0 = _context2["catch"](0);
25369 throw transformNotFoundError(_context2.t0);
25370
25371 case 10:
25372 case "end":
25373 return _context2.stop();
25374 }
25375 }
25376 }, _callee2, this, [[0, 7]]);
25377 }));
25378
25379 function send() {
25380 return _send3.apply(this, arguments);
25381 }
25382
25383 return send;
25384 }();
25385
25386 _proto.toFullJSON = function toFullJSON() {
25387 var expiredAt = this.expiredAt;
25388 return _objectSpread$7(_objectSpread$7({}, _ConversationBase.prototype.toFullJSON.call(this)), {}, {
25389 expiredAt: getTime(expiredAt)
25390 });
25391 };
25392
25393 _proto.toJSON = function toJSON() {
25394 var expiredAt = this.expiredAt,
25395 expired = this.expired;
25396 return _objectSpread$7(_objectSpread$7({}, _ConversationBase.prototype.toJSON.call(this)), {}, {
25397 expiredAt: expiredAt,
25398 expired: expired
25399 });
25400 };
25401
25402 createClass(TemporaryConversation, [{
25403 key: "expiredAt",
25404 set: function set(value) {
25405 this._expiredAt = decodeDate(value);
25406 },
25407 get: function get() {
25408 return this._expiredAt;
25409 }
25410 /**
25411 * 对话是否已失效
25412 * @type {Boolean}
25413 */
25414
25415 }, {
25416 key: "expired",
25417 get: function get() {
25418 return this.expiredAt < new Date();
25419 }
25420 }]);
25421
25422 return TemporaryConversation;
25423 }(ConversationBase);
25424
25425 var debug$9 = browser('LC:ConversationQuery');
25426
25427 var ConversationQuery = /*#__PURE__*/function () {
25428 ConversationQuery._encode = function _encode(value) {
25429 if (value instanceof Date) {
25430 return {
25431 __type: 'Date',
25432 iso: value.toJSON()
25433 };
25434 }
25435
25436 if (value instanceof RegExp) {
25437 return value.source;
25438 }
25439
25440 return value;
25441 };
25442
25443 ConversationQuery._quote = function _quote(s) {
25444 return "\\Q".concat(s.replace('\\E', '\\E\\\\E\\Q'), "\\E");
25445 };
25446
25447 ConversationQuery._calculateFlag = function _calculateFlag(options) {
25448 return ['withLastMessagesRefreshed', 'compact'].reduce( // eslint-disable-next-line no-bitwise
25449 function (prev, key) {
25450 return (prev << 1) + Boolean(options[key]);
25451 }, 0);
25452 }
25453 /**
25454 * 构造一个用 AND 连接所有查询的 ConversationQuery
25455 * @param {...ConversationQuery} queries
25456 * @return {ConversationQuery}
25457 */
25458 ;
25459
25460 ConversationQuery.and = function and() {
25461 for (var _len = arguments.length, queries = new Array(_len), _key = 0; _key < _len; _key++) {
25462 queries[_key] = arguments[_key];
25463 }
25464
25465 if (queries.length < 2) {
25466 throw new Error('The queries must contain at least two elements');
25467 }
25468
25469 if (!queries.every(function (q) {
25470 return q instanceof ConversationQuery;
25471 })) {
25472 throw new Error('The element of queries must be an instance of ConversationQuery');
25473 }
25474
25475 var combined = new ConversationQuery(queries[0]._client);
25476 combined._where.$and = queries.map(function (q) {
25477 return q._where;
25478 });
25479 return combined;
25480 }
25481 /**
25482 * 构造一个用 OR 连接所有查询的 ConversationQuery
25483 * @param {...ConversationQuery} queries
25484 * @return {ConversationQuery}
25485 */
25486 ;
25487
25488 ConversationQuery.or = function or() {
25489 var combined = ConversationQuery.and.apply(ConversationQuery, arguments);
25490 combined._where.$or = combined._where.$and;
25491 delete combined._where.$and;
25492 return combined;
25493 }
25494 /**
25495 * Create a ConversationQuery
25496 * @param {IMClient} client
25497 */
25498 ;
25499
25500 function ConversationQuery(client) {
25501 this._client = client;
25502 this._where = {};
25503 this._extraOptions = {};
25504 }
25505
25506 var _proto = ConversationQuery.prototype;
25507
25508 _proto._addCondition = function _addCondition(key, condition, value) {
25509 // Check if we already have a condition
25510 if (!this._where[key]) {
25511 this._where[key] = {};
25512 }
25513
25514 this._where[key][condition] = this.constructor._encode(value);
25515 return this;
25516 };
25517
25518 _proto.toJSON = function toJSON() {
25519 var json = {
25520 where: this._where,
25521 flag: this.constructor._calculateFlag(this._extraOptions)
25522 };
25523 if (typeof this._skip !== 'undefined') json.skip = this._skip;
25524 if (typeof this._limit !== 'undefined') json.limit = this._limit;
25525 if (typeof this._order !== 'undefined') json.sort = this._order;
25526 debug$9(json);
25527 return json;
25528 }
25529 /**
25530 * 增加查询条件,指定聊天室的组员包含某些成员即可返回
25531 * @param {string[]} peerIds - 成员 ID 列表
25532 * @return {ConversationQuery} self
25533 */
25534 ;
25535
25536 _proto.containsMembers = function containsMembers(peerIds) {
25537 return this.containsAll('m', peerIds);
25538 }
25539 /**
25540 * 增加查询条件,指定聊天室的组员条件满足条件的才返回
25541 *
25542 * @param {string[]} - 成员 ID 列表
25543 * @param {Boolean} includeSelf - 是否包含自己
25544 * @return {ConversationQuery} self
25545 */
25546 ;
25547
25548 _proto.withMembers = function withMembers(peerIds, includeSelf) {
25549 var peerIdsSet = new Set(peerIds);
25550
25551 if (includeSelf) {
25552 peerIdsSet.add(this._client.id);
25553 }
25554
25555 this.sizeEqualTo('m', peerIdsSet.size);
25556 return this.containsMembers(Array.from(peerIdsSet));
25557 }
25558 /**
25559 * 增加查询条件,当 conversation 的属性中对应的字段满足等于条件时即可返回
25560 *
25561 * @param {string} key
25562 * @param value
25563 * @return {ConversationQuery} self
25564 */
25565 ;
25566
25567 _proto.equalTo = function equalTo(key, value) {
25568 this._where[key] = this.constructor._encode(value);
25569 return this;
25570 }
25571 /**
25572 * 增加查询条件,当 conversation 的属性中对应的字段满足小于条件时即可返回
25573 * @param {string} key
25574 * @param value
25575 * @return {ConversationQuery} self
25576 */
25577 ;
25578
25579 _proto.lessThan = function lessThan(key, value) {
25580 return this._addCondition(key, '$lt', value);
25581 }
25582 /**
25583 * 增加查询条件,当 conversation 的属性中对应的字段满足小于等于条件时即可返回
25584 * @param {string} key
25585 * @param value
25586 * @return {ConversationQuery} self
25587 */
25588 ;
25589
25590 _proto.lessThanOrEqualTo = function lessThanOrEqualTo(key, value) {
25591 return this._addCondition(key, '$lte', value);
25592 }
25593 /**
25594 * 增加查询条件,当 conversation 的属性中对应的字段满足大于条件时即可返回
25595 *
25596 * @param {string} key
25597 * @param value
25598 * @return {ConversationQuery} self
25599 */
25600 ;
25601
25602 _proto.greaterThan = function greaterThan(key, value) {
25603 return this._addCondition(key, '$gt', value);
25604 }
25605 /**
25606 * 增加查询条件,当 conversation 的属性中对应的字段满足大于等于条件时即可返回
25607 *
25608 * @param {string} key
25609 * @param value
25610 * @return {ConversationQuery} self
25611 */
25612 ;
25613
25614 _proto.greaterThanOrEqualTo = function greaterThanOrEqualTo(key, value) {
25615 return this._addCondition(key, '$gte', value);
25616 }
25617 /**
25618 * 增加查询条件,当 conversation 的属性中对应的字段满足不等于条件时即可返回
25619 *
25620 * @param {string} key
25621 * @param value
25622 * @return {ConversationQuery} self
25623 */
25624 ;
25625
25626 _proto.notEqualTo = function notEqualTo(key, value) {
25627 return this._addCondition(key, '$ne', value);
25628 }
25629 /**
25630 * 增加查询条件,当 conversation 存在指定的字段时即可返回
25631 *
25632 * @since 3.5.0
25633 * @param {string} key
25634 * @return {ConversationQuery} self
25635 */
25636 ;
25637
25638 _proto.exists = function exists(key) {
25639 return this._addCondition(key, '$exists', true);
25640 }
25641 /**
25642 * 增加查询条件,当 conversation 不存在指定的字段时即可返回
25643 *
25644 * @since 3.5.0
25645 * @param {string} key
25646 * @return {ConversationQuery} self
25647 */
25648 ;
25649
25650 _proto.doesNotExist = function doesNotExist(key) {
25651 return this._addCondition(key, '$exists', false);
25652 }
25653 /**
25654 * 增加查询条件,当 conversation 的属性中对应的字段对应的值包含在指定值中时即可返回
25655 *
25656 * @param {string} key
25657 * @param values
25658 * @return {ConversationQuery} self
25659 */
25660 ;
25661
25662 _proto.containedIn = function containedIn(key, values) {
25663 return this._addCondition(key, '$in', values);
25664 }
25665 /**
25666 * 增加查询条件,当 conversation 的属性中对应的字段对应的值不包含在指定值中时即可返回
25667 *
25668 * @param {string} key
25669 * @param values
25670 * @return {ConversationQuery} self
25671 */
25672 ;
25673
25674 _proto.notContainsIn = function notContainsIn(key, values) {
25675 return this._addCondition(key, '$nin', values);
25676 }
25677 /**
25678 * 增加查询条件,当conversation的属性中对应的字段中的元素包含所有的值才可返回
25679 *
25680 * @param {string} key
25681 * @param values
25682 * @return {ConversationQuery} self
25683 */
25684 ;
25685
25686 _proto.containsAll = function containsAll(key, values) {
25687 return this._addCondition(key, '$all', values);
25688 }
25689 /**
25690 * 增加查询条件,当 conversation 的属性中对应的字段对应的值包含此字符串即可返回
25691 *
25692 * @param {string} key
25693 * @param {string} subString
25694 * @return {ConversationQuery} self
25695 */
25696 ;
25697
25698 _proto.contains = function contains(key, subString) {
25699 return this._addCondition(key, '$regex', ConversationQuery._quote(subString));
25700 }
25701 /**
25702 * 增加查询条件,当 conversation 的属性中对应的字段对应的值以此字符串起始即可返回
25703 *
25704 * @param {string} key
25705 * @param {string} prefix
25706 * @return {ConversationQuery} self
25707 */
25708 ;
25709
25710 _proto.startsWith = function startsWith(key, prefix) {
25711 return this._addCondition(key, '$regex', "^".concat(ConversationQuery._quote(prefix)));
25712 }
25713 /**
25714 * 增加查询条件,当 conversation 的属性中对应的字段对应的值以此字符串结束即可返回
25715 *
25716 * @param {string} key
25717 * @param {string} suffix
25718 * @return {ConversationQuery} self
25719 */
25720 ;
25721
25722 _proto.endsWith = function endsWith(key, suffix) {
25723 return this._addCondition(key, '$regex', "".concat(ConversationQuery._quote(suffix), "$"));
25724 }
25725 /**
25726 * 增加查询条件,当 conversation 的属性中对应的字段对应的值满足提供的正则表达式即可返回
25727 *
25728 * @param {string} key
25729 * @param {RegExp} regex
25730 * @return {ConversationQuery} self
25731 */
25732 ;
25733
25734 _proto.matches = function matches(key, regex) {
25735 this._addCondition(key, '$regex', regex); // Javascript regex options support mig as inline options but store them
25736 // as properties of the object. We support mi & should migrate them to
25737 // modifiers
25738
25739
25740 var _modifiers = '';
25741
25742 if (regex.ignoreCase) {
25743 _modifiers += 'i';
25744 }
25745
25746 if (regex.multiline) {
25747 _modifiers += 'm';
25748 }
25749
25750 if (_modifiers && _modifiers.length) {
25751 this._addCondition(key, '$options', _modifiers);
25752 }
25753
25754 return this;
25755 }
25756 /**
25757 * 添加查询约束条件,查找 key 类型是数组,该数组的长度匹配提供的数值
25758 *
25759 * @param {string} key
25760 * @param {Number} length
25761 * @return {ConversationQuery} self
25762 */
25763 ;
25764
25765 _proto.sizeEqualTo = function sizeEqualTo(key, length) {
25766 return this._addCondition(key, '$size', length);
25767 }
25768 /**
25769 * 设置返回集合的大小上限
25770 *
25771 * @param {Number} limit - 上限
25772 * @return {ConversationQuery} self
25773 */
25774 ;
25775
25776 _proto.limit = function limit(_limit) {
25777 this._limit = _limit;
25778 return this;
25779 }
25780 /**
25781 * 设置返回集合的起始位置,一般用于分页
25782 *
25783 * @param {Number} skip - 起始位置跳过几个对象
25784 * @return {ConversationQuery} self
25785 */
25786 ;
25787
25788 _proto.skip = function skip(_skip) {
25789 this._skip = _skip;
25790 return this;
25791 }
25792 /**
25793 * 设置返回集合按照指定key进行增序排列
25794 *
25795 * @param {string} key
25796 * @return {ConversationQuery} self
25797 */
25798 ;
25799
25800 _proto.ascending = function ascending(key) {
25801 this._order = key;
25802 return this;
25803 }
25804 /**
25805 * 设置返回集合按照指定key进行增序排列,如果已设置其他排序,原排序的优先级较高
25806 *
25807 * @param {string} key
25808 * @return {ConversationQuery} self
25809 */
25810 ;
25811
25812 _proto.addAscending = function addAscending(key) {
25813 if (this._order) {
25814 this._order += ",".concat(key);
25815 } else {
25816 this._order = key;
25817 }
25818
25819 return this;
25820 }
25821 /**
25822 * 设置返回集合按照指定 key 进行降序排列
25823 *
25824 * @param {string} key
25825 * @return {ConversationQuery} self
25826 */
25827 ;
25828
25829 _proto.descending = function descending(key) {
25830 this._order = "-".concat(key);
25831 return this;
25832 }
25833 /**
25834 * 设置返回集合按照指定 key 进行降序排列,如果已设置其他排序,原排序的优先级较高
25835 *
25836 * @param {string} key
25837 * @return {ConversationQuery} self
25838 */
25839 ;
25840
25841 _proto.addDescending = function addDescending(key) {
25842 if (this._order) {
25843 this._order += ",-".concat(key);
25844 } else {
25845 this._order = "-".concat(key);
25846 }
25847
25848 return this;
25849 }
25850 /**
25851 * 设置返回的 conversations 刷新最后一条消息
25852 * @param {Boolean} [enabled=true]
25853 * @return {ConversationQuery} self
25854 */
25855 ;
25856
25857 _proto.withLastMessagesRefreshed = function withLastMessagesRefreshed() {
25858 var enabled = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : true;
25859 this._extraOptions.withLastMessagesRefreshed = enabled;
25860 return this;
25861 }
25862 /**
25863 * 设置返回的 conversations 为精简模式,即不含成员列表
25864 * @param {Boolean} [enabled=true]
25865 * @return {ConversationQuery} self
25866 */
25867 ;
25868
25869 _proto.compact = function compact() {
25870 var enabled = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : true;
25871 this._extraOptions.compact = enabled;
25872 return this;
25873 }
25874 /**
25875 * 执行查询
25876 * @return {Promise.<ConversationBase[]>}
25877 */
25878 ;
25879
25880 _proto.find =
25881 /*#__PURE__*/
25882 function () {
25883 var _find = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee() {
25884 return regenerator.wrap(function _callee$(_context) {
25885 while (1) {
25886 switch (_context.prev = _context.next) {
25887 case 0:
25888 return _context.abrupt("return", this._client._executeQuery(this));
25889
25890 case 1:
25891 case "end":
25892 return _context.stop();
25893 }
25894 }
25895 }, _callee, this);
25896 }));
25897
25898 function find() {
25899 return _find.apply(this, arguments);
25900 }
25901
25902 return find;
25903 }()
25904 /**
25905 * 返回符合条件的第一个结果
25906 * @return {Promise.<ConversationBase>}
25907 */
25908 ;
25909
25910 _proto.first =
25911 /*#__PURE__*/
25912 function () {
25913 var _first = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee2() {
25914 return regenerator.wrap(function _callee2$(_context2) {
25915 while (1) {
25916 switch (_context2.prev = _context2.next) {
25917 case 0:
25918 _context2.next = 2;
25919 return this.limit(1).find();
25920
25921 case 2:
25922 return _context2.abrupt("return", _context2.sent[0]);
25923
25924 case 3:
25925 case "end":
25926 return _context2.stop();
25927 }
25928 }
25929 }, _callee2, this);
25930 }));
25931
25932 function first() {
25933 return _first.apply(this, arguments);
25934 }
25935
25936 return first;
25937 }();
25938
25939 return ConversationQuery;
25940 }();
25941
25942 var debug$a = browser('LC:SessionManager');
25943
25944 var SessionManager = /*#__PURE__*/function () {
25945 function SessionManager() {
25946 var _ref = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {},
25947 refresh = _ref.refresh,
25948 onBeforeGetSessionToken = _ref.onBeforeGetSessionToken;
25949
25950 this.refresh = refresh;
25951 this._onBeforeGetSessionToken = onBeforeGetSessionToken;
25952 this.setSessionToken(null, 0);
25953 }
25954
25955 var _proto = SessionManager.prototype;
25956
25957 _proto.setSessionToken = function setSessionToken(token, ttl) {
25958 debug$a('set session token', token, ttl);
25959 var sessionToken = new Expirable(token, ttl * 1000);
25960 this._sessionToken = sessionToken;
25961 delete this._pendingSessionTokenPromise;
25962 return sessionToken;
25963 };
25964
25965 _proto.setSessionTokenAsync = /*#__PURE__*/function () {
25966 var _setSessionTokenAsync = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee(promise) {
25967 var _this = this;
25968
25969 var currentSessionToken;
25970 return regenerator.wrap(function _callee$(_context) {
25971 while (1) {
25972 switch (_context.prev = _context.next) {
25973 case 0:
25974 currentSessionToken = this._sessionToken;
25975 this._pendingSessionTokenPromise = promise["catch"](function (error) {
25976 // revert, otherwise the following getSessionToken calls
25977 // will all be rejected
25978 _this._sessionToken = currentSessionToken;
25979 throw error;
25980 });
25981 _context.t0 = this.setSessionToken;
25982 _context.t1 = this;
25983 _context.t2 = toConsumableArray;
25984 _context.next = 7;
25985 return this._pendingSessionTokenPromise;
25986
25987 case 7:
25988 _context.t3 = _context.sent;
25989 _context.t4 = (0, _context.t2)(_context.t3);
25990 return _context.abrupt("return", _context.t0.apply.call(_context.t0, _context.t1, _context.t4));
25991
25992 case 10:
25993 case "end":
25994 return _context.stop();
25995 }
25996 }
25997 }, _callee, this);
25998 }));
25999
26000 function setSessionTokenAsync(_x) {
26001 return _setSessionTokenAsync.apply(this, arguments);
26002 }
26003
26004 return setSessionTokenAsync;
26005 }();
26006
26007 _proto.getSessionToken = /*#__PURE__*/function () {
26008 var _getSessionToken = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee2() {
26009 var _ref2,
26010 _ref2$autoRefresh,
26011 autoRefresh,
26012 _ref3,
26013 value,
26014 originalValue,
26015 _yield$this$setSessio,
26016 newValue,
26017 _args2 = arguments;
26018
26019 return regenerator.wrap(function _callee2$(_context2) {
26020 while (1) {
26021 switch (_context2.prev = _context2.next) {
26022 case 0:
26023 _ref2 = _args2.length > 0 && _args2[0] !== undefined ? _args2[0] : {}, _ref2$autoRefresh = _ref2.autoRefresh, autoRefresh = _ref2$autoRefresh === void 0 ? true : _ref2$autoRefresh;
26024 debug$a('get session token');
26025
26026 if (this._onBeforeGetSessionToken) {
26027 this._onBeforeGetSessionToken(this);
26028 }
26029
26030 _context2.t0 = this._sessionToken;
26031
26032 if (_context2.t0) {
26033 _context2.next = 8;
26034 break;
26035 }
26036
26037 _context2.next = 7;
26038 return this._pendingSessionTokenPromise;
26039
26040 case 7:
26041 _context2.t0 = _context2.sent;
26042
26043 case 8:
26044 _ref3 = _context2.t0;
26045 value = _ref3.value;
26046 originalValue = _ref3.originalValue;
26047
26048 if (!(value === Expirable.EXPIRED && autoRefresh && this.refresh)) {
26049 _context2.next = 19;
26050 break;
26051 }
26052
26053 debug$a('refresh expired session token');
26054 _context2.next = 15;
26055 return this.setSessionTokenAsync(this.refresh(this, originalValue));
26056
26057 case 15:
26058 _yield$this$setSessio = _context2.sent;
26059 newValue = _yield$this$setSessio.value;
26060 debug$a('session token', newValue);
26061 return _context2.abrupt("return", newValue);
26062
26063 case 19:
26064 debug$a('session token', value);
26065 return _context2.abrupt("return", value);
26066
26067 case 21:
26068 case "end":
26069 return _context2.stop();
26070 }
26071 }
26072 }, _callee2, this);
26073 }));
26074
26075 function getSessionToken() {
26076 return _getSessionToken.apply(this, arguments);
26077 }
26078
26079 return getSessionToken;
26080 }();
26081
26082 _proto.revoke = function revoke() {
26083 if (this._sessionToken) this._sessionToken.expiredAt = -1;
26084 };
26085
26086 return SessionManager;
26087 }();
26088
26089 var _dec$2, _dec2, _class$3;
26090
26091 function ownKeys$8(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); if (enumerableOnly) symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; }); keys.push.apply(keys, symbols); } return keys; }
26092
26093 function _objectSpread$8(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i] != null ? arguments[i] : {}; if (i % 2) { ownKeys$8(Object(source), true).forEach(function (key) { defineProperty(target, key, source[key]); }); } else if (Object.getOwnPropertyDescriptors) { Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)); } else { ownKeys$8(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } } return target; }
26094 var debug$b = browser('LC:IMClient');
26095 var INVITED$1 = INVITED,
26096 KICKED$1 = KICKED,
26097 MEMBERS_JOINED$1 = MEMBERS_JOINED,
26098 MEMBERS_LEFT$1 = MEMBERS_LEFT,
26099 MEMBER_INFO_UPDATED$1 = MEMBER_INFO_UPDATED,
26100 BLOCKED$1 = BLOCKED,
26101 UNBLOCKED$1 = UNBLOCKED,
26102 MEMBERS_BLOCKED$1 = MEMBERS_BLOCKED,
26103 MEMBERS_UNBLOCKED$1 = MEMBERS_UNBLOCKED,
26104 MUTED$1 = MUTED,
26105 UNMUTED$1 = UNMUTED,
26106 MEMBERS_MUTED$1 = MEMBERS_MUTED,
26107 MEMBERS_UNMUTED$1 = MEMBERS_UNMUTED,
26108 MESSAGE$2 = MESSAGE$1,
26109 UNREAD_MESSAGES_COUNT_UPDATE$1 = UNREAD_MESSAGES_COUNT_UPDATE,
26110 CLOSE$1 = CLOSE,
26111 CONFLICT$1 = CONFLICT,
26112 UNHANDLED_MESSAGE$1 = UNHANDLED_MESSAGE,
26113 CONVERSATION_INFO_UPDATED$1 = CONVERSATION_INFO_UPDATED,
26114 MESSAGE_RECALL$1 = MESSAGE_RECALL,
26115 MESSAGE_UPDATE$1 = MESSAGE_UPDATE,
26116 INFO_UPDATED$1 = INFO_UPDATED;
26117
26118 var isTemporaryConversatrionId = function isTemporaryConversatrionId(id) {
26119 return /^_tmp:/.test(id);
26120 };
26121 /**
26122 * 1 patch-msg
26123 * 1 temp-conv-msg
26124 * 0 auto-bind-deviceid-and-installation
26125 * 1 transient-msg-ack
26126 * 1 keep-notification
26127 * 1 partial-failed-msg
26128 * 0 group-chat-rcp
26129 * 1 omit-peer-id
26130 * @ignore
26131 */
26132
26133
26134 var configBitmap = 187;
26135 var IMClient = (_dec$2 = throttle(1000), _dec2 = throttle(1000), (_class$3 = /*#__PURE__*/function (_EventEmitter) {
26136 inheritsLoose(IMClient, _EventEmitter);
26137
26138 /**
26139 * 无法直接实例化,请使用 {@link Realtime#createIMClient} 创建新的 IMClient。
26140 *
26141 * @extends EventEmitter
26142 */
26143 function IMClient(id) {
26144 var _this;
26145
26146 var options = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {};
26147 var props = arguments.length > 2 ? arguments[2] : undefined;
26148
26149 if (!(id === undefined || typeof id === 'string')) {
26150 throw new TypeError("Client id [".concat(id, "] is not a String"));
26151 }
26152
26153 _this = _EventEmitter.call(this) || this;
26154 Object.assign(assertThisInitialized(_this), {
26155 /**
26156 * @var id {String} 客户端 id
26157 * @memberof IMClient#
26158 */
26159 id: id,
26160 options: options
26161 }, props);
26162
26163 if (!_this._messageParser) {
26164 throw new Error('IMClient must be initialized with a MessageParser');
26165 }
26166
26167 _this._conversationCache = new Cache("client:".concat(_this.id));
26168 _this._ackMessageBuffer = {};
26169 internal(assertThisInitialized(_this)).lastPatchTime = Date.now();
26170 internal(assertThisInitialized(_this)).lastNotificationTime = undefined;
26171 internal(assertThisInitialized(_this))._eventemitter = new eventemitter3();
26172
26173 if (debug$b.enabled) {
26174 values_1(IMEvent).forEach(function (event) {
26175 return _this.on(event, function () {
26176 for (var _len = arguments.length, payload = new Array(_len), _key = 0; _key < _len; _key++) {
26177 payload[_key] = arguments[_key];
26178 }
26179
26180 return _this._debug("".concat(event, " event emitted. %o"), payload);
26181 });
26182 });
26183 } // onIMClientCreate hook
26184
26185
26186 applyDecorators(_this._plugins.onIMClientCreate, assertThisInitialized(_this));
26187 return _this;
26188 }
26189
26190 var _proto = IMClient.prototype;
26191
26192 _proto._debug = function _debug() {
26193 for (var _len2 = arguments.length, params = new Array(_len2), _key2 = 0; _key2 < _len2; _key2++) {
26194 params[_key2] = arguments[_key2];
26195 }
26196
26197 debug$b.apply(void 0, params.concat(["[".concat(this.id, "]")]));
26198 }
26199 /**
26200 * @override
26201 * @private
26202 */
26203 ;
26204
26205 _proto._dispatchCommand =
26206 /*#__PURE__*/
26207 function () {
26208 var _dispatchCommand2 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee(command) {
26209 return regenerator.wrap(function _callee$(_context) {
26210 while (1) {
26211 switch (_context.prev = _context.next) {
26212 case 0:
26213 this._debug(trim(command), 'received');
26214
26215 if (command.serverTs && command.notificationType === 1) {
26216 internal(this).lastNotificationTime = getTime(decodeDate(command.serverTs));
26217 }
26218
26219 _context.t0 = command.cmd;
26220 _context.next = _context.t0 === CommandType.conv ? 5 : _context.t0 === CommandType.direct ? 6 : _context.t0 === CommandType.session ? 7 : _context.t0 === CommandType.unread ? 8 : _context.t0 === CommandType.rcp ? 9 : _context.t0 === CommandType.patch ? 10 : 11;
26221 break;
26222
26223 case 5:
26224 return _context.abrupt("return", this._dispatchConvMessage(command));
26225
26226 case 6:
26227 return _context.abrupt("return", this._dispatchDirectMessage(command));
26228
26229 case 7:
26230 return _context.abrupt("return", this._dispatchSessionMessage(command));
26231
26232 case 8:
26233 return _context.abrupt("return", this._dispatchUnreadMessage(command));
26234
26235 case 9:
26236 return _context.abrupt("return", this._dispatchRcpMessage(command));
26237
26238 case 10:
26239 return _context.abrupt("return", this._dispatchPatchMessage(command));
26240
26241 case 11:
26242 return _context.abrupt("return", this.emit(UNHANDLED_MESSAGE$1, command));
26243
26244 case 12:
26245 case "end":
26246 return _context.stop();
26247 }
26248 }
26249 }, _callee, this);
26250 }));
26251
26252 function _dispatchCommand(_x) {
26253 return _dispatchCommand2.apply(this, arguments);
26254 }
26255
26256 return _dispatchCommand;
26257 }();
26258
26259 _proto._dispatchSessionMessage = /*#__PURE__*/function () {
26260 var _dispatchSessionMessage2 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee2(message) {
26261 var _message$sessionMessa, code, reason;
26262
26263 return regenerator.wrap(function _callee2$(_context2) {
26264 while (1) {
26265 switch (_context2.prev = _context2.next) {
26266 case 0:
26267 _message$sessionMessa = message.sessionMessage, code = _message$sessionMessa.code, reason = _message$sessionMessa.reason;
26268 _context2.t0 = message.op;
26269 _context2.next = _context2.t0 === OpType.closed ? 4 : 8;
26270 break;
26271
26272 case 4:
26273 internal(this)._eventemitter.emit('close');
26274
26275 if (!(code === ErrorCode.SESSION_CONFLICT)) {
26276 _context2.next = 7;
26277 break;
26278 }
26279
26280 return _context2.abrupt("return", this.emit(CONFLICT$1, {
26281 reason: reason
26282 }));
26283
26284 case 7:
26285 return _context2.abrupt("return", this.emit(CLOSE$1, {
26286 code: code,
26287 reason: reason
26288 }));
26289
26290 case 8:
26291 this.emit(UNHANDLED_MESSAGE$1, message);
26292 throw new Error('Unrecognized session command');
26293
26294 case 10:
26295 case "end":
26296 return _context2.stop();
26297 }
26298 }
26299 }, _callee2, this);
26300 }));
26301
26302 function _dispatchSessionMessage(_x2) {
26303 return _dispatchSessionMessage2.apply(this, arguments);
26304 }
26305
26306 return _dispatchSessionMessage;
26307 }();
26308
26309 _proto._dispatchUnreadMessage = function _dispatchUnreadMessage(_ref) {
26310 var _this2 = this;
26311
26312 var _ref$unreadMessage = _ref.unreadMessage,
26313 convs = _ref$unreadMessage.convs,
26314 notifTime = _ref$unreadMessage.notifTime;
26315 internal(this).lastUnreadNotifTime = notifTime; // ensure all converstions are cached
26316
26317 return this.getConversations(convs.map(function (conv) {
26318 return conv.cid;
26319 })).then(function () {
26320 return (// update conversations data
26321 Promise.all(convs.map(function (_ref2) {
26322 var cid = _ref2.cid,
26323 unread = _ref2.unread,
26324 mid = _ref2.mid,
26325 ts = _ref2.timestamp,
26326 from = _ref2.from,
26327 data = _ref2.data,
26328 binaryMsg = _ref2.binaryMsg,
26329 patchTimestamp = _ref2.patchTimestamp,
26330 mentioned = _ref2.mentioned;
26331
26332 var conversation = _this2._conversationCache.get(cid); // deleted conversation
26333
26334
26335 if (!conversation) return null;
26336 var timestamp;
26337
26338 if (ts) {
26339 timestamp = decodeDate(ts);
26340 conversation.lastMessageAt = timestamp; // eslint-disable-line no-param-reassign
26341 }
26342
26343 return (mid ? _this2._messageParser.parse(binaryMsg || data).then(function (message) {
26344 var messageProps = {
26345 id: mid,
26346 cid: cid,
26347 timestamp: timestamp,
26348 updatedAt: patchTimestamp,
26349 from: from
26350 };
26351 Object.assign(message, messageProps);
26352 conversation.lastMessage = message; // eslint-disable-line no-param-reassign
26353 }) : Promise.resolve()).then(function () {
26354 conversation._setUnreadMessagesMentioned(mentioned);
26355
26356 var countNotUpdated = unread === internal(conversation).unreadMessagesCount;
26357 if (countNotUpdated) return null; // to be filtered
26358 // manipulate internal property directly to skip unreadmessagescountupdate event
26359
26360 internal(conversation).unreadMessagesCount = unread;
26361 return conversation;
26362 }); // filter conversations without unread count update
26363 })).then(function (conversations) {
26364 return conversations.filter(function (conversation) {
26365 return conversation;
26366 });
26367 })
26368 );
26369 }).then(function (conversations) {
26370 if (conversations.length) {
26371 /**
26372 * 未读消息数目更新
26373 * @event IMClient#UNREAD_MESSAGES_COUNT_UPDATE
26374 * @since 3.4.0
26375 * @param {Conversation[]} conversations 未读消息数目有更新的对话列表
26376 */
26377 _this2.emit(UNREAD_MESSAGES_COUNT_UPDATE$1, conversations);
26378 }
26379 });
26380 };
26381
26382 _proto._dispatchRcpMessage = /*#__PURE__*/function () {
26383 var _dispatchRcpMessage2 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee3(message) {
26384 var rcpMessage, read, conversationId, messageId, timestamp, conversation;
26385 return regenerator.wrap(function _callee3$(_context3) {
26386 while (1) {
26387 switch (_context3.prev = _context3.next) {
26388 case 0:
26389 rcpMessage = message.rcpMessage, read = message.rcpMessage.read;
26390 conversationId = rcpMessage.cid;
26391 messageId = rcpMessage.id;
26392 timestamp = decodeDate(rcpMessage.t);
26393 conversation = this._conversationCache.get(conversationId); // conversation not cached means the client does not send the message
26394 // during this session
26395
26396 if (conversation) {
26397 _context3.next = 7;
26398 break;
26399 }
26400
26401 return _context3.abrupt("return");
26402
26403 case 7:
26404 conversation._handleReceipt({
26405 messageId: messageId,
26406 timestamp: timestamp,
26407 read: read
26408 });
26409
26410 case 8:
26411 case "end":
26412 return _context3.stop();
26413 }
26414 }
26415 }, _callee3, this);
26416 }));
26417
26418 function _dispatchRcpMessage(_x3) {
26419 return _dispatchRcpMessage2.apply(this, arguments);
26420 }
26421
26422 return _dispatchRcpMessage;
26423 }();
26424
26425 _proto._dispatchPatchMessage = function _dispatchPatchMessage(_ref3) {
26426 var _this3 = this;
26427
26428 var patches = _ref3.patchMessage.patches;
26429 // ensure all converstions are cached
26430 return this.getConversations(patches.map(function (patch) {
26431 return patch.cid;
26432 })).then(function () {
26433 return Promise.all(patches.map(function (_ref4) {
26434 var cid = _ref4.cid,
26435 mid = _ref4.mid,
26436 timestamp = _ref4.timestamp,
26437 recall = _ref4.recall,
26438 data = _ref4.data,
26439 patchTimestamp = _ref4.patchTimestamp,
26440 from = _ref4.from,
26441 binaryMsg = _ref4.binaryMsg,
26442 mentionAll = _ref4.mentionAll,
26443 mentionPids = _ref4.mentionPids,
26444 patchCode = _ref4.patchCode,
26445 patchReason = _ref4.patchReason;
26446
26447 var conversation = _this3._conversationCache.get(cid); // deleted conversation
26448
26449
26450 if (!conversation) return null;
26451 return _this3._messageParser.parse(binaryMsg || data).then(function (message) {
26452 var patchTime = getTime(decodeDate(patchTimestamp));
26453 var messageProps = {
26454 id: mid,
26455 cid: cid,
26456 timestamp: timestamp,
26457 updatedAt: patchTime,
26458 from: from,
26459 mentionList: mentionPids,
26460 mentionedAll: mentionAll
26461 };
26462 Object.assign(message, messageProps);
26463
26464 message._setStatus(MessageStatus.SENT);
26465
26466 message._updateMentioned(_this3.id);
26467
26468 if (internal(_this3).lastPatchTime < patchTime) {
26469 internal(_this3).lastPatchTime = patchTime;
26470 } // update conversation lastMessage
26471
26472
26473 if (conversation.lastMessage && conversation.lastMessage.id === mid) {
26474 conversation.lastMessage = message; // eslint-disable-line no-param-reassign
26475 }
26476
26477 var reason;
26478
26479 if (patchCode) {
26480 reason = {
26481 code: patchCode.toNumber(),
26482 detail: patchReason
26483 };
26484 }
26485
26486 if (recall) {
26487 /**
26488 * 消息被撤回
26489 * @event IMClient#MESSAGE_RECALL
26490 * @param {AVMessage} message 被撤回的消息
26491 * @param {ConversationBase} conversation 消息所在的会话
26492 * @param {PatchReason} [reason] 撤回的原因,不存在代表是发送者主动撤回
26493 */
26494 _this3.emit(MESSAGE_RECALL$1, message, conversation, reason);
26495 /**
26496 * 消息被撤回
26497 * @event ConversationBase#MESSAGE_RECALL
26498 * @param {AVMessage} message 被撤回的消息
26499 * @param {PatchReason} [reason] 撤回的原因,不存在代表是发送者主动撤回
26500 */
26501
26502
26503 conversation.emit(MESSAGE_RECALL$1, message, reason);
26504 } else {
26505 /**
26506 * 消息被修改
26507 * @event IMClient#MESSAGE_UPDATE
26508 * @param {AVMessage} message 被修改的消息
26509 * @param {ConversationBase} conversation 消息所在的会话
26510 * @param {PatchReason} [reason] 修改的原因,不存在代表是发送者主动修改
26511 */
26512 _this3.emit(MESSAGE_UPDATE$1, message, conversation, reason);
26513 /**
26514 * 消息被修改
26515 * @event ConversationBase#MESSAGE_UPDATE
26516 * @param {AVMessage} message 被修改的消息
26517 * @param {PatchReason} [reason] 修改的原因,不存在代表是发送者主动修改
26518 */
26519
26520
26521 conversation.emit(MESSAGE_UPDATE$1, message, reason);
26522 }
26523 });
26524 }));
26525 });
26526 };
26527
26528 _proto._dispatchConvMessage = /*#__PURE__*/function () {
26529 var _dispatchConvMessage2 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee4(message) {
26530 var convMessage, _message$convMessage, initBy, m, info, attr, conversation, payload, _payload, _payload2, _payload3, _payload4, _payload5, _payload6, _payload7, _payload8, _payload9, _payload10, _payload11, pid, role, _internal, memberInfoMap, memberInfo, _payload12, attributes, _payload13;
26531
26532 return regenerator.wrap(function _callee4$(_context4) {
26533 while (1) {
26534 switch (_context4.prev = _context4.next) {
26535 case 0:
26536 convMessage = message.convMessage, _message$convMessage = message.convMessage, initBy = _message$convMessage.initBy, m = _message$convMessage.m, info = _message$convMessage.info, attr = _message$convMessage.attr;
26537 _context4.next = 3;
26538 return this.getConversation(convMessage.cid);
26539
26540 case 3:
26541 conversation = _context4.sent;
26542 _context4.t0 = message.op;
26543 _context4.next = _context4.t0 === OpType.joined ? 7 : _context4.t0 === OpType.left ? 12 : _context4.t0 === OpType.members_joined ? 17 : _context4.t0 === OpType.members_left ? 22 : _context4.t0 === OpType.members_blocked ? 27 : _context4.t0 === OpType.members_unblocked ? 31 : _context4.t0 === OpType.blocked ? 35 : _context4.t0 === OpType.unblocked ? 39 : _context4.t0 === OpType.members_shutuped ? 43 : _context4.t0 === OpType.members_unshutuped ? 47 : _context4.t0 === OpType.shutuped ? 51 : _context4.t0 === OpType.unshutuped ? 55 : _context4.t0 === OpType.member_info_changed ? 59 : _context4.t0 === OpType.updated ? 71 : 77;
26544 break;
26545
26546 case 7:
26547 conversation._addMembers([this.id]);
26548
26549 payload = {
26550 invitedBy: initBy
26551 };
26552 /**
26553 * 当前用户被添加至某个对话
26554 * @event IMClient#INVITED
26555 * @param {Object} payload
26556 * @param {String} payload.invitedBy 邀请者 id
26557 * @param {ConversationBase} conversation
26558 */
26559
26560 this.emit(INVITED$1, payload, conversation);
26561 /**
26562 * 当前用户被添加至当前对话
26563 * @event ConversationBase#INVITED
26564 * @param {Object} payload
26565 * @param {String} payload.invitedBy 该移除操作的发起者 id
26566 */
26567
26568 conversation.emit(INVITED$1, payload);
26569 return _context4.abrupt("return");
26570
26571 case 12:
26572 conversation._removeMembers([this.id]);
26573
26574 _payload = {
26575 kickedBy: initBy
26576 };
26577 /**
26578 * 当前用户被从某个对话中移除
26579 * @event IMClient#KICKED
26580 * @param {Object} payload
26581 * @param {String} payload.kickedBy 该移除操作的发起者 id
26582 * @param {ConversationBase} conversation
26583 */
26584
26585 this.emit(KICKED$1, _payload, conversation);
26586 /**
26587 * 当前用户被从当前对话中移除
26588 * @event ConversationBase#KICKED
26589 * @param {Object} payload
26590 * @param {String} payload.kickedBy 该移除操作的发起者 id
26591 */
26592
26593 conversation.emit(KICKED$1, _payload);
26594 return _context4.abrupt("return");
26595
26596 case 17:
26597 conversation._addMembers(m);
26598
26599 _payload2 = {
26600 invitedBy: initBy,
26601 members: m
26602 };
26603 /**
26604 * 有用户被添加至某个对话
26605 * @event IMClient#MEMBERS_JOINED
26606 * @param {Object} payload
26607 * @param {String[]} payload.members 被添加的用户 id 列表
26608 * @param {String} payload.invitedBy 邀请者 id
26609 * @param {ConversationBase} conversation
26610 */
26611
26612 this.emit(MEMBERS_JOINED$1, _payload2, conversation);
26613 /**
26614 * 有成员被添加至当前对话
26615 * @event ConversationBase#MEMBERS_JOINED
26616 * @param {Object} payload
26617 * @param {String[]} payload.members 被添加的成员 id 列表
26618 * @param {String} payload.invitedBy 邀请者 id
26619 */
26620
26621 conversation.emit(MEMBERS_JOINED$1, _payload2);
26622 return _context4.abrupt("return");
26623
26624 case 22:
26625 conversation._removeMembers(m);
26626
26627 _payload3 = {
26628 kickedBy: initBy,
26629 members: m
26630 };
26631 /**
26632 * 有成员被从某个对话中移除
26633 * @event IMClient#MEMBERS_LEFT
26634 * @param {Object} payload
26635 * @param {String[]} payload.members 被移除的成员 id 列表
26636 * @param {String} payload.kickedBy 该移除操作的发起者 id
26637 * @param {ConversationBase} conversation
26638 */
26639
26640 this.emit(MEMBERS_LEFT$1, _payload3, conversation);
26641 /**
26642 * 有成员被从当前对话中移除
26643 * @event ConversationBase#MEMBERS_LEFT
26644 * @param {Object} payload
26645 * @param {String[]} payload.members 被移除的成员 id 列表
26646 * @param {String} payload.kickedBy 该移除操作的发起者 id
26647 */
26648
26649 conversation.emit(MEMBERS_LEFT$1, _payload3);
26650 return _context4.abrupt("return");
26651
26652 case 27:
26653 _payload4 = {
26654 blockedBy: initBy,
26655 members: m
26656 };
26657 /**
26658 * 有成员被加入某个对话的黑名单
26659 * @event IMClient#MEMBERS_BLOCKED
26660 * @param {Object} payload
26661 * @param {String[]} payload.members 成员 id 列表
26662 * @param {String} payload.blockedBy 该操作的发起者 id
26663 * @param {ConversationBase} conversation
26664 */
26665
26666 this.emit(MEMBERS_BLOCKED$1, _payload4, conversation);
26667 /**
26668 * 有成员被加入当前对话的黑名单
26669 * @event ConversationBase#MEMBERS_BLOCKED
26670 * @param {Object} payload
26671 * @param {String[]} payload.members 成员 id 列表
26672 * @param {String} payload.blockedBy 该操作的发起者 id
26673 */
26674
26675 conversation.emit(MEMBERS_BLOCKED$1, _payload4);
26676 return _context4.abrupt("return");
26677
26678 case 31:
26679 _payload5 = {
26680 unblockedBy: initBy,
26681 members: m
26682 };
26683 /**
26684 * 有成员被移出某个对话的黑名单
26685 * @event IMClient#MEMBERS_UNBLOCKED
26686 * @param {Object} payload
26687 * @param {String[]} payload.members 成员 id 列表
26688 * @param {String} payload.unblockedBy 该操作的发起者 id
26689 * @param {ConversationBase} conversation
26690 */
26691
26692 this.emit(MEMBERS_UNBLOCKED$1, _payload5, conversation);
26693 /**
26694 * 有成员被移出当前对话的黑名单
26695 * @event ConversationBase#MEMBERS_UNBLOCKED
26696 * @param {Object} payload
26697 * @param {String[]} payload.members 成员 id 列表
26698 * @param {String} payload.unblockedBy 该操作的发起者 id
26699 */
26700
26701 conversation.emit(MEMBERS_UNBLOCKED$1, _payload5);
26702 return _context4.abrupt("return");
26703
26704 case 35:
26705 _payload6 = {
26706 blockedBy: initBy
26707 };
26708 /**
26709 * 当前用户被加入某个对话的黑名单
26710 * @event IMClient#BLOCKED
26711 * @param {Object} payload
26712 * @param {String} payload.blockedBy 该操作的发起者 id
26713 * @param {ConversationBase} conversation
26714 */
26715
26716 this.emit(BLOCKED$1, _payload6, conversation);
26717 /**
26718 * 当前用户被加入当前对话的黑名单
26719 * @event ConversationBase#BLOCKED
26720 * @param {Object} payload
26721 * @param {String} payload.blockedBy 该操作的发起者 id
26722 */
26723
26724 conversation.emit(BLOCKED$1, _payload6);
26725 return _context4.abrupt("return");
26726
26727 case 39:
26728 _payload7 = {
26729 unblockedBy: initBy
26730 };
26731 /**
26732 * 当前用户被移出某个对话的黑名单
26733 * @event IMClient#UNBLOCKED
26734 * @param {Object} payload
26735 * @param {String} payload.unblockedBy 该操作的发起者 id
26736 * @param {ConversationBase} conversation
26737 */
26738
26739 this.emit(UNBLOCKED$1, _payload7, conversation);
26740 /**
26741 * 当前用户被移出当前对话的黑名单
26742 * @event ConversationBase#UNBLOCKED
26743 * @param {Object} payload
26744 * @param {String} payload.unblockedBy 该操作的发起者 id
26745 */
26746
26747 conversation.emit(UNBLOCKED$1, _payload7);
26748 return _context4.abrupt("return");
26749
26750 case 43:
26751 _payload8 = {
26752 mutedBy: initBy,
26753 members: m
26754 };
26755 /**
26756 * 有成员在某个对话中被禁言
26757 * @event IMClient#MEMBERS_MUTED
26758 * @param {Object} payload
26759 * @param {String[]} payload.members 成员 id 列表
26760 * @param {String} payload.mutedBy 该操作的发起者 id
26761 * @param {ConversationBase} conversation
26762 */
26763
26764 this.emit(MEMBERS_MUTED$1, _payload8, conversation);
26765 /**
26766 * 有成员在当前对话中被禁言
26767 * @event ConversationBase#MEMBERS_MUTED
26768 * @param {Object} payload
26769 * @param {String[]} payload.members 成员 id 列表
26770 * @param {String} payload.mutedBy 该操作的发起者 id
26771 */
26772
26773 conversation.emit(MEMBERS_MUTED$1, _payload8);
26774 return _context4.abrupt("return");
26775
26776 case 47:
26777 _payload9 = {
26778 unmutedBy: initBy,
26779 members: m
26780 };
26781 /**
26782 * 有成员在某个对话中被解除禁言
26783 * @event IMClient#MEMBERS_UNMUTED
26784 * @param {Object} payload
26785 * @param {String[]} payload.members 成员 id 列表
26786 * @param {String} payload.unmutedBy 该操作的发起者 id
26787 * @param {ConversationBase} conversation
26788 */
26789
26790 this.emit(MEMBERS_UNMUTED$1, _payload9, conversation);
26791 /**
26792 * 有成员在当前对话中被解除禁言
26793 * @event ConversationBase#MEMBERS_UNMUTED
26794 * @param {Object} payload
26795 * @param {String[]} payload.members 成员 id 列表
26796 * @param {String} payload.unmutedBy 该操作的发起者 id
26797 */
26798
26799 conversation.emit(MEMBERS_UNMUTED$1, _payload9);
26800 return _context4.abrupt("return");
26801
26802 case 51:
26803 _payload10 = {
26804 mutedBy: initBy
26805 };
26806 /**
26807 * 有成员在某个对话中被禁言
26808 * @event IMClient#MUTED
26809 * @param {Object} payload
26810 * @param {String} payload.mutedBy 该操作的发起者 id
26811 * @param {ConversationBase} conversation
26812 */
26813
26814 this.emit(MUTED$1, _payload10, conversation);
26815 /**
26816 * 有成员在当前对话中被禁言
26817 * @event ConversationBase#MUTED
26818 * @param {Object} payload
26819 * @param {String} payload.mutedBy 该操作的发起者 id
26820 */
26821
26822 conversation.emit(MUTED$1, _payload10);
26823 return _context4.abrupt("return");
26824
26825 case 55:
26826 _payload11 = {
26827 unmutedBy: initBy
26828 };
26829 /**
26830 * 有成员在某个对话中被解除禁言
26831 * @event IMClient#UNMUTED
26832 * @param {Object} payload
26833 * @param {String} payload.unmutedBy 该操作的发起者 id
26834 * @param {ConversationBase} conversation
26835 */
26836
26837 this.emit(UNMUTED$1, _payload11, conversation);
26838 /**
26839 * 有成员在当前对话中被解除禁言
26840 * @event ConversationBase#UNMUTED
26841 * @param {Object} payload
26842 * @param {String} payload.unmutedBy 该操作的发起者 id
26843 */
26844
26845 conversation.emit(UNMUTED$1, _payload11);
26846 return _context4.abrupt("return");
26847
26848 case 59:
26849 pid = info.pid, role = info.role;
26850 _internal = internal(conversation), memberInfoMap = _internal.memberInfoMap; // 如果不存在缓存,且不是 role 的更新,则不通知
26851
26852 if (!(!memberInfoMap && !role)) {
26853 _context4.next = 63;
26854 break;
26855 }
26856
26857 return _context4.abrupt("return");
26858
26859 case 63:
26860 _context4.next = 65;
26861 return conversation.getMemberInfo(pid);
26862
26863 case 65:
26864 memberInfo = _context4.sent;
26865 internal(memberInfo).role = role;
26866 _payload12 = {
26867 member: pid,
26868 memberInfo: memberInfo,
26869 updatedBy: initBy
26870 };
26871 /**
26872 * 有成员的对话信息被更新
26873 * @event IMClient#MEMBER_INFO_UPDATED
26874 * @param {Object} payload
26875 * @param {String} payload.member 被更新对话信息的成员 id
26876 * @param {ConversationMumberInfo} payload.memberInfo 被更新的成员对话信息
26877 * @param {String} payload.updatedBy 该操作的发起者 id
26878 * @param {ConversationBase} conversation
26879 */
26880
26881 this.emit(MEMBER_INFO_UPDATED$1, _payload12, conversation);
26882 /**
26883 * 有成员的对话信息被更新
26884 * @event ConversationBase#MEMBER_INFO_UPDATED
26885 * @param {Object} payload
26886 * @param {String} payload.member 被更新对话信息的成员 id
26887 * @param {ConversationMumberInfo} payload.memberInfo 被更新的成员对话信息
26888 * @param {String} payload.updatedBy 该操作的发起者 id
26889 */
26890
26891 conversation.emit(MEMBER_INFO_UPDATED$1, _payload12);
26892 return _context4.abrupt("return");
26893
26894 case 71:
26895 attributes = decode(JSON.parse(attr.data));
26896
26897 conversation._updateServerAttributes(attributes);
26898
26899 _payload13 = {
26900 attributes: attributes,
26901 updatedBy: initBy
26902 };
26903 /**
26904 * 该对话信息被更新
26905 * @event IMClient#CONVERSATION_INFO_UPDATED
26906 * @param {Object} payload
26907 * @param {Object} payload.attributes 被更新的属性
26908 * @param {String} payload.updatedBy 该操作的发起者 id
26909 * @param {ConversationBase} conversation
26910 */
26911
26912 this.emit(CONVERSATION_INFO_UPDATED$1, _payload13, conversation);
26913 /**
26914 * 有对话信息被更新
26915 * @event ConversationBase#INFO_UPDATED
26916 * @param {Object} payload
26917 * @param {Object} payload.attributes 被更新的属性
26918 * @param {String} payload.updatedBy 该操作的发起者 id
26919 */
26920
26921 conversation.emit(INFO_UPDATED$1, _payload13);
26922 return _context4.abrupt("return");
26923
26924 case 77:
26925 this.emit(UNHANDLED_MESSAGE$1, message);
26926 throw new Error('Unrecognized conversation command');
26927
26928 case 79:
26929 case "end":
26930 return _context4.stop();
26931 }
26932 }
26933 }, _callee4, this);
26934 }));
26935
26936 function _dispatchConvMessage(_x4) {
26937 return _dispatchConvMessage2.apply(this, arguments);
26938 }
26939
26940 return _dispatchConvMessage;
26941 }();
26942
26943 _proto._dispatchDirectMessage = function _dispatchDirectMessage(originalMessage) {
26944 var _this4 = this;
26945
26946 var directMessage = originalMessage.directMessage,
26947 _originalMessage$dire = originalMessage.directMessage,
26948 id = _originalMessage$dire.id,
26949 cid = _originalMessage$dire.cid,
26950 fromPeerId = _originalMessage$dire.fromPeerId,
26951 timestamp = _originalMessage$dire.timestamp,
26952 _transient = _originalMessage$dire["transient"],
26953 patchTimestamp = _originalMessage$dire.patchTimestamp,
26954 mentionPids = _originalMessage$dire.mentionPids,
26955 mentionAll = _originalMessage$dire.mentionAll,
26956 binaryMsg = _originalMessage$dire.binaryMsg,
26957 msg = _originalMessage$dire.msg;
26958 var content = binaryMsg ? binaryMsg.toArrayBuffer() : msg;
26959 return Promise.all([this.getConversation(directMessage.cid), this._messageParser.parse(content)]).then(function (_ref5) {
26960 var _ref6 = slicedToArray(_ref5, 2),
26961 conversation = _ref6[0],
26962 message = _ref6[1];
26963
26964 // deleted conversation
26965 if (!conversation) return undefined;
26966 var messageProps = {
26967 id: id,
26968 cid: cid,
26969 timestamp: timestamp,
26970 updatedAt: patchTimestamp,
26971 from: fromPeerId,
26972 mentionList: mentionPids,
26973 mentionedAll: mentionAll
26974 };
26975 Object.assign(message, messageProps);
26976
26977 message._updateMentioned(_this4.id);
26978
26979 message._setStatus(MessageStatus.SENT); // filter outgoing message sent from another device
26980
26981
26982 if (message.from !== _this4.id) {
26983 if (!(_transient || conversation["transient"])) {
26984 _this4._sendAck(message);
26985 }
26986 }
26987
26988 return _this4._dispatchParsedMessage(message, conversation);
26989 });
26990 };
26991
26992 _proto._dispatchParsedMessage = function _dispatchParsedMessage(message, conversation) {
26993 var _this5 = this;
26994
26995 // beforeMessageDispatch hook
26996 return applyDispatcher(this._plugins.beforeMessageDispatch, [message, conversation]).then(function (shouldDispatch) {
26997 if (shouldDispatch === false) return;
26998 conversation.lastMessage = message; // eslint-disable-line no-param-reassign
26999
27000 conversation.lastMessageAt = message.timestamp; // eslint-disable-line no-param-reassign
27001 // filter outgoing message sent from another device
27002
27003 if (message.from !== _this5.id) {
27004 conversation.unreadMessagesCount += 1; // eslint-disable-line no-param-reassign
27005
27006 if (message.mentioned) conversation._setUnreadMessagesMentioned(true);
27007 }
27008 /**
27009 * 当前用户收到消息
27010 * @event IMClient#MESSAGE
27011 * @param {Message} message
27012 * @param {ConversationBase} conversation 收到消息的对话
27013 */
27014
27015
27016 _this5.emit(MESSAGE$2, message, conversation);
27017 /**
27018 * 当前对话收到消息
27019 * @event ConversationBase#MESSAGE
27020 * @param {Message} message
27021 */
27022
27023
27024 conversation.emit(MESSAGE$2, message);
27025 });
27026 };
27027
27028 _proto._sendAck = function _sendAck(message) {
27029 this._debug('send ack for %O', message);
27030
27031 var cid = message.cid;
27032
27033 if (!cid) {
27034 throw new Error('missing cid');
27035 }
27036
27037 if (!this._ackMessageBuffer[cid]) {
27038 this._ackMessageBuffer[cid] = [];
27039 }
27040
27041 this._ackMessageBuffer[cid].push(message);
27042
27043 return this._doSendAck();
27044 } // jsdoc-ignore-start
27045 ;
27046
27047 _proto. // jsdoc-ignore-end
27048 _doSendAck = function _doSendAck() {
27049 var _this6 = this;
27050
27051 // if not connected, just skip everything
27052 if (!this._connection.is('connected')) return;
27053
27054 this._debug('do send ack %O', this._ackMessageBuffer);
27055
27056 Promise.all(Object.keys(this._ackMessageBuffer).map(function (cid) {
27057 var convAckMessages = _this6._ackMessageBuffer[cid];
27058 var timestamps = convAckMessages.map(function (message) {
27059 return message.timestamp;
27060 });
27061 var command = new GenericCommand({
27062 cmd: 'ack',
27063 ackMessage: new AckCommand({
27064 cid: cid,
27065 fromts: Math.min.apply(null, timestamps),
27066 tots: Math.max.apply(null, timestamps)
27067 })
27068 });
27069 delete _this6._ackMessageBuffer[cid];
27070 return _this6._send(command, false)["catch"](function (error) {
27071 _this6._debug('send ack failed: %O', error);
27072
27073 _this6._ackMessageBuffer[cid] = convAckMessages;
27074 });
27075 }));
27076 };
27077
27078 _proto._omitPeerId = function _omitPeerId(value) {
27079 internal(this).peerIdOmittable = value;
27080 };
27081
27082 _proto._send = function _send(cmd) {
27083 var _this$_connection;
27084
27085 var command = cmd;
27086
27087 if (!internal(this).peerIdOmittable && this.id) {
27088 command.peerId = this.id;
27089 }
27090
27091 for (var _len3 = arguments.length, args = new Array(_len3 > 1 ? _len3 - 1 : 0), _key3 = 1; _key3 < _len3; _key3++) {
27092 args[_key3 - 1] = arguments[_key3];
27093 }
27094
27095 return (_this$_connection = this._connection).send.apply(_this$_connection, [command].concat(args));
27096 };
27097
27098 _proto._open = /*#__PURE__*/function () {
27099 var _open2 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee5(appId, tag, deviceId) {
27100 var isReconnect,
27101 _internal2,
27102 lastUnreadNotifTime,
27103 lastPatchTime,
27104 lastNotificationTime,
27105 command,
27106 signatureResult,
27107 sessionToken,
27108 resCommand,
27109 _resCommand,
27110 peerId,
27111 sessionMessage,
27112 _resCommand$sessionMe,
27113 token,
27114 tokenTTL,
27115 code,
27116 serverTs,
27117 serverTime,
27118 _args5 = arguments;
27119
27120 return regenerator.wrap(function _callee5$(_context5) {
27121 while (1) {
27122 switch (_context5.prev = _context5.next) {
27123 case 0:
27124 isReconnect = _args5.length > 3 && _args5[3] !== undefined ? _args5[3] : false;
27125
27126 this._debug('open session');
27127
27128 _internal2 = internal(this), lastUnreadNotifTime = _internal2.lastUnreadNotifTime, lastPatchTime = _internal2.lastPatchTime, lastNotificationTime = _internal2.lastNotificationTime;
27129 command = new GenericCommand({
27130 cmd: 'session',
27131 op: 'open',
27132 appId: appId,
27133 peerId: this.id,
27134 sessionMessage: new SessionCommand({
27135 ua: "js/".concat(version),
27136 r: isReconnect,
27137 lastUnreadNotifTime: lastUnreadNotifTime,
27138 lastPatchTime: lastPatchTime,
27139 configBitmap: configBitmap
27140 })
27141 });
27142
27143 if (isReconnect) {
27144 _context5.next = 13;
27145 break;
27146 }
27147
27148 Object.assign(command.sessionMessage, trim({
27149 tag: tag,
27150 deviceId: deviceId
27151 }));
27152
27153 if (!this.options.signatureFactory) {
27154 _context5.next = 11;
27155 break;
27156 }
27157
27158 _context5.next = 9;
27159 return runSignatureFactory(this.options.signatureFactory, [this._identity]);
27160
27161 case 9:
27162 signatureResult = _context5.sent;
27163 Object.assign(command.sessionMessage, keyRemap({
27164 signature: 's',
27165 timestamp: 't',
27166 nonce: 'n'
27167 }, signatureResult));
27168
27169 case 11:
27170 _context5.next = 17;
27171 break;
27172
27173 case 13:
27174 _context5.next = 15;
27175 return this._sessionManager.getSessionToken({
27176 autoRefresh: false
27177 });
27178
27179 case 15:
27180 sessionToken = _context5.sent;
27181
27182 if (sessionToken && sessionToken !== Expirable.EXPIRED) {
27183 Object.assign(command.sessionMessage, {
27184 st: sessionToken
27185 });
27186 }
27187
27188 case 17:
27189 _context5.prev = 17;
27190 _context5.next = 20;
27191 return this._send(command);
27192
27193 case 20:
27194 resCommand = _context5.sent;
27195 _context5.next = 32;
27196 break;
27197
27198 case 23:
27199 _context5.prev = 23;
27200 _context5.t0 = _context5["catch"](17);
27201
27202 if (!(_context5.t0.code === ErrorCode.SESSION_TOKEN_EXPIRED)) {
27203 _context5.next = 31;
27204 break;
27205 }
27206
27207 if (this._sessionManager) {
27208 _context5.next = 28;
27209 break;
27210 }
27211
27212 throw new Error('Unexpected session expiration');
27213
27214 case 28:
27215 debug$b('Session token expired, reopening');
27216
27217 this._sessionManager.revoke();
27218
27219 return _context5.abrupt("return", this._open(appId, tag, deviceId, isReconnect));
27220
27221 case 31:
27222 throw _context5.t0;
27223
27224 case 32:
27225 _resCommand = resCommand, peerId = _resCommand.peerId, sessionMessage = _resCommand.sessionMessage, _resCommand$sessionMe = _resCommand.sessionMessage, token = _resCommand$sessionMe.st, tokenTTL = _resCommand$sessionMe.stTtl, code = _resCommand$sessionMe.code, serverTs = _resCommand.serverTs;
27226
27227 if (!code) {
27228 _context5.next = 35;
27229 break;
27230 }
27231
27232 throw createError(sessionMessage);
27233
27234 case 35:
27235 if (peerId) {
27236 this.id = peerId;
27237 if (!this._identity) this._identity = peerId;
27238
27239 if (token) {
27240 this._sessionManager = this._sessionManager || this._createSessionManager();
27241
27242 this._sessionManager.setSessionToken(token, tokenTTL);
27243 }
27244
27245 serverTime = getTime(decodeDate(serverTs));
27246
27247 if (serverTs) {
27248 internal(this).lastPatchTime = serverTime;
27249 }
27250
27251 if (lastNotificationTime) {
27252 // Do not await for it as this is failable
27253 this._syncNotifications(lastNotificationTime)["catch"](function (error) {
27254 return console.warn('Syncing notifications failed:', error);
27255 });
27256 } else {
27257 // Set timestamp to now for next reconnection
27258 internal(this).lastNotificationTime = serverTime;
27259 }
27260 } else {
27261 console.warn('Unexpected session opened without peerId.');
27262 }
27263
27264 return _context5.abrupt("return", undefined);
27265
27266 case 37:
27267 case "end":
27268 return _context5.stop();
27269 }
27270 }
27271 }, _callee5, this, [[17, 23]]);
27272 }));
27273
27274 function _open(_x5, _x6, _x7) {
27275 return _open2.apply(this, arguments);
27276 }
27277
27278 return _open;
27279 }();
27280
27281 _proto._syncNotifications = /*#__PURE__*/function () {
27282 var _syncNotifications2 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee6(timestamp) {
27283 var _this7 = this;
27284
27285 var _yield$this$_fetchNot, hasMore, notifications;
27286
27287 return regenerator.wrap(function _callee6$(_context6) {
27288 while (1) {
27289 switch (_context6.prev = _context6.next) {
27290 case 0:
27291 _context6.next = 2;
27292 return this._fetchNotifications(timestamp);
27293
27294 case 2:
27295 _yield$this$_fetchNot = _context6.sent;
27296 hasMore = _yield$this$_fetchNot.hasMore;
27297 notifications = _yield$this$_fetchNot.notifications;
27298 notifications.forEach(function (notification) {
27299 var cmd = notification.cmd,
27300 op = notification.op,
27301 serverTs = notification.serverTs,
27302 notificationType = notification.notificationType,
27303 payload = objectWithoutProperties(notification, ["cmd", "op", "serverTs", "notificationType"]);
27304
27305 _this7._dispatchCommand(defineProperty({
27306 cmd: CommandType[cmd],
27307 op: OpType[op],
27308 serverTs: serverTs,
27309 notificationType: notificationType
27310 }, "".concat(cmd, "Message"), payload));
27311 });
27312
27313 if (!hasMore) {
27314 _context6.next = 8;
27315 break;
27316 }
27317
27318 return _context6.abrupt("return", this._syncNotifications(internal(this).lastNotificationTime));
27319
27320 case 8:
27321 return _context6.abrupt("return", undefined);
27322
27323 case 9:
27324 case "end":
27325 return _context6.stop();
27326 }
27327 }
27328 }, _callee6, this);
27329 }));
27330
27331 function _syncNotifications(_x8) {
27332 return _syncNotifications2.apply(this, arguments);
27333 }
27334
27335 return _syncNotifications;
27336 }();
27337
27338 _proto._fetchNotifications = /*#__PURE__*/function () {
27339 var _fetchNotifications2 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee7(timestamp) {
27340 return regenerator.wrap(function _callee7$(_context7) {
27341 while (1) {
27342 switch (_context7.prev = _context7.next) {
27343 case 0:
27344 return _context7.abrupt("return", this._requestWithSessionToken({
27345 method: 'GET',
27346 path: '/rtm/notifications',
27347 query: {
27348 start_ts: timestamp,
27349 notification_type: 'permanent'
27350 }
27351 }));
27352
27353 case 1:
27354 case "end":
27355 return _context7.stop();
27356 }
27357 }
27358 }, _callee7, this);
27359 }));
27360
27361 function _fetchNotifications(_x9) {
27362 return _fetchNotifications2.apply(this, arguments);
27363 }
27364
27365 return _fetchNotifications;
27366 }();
27367
27368 _proto._createSessionManager = function _createSessionManager() {
27369 var _this8 = this;
27370
27371 debug$b('create SessionManager');
27372 return new SessionManager({
27373 onBeforeGetSessionToken: this._connection.checkConnectionAvailability.bind(this._connection),
27374 refresh: function refresh(manager, expiredSessionToken) {
27375 return manager.setSessionTokenAsync(Promise.resolve(new GenericCommand({
27376 cmd: 'session',
27377 op: 'refresh',
27378 sessionMessage: new SessionCommand({
27379 ua: "js/".concat(version),
27380 st: expiredSessionToken
27381 })
27382 })).then( /*#__PURE__*/function () {
27383 var _ref7 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee8(command) {
27384 var signatureResult;
27385 return regenerator.wrap(function _callee8$(_context8) {
27386 while (1) {
27387 switch (_context8.prev = _context8.next) {
27388 case 0:
27389 if (!_this8.options.signatureFactory) {
27390 _context8.next = 5;
27391 break;
27392 }
27393
27394 _context8.next = 3;
27395 return runSignatureFactory(_this8.options.signatureFactory, [_this8._identity]);
27396
27397 case 3:
27398 signatureResult = _context8.sent;
27399 Object.assign(command.sessionMessage, keyRemap({
27400 signature: 's',
27401 timestamp: 't',
27402 nonce: 'n'
27403 }, signatureResult));
27404
27405 case 5:
27406 return _context8.abrupt("return", command);
27407
27408 case 6:
27409 case "end":
27410 return _context8.stop();
27411 }
27412 }
27413 }, _callee8);
27414 }));
27415
27416 return function (_x10) {
27417 return _ref7.apply(this, arguments);
27418 };
27419 }()).then(_this8._send.bind(_this8)).then(function (_ref8) {
27420 var _ref8$sessionMessage = _ref8.sessionMessage,
27421 token = _ref8$sessionMessage.st,
27422 ttl = _ref8$sessionMessage.stTtl;
27423 return [token, ttl];
27424 }));
27425 }
27426 });
27427 };
27428
27429 _proto._requestWithSessionToken = /*#__PURE__*/function () {
27430 var _requestWithSessionToken2 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee9(_ref9) {
27431 var headers, query, params, sessionToken;
27432 return regenerator.wrap(function _callee9$(_context9) {
27433 while (1) {
27434 switch (_context9.prev = _context9.next) {
27435 case 0:
27436 headers = _ref9.headers, query = _ref9.query, params = objectWithoutProperties(_ref9, ["headers", "query"]);
27437 _context9.next = 3;
27438 return this._sessionManager.getSessionToken();
27439
27440 case 3:
27441 sessionToken = _context9.sent;
27442 return _context9.abrupt("return", this._request(_objectSpread$8({
27443 headers: _objectSpread$8({
27444 'X-LC-IM-Session-Token': sessionToken
27445 }, headers),
27446 query: _objectSpread$8({
27447 client_id: this.id
27448 }, query)
27449 }, params)));
27450
27451 case 5:
27452 case "end":
27453 return _context9.stop();
27454 }
27455 }
27456 }, _callee9, this);
27457 }));
27458
27459 function _requestWithSessionToken(_x11) {
27460 return _requestWithSessionToken2.apply(this, arguments);
27461 }
27462
27463 return _requestWithSessionToken;
27464 }()
27465 /**
27466 * 关闭客户端
27467 * @return {Promise}
27468 */
27469 ;
27470
27471 _proto.close =
27472 /*#__PURE__*/
27473 function () {
27474 var _close = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee10() {
27475 var _ee, command;
27476
27477 return regenerator.wrap(function _callee10$(_context10) {
27478 while (1) {
27479 switch (_context10.prev = _context10.next) {
27480 case 0:
27481 this._debug('close session');
27482
27483 _ee = internal(this)._eventemitter;
27484
27485 _ee.emit('beforeclose');
27486
27487 if (!this._connection.is('connected')) {
27488 _context10.next = 7;
27489 break;
27490 }
27491
27492 command = new GenericCommand({
27493 cmd: 'session',
27494 op: 'close'
27495 });
27496 _context10.next = 7;
27497 return this._send(command);
27498
27499 case 7:
27500 _ee.emit('close');
27501
27502 this.emit(CLOSE$1, {
27503 code: 0
27504 });
27505
27506 case 9:
27507 case "end":
27508 return _context10.stop();
27509 }
27510 }
27511 }, _callee10, this);
27512 }));
27513
27514 function close() {
27515 return _close.apply(this, arguments);
27516 }
27517
27518 return close;
27519 }()
27520 /**
27521 * 获取 client 列表中在线的 client,每次查询最多 20 个 clientId,超出部分会被忽略
27522 * @param {String[]} clientIds 要查询的 client ids
27523 * @return {Primse.<String[]>} 在线的 client ids
27524 */
27525 ;
27526
27527 _proto.ping =
27528 /*#__PURE__*/
27529 function () {
27530 var _ping = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee11(clientIds) {
27531 var command, resCommand;
27532 return regenerator.wrap(function _callee11$(_context11) {
27533 while (1) {
27534 switch (_context11.prev = _context11.next) {
27535 case 0:
27536 this._debug('ping');
27537
27538 if (clientIds instanceof Array) {
27539 _context11.next = 3;
27540 break;
27541 }
27542
27543 throw new TypeError("clientIds ".concat(clientIds, " is not an Array"));
27544
27545 case 3:
27546 if (clientIds.length) {
27547 _context11.next = 5;
27548 break;
27549 }
27550
27551 return _context11.abrupt("return", Promise.resolve([]));
27552
27553 case 5:
27554 command = new GenericCommand({
27555 cmd: 'session',
27556 op: 'query',
27557 sessionMessage: new SessionCommand({
27558 sessionPeerIds: clientIds
27559 })
27560 });
27561 _context11.next = 8;
27562 return this._send(command);
27563
27564 case 8:
27565 resCommand = _context11.sent;
27566 return _context11.abrupt("return", resCommand.sessionMessage.onlineSessionPeerIds);
27567
27568 case 10:
27569 case "end":
27570 return _context11.stop();
27571 }
27572 }
27573 }, _callee11, this);
27574 }));
27575
27576 function ping(_x12) {
27577 return _ping.apply(this, arguments);
27578 }
27579
27580 return ping;
27581 }()
27582 /**
27583 * 获取某个特定的对话
27584 * @param {String} id 对话 id,对应 _Conversation 表中的 objectId
27585 * @param {Boolean} [noCache=false] 强制不从缓存中获取
27586 * @return {Promise.<ConversationBase>} 如果 id 对应的对话不存在则返回 null
27587 */
27588 ;
27589
27590 _proto.getConversation =
27591 /*#__PURE__*/
27592 function () {
27593 var _getConversation = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee12(id) {
27594 var noCache,
27595 cachedConversation,
27596 _args12 = arguments;
27597 return regenerator.wrap(function _callee12$(_context12) {
27598 while (1) {
27599 switch (_context12.prev = _context12.next) {
27600 case 0:
27601 noCache = _args12.length > 1 && _args12[1] !== undefined ? _args12[1] : false;
27602
27603 if (!(typeof id !== 'string')) {
27604 _context12.next = 3;
27605 break;
27606 }
27607
27608 throw new TypeError("".concat(id, " is not a String"));
27609
27610 case 3:
27611 if (noCache) {
27612 _context12.next = 7;
27613 break;
27614 }
27615
27616 cachedConversation = this._conversationCache.get(id);
27617
27618 if (!cachedConversation) {
27619 _context12.next = 7;
27620 break;
27621 }
27622
27623 return _context12.abrupt("return", cachedConversation);
27624
27625 case 7:
27626 if (!isTemporaryConversatrionId(id)) {
27627 _context12.next = 14;
27628 break;
27629 }
27630
27631 _context12.next = 10;
27632 return this._getTemporaryConversations([id]);
27633
27634 case 10:
27635 _context12.t0 = _context12.sent[0];
27636
27637 if (_context12.t0) {
27638 _context12.next = 13;
27639 break;
27640 }
27641
27642 _context12.t0 = null;
27643
27644 case 13:
27645 return _context12.abrupt("return", _context12.t0);
27646
27647 case 14:
27648 return _context12.abrupt("return", this.getQuery().equalTo('objectId', id).find().then(function (conversations) {
27649 return conversations[0] || null;
27650 }));
27651
27652 case 15:
27653 case "end":
27654 return _context12.stop();
27655 }
27656 }
27657 }, _callee12, this);
27658 }));
27659
27660 function getConversation(_x13) {
27661 return _getConversation.apply(this, arguments);
27662 }
27663
27664 return getConversation;
27665 }()
27666 /**
27667 * 通过 id 批量获取某个特定的对话
27668 * @since 3.4.0
27669 * @param {String[]} ids 对话 id 列表,对应 _Conversation 表中的 objectId
27670 * @param {Boolean} [noCache=false] 强制不从缓存中获取
27671 * @return {Promise.<ConversationBase[]>} 如果 id 对应的对话不存在则返回 null
27672 */
27673 ;
27674
27675 _proto.getConversations =
27676 /*#__PURE__*/
27677 function () {
27678 var _getConversations = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee13(ids) {
27679 var _this9 = this;
27680
27681 var noCache,
27682 remoteConversationIds,
27683 remoteTemporaryConversationIds,
27684 query,
27685 remoteTemporaryConversationsPromise,
27686 _args13 = arguments;
27687 return regenerator.wrap(function _callee13$(_context13) {
27688 while (1) {
27689 switch (_context13.prev = _context13.next) {
27690 case 0:
27691 noCache = _args13.length > 1 && _args13[1] !== undefined ? _args13[1] : false;
27692 remoteConversationIds = noCache ? ids : ids.filter(function (id) {
27693 return _this9._conversationCache.get(id) === null;
27694 });
27695
27696 if (!remoteConversationIds.length) {
27697 _context13.next = 9;
27698 break;
27699 }
27700
27701 remoteTemporaryConversationIds = remove_1(remoteConversationIds, isTemporaryConversatrionId);
27702 query = [];
27703
27704 if (remoteConversationIds.length) {
27705 query.push(this.getQuery().containedIn('objectId', remoteConversationIds).limit(999).find());
27706 }
27707
27708 if (remoteTemporaryConversationIds.length) {
27709 remoteTemporaryConversationsPromise = remoteTemporaryConversationIds.map(this._getTemporaryConversations.bind(this));
27710 query.push.apply(query, toConsumableArray(remoteTemporaryConversationsPromise));
27711 }
27712
27713 _context13.next = 9;
27714 return Promise.all(query);
27715
27716 case 9:
27717 return _context13.abrupt("return", ids.map(function (id) {
27718 return _this9._conversationCache.get(id);
27719 }));
27720
27721 case 10:
27722 case "end":
27723 return _context13.stop();
27724 }
27725 }
27726 }, _callee13, this);
27727 }));
27728
27729 function getConversations(_x14) {
27730 return _getConversations.apply(this, arguments);
27731 }
27732
27733 return getConversations;
27734 }();
27735
27736 _proto._getTemporaryConversations = /*#__PURE__*/function () {
27737 var _getTemporaryConversations2 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee14(ids) {
27738 var command, resCommand;
27739 return regenerator.wrap(function _callee14$(_context14) {
27740 while (1) {
27741 switch (_context14.prev = _context14.next) {
27742 case 0:
27743 command = new GenericCommand({
27744 cmd: 'conv',
27745 op: 'query',
27746 convMessage: new ConvCommand({
27747 tempConvIds: ids
27748 })
27749 });
27750 _context14.next = 3;
27751 return this._send(command);
27752
27753 case 3:
27754 resCommand = _context14.sent;
27755 return _context14.abrupt("return", this._handleQueryResults(resCommand));
27756
27757 case 5:
27758 case "end":
27759 return _context14.stop();
27760 }
27761 }
27762 }, _callee14, this);
27763 }));
27764
27765 function _getTemporaryConversations(_x15) {
27766 return _getTemporaryConversations2.apply(this, arguments);
27767 }
27768
27769 return _getTemporaryConversations;
27770 }()
27771 /**
27772 * 构造一个 ConversationQuery 来查询对话
27773 * @return {ConversationQuery.<PersistentConversation>}
27774 */
27775 ;
27776
27777 _proto.getQuery = function getQuery() {
27778 return new ConversationQuery(this);
27779 }
27780 /**
27781 * 构造一个 ConversationQuery 来查询聊天室
27782 * @return {ConversationQuery.<ChatRoom>}
27783 */
27784 ;
27785
27786 _proto.getChatRoomQuery = function getChatRoomQuery() {
27787 return this.getQuery().equalTo('tr', true);
27788 }
27789 /**
27790 * 构造一个 ConversationQuery 来查询服务号
27791 * @return {ConversationQuery.<ServiceConversation>}
27792 */
27793 ;
27794
27795 _proto.getServiceConversationQuery = function getServiceConversationQuery() {
27796 return this.getQuery().equalTo('sys', true);
27797 };
27798
27799 _proto._executeQuery = /*#__PURE__*/function () {
27800 var _executeQuery2 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee15(query) {
27801 var queryJSON, command, resCommand;
27802 return regenerator.wrap(function _callee15$(_context15) {
27803 while (1) {
27804 switch (_context15.prev = _context15.next) {
27805 case 0:
27806 queryJSON = query.toJSON();
27807 queryJSON.where = new JsonObjectMessage({
27808 data: JSON.stringify(encode(queryJSON.where))
27809 });
27810 command = new GenericCommand({
27811 cmd: 'conv',
27812 op: 'query',
27813 convMessage: new ConvCommand(queryJSON)
27814 });
27815 _context15.next = 5;
27816 return this._send(command);
27817
27818 case 5:
27819 resCommand = _context15.sent;
27820 return _context15.abrupt("return", this._handleQueryResults(resCommand));
27821
27822 case 7:
27823 case "end":
27824 return _context15.stop();
27825 }
27826 }
27827 }, _callee15, this);
27828 }));
27829
27830 function _executeQuery(_x16) {
27831 return _executeQuery2.apply(this, arguments);
27832 }
27833
27834 return _executeQuery;
27835 }();
27836
27837 _proto._handleQueryResults = /*#__PURE__*/function () {
27838 var _handleQueryResults2 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee16(resCommand) {
27839 var conversations, commandString;
27840 return regenerator.wrap(function _callee16$(_context16) {
27841 while (1) {
27842 switch (_context16.prev = _context16.next) {
27843 case 0:
27844 _context16.prev = 0;
27845 conversations = decode(JSON.parse(resCommand.convMessage.results.data));
27846 _context16.next = 8;
27847 break;
27848
27849 case 4:
27850 _context16.prev = 4;
27851 _context16.t0 = _context16["catch"](0);
27852 commandString = JSON.stringify(trim(resCommand));
27853 throw new Error("Parse query result failed: ".concat(_context16.t0.message, ". Command: ").concat(commandString));
27854
27855 case 8:
27856 _context16.next = 10;
27857 return Promise.all(conversations.map(this._parseConversationFromRawData.bind(this)));
27858
27859 case 10:
27860 conversations = _context16.sent;
27861 return _context16.abrupt("return", conversations.map(this._upsertConversationToCache.bind(this)));
27862
27863 case 12:
27864 case "end":
27865 return _context16.stop();
27866 }
27867 }
27868 }, _callee16, this, [[0, 4]]);
27869 }));
27870
27871 function _handleQueryResults(_x17) {
27872 return _handleQueryResults2.apply(this, arguments);
27873 }
27874
27875 return _handleQueryResults;
27876 }();
27877
27878 _proto._upsertConversationToCache = function _upsertConversationToCache(fetchedConversation) {
27879 var conversation = this._conversationCache.get(fetchedConversation.id);
27880
27881 if (!conversation) {
27882 conversation = fetchedConversation;
27883
27884 this._debug('no match, set cache');
27885
27886 this._conversationCache.set(fetchedConversation.id, fetchedConversation);
27887 } else {
27888 this._debug('update cached conversation');
27889
27890 ['creator', 'createdAt', 'updatedAt', 'lastMessageAt', 'lastMessage', 'mutedMembers', 'members', '_attributes', 'transient', 'muted'].forEach(function (key) {
27891 var value = fetchedConversation[key];
27892 if (value !== undefined) conversation[key] = value;
27893 });
27894 if (conversation._reset) conversation._reset();
27895 }
27896
27897 return conversation;
27898 }
27899 /**
27900 * 反序列化消息,与 {@link Message#toFullJSON} 相对。
27901 * @param {Object}
27902 * @return {AVMessage} 解析后的消息
27903 * @since 4.0.0
27904 */
27905 ;
27906
27907 _proto.parseMessage =
27908 /*#__PURE__*/
27909 function () {
27910 var _parseMessage = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee17(_ref10) {
27911 var data, _ref10$bin, bin, properties, content, message;
27912
27913 return regenerator.wrap(function _callee17$(_context17) {
27914 while (1) {
27915 switch (_context17.prev = _context17.next) {
27916 case 0:
27917 data = _ref10.data, _ref10$bin = _ref10.bin, bin = _ref10$bin === void 0 ? false : _ref10$bin, properties = objectWithoutProperties(_ref10, ["data", "bin"]);
27918 content = bin ? base64Arraybuffer_2(data) : data;
27919 _context17.next = 4;
27920 return this._messageParser.parse(content);
27921
27922 case 4:
27923 message = _context17.sent;
27924 Object.assign(message, properties);
27925
27926 message._updateMentioned(this.id);
27927
27928 return _context17.abrupt("return", message);
27929
27930 case 8:
27931 case "end":
27932 return _context17.stop();
27933 }
27934 }
27935 }, _callee17, this);
27936 }));
27937
27938 function parseMessage(_x18) {
27939 return _parseMessage.apply(this, arguments);
27940 }
27941
27942 return parseMessage;
27943 }()
27944 /**
27945 * 反序列化对话,与 {@link Conversation#toFullJSON} 相对。
27946 * @param {Object}
27947 * @return {ConversationBase} 解析后的对话
27948 * @since 4.0.0
27949 */
27950 ;
27951
27952 _proto.parseConversation =
27953 /*#__PURE__*/
27954 function () {
27955 var _parseConversation = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee18(_ref11) {
27956 var id, lastMessageAt, lastMessage, lastDeliveredAt, lastReadAt, unreadMessagesCount, members, mentioned, properties, conversationData, _transient2, system, expiredAt;
27957
27958 return regenerator.wrap(function _callee18$(_context18) {
27959 while (1) {
27960 switch (_context18.prev = _context18.next) {
27961 case 0:
27962 id = _ref11.id, lastMessageAt = _ref11.lastMessageAt, lastMessage = _ref11.lastMessage, lastDeliveredAt = _ref11.lastDeliveredAt, lastReadAt = _ref11.lastReadAt, unreadMessagesCount = _ref11.unreadMessagesCount, members = _ref11.members, mentioned = _ref11.mentioned, properties = objectWithoutProperties(_ref11, ["id", "lastMessageAt", "lastMessage", "lastDeliveredAt", "lastReadAt", "unreadMessagesCount", "members", "mentioned"]);
27963 conversationData = {
27964 id: id,
27965 lastMessageAt: lastMessageAt,
27966 lastMessage: lastMessage,
27967 lastDeliveredAt: lastDeliveredAt,
27968 lastReadAt: lastReadAt,
27969 unreadMessagesCount: unreadMessagesCount,
27970 members: members,
27971 mentioned: mentioned
27972 };
27973
27974 if (!lastMessage) {
27975 _context18.next = 7;
27976 break;
27977 }
27978
27979 _context18.next = 5;
27980 return this.parseMessage(lastMessage);
27981
27982 case 5:
27983 conversationData.lastMessage = _context18.sent;
27984
27985 conversationData.lastMessage._setStatus(MessageStatus.SENT);
27986
27987 case 7:
27988 _transient2 = properties["transient"], system = properties.system, expiredAt = properties.expiredAt;
27989
27990 if (!_transient2) {
27991 _context18.next = 10;
27992 break;
27993 }
27994
27995 return _context18.abrupt("return", new ChatRoom(conversationData, properties, this));
27996
27997 case 10:
27998 if (!system) {
27999 _context18.next = 12;
28000 break;
28001 }
28002
28003 return _context18.abrupt("return", new ServiceConversation(conversationData, properties, this));
28004
28005 case 12:
28006 if (!(expiredAt || isTemporaryConversatrionId(id))) {
28007 _context18.next = 14;
28008 break;
28009 }
28010
28011 return _context18.abrupt("return", new TemporaryConversation(conversationData, {
28012 expiredAt: expiredAt
28013 }, this));
28014
28015 case 14:
28016 return _context18.abrupt("return", new Conversation(conversationData, properties, this));
28017
28018 case 15:
28019 case "end":
28020 return _context18.stop();
28021 }
28022 }
28023 }, _callee18, this);
28024 }));
28025
28026 function parseConversation(_x19) {
28027 return _parseConversation.apply(this, arguments);
28028 }
28029
28030 return parseConversation;
28031 }();
28032
28033 _proto._parseConversationFromRawData = /*#__PURE__*/function () {
28034 var _parseConversationFromRawData2 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee19(rawData) {
28035 var data, ttl;
28036 return regenerator.wrap(function _callee19$(_context19) {
28037 while (1) {
28038 switch (_context19.prev = _context19.next) {
28039 case 0:
28040 data = keyRemap({
28041 objectId: 'id',
28042 lm: 'lastMessageAt',
28043 m: 'members',
28044 tr: 'transient',
28045 sys: 'system',
28046 c: 'creator',
28047 mu: 'mutedMembers'
28048 }, rawData);
28049
28050 if (data.msg) {
28051 data.lastMessage = {
28052 data: data.msg,
28053 bin: data.bin,
28054 from: data.msg_from,
28055 id: data.msg_mid,
28056 timestamp: data.msg_timestamp,
28057 updatedAt: data.patch_timestamp
28058 };
28059 delete data.lastMessageFrom;
28060 delete data.lastMessageId;
28061 delete data.lastMessageTimestamp;
28062 delete data.lastMessagePatchTimestamp;
28063 }
28064
28065 ttl = data.ttl;
28066 if (ttl) data.expiredAt = Date.now() + ttl * 1000;
28067 return _context19.abrupt("return", this.parseConversation(data));
28068
28069 case 5:
28070 case "end":
28071 return _context19.stop();
28072 }
28073 }
28074 }, _callee19, this);
28075 }));
28076
28077 function _parseConversationFromRawData(_x20) {
28078 return _parseConversationFromRawData2.apply(this, arguments);
28079 }
28080
28081 return _parseConversationFromRawData;
28082 }()
28083 /**
28084 * 创建一个对话
28085 * @param {Object} options 除了下列字段外的其他字段将被视为对话的自定义属性
28086 * @param {String[]} options.members 对话的初始成员列表,默认包含当前 client
28087 * @param {String} [options.name] 对话的名字
28088 * @param {Boolean} [options.unique=true] 唯一对话,当其为 true 时,如果当前已经有相同成员的对话存在则返回该对话,否则会创建新的对话
28089 * @return {Promise.<Conversation>}
28090 */
28091 ;
28092
28093 _proto.createConversation =
28094 /*#__PURE__*/
28095 function () {
28096 var _createConversation = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee20() {
28097 var _ref12,
28098 m,
28099 name,
28100 _transient3,
28101 _ref12$unique,
28102 unique,
28103 tempConv,
28104 tempConvTTL,
28105 properties,
28106 members,
28107 attr,
28108 startCommandJson,
28109 command,
28110 params,
28111 signatureResult,
28112 _yield$this$_send,
28113 _yield$this$_send$con,
28114 cid,
28115 cdate,
28116 ttl,
28117 data,
28118 conversation,
28119 _args20 = arguments;
28120
28121 return regenerator.wrap(function _callee20$(_context20) {
28122 while (1) {
28123 switch (_context20.prev = _context20.next) {
28124 case 0:
28125 _ref12 = _args20.length > 0 && _args20[0] !== undefined ? _args20[0] : {}, m = _ref12.members, name = _ref12.name, _transient3 = _ref12["transient"], _ref12$unique = _ref12.unique, unique = _ref12$unique === void 0 ? true : _ref12$unique, tempConv = _ref12._tempConv, tempConvTTL = _ref12._tempConvTTL, properties = objectWithoutProperties(_ref12, ["members", "name", "transient", "unique", "_tempConv", "_tempConvTTL"]);
28126
28127 if (_transient3 || Array.isArray(m)) {
28128 _context20.next = 3;
28129 break;
28130 }
28131
28132 throw new TypeError("conversation members ".concat(m, " is not an array"));
28133
28134 case 3:
28135 members = new Set(m);
28136 members.add(this.id);
28137 members = Array.from(members).sort();
28138 attr = properties || {};
28139
28140 if (!name) {
28141 _context20.next = 11;
28142 break;
28143 }
28144
28145 if (!(typeof name !== 'string')) {
28146 _context20.next = 10;
28147 break;
28148 }
28149
28150 throw new TypeError("conversation name ".concat(name, " is not a string"));
28151
28152 case 10:
28153 attr.name = name;
28154
28155 case 11:
28156 attr = new JsonObjectMessage({
28157 data: JSON.stringify(encode(attr))
28158 });
28159 startCommandJson = {
28160 m: members,
28161 attr: attr,
28162 "transient": _transient3,
28163 unique: unique,
28164 tempConv: tempConv,
28165 tempConvTTL: tempConvTTL
28166 };
28167 command = new GenericCommand({
28168 cmd: 'conv',
28169 op: 'start',
28170 convMessage: new ConvCommand(startCommandJson)
28171 });
28172
28173 if (!this.options.conversationSignatureFactory) {
28174 _context20.next = 20;
28175 break;
28176 }
28177
28178 params = [null, this._identity, members, 'create'];
28179 _context20.next = 18;
28180 return runSignatureFactory(this.options.conversationSignatureFactory, params);
28181
28182 case 18:
28183 signatureResult = _context20.sent;
28184 Object.assign(command.convMessage, keyRemap({
28185 signature: 's',
28186 timestamp: 't',
28187 nonce: 'n'
28188 }, signatureResult));
28189
28190 case 20:
28191 _context20.next = 22;
28192 return this._send(command);
28193
28194 case 22:
28195 _yield$this$_send = _context20.sent;
28196 _yield$this$_send$con = _yield$this$_send.convMessage;
28197 cid = _yield$this$_send$con.cid;
28198 cdate = _yield$this$_send$con.cdate;
28199 ttl = _yield$this$_send$con.tempConvTTL;
28200 data = _objectSpread$8({
28201 name: name,
28202 "transient": _transient3,
28203 unique: unique,
28204 id: cid,
28205 createdAt: cdate,
28206 updatedAt: cdate,
28207 lastMessageAt: null,
28208 creator: this.id,
28209 members: _transient3 ? [] : members
28210 }, properties);
28211 if (ttl) data.expiredAt = Date.now() + ttl * 1000;
28212 _context20.next = 31;
28213 return this.parseConversation(data);
28214
28215 case 31:
28216 conversation = _context20.sent;
28217 return _context20.abrupt("return", this._upsertConversationToCache(conversation));
28218
28219 case 33:
28220 case "end":
28221 return _context20.stop();
28222 }
28223 }
28224 }, _callee20, this);
28225 }));
28226
28227 function createConversation() {
28228 return _createConversation.apply(this, arguments);
28229 }
28230
28231 return createConversation;
28232 }()
28233 /**
28234 * 创建一个聊天室
28235 * @since 4.0.0
28236 * @param {Object} options 除了下列字段外的其他字段将被视为对话的自定义属性
28237 * @param {String} [options.name] 对话的名字
28238 * @return {Promise.<ChatRoom>}
28239 */
28240 ;
28241
28242 _proto.createChatRoom =
28243 /*#__PURE__*/
28244 function () {
28245 var _createChatRoom = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee21(param) {
28246 return regenerator.wrap(function _callee21$(_context21) {
28247 while (1) {
28248 switch (_context21.prev = _context21.next) {
28249 case 0:
28250 return _context21.abrupt("return", this.createConversation(_objectSpread$8(_objectSpread$8({}, param), {}, {
28251 "transient": true,
28252 members: null,
28253 unique: false,
28254 _tempConv: false
28255 })));
28256
28257 case 1:
28258 case "end":
28259 return _context21.stop();
28260 }
28261 }
28262 }, _callee21, this);
28263 }));
28264
28265 function createChatRoom(_x21) {
28266 return _createChatRoom.apply(this, arguments);
28267 }
28268
28269 return createChatRoom;
28270 }()
28271 /**
28272 * 创建一个临时对话
28273 * @since 4.0.0
28274 * @param {Object} options
28275 * @param {String[]} options.members 对话的初始成员列表,默认包含当前 client
28276 * @param {String} [options.ttl] 对话存在时间,单位为秒,最大值与默认值均为 86400(一天),过期后该对话不再可用。
28277 * @return {Promise.<TemporaryConversation>}
28278 */
28279 ;
28280
28281 _proto.createTemporaryConversation =
28282 /*#__PURE__*/
28283 function () {
28284 var _createTemporaryConversation = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee22(_ref13) {
28285 var _tempConvTTL, param;
28286
28287 return regenerator.wrap(function _callee22$(_context22) {
28288 while (1) {
28289 switch (_context22.prev = _context22.next) {
28290 case 0:
28291 _tempConvTTL = _ref13.ttl, param = objectWithoutProperties(_ref13, ["ttl"]);
28292 return _context22.abrupt("return", this.createConversation(_objectSpread$8(_objectSpread$8({}, param), {}, {
28293 _tempConv: true,
28294 _tempConvTTL: _tempConvTTL
28295 })));
28296
28297 case 2:
28298 case "end":
28299 return _context22.stop();
28300 }
28301 }
28302 }, _callee22, this);
28303 }));
28304
28305 function createTemporaryConversation(_x22) {
28306 return _createTemporaryConversation.apply(this, arguments);
28307 }
28308
28309 return createTemporaryConversation;
28310 }() // jsdoc-ignore-start
28311 ;
28312
28313 _proto. // jsdoc-ignore-end
28314 _doSendRead = function _doSendRead() {
28315 var _this10 = this;
28316
28317 // if not connected, just skip everything
28318 if (!this._connection.is('connected')) return;
28319 var buffer = internal(this).readConversationsBuffer;
28320 var conversations = Array.from(buffer);
28321 if (!conversations.length) return;
28322 var ids = conversations.map(function (conversation) {
28323 if (!(conversation instanceof ConversationBase)) {
28324 throw new TypeError("".concat(conversation, " is not a Conversation"));
28325 }
28326
28327 return conversation.id;
28328 });
28329
28330 this._debug("mark [".concat(ids, "] as read"));
28331
28332 buffer.clear();
28333
28334 this._sendReadCommand(conversations)["catch"](function (error) {
28335 _this10._debug('send read failed: %O', error);
28336
28337 conversations.forEach(buffer.add.bind(buffer));
28338 });
28339 };
28340
28341 _proto._sendReadCommand = function _sendReadCommand(conversations) {
28342 var _this11 = this;
28343
28344 return this._send(new GenericCommand({
28345 cmd: 'read',
28346 readMessage: new ReadCommand({
28347 convs: conversations.map(function (conversation) {
28348 return new ReadTuple({
28349 cid: conversation.id,
28350 mid: conversation.lastMessage && conversation.lastMessage.from !== _this11.id ? conversation.lastMessage.id : undefined,
28351 timestamp: (conversation.lastMessageAt || new Date()).getTime()
28352 });
28353 })
28354 })
28355 }), false);
28356 };
28357
28358 return IMClient;
28359 }(eventemitter3), (applyDecoratedDescriptor(_class$3.prototype, "_doSendAck", [_dec$2], Object.getOwnPropertyDescriptor(_class$3.prototype, "_doSendAck"), _class$3.prototype), applyDecoratedDescriptor(_class$3.prototype, "_doSendRead", [_dec2], Object.getOwnPropertyDescriptor(_class$3.prototype, "_doSendRead"), _class$3.prototype)), _class$3));
28360 /**
28361 * 修改、撤回消息的原因
28362 * @typedef PatchReason
28363 * @type {Object}
28364 * @property {number} code 负数为内置 code,正数为开发者在 hook 中自定义的 code。比如因为敏感词过滤被修改的 code 为 -4408。
28365 * @property {string} [detail] 具体的原因说明。
28366 */
28367
28368 var RECONNECT_ERROR = 'reconnecterror';
28369
28370 var CoreEvent = /*#__PURE__*/Object.freeze({
28371 __proto__: null,
28372 RECONNECT_ERROR: RECONNECT_ERROR,
28373 DISCONNECT: DISCONNECT,
28374 RECONNECT: RECONNECT,
28375 RETRY: RETRY,
28376 SCHEDULE: SCHEDULE,
28377 OFFLINE: OFFLINE,
28378 ONLINE: ONLINE
28379 });
28380
28381 var _class$4;
28382
28383 function ownKeys$9(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); if (enumerableOnly) symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; }); keys.push.apply(keys, symbols); } return keys; }
28384
28385 function _objectSpread$9(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i] != null ? arguments[i] : {}; if (i % 2) { ownKeys$9(Object(source), true).forEach(function (key) { defineProperty(target, key, source[key]); }); } else if (Object.getOwnPropertyDescriptors) { Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)); } else { ownKeys$9(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } } return target; }
28386
28387 var // jsdoc-ignore-end
28388 BinaryMessage = IE10Compatible(_class$4 = /*#__PURE__*/function (_Message) {
28389 inheritsLoose(BinaryMessage, _Message);
28390
28391 /**
28392 * 二进制消息
28393 * @extends Message
28394 * @param {ArrayBuffer} buffer
28395 * @since 4.0.0
28396 */
28397 function BinaryMessage(buffer) {
28398 if (!(buffer instanceof ArrayBuffer)) {
28399 throw new TypeError("".concat(buffer, " is not an ArrayBuffer"));
28400 }
28401
28402 return _Message.call(this, buffer) || this;
28403 }
28404 /**
28405 * @type ArrayBuffer
28406 */
28407
28408
28409 BinaryMessage.validate = function validate(target) {
28410 return target instanceof ArrayBuffer;
28411 };
28412
28413 var _proto = BinaryMessage.prototype;
28414
28415 _proto.toJSON = function toJSON() {
28416 return _objectSpread$9(_objectSpread$9({}, _Message.prototype._toJSON.call(this)), {}, {
28417 data: base64Arraybuffer_1(this.content)
28418 });
28419 };
28420
28421 _proto.toFullJSON = function toFullJSON() {
28422 return _objectSpread$9(_objectSpread$9({}, _Message.prototype.toFullJSON.call(this)), {}, {
28423 bin: true,
28424 data: base64Arraybuffer_1(this.content)
28425 });
28426 };
28427
28428 createClass(BinaryMessage, [{
28429 key: "buffer",
28430 get: function get() {
28431 return this.content;
28432 },
28433 set: function set(buffer) {
28434 this.content = buffer;
28435 }
28436 }]);
28437
28438 return BinaryMessage;
28439 }(Message)) || _class$4;
28440
28441 var _dec$3, _class$5;
28442
28443 var // jsdoc-ignore-end
28444 TextMessage = (_dec$3 = messageType(-1), _dec$3(_class$5 = IE10Compatible(_class$5 = /*#__PURE__*/function (_TypedMessage) {
28445 inheritsLoose(TextMessage, _TypedMessage);
28446
28447 /**
28448 * 文类类型消息
28449 * @extends TypedMessage
28450 * @param {String} [text='']
28451 * @throws {TypeError} text 不是 String 类型
28452 */
28453 function TextMessage() {
28454 var _this;
28455
28456 var text = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : '';
28457
28458 if (typeof text !== 'string') {
28459 throw new TypeError("".concat(text, " is not a string"));
28460 }
28461
28462 _this = _TypedMessage.call(this) || this;
28463
28464 _this.setText(text);
28465
28466 return _this;
28467 }
28468
28469 return TextMessage;
28470 }(TypedMessage)) || _class$5) || _class$5);
28471 /**
28472 * @name TYPE
28473 * @memberof TextMessage
28474 * @type Number
28475 * @static
28476 * @const
28477 */
28478
28479 var _class$6;
28480
28481 function ownKeys$a(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); if (enumerableOnly) symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; }); keys.push.apply(keys, symbols); } return keys; }
28482
28483 function _objectSpread$a(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i] != null ? arguments[i] : {}; if (i % 2) { ownKeys$a(Object(source), true).forEach(function (key) { defineProperty(target, key, source[key]); }); } else if (Object.getOwnPropertyDescriptors) { Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)); } else { ownKeys$a(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } } return target; }
28484
28485 function _createForOfIteratorHelper(o, allowArrayLike) { var it; if (typeof Symbol === "undefined" || o[Symbol.iterator] == null) { if (Array.isArray(o) || (it = _unsupportedIterableToArray$1(o)) || allowArrayLike && o && typeof o.length === "number") { if (it) o = it; var i = 0; var F = function F() {}; return { s: F, n: function n() { if (i >= o.length) return { done: true }; return { done: false, value: o[i++] }; }, e: function e(_e) { throw _e; }, f: F }; } throw new TypeError("Invalid attempt to iterate non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); } var normalCompletion = true, didErr = false, err; return { s: function s() { it = o[Symbol.iterator](); }, n: function n() { var step = it.next(); normalCompletion = step.done; return step; }, e: function e(_e2) { didErr = true; err = _e2; }, f: function f() { try { if (!normalCompletion && it["return"] != null) it["return"](); } finally { if (didErr) throw err; } } }; }
28486
28487 function _unsupportedIterableToArray$1(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray$1(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray$1(o, minLen); }
28488
28489 function _arrayLikeToArray$1(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) { arr2[i] = arr[i]; } return arr2; }
28490 var debug$c = browser('LC:MessageParser');
28491
28492 var tryParseJson = function tryParseJson(target, key, descriptor) {
28493 var fn = descriptor.value; // eslint-disable-next-line no-param-reassign
28494
28495 descriptor.value = function wrapper(param) {
28496 var content;
28497
28498 if (typeof param !== 'string') {
28499 content = param;
28500 } else {
28501 try {
28502 content = JSON.parse(param);
28503 } catch (error) {
28504 content = param;
28505 }
28506 }
28507
28508 return fn.call(this, content);
28509 };
28510 };
28511
28512 var applyPlugins = function applyPlugins(target, key, descriptor) {
28513 var fn = descriptor.value; // eslint-disable-next-line no-param-reassign
28514
28515 descriptor.value = function wrapper(json) {
28516 var _this = this;
28517
28518 return Promise.resolve(json).then(applyMiddlewares(this._plugins.beforeMessageParse)).then(function (decoratedJson) {
28519 return fn.call(_this, decoratedJson);
28520 }).then(applyMiddlewares(this._plugins.afterMessageParse));
28521 };
28522 };
28523
28524 var MessageParser = (_class$6 = /*#__PURE__*/function () {
28525 /**
28526 * 消息解析器
28527 * @param {Object} plugins 插件,插件的 messageClasses 会自动被注册,在解析时 beforeMessageParse 与 afterMessageParse Middleware 会被应用。
28528 */
28529 function MessageParser() {
28530 var plugins = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {};
28531 this._plugins = plugins;
28532 this._messageClasses = [];
28533 this.register(plugins.messageClasses);
28534 }
28535 /**
28536 * 注册消息类
28537 *
28538 * @param {Function | Function[]} messageClass 消息类,需要实现 {@link AVMessage} 接口,
28539 * 建议继承自 {@link TypedMessage},也可以传入一个消息类数组。
28540 * @throws {TypeError} 如果 messageClass 没有实现 {@link AVMessage} 接口则抛出异常
28541 */
28542
28543
28544 var _proto = MessageParser.prototype;
28545
28546 _proto.register = function register(messageClasses) {
28547 var _this2 = this;
28548
28549 ensureArray(messageClasses).map(function (klass) {
28550 return _this2._register(klass);
28551 });
28552 };
28553
28554 _proto._register = function _register(messageClass) {
28555 if (messageClass && messageClass.parse && messageClass.prototype && messageClass.prototype.getPayload) {
28556 this._messageClasses.unshift(messageClass);
28557 } else {
28558 throw new TypeError('Invalid messageClass');
28559 }
28560 } // jsdoc-ignore-start
28561 ;
28562
28563 _proto. // jsdoc-ignore-end
28564
28565 /**
28566 * 解析消息内容
28567 * @param {Object | string | any} target 消息内容,如果是字符串会尝试 parse 为 JSON。
28568 * @return {AVMessage} 解析后的消息
28569 * @throws {Error} 如果不匹配任何注册的消息则抛出异常
28570 */
28571 parse = function parse(content) {
28572 debug$c('parsing message: %O', content); // eslint-disable-next-line
28573
28574 var _iterator = _createForOfIteratorHelper(this._messageClasses),
28575 _step;
28576
28577 try {
28578 for (_iterator.s(); !(_step = _iterator.n()).done;) {
28579 var Klass = _step.value;
28580 var contentCopy = isPlainObject_1(content) ? _objectSpread$a({}, content) : content;
28581 var valid = void 0;
28582 var result = void 0;
28583
28584 try {
28585 valid = Klass.validate(contentCopy);
28586 } catch (error) {// eslint-disable-line no-empty
28587 }
28588
28589 if (valid) {
28590 try {
28591 result = Klass.parse(contentCopy);
28592 } catch (error) {
28593 console.warn('parsing a valid message content error', {
28594 error: error,
28595 Klass: Klass,
28596 content: contentCopy
28597 });
28598 }
28599
28600 if (result !== undefined) {
28601 debug$c('parse result: %O', result);
28602 return result;
28603 }
28604 }
28605 }
28606 } catch (err) {
28607 _iterator.e(err);
28608 } finally {
28609 _iterator.f();
28610 }
28611
28612 throw new Error('No Message Class matched');
28613 };
28614
28615 return MessageParser;
28616 }(), (applyDecoratedDescriptor(_class$6.prototype, "parse", [tryParseJson, applyPlugins], Object.getOwnPropertyDescriptor(_class$6.prototype, "parse"), _class$6.prototype)), _class$6);
28617
28618 function ownKeys$b(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); if (enumerableOnly) symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; }); keys.push.apply(keys, symbols); } return keys; }
28619
28620 function _objectSpread$b(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i] != null ? arguments[i] : {}; if (i % 2) { ownKeys$b(Object(source), true).forEach(function (key) { defineProperty(target, key, source[key]); }); } else if (Object.getOwnPropertyDescriptors) { Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)); } else { ownKeys$b(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } } return target; }
28621 var debug$d = browser('LC:IMPlugin');
28622 /**
28623 * 消息优先级枚举
28624 * @enum {Number}
28625 * @since 3.3.0
28626 */
28627
28628 var MessagePriority = {
28629 /** 高 */
28630 HIGH: 1,
28631
28632 /** 普通 */
28633 NORMAL: 2,
28634
28635 /** 低 */
28636 LOW: 3
28637 };
28638 Object.freeze(MessagePriority);
28639 /**
28640 * 为 Conversation 定义一个新属性
28641 * @param {String} prop 属性名
28642 * @param {Object} [descriptor] 属性的描述符,参见 {@link https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/getOwnPropertyDescriptor#Description getOwnPropertyDescriptor#Description - MDN},默认为该属性名对应的 Conversation 自定义属性的 getter/setter
28643 * @returns void
28644 * @example
28645 *
28646 * conversation.get('type');
28647 * conversation.set('type', 1);
28648 *
28649 * // equals to
28650 * defineConversationProperty('type');
28651 * conversation.type;
28652 * conversation.type = 1;
28653 */
28654
28655 var defineConversationProperty = function defineConversationProperty(prop) {
28656 var descriptor = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {
28657 get: function get() {
28658 return this.get(prop);
28659 },
28660 set: function set(value) {
28661 this.set(prop, value);
28662 }
28663 };
28664 Object.defineProperty(Conversation.prototype, prop, descriptor);
28665 };
28666
28667 var onRealtimeCreate = function onRealtimeCreate(realtime) {
28668 /* eslint-disable no-param-reassign */
28669 var deviceId = v4_1();
28670 realtime._IMClients = {};
28671 realtime._IMClientsCreationCount = 0;
28672 var messageParser = new MessageParser(realtime._plugins);
28673 realtime._messageParser = messageParser;
28674
28675 var signAVUser = /*#__PURE__*/function () {
28676 var _ref = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee(user) {
28677 return regenerator.wrap(function _callee$(_context) {
28678 while (1) {
28679 switch (_context.prev = _context.next) {
28680 case 0:
28681 return _context.abrupt("return", realtime._request({
28682 method: 'POST',
28683 path: '/rtm/sign',
28684 data: {
28685 session_token: user.getSessionToken()
28686 }
28687 }));
28688
28689 case 1:
28690 case "end":
28691 return _context.stop();
28692 }
28693 }
28694 }, _callee);
28695 }));
28696
28697 return function signAVUser(_x) {
28698 return _ref.apply(this, arguments);
28699 };
28700 }();
28701 /**
28702 * 注册消息类
28703 *
28704 * 在接收消息、查询消息时,会按照消息类注册顺序的逆序依次尝试解析消息内容
28705 *
28706 * @memberof Realtime
28707 * @instance
28708 * @param {Function | Function[]} messageClass 消息类,需要实现 {@link AVMessage} 接口,
28709 * 建议继承自 {@link TypedMessage}
28710 * @throws {TypeError} 如果 messageClass 没有实现 {@link AVMessage} 接口则抛出异常
28711 */
28712
28713
28714 var register = messageParser.register.bind(messageParser);
28715 /**
28716 * 创建一个即时通讯客户端,多次创建相同 id 的客户端会返回同一个实例
28717 * @memberof Realtime
28718 * @instance
28719 * @param {String|AV.User} [identity] 客户端 identity,如果不指定该参数,服务端会随机生成一个字符串作为 identity,
28720 * 如果传入一个已登录的 AV.User,则会使用该用户的 id 作为客户端 identity 登录。
28721 * @param {Object} [options]
28722 * @param {Function} [options.signatureFactory] open session 时的签名方法 // TODO need details
28723 * @param {Function} [options.conversationSignatureFactory] 对话创建、增减成员操作时的签名方法
28724 * @param {Function} [options.blacklistSignatureFactory] 黑名单操作时的签名方法
28725 * @param {String} [options.tag] 客户端类型标记,以支持单点登录功能
28726 * @param {String} [options.isReconnect=false] 单点登录时标记该次登录是不是应用启动时自动重新登录
28727 * @return {Promise.<IMClient>}
28728 */
28729
28730 var createIMClient = /*#__PURE__*/function () {
28731 var _ref2 = asyncToGenerator( /*#__PURE__*/regenerator.mark(function _callee2(identity) {
28732 var _realtime$_open$then;
28733
28734 var _ref3,
28735 tag,
28736 isReconnect,
28737 clientOptions,
28738 lagecyTag,
28739 id,
28740 buildinOptions,
28741 sessionToken,
28742 _tag,
28743 promise,
28744 _args2 = arguments;
28745
28746 return regenerator.wrap(function _callee2$(_context2) {
28747 while (1) {
28748 switch (_context2.prev = _context2.next) {
28749 case 0:
28750 _ref3 = _args2.length > 1 && _args2[1] !== undefined ? _args2[1] : {}, tag = _ref3.tag, isReconnect = _ref3.isReconnect, clientOptions = objectWithoutProperties(_ref3, ["tag", "isReconnect"]);
28751 lagecyTag = _args2.length > 2 ? _args2[2] : undefined;
28752 buildinOptions = {};
28753
28754 if (!identity) {
28755 _context2.next = 19;
28756 break;
28757 }
28758
28759 if (!(typeof identity === 'string')) {
28760 _context2.next = 8;
28761 break;
28762 }
28763
28764 id = identity;
28765 _context2.next = 17;
28766 break;
28767
28768 case 8:
28769 if (!(identity.id && identity.getSessionToken)) {
28770 _context2.next = 16;
28771 break;
28772 }
28773
28774 id = identity.id;
28775 sessionToken = identity.getSessionToken();
28776
28777 if (sessionToken) {
28778 _context2.next = 13;
28779 break;
28780 }
28781
28782 throw new Error('User must be authenticated');
28783
28784 case 13:
28785 buildinOptions.signatureFactory = signAVUser;
28786 _context2.next = 17;
28787 break;
28788
28789 case 16:
28790 throw new TypeError('Identity must be a String or an AV.User');
28791
28792 case 17:
28793 if (!(realtime._IMClients[id] !== undefined)) {
28794 _context2.next = 19;
28795 break;
28796 }
28797
28798 return _context2.abrupt("return", realtime._IMClients[id]);
28799
28800 case 19:
28801 if (lagecyTag) {
28802 console.warn('DEPRECATION createIMClient tag param: Use options.tag instead.');
28803 }
28804
28805 _tag = tag || lagecyTag;
28806 promise = (_realtime$_open$then = realtime._open().then(function (connection) {
28807 var client = new IMClient(id, _objectSpread$b(_objectSpread$b({}, buildinOptions), clientOptions), {
28808 _connection: connection,
28809 _request: realtime._request.bind(realtime),
28810 _messageParser: messageParser,
28811 _plugins: realtime._plugins,
28812 _identity: identity
28813 });
28814 connection.on(RECONNECT, function () {
28815 return client._open(realtime._options.appId, _tag, deviceId, true)
28816 /**
28817 * 客户端连接恢复正常,该事件通常在 {@link Realtime#event:RECONNECT} 之后发生
28818 * @event IMClient#RECONNECT
28819 * @see Realtime#event:RECONNECT
28820 * @since 3.2.0
28821 */
28822
28823 /**
28824 * 客户端重新登录发生错误(网络连接已恢复,但重新登录错误)
28825 * @event IMClient#RECONNECT_ERROR
28826 * @since 3.2.0
28827 */
28828 .then(function () {
28829 return client.emit(RECONNECT);
28830 }, function (error) {
28831 return client.emit(RECONNECT_ERROR, error);
28832 });
28833 });
28834
28835 internal(client)._eventemitter.on('beforeclose', function () {
28836 delete realtime._IMClients[client.id];
28837
28838 if (realtime._firstIMClient === client) {
28839 delete realtime._firstIMClient;
28840 }
28841 }, realtime);
28842
28843 internal(client)._eventemitter.on('close', function () {
28844 realtime._deregister(client);
28845 }, realtime);
28846
28847 return client._open(realtime._options.appId, _tag, deviceId, isReconnect).then(function () {
28848 realtime._IMClients[client.id] = client;
28849 realtime._IMClientsCreationCount += 1;
28850
28851 if (realtime._IMClientsCreationCount === 1) {
28852 client._omitPeerId(true);
28853
28854 realtime._firstIMClient = client;
28855 } else if (realtime._IMClientsCreationCount > 1 && realtime._firstIMClient) {
28856 realtime._firstIMClient._omitPeerId(false);
28857 }
28858
28859 realtime._register(client);
28860
28861 return client;
28862 })["catch"](function (error) {
28863 delete realtime._IMClients[client.id];
28864 throw error;
28865 });
28866 })).then.apply(_realtime$_open$then, toConsumableArray(finalize(function () {
28867 realtime._deregisterPending(promise);
28868 })))["catch"](function (error) {
28869 delete realtime._IMClients[id];
28870 throw error;
28871 });
28872
28873 if (identity) {
28874 realtime._IMClients[id] = promise;
28875 }
28876
28877 realtime._registerPending(promise);
28878
28879 return _context2.abrupt("return", promise);
28880
28881 case 25:
28882 case "end":
28883 return _context2.stop();
28884 }
28885 }
28886 }, _callee2);
28887 }));
28888
28889 return function createIMClient(_x2) {
28890 return _ref2.apply(this, arguments);
28891 };
28892 }();
28893
28894 Object.assign(realtime, {
28895 register: register,
28896 createIMClient: createIMClient
28897 });
28898 /* eslint-enable no-param-reassign */
28899 };
28900
28901 var beforeCommandDispatch = function beforeCommandDispatch(command, realtime) {
28902 var isIMCommand = command.service === null || command.service === 2;
28903 if (!isIMCommand) return true;
28904 var targetClient = command.peerId ? realtime._IMClients[command.peerId] : realtime._firstIMClient;
28905
28906 if (targetClient) {
28907 Promise.resolve(targetClient).then(function (client) {
28908 return client._dispatchCommand(command);
28909 })["catch"](debug$d);
28910 } else {
28911 debug$d('[WARN] Unexpected message received without any live client match: %O', trim(command));
28912 }
28913
28914 return false;
28915 };
28916
28917 var IMPlugin = {
28918 name: 'leancloud-realtime-plugin-im',
28919 onRealtimeCreate: onRealtimeCreate,
28920 beforeCommandDispatch: beforeCommandDispatch,
28921 messageClasses: [Message, BinaryMessage, RecalledMessage, TextMessage]
28922 };
28923
28924 function ownKeys$c(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); if (enumerableOnly) symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; }); keys.push.apply(keys, symbols); } return keys; }
28925
28926 function _objectSpread$c(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i] != null ? arguments[i] : {}; if (i % 2) { ownKeys$c(Object(source), true).forEach(function (key) { defineProperty(target, key, source[key]); }); } else if (Object.getOwnPropertyDescriptors) { Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)); } else { ownKeys$c(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } } return target; }
28927 Realtime.defineConversationProperty = defineConversationProperty;
28928 Realtime.__preRegisteredPlugins = [IMPlugin];
28929
28930 var Event = _objectSpread$c(_objectSpread$c({}, CoreEvent), IMEvent);
28931
28932 /** core + plugins + platform adapters */
28933 setAdapters({
28934 WebSocket: lib_4,
28935 request: lib_1$1
28936 });
28937
28938 exports.BinaryMessage = BinaryMessage;
28939 exports.ChatRoom = ChatRoom;
28940 exports.Conversation = Conversation;
28941 exports.ConversationMemberRole = ConversationMemberRole;
28942 exports.ConversationQuery = ConversationQuery;
28943 exports.ErrorCode = ErrorCode;
28944 exports.Event = Event;
28945 exports.EventEmitter = eventemitter3;
28946 exports.IE10Compatible = IE10Compatible;
28947 exports.IMPlugin = IMPlugin;
28948 exports.Message = Message;
28949 exports.MessageParser = MessageParser;
28950 exports.MessagePriority = MessagePriority;
28951 exports.MessageQueryDirection = MessageQueryDirection;
28952 exports.MessageStatus = MessageStatus;
28953 exports.Promise = polyfilledPromise;
28954 exports.Protocals = message;
28955 exports.Protocols = message;
28956 exports.Realtime = Realtime;
28957 exports.RecalledMessage = RecalledMessage;
28958 exports.ServiceConversation = ServiceConversation;
28959 exports.TemporaryConversation = TemporaryConversation;
28960 exports.TextMessage = TextMessage;
28961 exports.TypedMessage = TypedMessage;
28962 exports.debug = debug$2;
28963 exports.defineConversationProperty = defineConversationProperty;
28964 exports.getAdapter = getAdapter;
28965 exports.messageField = messageField;
28966 exports.messageType = messageType;
28967 exports.setAdapters = setAdapters;
28968
28969 Object.defineProperty(exports, '__esModule', { value: true });
28970
28971})));
28972//# sourceMappingURL=im-browser.js.map