PageSourceSearch

https://mxtoolbox.com/bundles/mxSharedMin.js?v=hEw3jRZcA6zGqZ6qTCbnteSqO2vQKCVpd2QGvSv5BxI1

js mxtoolbox.com collected 2026-10-01 06:49:19 UTC 51,397 bytes, 1,545 lines download raw bytes

1/* Minification failed. Returning unminified contents.
2(96,33-34): run-time error JS1014: Invalid character: `
3(96,35-36): run-time error JS1004: Expected ';': {
4(96,50-51): run-time error JS1195: Expected expression: /
5(96,55-56): run-time error JS1014: Invalid character: `
6(97,9-10): run-time error JS1002: Syntax error: }
7(98,33-34): run-time error JS1014: Invalid character: `
8(98,44-45): run-time error JS1004: Expected ';': {
9(98,59-60): run-time error JS1014: Invalid character: `
10(99,9-10): run-time error JS1002: Syntax error: }
11(107,29-30): run-time error JS1004: Expected ';': {
12(108,16-17): run-time error JS1014: Invalid character: `
13(108,22-23): run-time error JS1004: Expected ';': :
14(112,16-17): run-time error JS1014: Invalid character: `
15(112,22-23): run-time error JS1004: Expected ';': :
16(162,19-20): run-time error JS1014: Invalid character: `
17(162,25-26): run-time error JS1004: Expected ';': :
18(571,1-2): run-time error JS1002: Syntax error: }
19(572,12-13): run-time error JS1195: Expected expression: )
20(572,14-15): run-time error JS1004: Expected ';': {
21(619,2-3): run-time error JS1195: Expected expression: )
22(620,12-13): run-time error JS1195: Expected expression: )
23(620,14-15): run-time error JS1004: Expected ';': {
24(766,2-3): run-time error JS1195: Expected expression: )
25(767,12-13): run-time error JS1195: Expected expression: )
26(767,14-15): run-time error JS1004: Expected ';': {
27(801,2-3): run-time error JS1195: Expected expression: )
28(823,16-17): run-time error JS1004: Expected ';': {
29(1081,2-3): run-time error JS1195: Expected expression: )
30(1083,1-2): run-time error JS1197: Too many errors. The file might not be a JavaScript file: (
31(108,9-22): run-time error JS1018: 'return' statement outside of function: return `https
32 */
33(function () {
34    // Do not copy this this script is intended to be unique
35    // and shared among all the master pages
36    // all the functions here must be declared here and only here
37
38    window.MXT = window.MXT || {};
39    var _postRun = {
40        functions: [],
41        hasRun: false
42    };
43    let _adminConsoleMsgs = [];
44    // =============== Temp Shared Code
45    // This may be replaced with MXT.WriteLog
46    // In the meantime we need it for AB variation calls
47    window.MxErrorHandler = function (input, details, e) {
48        /* Remove this restriction for now - we can put it back in the future
49        if (input.indexOf("VWO") === -1 && details.indexOf("VWO") === -1) {
50            // Only engage for Errors that contain "VWO"
51            return false;
52        }
53        */
54
55        if (typeof e === "undefined") {
56            e = "undefined";
57        }
58
59        var userAgent = "";
60
61        if (navigator) {
62            if (navigator.userAgent) {
63                userAgent = navigator.userAgent;
64            }
65        }
66
67        var params = {
68            "input": input,
69            "details": details,
70            "stackTrace": e,
71            "userAgent": userAgent
72        };
73        $.ajax({
74            type: "POST",
75            url: GetMxWebsite() + "Public/Lookup.aspx/ReportException3",
76            data: JSON.stringify(params),
77            contentType: "application/json; charset=utf-8",
78            dataType: "json",
79            success: function (msg) {
80                //console.log(msg);
81            },
82            error: function (err) {
83                //console.log(err);
84            }
85        });
86
87    };
88
89    // =============== MXT Interface
90    MXT.GetMxWebsite = GetMxWebsite;
91    MXT.GetMxDeliveryWebsite = GetMxDeliveryWebsite;
92    MXT.API = MakeApiCall;
93    MXT.getCookie = MXT.GetCookie = GetCookie;
94    MXT.setCookie = MXT.SetCookie = SetCookie;
95    MXT.deleteCookie = DeleteCookie;
96    MXT.AddPostRun = AddPostRun;
97    MXT.ListPostRun = ListPostRun;
98    MXT.RunPosts = RunPosts;
99    MXT.MxUrl = MxUrl;
100    MXT.EscapeRegex = EscapeRegex;
101    MXT.StringFormat = StringFormat;
102    MXT.Deprecated = Deprecated;
103    MXT.AdminConsole = AdminConsole;
104    MXT.Watcher = Watcher;
105    MXT.OnPasswordChange = OnPasswordChange;
106    MXT.HTMLEncode = HTMLEncode;
107    MXT.HTMLDecode = HTMLDecode;
108    MXT.GetDeliveryTemplateUrl = GetDeliveryTemplateUrl;
109
110    // =============== Placeholders
111    // In case the application does not load the other resource
112    MXT.AddABTestTrigger = MXT.AddABTestTrigger || function () { };
113
114    window.init = AB265init;
115
116    // =============== Initialize
117    InitMxToolboxHostDomain();
118    function InitMxToolboxHostDomain() {
119        let hostName = window.location.hostname.toLowerCase();
120        let hostSplit = hostName.split(".");
121
122        MXT.HOST_NAME = hostName;
123        MXT.ISLOCAL = hostName.includes('local');
124        MXT.DOMAIN_NAME = hostSplit.slice(-2).join('.');
125        MXT.DOMAIN_ENDING = hostSplit.slice(-1)[0];
126
127        if (MXT.ISLOCAL) {
128            MXT.DELIVERY_HOST = `${MXT.HOST_NAME}/site`;
129        } else {
130            MXT.DELIVERY_HOST = `delivery.${MXT.HOST_NAME}`;
131        }
132    }
133
134    // =============== Events
135    // To let early callers know that the mx shared library is ready
136    document.dispatchEvent(new CustomEvent('mx-shared-ready'));
137
138    // =============== MXT Methods
139    function GetMxWebsite() {
140        return `https://${MXT.HOST_NAME}/`;
141    }
142
143    function GetMxDeliveryWebsite() {
144        return `https://${MXT.DELIVERY_HOST}${(MXT.DELIVERY_HOST[MXT.DELIVERY_HOST.length - 1] == "/" ? "" : "/") }`;
145    }
146
147    /**
148     * Used to indicate that an old function should not be used anymore
149     * NOTE
150     * The reason for this is urge the moving of global functions into the MXT namespace.
151     * When a file is converted to use the MXT namespace, this utility will help
152     * identify when we are still calling the old global.
153     *
154     * @param {*} newFunctionName This string will have an 'eval' applied. Make sure it's correct.
155     * @param {*} oldFunctionName Optional - The old function name
156     * @param {*} oldFnOverride Optional
157     * @returns {fn} conversion function
158     */
159    function Deprecated(newFunctionName, oldFunctionName, oldFnOverride) {
160        return function () {
161            let msg = '';
162            let fn;
163
164            if (oldFunctionName) {
165                msg += '"' + oldFunctionName + '" is deprecated. ';
166            }
167            msg += 'Use "' + newFunctionName + '" instead. ';
168
169            if (oldFnOverride) {
170                fn = oldFnOverride;
171                msg += 'NOTE: The new function uses a different signature. ';
172            } else {
173                fn = eval(newFunctionName);
174            }
175
176            MXT.AdminConsole(msg);
177            // 'arguments' is a hidden property available to all functions. This returned function is what the
178            //       CALLEE is calling, so it has the params.
179            // Using apply to pass through all old 'arguments' into new function.
180            // Using Array.prototype.slice.call to turn arguments into real array
181            fn.apply(this, Array.prototype.slice.call(arguments));
182        };
183    }
184
185
186    /**
187     * This is for AngularJs templates that need to live in classic and DC2
188     */
189    function GetDeliveryTemplateUrl(templateUrl) {
190        let url = templateUrl;
191
192        // Only Classic MXT will have MXT.currentLocation
193        if (MXT.currentLocation) {
194            url = `https://${MXT.DELIVERY_HOST}/${templateUrl}`;
195        }
196
197        return url;
198    }
199
200    /**
201     * Helper to angular $watch and $on that reports when watches are fired.
202     *
203     * @param {*} fn
204     * @returns
205     */
206    function Watcher(fn) {
207        let controllerName = '';
208        try {
209            controllerName = arguments.callee.caller.name;
210        } catch (error) {
211            // This is most likely because the caller of this Watcher function has
212            // 'use strict'; at the top of the file.. therefore it will block our attempts
213            // to look behind the scenes.
214        }
215        return function WatchInterceptor() {
216            AdminConsole('WATCH "' + fn.name + '" fired in ' + controllerName);
217            fn.apply(this, Array.prototype.slice.call(arguments));
218        };
219    }
220
221    /**
222     * Admin Console outputs a console.log(), but only if the USER is considered an ADMIN.
223     *
224     * @param {*} [arguments] native arguments
225     */
226    function AdminConsole() {
227        // 'arguments' is a hidden property available to all functions.
228        let fnArguments = Array.prototype.slice.call(arguments);
229
230        if (MXT.isUserLoaded) {
231            // The MXT.User is not properly loaded by this time, but the mxUser.js has set the is_admin bit in the window variable.
232            // I'm pretty sure this is why the deprecated message that calls this exists
233            // This is a shim until we figure out a better way.
234
235            if (window._is_admin && window._admin_console) {  // TODO - Add condition of inpers
235onated
236                // 'arguments' is a hidden property available to all functions.
237                // Using apply to pass through all 'arguments' to console.
238                // Using Array.prototype.slice.call to turn arguments into real array
239                // Colorizing tag with '%c' which console.log in chrome, safari and edge support
240                console.log.apply(this, ['%cMXT ADMIN LOG:', 'color:#FF9900;'].concat(fnArguments));
241            }
242        } else {
243            _adminConsoleMsgs.push(fnArguments);
244            MXT.OnUserLoaded(function (event, user) {
245                let i, len;
246                for (i = 0, len = _adminConsoleMsgs.length; i < len; i++) {
247                    AdminConsole.apply(this, _adminConsoleMsgs[i]);
248                }
249                _adminConsoleMsgs.length = 0;
250            });
251        }
252    }
253
254    function OnPasswordChange(element) {
255        var decode = decodeURIComponent($(element).val());
256        $(element).val(encodeURIComponent(decode));
257    }
258
259    function MakeApiCall(type, href, success, params) {
260        var apiUrl = MXT.GetMxWebsite() + "api/";
261
262        params = params || {};
263        params = $.extend({
264            type: {
265                GET: 'GET',
266                POST: 'POST',
267                DELETE: 'DELETE',
268                PUT: 'PUT'
269            }[type.toUpperCase()] || 'GET',
270            async: undefined,
271            contentType: 'application/json; charset=utf-8',
272            dataType: 'json',
273            data: null
274        }, params);
275
276        // v1 or v2
277        apiUrl += 'v' + (params.isV2 ? '2' : '1');
278
279        //Are we passing in a path or a full href?
280        href = href[0] === '/' ? apiUrl + href : href;
281
282        $.ajax({
283            type: params.type,
284            async: params.async,
285            data: params.data,
286            url: href,
287            contentType: params.contentType,
288            dataType: params.dataType,
289            success: function (data) {
290                success(data);
291            },
292            error: function (xhr, status, error) {
293                console.log(xhr, status, error);
294            }
295        });
296    }
297
298    function SetCookie(name, value, days, domain) {
299        let expires = '';
300        let date = new Date();
301
302        if (days) {
303            date.setTime(date.getTime() + (days * 24 * 60 * 60 * 1000));
304            expires = "; expires=" + date.toGMTString();
305        }
306
307        // Anything over 4k can not be stored in a cookie. We are going to store it in local storage instead
308        if (value.length > 3900) {
309            localStorage.setItem(name, value);
310        } else {
311            document.cookie = name + "=" + encodeURIComponent(value) + expires + "; " + (domain ? "domain=" + domain : "") + "; path=/";
312        }
313
314        return document.cookie;
315    }
316
317    function DeleteCookie(name) {
318        let isCookie = !!FindCookie(name);
319        if (isCookie) {
320            MXT.setCookie(name, '', -1);
321        } else {
322            localStorage.removeItem(name);
323        }
324    }
325
326    function GetCookie(name) {
327        let cookieValue = FindCookie(name);
328        let localStorageItem;
329
330        if (cookieValue) {
331            return decodeURIComponent(cookieValue);
332        } else {
333            // We did not find it in cookies.. try localStorage
334
335            localStorageItem = localStorage.getItem(name);
336            if (localStorageItem) {
337                return localStorageItem;
338            }
339        }
340
341        return null;
342    }
343
344    function FindCookie(name) {
345        let nameEQ = name + "=";
346        let ca = document.cookie.split(';');
347
348        for (var i = 0, len = ca.length; i < len; i++) {
349            var c = ca[i];
350            while (c.charAt(0) === ' ') c = c.substring(1, c.length);
351            if (c.indexOf(nameEQ) === 0) return c.substring(nameEQ.length, c.length);
352        }
353
354        return null;
355    }
356
357    /**
358         * These are tools for VWO and Optimize to trigger code execution
359         * AFTER VWO and Optimize have run it's test code on the page.
360         * To add a function to run after VWO/Optimize, use either:
361         * window.MXT.AddPostRun(fn)
362         *      if there are no parameters that need to be passed into the executed code
363         * window.MXT.AddPostRun(function(){ your code that uses parameters outside this })
364         *      if you have parameters. Look at ShowSwitchResponsiveLink in this file
365         *      for an example.
366         *
367         * VWO/Optimize then can call window.MXT.RunPosts() when it's done.
368         *
369         * In VWO, go into any of the javascript edit (Control or Variation),
370         * Click on the Edit Campaign Code item. This is where we can set code that
371         * runs after the variation code runs. All variations use the same campaign code.
372         * This is what you put in there:
373         * (function(){
374              var MXT = window.MXT || {
375                RunPosts: function(){
376                  console.log('VWO On Done error. No MXT found');
377                }
378              };
379              if (MXT.RunPosts){
380                MXT.RunPosts();
381              }
382            })();
383         *
384         * In Optimize: I could not figure out a solution to this one.. No optimize post execution
385         * until we figure this out.
386         */
387
388    function AddPostRun(fn) {
389        _postRun.functions.push(fn);
390    }
391
392    function ListPostRun() {
393        console.log(_postRun);
394    }
395
396    function RunPosts() {
397        if (!_postRun.hasRun) {
398            let i, len;
399            for (i = 0, len = _postRun.functions.length; i < len; i++) {
400                _postRun.functions[i]();
401            }
402            // reset
403            _postRun.functions = [];
404        }
405    }
406
407    function AB265init(i) { //Put in place to fix a timing issue with AB-265 without restarting the test.
408        i = i || 0;
409        if (i < 10) {
410            i++;
411            setTimeout(function () {
412                window.init(i);
413            }, 300);
414        }
415    }
416
417    // MxUrl accepts a param that can be:
418    //      [object] 'document.location'
419    //      [string] a css selector
420    //      [string] url (distinguished by '/' characters present)
421    function MxUrl(obj) {
422        let _$elem;
423        let _href;
424        let _location;
425        let _params;
426        let _this;
427
428        // if string is passed in, it's either a class name or url string
429        if (typeof obj === 'string') {
430            if (obj.indexOf('/') > -1) {
431                // The obj contains a '/' so it is most likely a url string
432                _href = obj;
433                _location = ParseURL(_href);
434            } else {
435                // The obj does not contain a '/' so it is most likely a css selector
436                _$elem = $(obj);
437                _href = _$elem.attr('href');
438                _location = ParseURL(_href);
439            }
440        } else {
441            // The obj is an object, so it's expected that it is a 'document.location'
442            _href = obj.href;
443            _location = obj;
444        }
445        _params = ParseParams(_location.search);
446
447        _this = {
448            $elem: _$elem,
449            href: _href,
450            location: _location,
451            params: _params,
452            UpdateQS: UpdateQS,
453            IsPage: IsPage,
454            HasParam: HasParam,
455            GetUrl: GetUrl,
456            MergeParams: MergeParams
457        };
458        return _this;
459
460        function ParseURL(url) {
461            let parser = document.createElement('a');
462            // Let the browser do the work
463            parser.href = url;
464
465            // IE11 compatibiliy.. silly, I know. https://gist.github.com/koron/c66b67c6bcdd286f6209
466            parser.href = parser.href;
467
468            return {
469                protocol: parser.protocol,
470                host: parser.host,
471                hostname: parser.hostname,
472                port: parser.port,
473                pathname: parser.pathname.indexOf('/') !== 0 ? '/' + parser.pathname : parser.pathname,
474                search: parser.search,
475                hash: parser.hash
476            };
477        }
478
479        function ParseParams(search) {
480            let searchObject = {},
481                queries, split, i;
482            if (search === "") {
483                return {};
484            }
485            queries = search.replace(/^\?/, '').split('&');
486            for (i = 0; i < queries.length; i++) {
487                split = queries[i].split('=');
488                searchObject[split[0]] = split[1];
489            }
490            return searchObject;
491        }
492
493        function IsPage(page) {
494            return _location.pathname.toLowerCase().indexOf(page) > -1;
495        }
496
497        function HasParam(key, value) {
498            for (let param in _params) {
499                if (_params.hasOwnProperty(param)) {
500                    if (param.toLowerCase() === key.toLowerCase()) {
501                        return value ? _params[param] === value : true;
502                    }
503                }
504            }
505            return false;
506        }
507
508        function UpdateQS(paramToChange, value, deleteUndefined) {
509            let foundParam = false;
510            for (let param in _params) {
511                if (_params.hasOwnProperty(param)) {
512                    if (param.toLowerCase() === paramToChange.toLowerCase()) {
513                        _params[param] = value;
514                        foundParam = true;
515                        break;
516                    }
517                }
518            }
519            if (!foundParam) {
520                _params[paramToChange] = value;
521            }
522
523            // If nessassary, delete the param if it has no value
524            if (deleteUndefined && !value) {
525                delete _params[paramToChange];
526            }
527
528            if (_$elem) {
529                _$elem.attr('href', GetUrl());
530            }
531
532            return _this;
533        }
534
535        function GetUrl() {
536            let returnUrl;
537            returnUrl = _location.protocol + '//' + _location.host + _location.pathname;
538            if (_params) {
539                returnUrl += '?' + ParamsToQs();
540            }
541            return returnUrl;
542        }
543
544        function ParamsToQs() {
545            let returnQs = [];
546            for (let param in _params) {
547                if (_params.hasOwnProperty(param)) {
548                    returnQs.push(param + '=' + _params[param]);
549                }
550            }
551            return returnQs.join('&');
552        }
553
554        function MergeParams(params) {
555            for (param in params) {
556                if (params.hasOwnProperty(param)) {
557                    UpdateQS(param, params[param]);
558                }
559            }
560        }
561    }
562
563    function StringFormat(str) {
564        let argCount = arguments.length;
565        let i, len, replace, re;
566
567        for (i = 1, len = argCount; i < len; i++) {
568            replace = EscapeRegex('{' + (i - 1) + '}');
569            re = new RegExp(replace, "g");
570            str = str.replace(re, arguments[i]);
571
572        }
573
574        return str;
575    }
576
577    function EscapeRegex(value) {
578        return value.replace(/[\-\[\]{}()*+?.,\\\^$|#\s]/g, "\\$&");
579    }
580
581    /**
582     * Converts a string to html characters
583     * @param {string} str String with unescaped HTML characters
584     */
585    function HTMLEncode(str) {
586        var buf = [];
587
588        for (var i = str.length - 1; i >= 0; i--) {
589            buf.unshift(['&#', str[i].charCodeAt(), ';'].join(''));
590        }
591
592        return buf.join('');
593    }
594    /**
595     * Converts HTML Entities to regular characters
596     * @param {any} str String of HTML Entities
597     */
598    function HTMLDecode(str) {
599        return str.replace(/&#(\d+);/g, function (match, dec) {
600            return String.fromCharCode(dec);
601        });
602    }
603})();;
604(function () {
605    //
606    // !! THIS FILE REQUIRES MXSHARED !!
607    //
608    // Do not copy this this script is intended to be unique
609    // and shared among all the master pages
610    // all the functions here must be declared here and only here
611
612    window.MXT = window.MXT || {};
613
614    let MXT = window.MXT;
615
616    MXT.AppLog = {};
617    MXT.AppLog.WriteTypedEntry = WriteTypedEntry;
618    MXT.AppLog.TraceEventType = {
619        Critical: 1,
620        Error: 2,
621        Warning: 4,
622        Information: 8,
623        Verbose: 16
624    };
625
626    function WriteTypedEntry(type, errMsg, traceEventType, detail) {
627        if (detail) {
628            if (typeof detail == 'object') {
629                detail = JSON.stringify(detail);
630            } 
631        }
632
633        var clientMessage = {
634            Location: type,
635            Message: errMsg,
636            TraceEventType: traceEventType,
637            Detail: detail
638        };
639
640        $.post('/api/v1/Loggly', clientMessage, WriteTypedEntrySuccess, WriteTypedEntryFail);
641
642        function WriteTypedEntrySuccess(data) {
643            console.log('data', data);
644        }
645
646        function WriteTypedEntryFail(response) {
647            console.log('response', response);
648        }
649    }
650
651})();;
652(function () {
653    //
654    // !! THIS FILE REQUIRES MXSHARED !!
655    //
656    // Do not copy this this script is intended to be unique
657    // and shared among all the master pages
658    // all the functions here must be declared here and only here
659
660    window.MXT = window.MXT || {};
661    window.MXT.OnUserLoaded = onUserLoaded;
662    window.MXT.RegistrationValidation = registrationValidation;
663    window.MXT.GetPasswordMinMax = getPasswordMinMax;
664
665    // Global variables
666    window._is_paid = 0;
667    window._is_logged_in = 0;
668    window._is_admin = 0;
669    window._numDomainHealthMonitors = 0;
670    window._domainName = window.location.host.split('.').slice(-2).join('.');
671
672    // Private variables
673    _passwordMinLength = 8;
674    _passwordMaxLength = 128;
675
676    (function GetUser() {
677        $.getJSON('/api/v1/user', getUserSuccess)
678            .fail(getUserFail);
679
680    })();
681
682    function getUserSuccess(user) {
683        // Store the cookies
684        /*
685         * Features:
686         * If the cookie is present the backend won't return it, so just read from the cookie for now
687         * We need to stop storing Features with the user, once that is done clean here
688         */
689        if (user.Features && Object.getOwnPropertyNames(user.Features).length > 0) {
690            localStorage.setItem('_mxt_f', JSON.stringify(user.Features));
691        } else {
692            user.Features = JSON.parse(localStorage.getItem('_mxt_f')) || {};
693        }
694        // Store user without the Features
695        var _mxt_u = Object.assign({}, user); // Copy so it does not kill the prop Features on the real object
696        delete _mxt_u.Features;        
697        MXT.setCookie('_mxt_u', JSON.stringify(_mxt_u), null, '.' + window._domainName);
698        // Cookie Segment for ABtesting
699        var _mxt_segment = "anon"; // for cookie _mxt_s
700        // Set global variables
701        if (user.IsLoggedIn) {
702            window._is_logged_in = 1;
703            _mxt_segment = "free";
704            if (user.IsPaidUser) {
705                window._is_paid = 1;
706                _mxt_segment = "paid";
707            }
708            if (user.IsAdmin) {
709                window._is_admin = 1;
710            }
711            // SetCustomerIo
712            var _cio = window._cio || [];
713            if (_cio['identify']) {
714                _cio.identify({
715                    id: user.MxVisitorUid,
716                    email: user.UserName
717                });
718            }
719            window._numDomainHealthMonitors = user.NumDomainHealthMonitors;
720        } else {
721            // Set the Temp Auth Key if is not logged in
722            if (user.TempAuthKey) {
723                window.TempAuthKey = user.TempAuthKey;
724            }
725        }
726
727        // Set Segment Cookie
728        MXT.setCookie('_mxt_s', _mxt_segment, null, '.' + window._domainName);
729        MXT.isUserLoaded = true;        
730
731        // Raised each time User object comes back (for external integrations)
732        $(document).trigger('userLoaded', user);
733        document.dispatchEvent(new CustomEvent('mx-user-loaded', { 'user': user })); // For those who don't use jQuery
734    }
735
736    function getUserFail() {
737        // Delete the cookie/storage
738        MXT.deleteCookie('_mxt_u');
739        MXT.deleteCookie('_mxt_f'); // If you see this line after 9/25/2021, please remove 
740        localStorage.removeItem('_mxt_f');
741
742        MXT.isUserLoaded = true;
743
744        // Raised each time User object comes back (for external integrations)
745        $(document).trigger('userLoaded', null);
746        document.dispatchEvent(new CustomEvent('mx-user-loaded', { 'user': null })); // For those who don't use jQuery
747    }
748
749    // Wrap up function to execute something as soon as the User is loaded
750    // Async user integrations: Used by Ab Test and by MxMaster (to load the header)
751    function onUserLoaded(callback) {
752        if (MXT.isUserLoaded) {
753            // Already loaded, send from cookie
754            // We are mocking the trigger and the first argument must be the event (null to let the called know that it was immediate)
755            var event = null;
756            var user = JSON.parse(MXT.getCookie('_mxt_u'));
757            user.Features = JSON.parse(localStorage.getItem('_mxt_f')) || {};
758            callback(event, user);
759        } else {
760            // The trigger will handle this
761            $(document).on('userLoaded', callback);
762        }
763    }
764
765    // This is a form validator for our Registration forms
766    // Starting with password validation, it can be extended to any and everything.
767    function registrationValidation(registration) {
768        let returnMessage = '';
769        if (typeof registration.name !== 'undefined' && (registration.name === '' || registration.name.length === 0)) {
770            returnMessage += 'Name can not be empty.<br />';
771        }
772        if (typeof registration.email !== 'undefined' && (registration.email === '' || registration.email.length === 0)) {
773            returnMessage += 'Email address can not be empty.<br />';
774        }
775        if (typeof registration.password !== 'undefined' && registration.password.length < 8) {
776            returnMessage += 'Password too short. Password must be at least 8 characters.<br />';
777        }
778        if (typeof registration.password !== 'undefined' && registration.password.length > 128) {
779            returnMessage += 'Password too long. Password can not exceed 128 characters. <br />';
780        }
781        if (typeof registration.name !== 'undefined' && registration.company.length > 50) {
782            returnMessage += 'Company Name too long. Company Name can not exceed 50 characters. <br />';
783        }
784        if (typeof registration.domain !== 'undefined' && (registration.domain === '' || registration.domain.length === 0)) {
785            returnMessage += 'Domain can not be empty.<br />';
786        }
787        return returnMessage;
788    }
789
790    function getPasswordMinMax() {
791        let passwordLengths = {
792            min: _passwordMinLength,
793            max: _passwordMaxLength
794        };
795        return passwordLengths;
796    }
797
798})();;
799(function () {
800    // Do not copy this this script is intended to be unique
801    // and shared among all the master pages
802    // all the functions here must be declared here and only here
803
804    // =============== Windows Interface
805    // These are here for backwards compatibility. We should remove calls to these
806    // and replace them with MXT calls.
807    // Be aware that any functionality that needs to work on any browers that 
808    // do not support a root object called 'window' will fail. Some stateless 
809    // browsers are like this
810    window.setIpAddress = SetIpAddress;
811
812    window.MXT = window.MXT || {};
813
814    // =============== MXT Interface
815    MXT.SetIpAddress = SetIpAddress;
816
817    // =============== MXT Methods
818    //Called on Init from MxMaster
819    function SetIpAddress() {
820        // Derive the API host from the current site's domain so the DEVS site (mxtoolbox.net)
821        // calls the DEVS API and PROD (mxtoolbox.com) calls the PROD API. This was previously
822        // hardcoded to api.mxtoolbox.com, so the DEVS site always hit the PROD API. (PROD-6449)
823        var host = (window.location.hostname || '').toLowerCase();
824        var match = host.match(/mxtoolbox\.(com|net)$/);
825        var baseDomain = match ? 'mxtoolbox.' + match[1] : 'mxtoolbox.com';
826        var whatsmyipUrl = 'https://api.' + baseDomain + '/api/v1/utils/wh
826atsmyip';
827
828        $.get(whatsmyipUrl, function (data) {
829            // ******* TODO ******** Move this out of here. This should only return data
830            $('#lnkIp').html(data);
831        });
832    }
833})();;
834/*
835 * JavaScript MD5
836 * https://github.com/blueimp/JavaScript-MD5
837 *
838 * Copyright 2011, Sebastian Tschan
839 * https://blueimp.net
840 *
841 * Licensed under the MIT license:
842 * https://opensource.org/licenses/MIT
843 *
844 * Based on
845 * A JavaScript implementation of the RSA Data Security, Inc. MD5 Message
846 * Digest Algorithm, as defined in RFC 1321.
847 * Version 2.2 Copyright (C) Paul Johnston 1999 - 2009
848 * Other contributors: Greg Holt, Andrew Kepert, Ydnar, Lostinet
849 * Distributed under the BSD License
850 * See http://pajhome.org.uk/crypt/md5 for more info.
851 */
852
853/* global define */
854
855;(function ($) {
856  'use strict'
857
858  /*
859  * Add integers, wrapping at 2^32. This uses 16-bit operations internally
860  * to work around bugs in some JS interpreters.
861  */
862  function safeAdd (x, y) {
863    var lsw = (x & 0xffff) + (y & 0xffff)
864    var msw = (x >> 16) + (y >> 16) + (lsw >> 16)
865    return (msw << 16) | (lsw & 0xffff)
866  }
867
868  /*
869  * Bitwise rotate a 32-bit number to the left.
870  */
871  function bitRotateLeft (num, cnt) {
872    return (num << cnt) | (num >>> (32 - cnt))
873  }
874
875  /*
876  * These functions implement the four basic operations the algorithm uses.
877  */
878  function md5cmn (q, a, b, x, s, t) {
879    return safeAdd(bitRotateLeft(safeAdd(safeAdd(a, q), safeAdd(x, t)), s), b)
880  }
881  function md5ff (a, b, c, d, x, s, t) {
882    return md5cmn((b & c) | (~b & d), a, b, x, s, t)
883  }
884  function md5gg (a, b, c, d, x, s, t) {
885    return md5cmn((b & d) | (c & ~d), a, b, x, s, t)
886  }
887  function md5hh (a, b, c, d, x, s, t) {
888    return md5cmn(b ^ c ^ d, a, b, x, s, t)
889  }
890  function md5ii (a, b, c, d, x, s, t) {
891    return md5cmn(c ^ (b | ~d), a, b, x, s, t)
892  }
893
894  /*
895  * Calculate the MD5 of an array of little-endian words, and a bit length.
896  */
897  function binlMD5 (x, len) {
898    /* append padding */
899    x[len >> 5] |= 0x80 << (len % 32)
900    x[((len + 64) >>> 9 << 4) + 14] = len
901
902    var i
903    var olda
904    var oldb
905    var oldc
906    var oldd
907    var a = 1732584193
908    var b = -271733879
909    var c = -1732584194
910    var d = 271733878
911
912    for (i = 0; i < x.length; i += 16) {
913      olda = a
914      oldb = b
915      oldc = c
916      oldd = d
917
918      a = md5ff(a, b, c, d, x[i], 7, -680876936)
919      d = md5ff(d, a, b, c, x[i + 1], 12, -389564586)
920      c = md5ff(c, d, a, b, x[i + 2], 17, 606105819)
921      b = md5ff(b, c, d, a, x[i + 3], 22, -1044525330)
922      a = md5ff(a, b, c, d, x[i + 4], 7, -176418897)
923      d = md5ff(d, a, b, c, x[i + 5], 12, 1200080426)
924      c = md5ff(c, d, a, b, x[i + 6], 17, -1473231341)
925      b = md5ff(b, c, d, a, x[i + 7], 22, -45705983)
926      a = md5ff(a, b, c, d, x[i + 8], 7, 1770035416)
927      d = md5ff(d, a, b, c, x[i + 9], 12, -1958414417)
928      c = md5ff(c, d, a, b, x[i + 10], 17, -42063)
929      b = md5ff(b, c, d, a, x[i + 11], 22, -1990404162)
930      a = md5ff(a, b, c, d, x[i + 12], 7, 1804603682)
931      d = md5ff(d, a, b, c, x[i + 13], 12, -40341101)
932      c = md5ff(c, d, a, b, x[i + 14], 17, -1502002290)
933      b = md5ff(b, c, d, a, x[i + 15], 22, 1236535329)
934
935      a = md5gg(a, b, c, d, x[i + 1], 5, -165796510)
936      d = md5gg(d, a, b, c, x[i + 6], 9, -1069501632)
937      c = md5gg(c, d, a, b, x[i + 11], 14, 643717713)
938      b = md5gg(b, c, d, a, x[i], 20, -373897302)
939      a = md5gg(a, b, c, d, x[i + 5], 5, -701558691)
940      d = md5gg(d, a, b, c, x[i + 10], 9, 38016083)
941      c = md5gg(c, d, a, b, x[i + 15], 14, -660478335)
942      b = md5gg(b, c, d, a, x[i + 4], 20, -405537848)
943      a = md5gg(a, b, c, d, x[i + 9], 5, 568446438)
944      d = md5gg(d, a, b, c, x[i + 14], 9, -1019803690)
945      c = md5gg(c, d, a, b, x[i + 3], 14, -187363961)
946      b = md5gg(b, c, d, a, x[i + 8], 20, 1163531501)
947      a = md5gg(a, b, c, d, x[i + 13], 5, -1444681467)
948      d = md5gg(d, a, b, c, x[i + 2], 9, -51403784)
949      c = md5gg(c, d, a, b, x[i + 7], 14, 1735328473)
950      b = md5gg(b, c, d, a, x[i + 12], 20, -1926607734)
951
952      a = md5hh(a, b, c, d, x[i + 5], 4, -378558)
953      d = md5hh(d, a, b, c, x[i + 8], 11, -2022574463)
954      c = md5hh(c, d, a, b, x[i + 11], 16, 1839030562)
955      b = md5hh(b, c, d, a, x[i + 14], 23, -35309556)
956      a = md5hh(a, b, c, d, x[i + 1], 4, -1530992060)
957      d = md5hh(d, a, b, c, x[i + 4], 11, 1272893353)
958      c = md5hh(c, d, a, b, x[i + 7], 16, -155497632)
959      b = md5hh(b, c, d, a, x[i + 10], 23, -1094730640)
960      a = md5hh(a, b, c, d, x[i + 13], 4, 681279174)
961      d = md5hh(d, a, b, c, x[i], 11, -358537222)
962      c = md5hh(c, d, a, b, x[i + 3], 16, -722521979)
963      b = md5hh(b, c, d, a, x[i + 6], 23, 76029189)
964      a = md5hh(a, b, c, d, x[i + 9], 4, -640364487)
965      d = md5hh(d, a, b, c, x[i + 12], 11, -421815835)
966      c = md5hh(c, d, a, b, x[i + 15], 16, 530742520)
967      b = md5hh(b, c, d, a, x[i + 2], 23, -995338651)
968
969      a = md5ii(a, b, c, d, x[i], 6, -198630844)
970      d = md5ii(d, a, b, c, x[i + 7], 10, 1126891415)
971      c = md5ii(c, d, a, b, x[i + 14], 15, -1416354905)
972      b = md5ii(b, c, d, a, x[i + 5], 21, -57434055)
973      a = md5ii(a, b, c, d, x[i + 12], 6, 1700485571)
974      d = md5ii(d, a, b, c, x[i + 3], 10, -1894986606)
975      c = md5ii(c, d, a, b, x[i + 10], 15, -1051523)
976      b = md5ii(b, c, d, a, x[i + 1], 21, -2054922799)
977      a = md5ii(a, b, c, d, x[i + 8], 6, 1873313359)
978      d = md5ii(d, a, b, c, x[i + 15], 10, -30611744)
979      c = md5ii(c, d, a, b, x[i + 6], 15, -1560198380)
980      b = md5ii(b, c, d, a, x[i + 13], 21, 1309151649)
981      a = md5ii(a, b, c, d, x[i + 4], 6, -145523070)
982      d = md5ii(d, a, b, c, x[i + 11], 10, -1120210379)
983      c = md5ii(c, d, a, b, x[i + 2], 15, 718787259)
984      b = md5ii(b, c, d, a, x[i + 9], 21, -343485551)
985
986      a = safeAdd(a, olda)
987      b = safeAdd(b, oldb)
988      c = safeAdd(c, oldc)
989      d = safeAdd(d, oldd)
990    }
991    return [a, b, c, d]
992  }
993
994  /*
995  * Convert an array of little-endian words to a string
996  */
997  function binl2rstr (input) {
998    var i
999    var output = ''
1000    var length32 = input.length * 32
1001    for (i = 0; i < length32; i += 8) {
1002      output += String.fromCharCode((input[i >> 5] >>> (i % 32)) & 0xff)
1003    }
1004    return output
1005  }
1006
1007  /*
1008  * Convert a raw string to an array of little-endian words
1009  * Characters >255 have their high-byte silently ignored.
1010  */
1011  function rstr2binl (input) {
1012    var i
1013    var output = []
1014    output[(input.length >> 2) - 1] = undefined
1015    for (i = 0; i < output.length; i += 1) {
1016      output[i] = 0
1017    }
1018    var length8 = input.length * 8
1019    for (i = 0; i < length8; i += 8) {
1020      output[i >> 5] |= (input.charCodeAt(i / 8) & 0xff) << (i % 32)
1021    }
1022    return output
1023  }
1024
1025  /*
1026  * Calculate the MD5 of a raw string
1027  */
1028  function rstrMD5 (s) {
1029    return binl2rstr(binlMD5(rstr2binl(s), s.length * 8))
1030  }
1031
1032  /*
1033  * Calculate the HMAC-MD5, of a key and some data (raw strings)
1034  */
1035  function rstrHMACMD5 (key, data) {
1036    var i
1037    var bkey = rstr2binl(key)
1038    var ipad = []
1039    var opad = []
1040    var hash
1041    ipad[15] = opad[15] = undefined
1042    if (bkey.length > 16) {
1043      bkey = binlMD5(bkey, key.length * 8)
1044    }
1045    for (i = 0; i < 16; i += 1) {
1046      ipad[i] = bkey[i] ^ 0x36363636
1047      opad[i] = bkey[i] ^ 0x5c5c5c5c
1048    }
1049    hash = binlMD5(ipad.concat(rstr2binl(data)), 512 + data.length * 8)
1050    return binl2rstr(binlMD5(opad.concat(hash), 512 + 128))
1051  }
1052
1053  /*
1054  * Convert a raw string to a hex string
1055  */
1056  function rstr2hex (input) {
1057    var hexTab = '0123456789abcdef'
1058    var output = ''
1059    var x
1060    var i
1061    for (i = 0; i < input.length; i += 1) {
1062      x = input.charCodeAt(i)
1063      output += hexTab.charAt((x >>> 4) & 0x0f) + hexTab.charAt(x & 0x0f)
1064    }
1065    return output
1066  }
1067
1068  /*
1069  * Encode a string as utf-8
1070  */
1071  function str2rstrUTF8 (input) {
1072    return unescape(encodeURIComponent(input))
1073  }
1074
1075  /*
1076  * Take string arguments and return either raw or hex encoded strings
1077  */
1078  function rawMD5 (s) {
1079    return rstrMD5(str2rstrUTF8(s))
1080  }
1081  function hexMD5 (s) {
1082    return rstr2hex(rawMD5(s))
1083  }
1084  function rawHMACMD5 (k, d) {
1085    return rstrHMACMD5(str2rstrUTF8(k), str2rstrUTF8(d))
1086  }
1087  function hexHMACMD5 (k, d) {
1088    return rstr2hex(rawHMACMD5(k, d))
1089  }
1090
1091  function md5 (string, key, raw) {
1092    if (!key) {
1093      if (!raw) {
1094        return hexMD5(string)
1095      }
1096      return rawMD5(string)
1097    }
1098    if (!raw) {
1099      return hexHMACMD5(key, string)
1100    }
1101    return rawHMACMD5(key, string)
1102  }
1103
1104  if (typeof define === 'function' && define.amd) {
1105    define(function () {
1106      return md5
1107    })
1108  } else if (typeof module === 'object' && module.exports) {
1109    module.exports = md5
1110  } else {
1111    $.md5 = md5
1112  }
1113})(this)
1114;
1115(function () {
1116    //
1117    // !! THIS FILE REQUIRES MXSHARED !!
1118    //
1119    // Do not copy this this script is intended to be unique
1120    // and shared among all the master pages
1121    // all the functions here must be declared here and only here
1122
1123    window.MXT = window.MXT || {};
1124
1125    MXT.IsMobile = IsMobile;
1126    MXT.IsTablet = IsTablet;
1127
1128    //Mobile handler
1129    function IsMobile(ignoreCookie) {
1130        if (!MXT.getCookie('ismobile') || ignoreCookie) {
1131            if (!MXT.IsTablet() && (MXT.CheckUserAgent(['ipod', 'iphone', 'android', 'blackberry', 'palm', 'smartphone', 'windows ce']))) {
1132                if (ignoreCookie == false) {
1133                    MXT.setCookie('ismobile', true);
1134                }
1135                return true;
1136            }
1137            else {
1138                if (ignoreCookie == false) {
1139                    MXT.setCookie('ismobile', false);
1140                }
1141                return false;
1142            }
1143        }
1144        else {
1145            if (MXT.getCookie('ismobile')) {
1146                return MXT.getCookie('ismobile').toLowerCase() === 'true' ? true : false;
1147            }
1148            return false;
1149        }
1150    }
1151
1152    function IsTablet() {
1153        if (MXT.CheckUserAgent(["ipad", "android!mobile", "tablet", "kindle", "playbook", "xoom", "sch-i800"])) {
1154            return true;
1155        }
1156        return false;
1157    }
1158})();;
1159(function () {
1160    window.MXT = window.MXT || {};
1161
1162    // =============== MXT Interface
1163    MXT.ProductUrlCarry = ProductUrlCarry;
1164
1165    // =============== MXT Methods
1166
1167    /**
1168     * Finds Sign Up or Upgrade buttons and attaches any page url querystrings to it's href
1169     * Button querystrings have a higher priority than the page querystrings. So if both have
1170     * the same parameter, the button rules.
1171     * */
1172    function ProductUrlCarry() {
1173        let pagequerystring, productBuyButtons, buttonUrl, $button, url;
1174
1175        // Get pages url
1176        pagequerystring = MXT.MxUrl(document.location.href);
1177
1178        // Grab all upgrade buttons on page
1179        productBuyButtons = $('.--upgrade');
1180
1181        productBuyButtons.each(function (index, button) {
1182            // Get button iteration back into jquery
1183            $button = $(button);
1184            // Get this button's url
1185            buttonUrl = MXT.MxUrl($button.attr('href'));
1186
1187            // Copy the all of the button params into the page url
1188            // This sets the priority of buttons over page
1189            pagequerystring.MergeParams(buttonUrl.params);
1190
1191            // Copy the params back into the button
1192            buttonUrl.MergeParams(pagequerystring.params);
1193
1194            // Assign the full url to the button
1195            url = buttonUrl.GetUrl();
1196            $button.attr('href', url);
1197        });
1198    }
1199})();
1200/**
1201 * Object.assign()
1202
1203 * The Object.assign() method is used to copy the values of all enumerable own properties 
1204 * from one or more source objects to a target object. It will return the target object.
1205 */
1206if (typeof Object.assign !== 'function') {
1207    // Must be writable: true, enumerable: false, configurable: true
1208    Object.defineProperty(Object, "assign", {
1209        value: function assign(target, varArgs) { // .length of function is 2
1210            'use strict';
1211            if (target === null || target === undefined) {
1212                throw new TypeError('Cannot convert undefined or null to object');
1213            }
1214
1215            var to = Object(target);
1216
1217            for (var index = 1; index < arguments.length; index++) {
1218                var nextSource = arguments[index];
1219
1220                if (nextSource !== null && nextSource !== undefined) {
1221                    for (var nextKey in nextSource) {
1222                        // Avoid bugs when hasOwnProperty is shadowed
1223                        if (Object.prototype.hasOwnProperty.call(nextSource, nextKey)) {
1224                            to[nextKey] = nextSource[nextKey];
1225                        }
1226                    }
1227                }
1228            }
1229            return to;
1230        },
1231        writable: true,
1232        configurable: true
1233    });
1234}
1235
1236
1237
1238/**
1239 * window.Promise Polyfill
1240
vendor: 5,040 bytes, lines 1241-1401
1241 * Lightweight ES6 Promise polyfill for the browser and node. Adheres closely to the spec. 
1242 * It is a perfect polyfill IE or any other browser that does not support native promises.
1243 */
1244(function (global, factory) {
1245    typeof exports === 'object' && typeof module !== 'undefined' ? factory() :
1246        typeof define === 'function' && define.amd ? define(factory) :
1247            (factory());
1248}(this, (function () {
1249    'use strict';
1250
1251    /**
1252     * @this {Promise}
1253     */
1254    function finallyConstructor(callback) {
1255        var constructor = this.constructor;
1256        return this.then(
1257            function (value) {
1258                // @ts-ignore
1259                return constructor.resolve(callback()).then(function () {
1260                    return value;
1261                });
1262            },
1263            function (reason) {
1264                // @ts-ignore
1265                return constructor.resolve(callback()).then(function () {
1266                    // @ts-ignore
1267                    return constructor.reject(reason);
1268                });
1269            }
1270        );
1271    }
1272
1273    // Store setTimeout reference so promise-polyfill will be unaffected by
1274    // other code modifying setTimeout (like sinon.useFakeTimers())
1275    var setTimeoutFunc = setTimeout;
1276
1277    function isArray(x) {
1278        return Boolean(x && typeof x.length !== 'undefined');
1279    }
1280
1281    function noop() { }
1282
1283    // Polyfill for Function.prototype.bind
1284    function bind(fn, thisArg) {
1285        return function () {
1286            fn.apply(thisArg, arguments);
1287        };
1288    }
1289
1290    /**
1291     * @constructor
1292     * @param {Function} fn
1293     */
1294    function Promise(fn) {
1295        if (!(this instanceof Promise))
1296            throw new TypeError('Promises must be constructed via new');
1297        if (typeof fn !== 'function') throw new TypeError('not a function');
1298        /** @type {!number} */
1299        this._state = 0;
1300        /** @type {!boolean} */
1301        this._handled = false;
1302        /** @type {Promise|undefined} */
1303        this._value = undefined;
1304        /** @type {!Array<!Function>} */
1305        this._deferreds = [];
1306
1307        doResolve(fn, this);
1308    }
1309
1310    function handle(self, deferred) {
1311        while (self._state === 3) {
1312            self = self._value;
1313        }
1314        if (self._state === 0) {
1315            self._deferreds.push(deferred);
1316            return;
1317        }
1318        self._handled = true;
1319        Promise._immediateFn(function () {
1320            var cb = self._state === 1 ? deferred.onFulfilled : deferred.onRejected;
1321            if (cb === null) {
1322                (self._state === 1 ? resolve : reject)(deferred.promise, self._value);
1323                return;
1324            }
1325            var ret;
1326            try {
1327                ret = cb(self._value);
1328            } catch (e) {
1329                reject(deferred.promise, e);
1330                return;
1331            }
1332            resolve(deferred.promise, ret);
1333        });
1334    }
1335
1336    function resolve(self, newValue) {
1337        try {
1338            // Promise Resolution Procedure: https://github.com/promises-aplus/promises-spec#the-promise-resolution-procedure
1339            if (newValue === self)
1340                throw new TypeError('A promise cannot be resolved with itself.');
1341            if (
1342                newValue &&
1343                (typeof newValue === 'object' || typeof newValue === 'function')
1344            ) {
1345                var then = newValue.then;
1346                if (newValue instanceof Promise) {
1347                    self._state = 3;
1348                    self._value = newValue;
1349                    finale(self);
1350                    return;
1351                } else if (typeof then === 'function') {
1352                    doResolve(bind(then, newValue), self);
1353                    return;
1354                }
1355            }
1356            self._state = 1;
1357            self._value = newValue;
1358            finale(self);
1359        } catch (e) {
1360            reject(self, e);
1361        }
1362    }
1363
1364    function reject(self, newValue) {
1365        self._state = 2;
1366        self._value = newValue;
1367        finale(self);
1368    }
1369
1370    function finale(self) {
1371        if (self._state === 2 && self._deferreds.length === 0) {
1372            Promise._immediateFn(function () {
1373                if (!self._handled) {
1374                    Promise._unhandledRejectionFn(self._value);
1375                }
1376            });
1377        }
1378
1379        for (var i = 0, len = self._deferreds.length; i < len; i++) {
1380            handle(self, self._deferreds[i]);
1381        }
1382        self._deferreds = null;
1383    }
1384
1385    /**
1386     * @constructor
1387     */
1388    function Handler(onFulfilled, onRejected, promise) {
1389        this.onFulfilled = typeof onFulfilled === 'function' ? onFulfilled : null;
1390        this.onRejected = typeof onRejected === 'function' ? onRejected : null;
1391        this.promise = promise;
1392    }
1393
1394    /**
1395     * Take a potentially misbehaving resolver function and make sure
1396     * onFulfilled and onRejected are only called once.
1397     *
1398     * Makes no guarantees about asynchrony.
1399     */
1400    function doResolve(fn, self) {
1401        var done = false;
vendor: 4,370 bytes, lines 1402-1545
1402        try {
1403            fn(
1404                function (value) {
1405                    if (done) return;
1406                    done = true;
1407                    resolve(self, value);
1408                },
1409                function (reason) {
1410                    if (done) return;
1411                    done = true;
1412                    reject(self, reason);
1413                }
1414            );
1415        } catch (ex) {
1416            if (done) return;
1417            done = true;
1418            reject(self, ex);
1419        }
1420    }
1421
1422    Promise.prototype['catch'] = function (onRejected) {
1423        return this.then(null, onRejected);
1424    };
1425
1426    Promise.prototype.then = function (onFulfilled, onRejected) {
1427        // @ts-ignore
1428        var prom = new this.constructor(noop);
1429
1430        handle(this, new Handler(onFulfilled, onRejected, prom));
1431        return prom;
1432    };
1433
1434    Promise.prototype['finally'] = finallyConstructor;
1435
1436    Promise.all = function (arr) {
1437        return new Promise(function (resolve, reject) {
1438            if (!isArray(arr)) {
1439                return reject(new TypeError('Promise.all accepts an array'));
1440            }
1441
1442            var args = Array.prototype.slice.call(arr);
1443            if (args.length === 0) return resolve([]);
1444            var remaining = args.length;
1445
1446            function res(i, val) {
1447                try {
1448                    if (val && (typeof val === 'object' || typeof val === 'function')) {
1449                        var then = val.then;
1450                        if (typeof then === 'function') {
1451                            then.call(
1452                                val,
1453                                function (val) {
1454                                    res(i, val);
1455                                },
1456                                reject
1457                            );
1458                            return;
1459                        }
1460                    }
1461                    args[i] = val;
1462                    if (--remaining === 0) {
1463                        resolve(args);
1464                    }
1465                } catch (ex) {
1466                    reject(ex);
1467                }
1468            }
1469
1470            for (var i = 0; i < args.length; i++) {
1471                res(i, args[i]);
1472            }
1473        });
1474    };
1475
1476    Promise.resolve = function (value) {
1477        if (value && typeof value === 'object' && value.constructor === Promise) {
1478            return value;
1479        }
1480
1481        return new Promise(function (resolve) {
1482            resolve(value);
1483        });
1484    };
1485
1486    Promise.reject = function (value) {
1487        return new Promise(function (resolve, reject) {
1488            reject(value);
1489        });
1490    };
1491
1492    Promise.race = function (arr) {
1493        return new Promise(function (resolve, reject) {
1494            if (!isArray(arr)) {
1495                return reject(new TypeError('Promise.race accepts an array'));
1496            }
1497
1498            for (var i = 0, len = arr.length; i < len; i++) {
1499                Promise.resolve(arr[i]).then(resolve, reject);
1500            }
1501        });
1502    };
1503
1504    // Use polyfill for setImmediate for performance gains
1505    Promise._immediateFn =
1506        // @ts-ignore
1507        (typeof setImmediate === 'function' &&
1508            function (fn) {
1509                // @ts-ignore
1510                setImmediate(fn);
1511            }) ||
1512        function (fn) {
1513            setTimeoutFunc(fn, 0);
1514        };
1515
1516    Promise._unhandledRejectionFn = function _unhandledRejectionFn(err) {
1517        if (typeof console !== 'undefined' && console) {
1518            console.warn('Possible Unhandled Promise Rejection:', err); // eslint-disable-line no-console
1519        }
1520    };
1521
1522    /** @suppress {undefinedVars} */
1523    var globalNS = (function () {
1524        // the only reliable means to get the global object is
1525        // `Function('return this')()`
1526        // However, this causes CSP violations in Chrome apps.
1527        if (typeof self !== 'undefined') {
1528            return self;
1529        }
1530        if (typeof window !== 'undefined') {
1531            return window;
1532        }
1533        if (typeof global !== 'undefined') {
1534            return global;
1535        }
1536        throw new Error('unable to locate global object');
1537    })();
1538
1539    if (!('Promise' in globalNS)) {
1540        globalNS['Promise'] = Promise;
1541    } else if (!globalNS.Promise.prototype['finally']) {
1542        globalNS.Promise.prototype['finally'] = finallyConstructor;
1543    }
1544
1545})));;

Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.