platform.wyscout.com
Open in
urlscan Pro
52.30.223.195
Public Scan
URL:
http://platform.wyscout.com/app/platform.engine/ui/js/lib/video-metrics.js?_=1639336379443
Submission: On December 12 via manual from DK — Scanned from DE
Submission: On December 12 via manual from DK — Scanned from DE
Form analysis
0 forms found in the DOMText Content
var WyMetrics = (function (exports, _, os, React, PropTypes) { 'use strict'; _ = _ && _.hasOwnProperty('default') ? _['default'] : _; os = os && os.hasOwnProperty('default') ? os['default'] : os; var React__default = 'default' in React ? React['default'] : React; PropTypes = PropTypes && PropTypes.hasOwnProperty('default') ? PropTypes['default'] : PropTypes; var decodedFrameCount = function decodedFrameCount(video) { return video.webkitDecodedFrameCount; }; var decodedVideoByteCount = function decodedVideoByteCount(video) { return video.webkitVideoDecodedByteCount; }; var decodedAudioByteCount = function decodedAudioByteCount(video) { return video.webkitAudioDecodedByteCount; }; var displayIsFullscreen = function displayIsFullscreen(video) { return video.webkitDisplayingFullscreen; }; var displaySupportFullScreen = function displaySupportFullScreen(video) { return video.webkitSupportsFullscreen; }; var droppedFrameCount = function droppedFrameCount(video) { return video.webkitDroppedFrameCount; }; var duration = function duration(video) { return video.duration; }; var paused = function paused(video) { return video.paused; }; var currentSrc = function currentSrc(video) { return video.currentSrc; }; var networkState = function networkState(video) { return video.networkState; }; var currentTime = function currentTime(video) { return video.currentTime; }; // import WyAnalytics from '@wyscout/analytics'; var initAnalytics = function initAnalytics(userId) { }; var restApiBaseName = null; var env = process.env.REACT_APP_ENV || process.env.NODE_ENV; switch (env) { case 'rc': case 'release': restApiBaseName = 'https://restrc.wyscout.com/'; break; case 'preview': restApiBaseName = 'https://restpreview.wyscout.com/'; break; case 'production': restApiBaseName = 'https://rest.wyscout.com/'; break; default: restApiBaseName = 'https://restbeta.wyscout.com/'; break; } var API_HOSTNAME = restApiBaseName; var API_SERVER = 'http://5b9249cb4c818e001456e8f5.mockapi.io/video-metrics/v1/'; var MAX_SEEKING_VIDEO_TAG = 10; var MAX_PAUSED_SECONDS = 20; var ENABLING_STATUS_MILLISECONDS = 1000 * 60 * 10; // 10 minutes var TRANSMISSION_TYPE = { REST: 'rest', LOGSTASH: 'logstash' }; var NETWORK_STATE = { EMPTY: 0, IDLE: 1, LOADING: 2, NO_SOURCE: 3 }; var ANALYTICS_APP_SOURCE = 'Video Player'; var ANALYTICS_DETAILED_SOURCE = { VIDEO_START: 'Video Player Auto Start', VIDEO_COMPLETED: 'Video Player Completed' }; var PLAYER_TYPE = { PLATFORM: 'AEVideo', APPS: 'VP2018' }; var WYSCOUT_HOSTNAMES_SUFFIX = { DEFAULT: 'wyscout.com', RU: 'platform-ru.wyscout.com', CN: 'wyscout.cn' }; var bind = function bind(fn, thisArg) { return function wrap() { var args = new Array(arguments.length); for (var i = 0; i < args.length; i++) { args[i] = arguments[i]; } return fn.apply(thisArg, args); }; }; /*! * Determine if an object is a Buffer * * @author Feross Aboukhadijeh <https://feross.org> * @license MIT */ // The _isBuffer check is for Safari 5-7 support, because it's missing // Object.prototype.constructor. Remove this eventually var isBuffer_1 = function (obj) { return obj != null && (isBuffer(obj) || isSlowBuffer(obj) || !!obj._isBuffer) }; function isBuffer (obj) { return !!obj.constructor && typeof obj.constructor.isBuffer === 'function' && obj.constructor.isBuffer(obj) } // For Node v0.10 support. Remove this eventually. function isSlowBuffer (obj) { return typeof obj.readFloatLE === 'function' && typeof obj.slice === 'function' && isBuffer(obj.slice(0, 0)) } /*global toString:true*/ // utils is a library of generic helper functions non-specific to axios var toString = Object.prototype.toString; /** * Determine if a value is an Array * * @param {Object} val The value to test * @returns {boolean} True if value is an Array, otherwise false */ function isArray(val) { return toString.call(val) === '[object Array]'; } /** * Determine if a value is an ArrayBuffer * * @param {Object} val The value to test * @returns {boolean} True if value is an ArrayBuffer, otherwise false */ function isArrayBuffer(val) { return toString.call(val) === '[object ArrayBuffer]'; } /** * Determine if a value is a FormData * * @param {Object} val The value to test * @returns {boolean} True if value is an FormData, otherwise false */ function isFormData(val) { return (typeof FormData !== 'undefined') && (val instanceof FormData); } /** * Determine if a value is a view on an ArrayBuffer * * @param {Object} val The value to test * @returns {boolean} True if value is a view on an ArrayBuffer, otherwise false */ function isArrayBufferView(val) { var result; if ((typeof ArrayBuffer !== 'undefined') && (ArrayBuffer.isView)) { result = ArrayBuffer.isView(val); } else { result = (val) && (val.buffer) && (val.buffer instanceof ArrayBuffer); } return result; } /** * Determine if a value is a String * * @param {Object} val The value to test * @returns {boolean} True if value is a String, otherwise false */ function isString(val) { return typeof val === 'string'; } /** * Determine if a value is a Number * * @param {Object} val The value to test * @returns {boolean} True if value is a Number, otherwise false */ function isNumber(val) { return typeof val === 'number'; } /** * Determine if a value is undefined * * @param {Object} val The value to test * @returns {boolean} True if the value is undefined, otherwise false */ function isUndefined(val) { return typeof val === 'undefined'; } /** * Determine if a value is an Object * * @param {Object} val The value to test * @returns {boolean} True if value is an Object, otherwise false */ function isObject(val) { return val !== null && typeof val === 'object'; } /** * Determine if a value is a Date * * @param {Object} val The value to test * @returns {boolean} True if value is a Date, otherwise false */ function isDate(val) { return toString.call(val) === '[object Date]'; } /** * Determine if a value is a File * * @param {Object} val The value to test * @returns {boolean} True if value is a File, otherwise false */ function isFile(val) { return toString.call(val) === '[object File]'; } /** * Determine if a value is a Blob * * @param {Object} val The value to test * @returns {boolean} True if value is a Blob, otherwise false */ function isBlob(val) { return toString.call(val) === '[object Blob]'; } /** * Determine if a value is a Function * * @param {Object} val The value to test * @returns {boolean} True if value is a Function, otherwise false */ function isFunction(val) { return toString.call(val) === '[object Function]'; } /** * Determine if a value is a Stream * * @param {Object} val The value to test * @returns {boolean} True if value is a Stream, otherwise false */ function isStream(val) { return isObject(val) && isFunction(val.pipe); } /** * Determine if a value is a URLSearchParams object * * @param {Object} val The value to test * @returns {boolean} True if value is a URLSearchParams object, otherwise false */ function isURLSearchParams(val) { return typeof URLSearchParams !== 'undefined' && val instanceof URLSearchParams; } /** * Trim excess whitespace off the beginning and end of a string * * @param {String} str The String to trim * @returns {String} The String freed of excess whitespace */ function trim(str) { return str.replace(/^\s*/, '').replace(/\s*$/, ''); } /** * Determine if we're running in a standard browser environment * * This allows axios to run in a web worker, and react-native. * Both environments support XMLHttpRequest, but not fully standard globals. * * web workers: * typeof window -> undefined * typeof document -> undefined * * react-native: * navigator.product -> 'ReactNative' */ function isStandardBrowserEnv() { if (typeof navigator !== 'undefined' && navigator.product === 'ReactNative') { return false; } return ( typeof window !== 'undefined' && typeof document !== 'undefined' ); } /** * Iterate over an Array or an Object invoking a function for each item. * * If `obj` is an Array callback will be called passing * the value, index, and complete array for each item. * * If 'obj' is an Object callback will be called passing * the value, key, and complete object for each property. * * @param {Object|Array} obj The object to iterate * @param {Function} fn The callback to invoke for each item */ function forEach(obj, fn) { // Don't bother if no value provided if (obj === null || typeof obj === 'undefined') { return; } // Force an array if not already something iterable if (typeof obj !== 'object') { /*eslint no-param-reassign:0*/ obj = [obj]; } if (isArray(obj)) { // Iterate over array values for (var i = 0, l = obj.length; i < l; i++) { fn.call(null, obj[i], i, obj); } } else { // Iterate over object keys for (var key in obj) { if (Object.prototype.hasOwnProperty.call(obj, key)) { fn.call(null, obj[key], key, obj); } } } } /** * Accepts varargs expecting each argument to be an object, then * immutably merges the properties of each object and returns result. * * When multiple objects contain the same key the later object in * the arguments list will take precedence. * * Example: * * ```js * var result = merge({foo: 123}, {foo: 456}); * console.log(result.foo); // outputs 456 * ``` * * @param {Object} obj1 Object to merge * @returns {Object} Result of all merge properties */ function merge(/* obj1, obj2, obj3, ... */) { var result = {}; function assignValue(val, key) { if (typeof result[key] === 'object' && typeof val === 'object') { result[key] = merge(result[key], val); } else { result[key] = val; } } for (var i = 0, l = arguments.length; i < l; i++) { forEach(arguments[i], assignValue); } return result; } /** * Extends object a by mutably adding to it the properties of object b. * * @param {Object} a The object to be extended * @param {Object} b The object to copy properties from * @param {Object} thisArg The object to bind function to * @return {Object} The resulting value of object a */ function extend(a, b, thisArg) { forEach(b, function assignValue(val, key) { if (thisArg && typeof val === 'function') { a[key] = bind(val, thisArg); } else { a[key] = val; } }); return a; } var utils = { isArray: isArray, isArrayBuffer: isArrayBuffer, isBuffer: isBuffer_1, isFormData: isFormData, isArrayBufferView: isArrayBufferView, isString: isString, isNumber: isNumber, isObject: isObject, isUndefined: isUndefined, isDate: isDate, isFile: isFile, isBlob: isBlob, isFunction: isFunction, isStream: isStream, isURLSearchParams: isURLSearchParams, isStandardBrowserEnv: isStandardBrowserEnv, forEach: forEach, merge: merge, extend: extend, trim: trim }; var normalizeHeaderName = function normalizeHeaderName(headers, normalizedName) { utils.forEach(headers, function processHeader(value, name) { if (name !== normalizedName && name.toUpperCase() === normalizedName.toUpperCase()) { headers[normalizedName] = value; delete headers[name]; } }); }; /** * Update an Error with the specified config, error code, and response. * * @param {Error} error The error to update. * @param {Object} config The config. * @param {string} [code] The error code (for example, 'ECONNABORTED'). * @param {Object} [request] The request. * @param {Object} [response] The response. * @returns {Error} The error. */ var enhanceError = function enhanceError(error, config, code, request, response) { error.config = config; if (code) { error.code = code; } error.request = request; error.response = response; return error; }; /** * Create an Error with the specified message, config, error code, request and response. * * @param {string} message The error message. * @param {Object} config The config. * @param {string} [code] The error code (for example, 'ECONNABORTED'). * @param {Object} [request] The request. * @param {Object} [response] The response. * @returns {Error} The created error. */ var createError = function createError(message, config, code, request, response) { var error = new Error(message); return enhanceError(error, config, code, request, response); }; /** * Resolve or reject a Promise based on response status. * * @param {Function} resolve A function that resolves the promise. * @param {Function} reject A function that rejects the promise. * @param {object} response The response. */ var settle = function settle(resolve, reject, response) { var validateStatus = response.config.validateStatus; // Note: status is not exposed by XDomainRequest if (!response.status || !validateStatus || validateStatus(response.status)) { resolve(response); } else { reject(createError( 'Request failed with status code ' + response.status, response.config, null, response.request, response )); } }; function encode(val) { return encodeURIComponent(val). replace(/%40/gi, '@'). replace(/%3A/gi, ':'). replace(/%24/g, '$'). replace(/%2C/gi, ','). replace(/%20/g, '+'). replace(/%5B/gi, '['). replace(/%5D/gi, ']'); } /** * Build a URL by appending params to the end * * @param {string} url The base of the url (e.g., http://www.google.com) * @param {object} [params] The params to be appended * @returns {string} The formatted url */ var buildURL = function buildURL(url, params, paramsSerializer) { /*eslint no-param-reassign:0*/ if (!params) { return url; } var serializedParams; if (paramsSerializer) { serializedParams = paramsSerializer(params); } else if (utils.isURLSearchParams(params)) { serializedParams = params.toString(); } else { var parts = []; utils.forEach(params, function serialize(val, key) { if (val === null || typeof val === 'undefined') { return; } if (utils.isArray(val)) { key = key + '[]'; } else { val = [val]; } utils.forEach(val, function parseValue(v) { if (utils.isDate(v)) { v = v.toISOString(); } else if (utils.isObject(v)) { v = JSON.stringify(v); } parts.push(encode(key) + '=' + encode(v)); }); }); serializedParams = parts.join('&'); } if (serializedParams) { url += (url.indexOf('?') === -1 ? '?' : '&') + serializedParams; } return url; }; // Headers whose duplicates are ignored by node // c.f. https://nodejs.org/api/http.html#http_message_headers var ignoreDuplicateOf = [ 'age', 'authorization', 'content-length', 'content-type', 'etag', 'expires', 'from', 'host', 'if-modified-since', 'if-unmodified-since', 'last-modified', 'location', 'max-forwards', 'proxy-authorization', 'referer', 'retry-after', 'user-agent' ]; /** * Parse headers into an object * * ``` * Date: Wed, 27 Aug 2014 08:58:49 GMT * Content-Type: application/json * Connection: keep-alive * Transfer-Encoding: chunked * ``` * * @param {String} headers Headers needing to be parsed * @returns {Object} Headers parsed into an object */ var parseHeaders = function parseHeaders(headers) { var parsed = {}; var key; var val; var i; if (!headers) { return parsed; } utils.forEach(headers.split('\n'), function parser(line) { i = line.indexOf(':'); key = utils.trim(line.substr(0, i)).toLowerCase(); val = utils.trim(line.substr(i + 1)); if (key) { if (parsed[key] && ignoreDuplicateOf.indexOf(key) >= 0) { return; } if (key === 'set-cookie') { parsed[key] = (parsed[key] ? parsed[key] : []).concat([val]); } else { parsed[key] = parsed[key] ? parsed[key] + ', ' + val : val; } } }); return parsed; }; var isURLSameOrigin = ( utils.isStandardBrowserEnv() ? // Standard browser envs have full support of the APIs needed to test // whether the request URL is of the same origin as current location. (function standardBrowserEnv() { var msie = /(msie|trident)/i.test(navigator.userAgent); var urlParsingNode = document.createElement('a'); var originURL; /** * Parse a URL to discover it's components * * @param {String} url The URL to be parsed * @returns {Object} */ function resolveURL(url) { var href = url; if (msie) { // IE needs attribute set twice to normalize properties urlParsingNode.setAttribute('href', href); href = urlParsingNode.href; } urlParsingNode.setAttribute('href', href); // urlParsingNode provides the UrlUtils interface - http://url.spec.whatwg.org/#urlutils return { href: urlParsingNode.href, protocol: urlParsingNode.protocol ? urlParsingNode.protocol.replace(/:$/, '') : '', host: urlParsingNode.host, search: urlParsingNode.search ? urlParsingNode.search.replace(/^\?/, '') : '', hash: urlParsingNode.hash ? urlParsingNode.hash.replace(/^#/, '') : '', hostname: urlParsingNode.hostname, port: urlParsingNode.port, pathname: (urlParsingNode.pathname.charAt(0) === '/') ? urlParsingNode.pathname : '/' + urlParsingNode.pathname }; } originURL = resolveURL(window.location.href); /** * Determine if a URL shares the same origin as the current location * * @param {String} requestURL The URL to test * @returns {boolean} True if URL shares the same origin, otherwise false */ return function isURLSameOrigin(requestURL) { var parsed = (utils.isString(requestURL)) ? resolveURL(requestURL) : requestURL; return (parsed.protocol === originURL.protocol && parsed.host === originURL.host); }; })() : // Non standard browser envs (web workers, react-native) lack needed support. (function nonStandardBrowserEnv() { return function isURLSameOrigin() { return true; }; })() ); // btoa polyfill for IE<10 courtesy https://github.com/davidchambers/Base64.js var chars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/='; function E() { this.message = 'String contains an invalid character'; } E.prototype = new Error; E.prototype.code = 5; E.prototype.name = 'InvalidCharacterError'; function btoa(input) { var str = String(input); var output = ''; for ( // initialize result and counter var block, charCode, idx = 0, map = chars; // if the next str index does not exist: // change the mapping table to "=" // check if d has no fractional digits str.charAt(idx | 0) || (map = '=', idx % 1); // "8 - idx % 1 * 8" generates the sequence 2, 4, 6, 8 output += map.charAt(63 & block >> 8 - idx % 1 * 8) ) { charCode = str.charCodeAt(idx += 3 / 4); if (charCode > 0xFF) { throw new E(); } block = block << 8 | charCode; } return output; } var btoa_1 = btoa; var cookies = ( utils.isStandardBrowserEnv() ? // Standard browser envs support document.cookie (function standardBrowserEnv() { return { write: function write(name, value, expires, path, domain, secure) { var cookie = []; cookie.push(name + '=' + encodeURIComponent(value)); if (utils.isNumber(expires)) { cookie.push('expires=' + new Date(expires).toGMTString()); } if (utils.isString(path)) { cookie.push('path=' + path); } if (utils.isString(domain)) { cookie.push('domain=' + domain); } if (secure === true) { cookie.push('secure'); } document.cookie = cookie.join('; '); }, read: function read(name) { var match = document.cookie.match(new RegExp('(^|;\\s*)(' + name + ')=([^;]*)')); return (match ? decodeURIComponent(match[3]) : null); }, remove: function remove(name) { this.write(name, '', Date.now() - 86400000); } }; })() : // Non standard browser env (web workers, react-native) lack needed support. (function nonStandardBrowserEnv() { return { write: function write() {}, read: function read() { return null; }, remove: function remove() {} }; })() ); var btoa$1 = (typeof window !== 'undefined' && window.btoa && window.btoa.bind(window)) || btoa_1; var xhr = function xhrAdapter(config) { return new Promise(function dispatchXhrRequest(resolve, reject) { var requestData = config.data; var requestHeaders = config.headers; if (utils.isFormData(requestData)) { delete requestHeaders['Content-Type']; // Let the browser set it } var request = new XMLHttpRequest(); var loadEvent = 'onreadystatechange'; var xDomain = false; // For IE 8/9 CORS support // Only supports POST and GET calls and doesn't returns the response headers. // DON'T do this for testing b/c XMLHttpRequest is mocked, not XDomainRequest. if (process.env.NODE_ENV !== 'test' && typeof window !== 'undefined' && window.XDomainRequest && !('withCredentials' in request) && !isURLSameOrigin(config.url)) { request = new window.XDomainRequest(); loadEvent = 'onload'; xDomain = true; request.onprogress = function handleProgress() {}; request.ontimeout = function handleTimeout() {}; } // HTTP basic authentication if (config.auth) { var username = config.auth.username || ''; var password = config.auth.password || ''; requestHeaders.Authorization = 'Basic ' + btoa$1(username + ':' + password); } request.open(config.method.toUpperCase(), buildURL(config.url, config.params, config.paramsSerializer), true); // Set the request timeout in MS request.timeout = config.timeout; // Listen for ready state request[loadEvent] = function handleLoad() { if (!request || (request.readyState !== 4 && !xDomain)) { return; } // The request errored out and we didn't get a response, this will be // handled by onerror instead // With one exception: request that using file: protocol, most browsers // will return status as 0 even though it's a successful request if (request.status === 0 && !(request.responseURL && request.responseURL.indexOf('file:') === 0)) { return; } // Prepare the response var responseHeaders = 'getAllResponseHeaders' in request ? parseHeaders(request.getAllResponseHeaders()) : null; var responseData = !config.responseType || config.responseType === 'text' ? request.responseText : request.response; var response = { data: responseData, // IE sends 1223 instead of 204 (https://github.com/axios/axios/issues/201) status: request.status === 1223 ? 204 : request.status, statusText: request.status === 1223 ? 'No Content' : request.statusText, headers: responseHeaders, config: config, request: request }; settle(resolve, reject, response); // Clean up request request = null; }; // Handle low level network errors request.onerror = function handleError() { // Real errors are hidden from us by the browser // onerror should only fire if it's a network error reject(createError('Network Error', config, null, request)); // Clean up request request = null; }; // Handle timeout request.ontimeout = function handleTimeout() { reject(createError('timeout of ' + config.timeout + 'ms exceeded', config, 'ECONNABORTED', request)); // Clean up request request = null; }; // Add xsrf header // This is only done if running in a standard browser environment. // Specifically not if we're in a web worker, or react-native. if (utils.isStandardBrowserEnv()) { var cookies$$1 = cookies; // Add xsrf header var xsrfValue = (config.withCredentials || isURLSameOrigin(config.url)) && config.xsrfCookieName ? cookies$$1.read(config.xsrfCookieName) : undefined; if (xsrfValue) { requestHeaders[config.xsrfHeaderName] = xsrfValue; } } // Add headers to the request if ('setRequestHeader' in request) { utils.forEach(requestHeaders, function setRequestHeader(val, key) { if (typeof requestData === 'undefined' && key.toLowerCase() === 'content-type') { // Remove Content-Type if data is undefined delete requestHeaders[key]; } else { // Otherwise add header to the request request.setRequestHeader(key, val); } }); } // Add withCredentials to request if needed if (config.withCredentials) { request.withCredentials = true; } // Add responseType to request if needed if (config.responseType) { try { request.responseType = config.responseType; } catch (e) { // Expected DOMException thrown by browsers not compatible XMLHttpRequest Level 2. // But, this can be suppressed for 'json' type as it can be parsed by default 'transformResponse' function. if (config.responseType !== 'json') { throw e; } } } // Handle progress if needed if (typeof config.onDownloadProgress === 'function') { request.addEventListener('progress', config.onDownloadProgress); } // Not all browsers support upload events if (typeof config.onUploadProgress === 'function' && request.upload) { request.upload.addEventListener('progress', config.onUploadProgress); } if (config.cancelToken) { // Handle cancellation config.cancelToken.promise.then(function onCanceled(cancel) { if (!request) { return; } request.abort(); reject(cancel); // Clean up request request = null; }); } if (requestData === undefined) { requestData = null; } // Send the request request.send(requestData); }); }; var DEFAULT_CONTENT_TYPE = { 'Content-Type': 'application/x-www-form-urlencoded' }; function setContentTypeIfUnset(headers, value) { if (!utils.isUndefined(headers) && utils.isUndefined(headers['Content-Type'])) { headers['Content-Type'] = value; } } function getDefaultAdapter() { var adapter; if (typeof XMLHttpRequest !== 'undefined') { // For browsers use XHR adapter adapter = xhr; } else if (typeof process !== 'undefined') { // For node use HTTP adapter adapter = xhr; } return adapter; } var defaults = { adapter: getDefaultAdapter(), transformRequest: [function transformRequest(data, headers) { normalizeHeaderName(headers, 'Content-Type'); if (utils.isFormData(data) || utils.isArrayBuffer(data) || utils.isBuffer(data) || utils.isStream(data) || utils.isFile(data) || utils.isBlob(data) ) { return data; } if (utils.isArrayBufferView(data)) { return data.buffer; } if (utils.isURLSearchParams(data)) { setContentTypeIfUnset(headers, 'application/x-www-form-urlencoded;charset=utf-8'); return data.toString(); } if (utils.isObject(data)) { setContentTypeIfUnset(headers, 'application/json;charset=utf-8'); return JSON.stringify(data); } return data; }], transformResponse: [function transformResponse(data) { /*eslint no-param-reassign:0*/ if (typeof data === 'string') { try { data = JSON.parse(data); } catch (e) { /* Ignore */ } } return data; }], /** * A timeout in milliseconds to abort a request. If set to 0 (default) a * timeout is not created. */ timeout: 0, xsrfCookieName: 'XSRF-TOKEN', xsrfHeaderName: 'X-XSRF-TOKEN', maxContentLength: -1, validateStatus: function validateStatus(status) { return status >= 200 && status < 300; } }; defaults.headers = { common: { 'Accept': 'application/json, text/plain, */*' } }; utils.forEach(['delete', 'get', 'head'], function forEachMethodNoData(method) { defaults.headers[method] = {}; }); utils.forEach(['post', 'put', 'patch'], function forEachMethodWithData(method) { defaults.headers[method] = utils.merge(DEFAULT_CONTENT_TYPE); }); var defaults_1 = defaults; function InterceptorManager() { this.handlers = []; } /** * Add a new interceptor to the stack * * @param {Function} fulfilled The function to handle `then` for a `Promise` * @param {Function} rejected The function to handle `reject` for a `Promise` * * @return {Number} An ID used to remove interceptor later */ InterceptorManager.prototype.use = function use(fulfilled, rejected) { this.handlers.push({ fulfilled: fulfilled, rejected: rejected }); return this.handlers.length - 1; }; /** * Remove an interceptor from the stack * * @param {Number} id The ID that was returned by `use` */ InterceptorManager.prototype.eject = function eject(id) { if (this.handlers[id]) { this.handlers[id] = null; } }; /** * Iterate over all the registered interceptors * * This method is particularly useful for skipping over any * interceptors that may have become `null` calling `eject`. * * @param {Function} fn The function to call for each interceptor */ InterceptorManager.prototype.forEach = function forEach(fn) { utils.forEach(this.handlers, function forEachHandler(h) { if (h !== null) { fn(h); } }); }; var InterceptorManager_1 = InterceptorManager; /** * Transform the data for a request or a response * * @param {Object|String} data The data to be transformed * @param {Array} headers The headers for the request or response * @param {Array|Function} fns A single function or Array of functions * @returns {*} The resulting transformed data */ var transformData = function transformData(data, headers, fns) { /*eslint no-param-reassign:0*/ utils.forEach(fns, function transform(fn) { data = fn(data, headers); }); return data; }; var isCancel = function isCancel(value) { return !!(value && value.__CANCEL__); }; /** * Determines whether the specified URL is absolute * * @param {string} url The URL to test * @returns {boolean} True if the specified URL is absolute, otherwise false */ var isAbsoluteURL = function isAbsoluteURL(url) { // A URL is considered absolute if it begins with "<scheme>://" or "//" (protocol-relative URL). // RFC 3986 defines scheme name as a sequence of characters beginning with a letter and followed // by any combination of letters, digits, plus, period, or hyphen. return /^([a-z][a-z\d\+\-\.]*:)?\/\//i.test(url); }; /** * Creates a new URL by combining the specified URLs * * @param {string} baseURL The base URL * @param {string} relativeURL The relative URL * @returns {string} The combined URL */ var combineURLs = function combineURLs(baseURL, relativeURL) { return relativeURL ? baseURL.replace(/\/+$/, '') + '/' + relativeURL.replace(/^\/+/, '') : baseURL; }; /** * Throws a `Cancel` if cancellation has been requested. */ function throwIfCancellationRequested(config) { if (config.cancelToken) { config.cancelToken.throwIfRequested(); } } /** * Dispatch a request to the server using the configured adapter. * * @param {object} config The config that is to be used for the request * @returns {Promise} The Promise to be fulfilled */ var dispatchRequest = function dispatchRequest(config) { throwIfCancellationRequested(config); // Support baseURL config if (config.baseURL && !isAbsoluteURL(config.url)) { config.url = combineURLs(config.baseURL, config.url); } // Ensure headers exist config.headers = config.headers || {}; // Transform request data config.data = transformData( config.data, config.headers, config.transformRequest ); // Flatten headers config.headers = utils.merge( config.headers.common || {}, config.headers[config.method] || {}, config.headers || {} ); utils.forEach( ['delete', 'get', 'head', 'post', 'put', 'patch', 'common'], function cleanHeaderConfig(method) { delete config.headers[method]; } ); var adapter = config.adapter || defaults_1.adapter; return adapter(config).then(function onAdapterResolution(response) { throwIfCancellationRequested(config); // Transform response data response.data = transformData( response.data, response.headers, config.transformResponse ); return response; }, function onAdapterRejection(reason) { if (!isCancel(reason)) { throwIfCancellationRequested(config); // Transform response data if (reason && reason.response) { reason.response.data = transformData( reason.response.data, reason.response.headers, config.transformResponse ); } } return Promise.reject(reason); }); }; /** * Create a new instance of Axios * * @param {Object} instanceConfig The default config for the instance */ function Axios(instanceConfig) { this.defaults = instanceConfig; this.interceptors = { request: new InterceptorManager_1(), response: new InterceptorManager_1() }; } /** * Dispatch a request * * @param {Object} config The config specific for this request (merged with this.defaults) */ Axios.prototype.request = function request(config) { /*eslint no-param-reassign:0*/ // Allow for axios('example/url'[, config]) a la fetch API if (typeof config === 'string') { config = utils.merge({ url: arguments[0] }, arguments[1]); } config = utils.merge(defaults_1, {method: 'get'}, this.defaults, config); config.method = config.method.toLowerCase(); // Hook up interceptors middleware var chain = [dispatchRequest, undefined]; var promise = Promise.resolve(config); this.interceptors.request.forEach(function unshiftRequestInterceptors(interceptor) { chain.unshift(interceptor.fulfilled, interceptor.rejected); }); this.interceptors.response.forEach(function pushResponseInterceptors(interceptor) { chain.push(interceptor.fulfilled, interceptor.rejected); }); while (chain.length) { promise = promise.then(chain.shift(), chain.shift()); } return promise; }; // Provide aliases for supported request methods utils.forEach(['delete', 'get', 'head', 'options'], function forEachMethodNoData(method) { /*eslint func-names:0*/ Axios.prototype[method] = function(url, config) { return this.request(utils.merge(config || {}, { method: method, url: url })); }; }); utils.forEach(['post', 'put', 'patch'], function forEachMethodWithData(method) { /*eslint func-names:0*/ Axios.prototype[method] = function(url, data, config) { return this.request(utils.merge(config || {}, { method: method, url: url, data: data })); }; }); var Axios_1 = Axios; /** * A `Cancel` is an object that is thrown when an operation is canceled. * * @class * @param {string=} message The message. */ function Cancel(message) { this.message = message; } Cancel.prototype.toString = function toString() { return 'Cancel' + (this.message ? ': ' + this.message : ''); }; Cancel.prototype.__CANCEL__ = true; var Cancel_1 = Cancel; /** * A `CancelToken` is an object that can be used to request cancellation of an operation. * * @class * @param {Function} executor The executor function. */ function CancelToken(executor) { if (typeof executor !== 'function') { throw new TypeError('executor must be a function.'); } var resolvePromise; this.promise = new Promise(function promiseExecutor(resolve) { resolvePromise = resolve; }); var token = this; executor(function cancel(message) { if (token.reason) { // Cancellation has already been requested return; } token.reason = new Cancel_1(message); resolvePromise(token.reason); }); } /** * Throws a `Cancel` if cancellation has been requested. */ CancelToken.prototype.throwIfRequested = function throwIfRequested() { if (this.reason) { throw this.reason; } }; /** * Returns an object that contains a new `CancelToken` and a function that, when called, * cancels the `CancelToken`. */ CancelToken.source = function source() { var cancel; var token = new CancelToken(function executor(c) { cancel = c; }); return { token: token, cancel: cancel }; }; var CancelToken_1 = CancelToken; /** * Syntactic sugar for invoking a function and expanding an array for arguments. * * Common use case would be to use `Function.prototype.apply`. * * ```js * function f(x, y, z) {} * var args = [1, 2, 3]; * f.apply(null, args); * ``` * * With `spread` this example can be re-written. * * ```js * spread(function(x, y, z) {})([1, 2, 3]); * ``` * * @param {Function} callback * @returns {Function} */ var spread = function spread(callback) { return function wrap(arr) { return callback.apply(null, arr); }; }; /** * Create an instance of Axios * * @param {Object} defaultConfig The default config for the instance * @return {Axios} A new instance of Axios */ function createInstance(defaultConfig) { var context = new Axios_1(defaultConfig); var instance = bind(Axios_1.prototype.request, context); // Copy axios.prototype to instance utils.extend(instance, Axios_1.prototype, context); // Copy context to instance utils.extend(instance, context); return instance; } // Create the default instance to be exported var axios = createInstance(defaults_1); // Expose Axios class to allow class inheritance axios.Axios = Axios_1; // Factory for creating new instances axios.create = function create(instanceConfig) { return createInstance(utils.merge(defaults_1, instanceConfig)); }; // Expose Cancel & CancelToken axios.Cancel = Cancel_1; axios.CancelToken = CancelToken_1; axios.isCancel = isCancel; // Expose all/spread axios.all = function all(promises) { return Promise.all(promises); }; axios.spread = spread; var axios_1 = axios; // Allow use of default import syntax in TypeScript var default_1 = axios; axios_1.default = default_1; var axios$1 = axios_1; var bind$1 = function bind(fn, thisArg) { return function wrap() { var args = new Array(arguments.length); for (var i = 0; i < args.length; i++) { args[i] = arguments[i]; } return fn.apply(thisArg, args); }; }; /*global toString:true*/ // utils is a library of generic helper functions non-specific to axios var toString$1 = Object.prototype.toString; /** * Determine if a value is an Array * * @param {Object} val The value to test * @returns {boolean} True if value is an Array, otherwise false */ function isArray$1(val) { return toString$1.call(val) === '[object Array]'; } /** * Determine if a value is an ArrayBuffer * * @param {Object} val The value to test * @returns {boolean} True if value is an ArrayBuffer, otherwise false */ function isArrayBuffer$1(val) { return toString$1.call(val) === '[object ArrayBuffer]'; } /** * Determine if a value is a FormData * * @param {Object} val The value to test * @returns {boolean} True if value is an FormData, otherwise false */ function isFormData$1(val) { return (typeof FormData !== 'undefined') && (val instanceof FormData); } /** * Determine if a value is a view on an ArrayBuffer * * @param {Object} val The value to test * @returns {boolean} True if value is a view on an ArrayBuffer, otherwise false */ function isArrayBufferView$1(val) { var result; if ((typeof ArrayBuffer !== 'undefined') && (ArrayBuffer.isView)) { result = ArrayBuffer.isView(val); } else { result = (val) && (val.buffer) && (val.buffer instanceof ArrayBuffer); } return result; } /** * Determine if a value is a String * * @param {Object} val The value to test * @returns {boolean} True if value is a String, otherwise false */ function isString$1(val) { return typeof val === 'string'; } /** * Determine if a value is a Number * * @param {Object} val The value to test * @returns {boolean} True if value is a Number, otherwise false */ function isNumber$1(val) { return typeof val === 'number'; } /** * Determine if a value is undefined * * @param {Object} val The value to test * @returns {boolean} True if the value is undefined, otherwise false */ function isUndefined$1(val) { return typeof val === 'undefined'; } /** * Determine if a value is an Object * * @param {Object} val The value to test * @returns {boolean} True if value is an Object, otherwise false */ function isObject$1(val) { return val !== null && typeof val === 'object'; } /** * Determine if a value is a Date * * @param {Object} val The value to test * @returns {boolean} True if value is a Date, otherwise false */ function isDate$1(val) { return toString$1.call(val) === '[object Date]'; } /** * Determine if a value is a File * * @param {Object} val The value to test * @returns {boolean} True if value is a File, otherwise false */ function isFile$1(val) { return toString$1.call(val) === '[object File]'; } /** * Determine if a value is a Blob * * @param {Object} val The value to test * @returns {boolean} True if value is a Blob, otherwise false */ function isBlob$1(val) { return toString$1.call(val) === '[object Blob]'; } /** * Determine if a value is a Function * * @param {Object} val The value to test * @returns {boolean} True if value is a Function, otherwise false */ function isFunction$1(val) { return toString$1.call(val) === '[object Function]'; } /** * Determine if a value is a Stream * * @param {Object} val The value to test * @returns {boolean} True if value is a Stream, otherwise false */ function isStream$1(val) { return isObject$1(val) && isFunction$1(val.pipe); } /** * Determine if a value is a URLSearchParams object * * @param {Object} val The value to test * @returns {boolean} True if value is a URLSearchParams object, otherwise false */ function isURLSearchParams$1(val) { return typeof URLSearchParams !== 'undefined' && val instanceof URLSearchParams; } /** * Trim excess whitespace off the beginning and end of a string * * @param {String} str The String to trim * @returns {String} The String freed of excess whitespace */ function trim$1(str) { return str.replace(/^\s*/, '').replace(/\s*$/, ''); } /** * Determine if we're running in a standard browser environment * * This allows axios to run in a web worker, and react-native. * Both environments support XMLHttpRequest, but not fully standard globals. * * web workers: * typeof window -> undefined * typeof document -> undefined * * react-native: * navigator.product -> 'ReactNative' */ function isStandardBrowserEnv$1() { if (typeof navigator !== 'undefined' && navigator.product === 'ReactNative') { return false; } return ( typeof window !== 'undefined' && typeof document !== 'undefined' ); } /** * Iterate over an Array or an Object invoking a function for each item. * * If `obj` is an Array callback will be called passing * the value, index, and complete array for each item. * * If 'obj' is an Object callback will be called passing * the value, key, and complete object for each property. * * @param {Object|Array} obj The object to iterate * @param {Function} fn The callback to invoke for each item */ function forEach$1(obj, fn) { // Don't bother if no value provided if (obj === null || typeof obj === 'undefined') { return; } // Force an array if not already something iterable if (typeof obj !== 'object') { /*eslint no-param-reassign:0*/ obj = [obj]; } if (isArray$1(obj)) { // Iterate over array values for (var i = 0, l = obj.length; i < l; i++) { fn.call(null, obj[i], i, obj); } } else { // Iterate over object keys for (var key in obj) { if (Object.prototype.hasOwnProperty.call(obj, key)) { fn.call(null, obj[key], key, obj); } } } } /** * Accepts varargs expecting each argument to be an object, then * immutably merges the properties of each object and returns result. * * When multiple objects contain the same key the later object in * the arguments list will take precedence. * * Example: * * ```js * var result = merge({foo: 123}, {foo: 456}); * console.log(result.foo); // outputs 456 * ``` * * @param {Object} obj1 Object to merge * @returns {Object} Result of all merge properties */ function merge$1(/* obj1, obj2, obj3, ... */) { var result = {}; function assignValue(val, key) { if (typeof result[key] === 'object' && typeof val === 'object') { result[key] = merge$1(result[key], val); } else { result[key] = val; } } for (var i = 0, l = arguments.length; i < l; i++) { forEach$1(arguments[i], assignValue); } return result; } /** * Extends object a by mutably adding to it the properties of object b. * * @param {Object} a The object to be extended * @param {Object} b The object to copy properties from * @param {Object} thisArg The object to bind function to * @return {Object} The resulting value of object a */ function extend$1(a, b, thisArg) { forEach$1(b, function assignValue(val, key) { if (thisArg && typeof val === 'function') { a[key] = bind$1(val, thisArg); } else { a[key] = val; } }); return a; } var utils$1 = { isArray: isArray$1, isArrayBuffer: isArrayBuffer$1, isBuffer: isBuffer_1, isFormData: isFormData$1, isArrayBufferView: isArrayBufferView$1, isString: isString$1, isNumber: isNumber$1, isObject: isObject$1, isUndefined: isUndefined$1, isDate: isDate$1, isFile: isFile$1, isBlob: isBlob$1, isFunction: isFunction$1, isStream: isStream$1, isURLSearchParams: isURLSearchParams$1, isStandardBrowserEnv: isStandardBrowserEnv$1, forEach: forEach$1, merge: merge$1, extend: extend$1, trim: trim$1 }; var normalizeHeaderName$1 = function normalizeHeaderName(headers, normalizedName) { utils$1.forEach(headers, function processHeader(value, name) { if (name !== normalizedName && name.toUpperCase() === normalizedName.toUpperCase()) { headers[normalizedName] = value; delete headers[name]; } }); }; /** * Update an Error with the specified config, error code, and response. * * @param {Error} error The error to update. * @param {Object} config The config. * @param {string} [code] The error code (for example, 'ECONNABORTED'). * @param {Object} [request] The request. * @param {Object} [response] The response. * @returns {Error} The error. */ var enhanceError$1 = function enhanceError(error, config, code, request, response) { error.config = config; if (code) { error.code = code; } error.request = request; error.response = response; return error; }; /** * Create an Error with the specified message, config, error code, request and response. * * @param {string} message The error message. * @param {Object} config The config. * @param {string} [code] The error code (for example, 'ECONNABORTED'). * @param {Object} [request] The request. * @param {Object} [response] The response. * @returns {Error} The created error. */ var createError$1 = function createError(message, config, code, request, response) { var error = new Error(message); return enhanceError$1(error, config, code, request, response); }; /** * Resolve or reject a Promise based on response status. * * @param {Function} resolve A function that resolves the promise. * @param {Function} reject A function that rejects the promise. * @param {object} response The response. */ var settle$1 = function settle(resolve, reject, response) { var validateStatus = response.config.validateStatus; // Note: status is not exposed by XDomainRequest if (!response.status || !validateStatus || validateStatus(response.status)) { resolve(response); } else { reject(createError$1( 'Request failed with status code ' + response.status, response.config, null, response.request, response )); } }; function encode$1(val) { return encodeURIComponent(val). replace(/%40/gi, '@'). replace(/%3A/gi, ':'). replace(/%24/g, '$'). replace(/%2C/gi, ','). replace(/%20/g, '+'). replace(/%5B/gi, '['). replace(/%5D/gi, ']'); } /** * Build a URL by appending params to the end * * @param {string} url The base of the url (e.g., http://www.google.com) * @param {object} [params] The params to be appended * @returns {string} The formatted url */ var buildURL$1 = function buildURL(url, params, paramsSerializer) { /*eslint no-param-reassign:0*/ if (!params) { return url; } var serializedParams; if (paramsSerializer) { serializedParams = paramsSerializer(params); } else if (utils$1.isURLSearchParams(params)) { serializedParams = params.toString(); } else { var parts = []; utils$1.forEach(params, function serialize(val, key) { if (val === null || typeof val === 'undefined') { return; } if (utils$1.isArray(val)) { key = key + '[]'; } if (!utils$1.isArray(val)) { val = [val]; } utils$1.forEach(val, function parseValue(v) { if (utils$1.isDate(v)) { v = v.toISOString(); } else if (utils$1.isObject(v)) { v = JSON.stringify(v); } parts.push(encode$1(key) + '=' + encode$1(v)); }); }); serializedParams = parts.join('&'); } if (serializedParams) { url += (url.indexOf('?') === -1 ? '?' : '&') + serializedParams; } return url; }; // Headers whose duplicates are ignored by node // c.f. https://nodejs.org/api/http.html#http_message_headers var ignoreDuplicateOf$1 = [ 'age', 'authorization', 'content-length', 'content-type', 'etag', 'expires', 'from', 'host', 'if-modified-since', 'if-unmodified-since', 'last-modified', 'location', 'max-forwards', 'proxy-authorization', 'referer', 'retry-after', 'user-agent' ]; /** * Parse headers into an object * * ``` * Date: Wed, 27 Aug 2014 08:58:49 GMT * Content-Type: application/json * Connection: keep-alive * Transfer-Encoding: chunked * ``` * * @param {String} headers Headers needing to be parsed * @returns {Object} Headers parsed into an object */ var parseHeaders$1 = function parseHeaders(headers) { var parsed = {}; var key; var val; var i; if (!headers) { return parsed; } utils$1.forEach(headers.split('\n'), function parser(line) { i = line.indexOf(':'); key = utils$1.trim(line.substr(0, i)).toLowerCase(); val = utils$1.trim(line.substr(i + 1)); if (key) { if (parsed[key] && ignoreDuplicateOf$1.indexOf(key) >= 0) { return; } if (key === 'set-cookie') { parsed[key] = (parsed[key] ? parsed[key] : []).concat([val]); } else { parsed[key] = parsed[key] ? parsed[key] + ', ' + val : val; } } }); return parsed; }; var isURLSameOrigin$1 = ( utils$1.isStandardBrowserEnv() ? // Standard browser envs have full support of the APIs needed to test // whether the request URL is of the same origin as current location. (function standardBrowserEnv() { var msie = /(msie|trident)/i.test(navigator.userAgent); var urlParsingNode = document.createElement('a'); var originURL; /** * Parse a URL to discover it's components * * @param {String} url The URL to be parsed * @returns {Object} */ function resolveURL(url) { var href = url; if (msie) { // IE needs attribute set twice to normalize properties urlParsingNode.setAttribute('href', href); href = urlParsingNode.href; } urlParsingNode.setAttribute('href', href); // urlParsingNode provides the UrlUtils interface - http://url.spec.whatwg.org/#urlutils return { href: urlParsingNode.href, protocol: urlParsingNode.protocol ? urlParsingNode.protocol.replace(/:$/, '') : '', host: urlParsingNode.host, search: urlParsingNode.search ? urlParsingNode.search.replace(/^\?/, '') : '', hash: urlParsingNode.hash ? urlParsingNode.hash.replace(/^#/, '') : '', hostname: urlParsingNode.hostname, port: urlParsingNode.port, pathname: (urlParsingNode.pathname.charAt(0) === '/') ? urlParsingNode.pathname : '/' + urlParsingNode.pathname }; } originURL = resolveURL(window.location.href); /** * Determine if a URL shares the same origin as the current location * * @param {String} requestURL The URL to test * @returns {boolean} True if URL shares the same origin, otherwise false */ return function isURLSameOrigin(requestURL) { var parsed = (utils$1.isString(requestURL)) ? resolveURL(requestURL) : requestURL; return (parsed.protocol === originURL.protocol && parsed.host === originURL.host); }; })() : // Non standard browser envs (web workers, react-native) lack needed support. (function nonStandardBrowserEnv() { return function isURLSameOrigin() { return true; }; })() ); // btoa polyfill for IE<10 courtesy https://github.com/davidchambers/Base64.js var chars$1 = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/='; function E$1() { this.message = 'String contains an invalid character'; } E$1.prototype = new Error; E$1.prototype.code = 5; E$1.prototype.name = 'InvalidCharacterError'; function btoa$2(input) { var str = String(input); var output = ''; for ( // initialize result and counter var block, charCode, idx = 0, map = chars$1; // if the next str index does not exist: // change the mapping table to "=" // check if d has no fractional digits str.charAt(idx | 0) || (map = '=', idx % 1); // "8 - idx % 1 * 8" generates the sequence 2, 4, 6, 8 output += map.charAt(63 & block >> 8 - idx % 1 * 8) ) { charCode = str.charCodeAt(idx += 3 / 4); if (charCode > 0xFF) { throw new E$1(); } block = block << 8 | charCode; } return output; } var btoa_1$1 = btoa$2; var cookies$1 = ( utils$1.isStandardBrowserEnv() ? // Standard browser envs support document.cookie (function standardBrowserEnv() { return { write: function write(name, value, expires, path, domain, secure) { var cookie = []; cookie.push(name + '=' + encodeURIComponent(value)); if (utils$1.isNumber(expires)) { cookie.push('expires=' + new Date(expires).toGMTString()); } if (utils$1.isString(path)) { cookie.push('path=' + path); } if (utils$1.isString(domain)) { cookie.push('domain=' + domain); } if (secure === true) { cookie.push('secure'); } document.cookie = cookie.join('; '); }, read: function read(name) { var match = document.cookie.match(new RegExp('(^|;\\s*)(' + name + ')=([^;]*)')); return (match ? decodeURIComponent(match[3]) : null); }, remove: function remove(name) { this.write(name, '', Date.now() - 86400000); } }; })() : // Non standard browser env (web workers, react-native) lack needed support. (function nonStandardBrowserEnv() { return { write: function write() {}, read: function read() { return null; }, remove: function remove() {} }; })() ); var btoa$3 = (typeof window !== 'undefined' && window.btoa && window.btoa.bind(window)) || btoa_1$1; var xhr$1 = function xhrAdapter(config) { return new Promise(function dispatchXhrRequest(resolve, reject) { var requestData = config.data; var requestHeaders = config.headers; if (utils$1.isFormData(requestData)) { delete requestHeaders['Content-Type']; // Let the browser set it } var request = new XMLHttpRequest(); var loadEvent = 'onreadystatechange'; var xDomain = false; // For IE 8/9 CORS support // Only supports POST and GET calls and doesn't returns the response headers. // DON'T do this for testing b/c XMLHttpRequest is mocked, not XDomainRequest. if (process.env.NODE_ENV !== 'test' && typeof window !== 'undefined' && window.XDomainRequest && !('withCredentials' in request) && !isURLSameOrigin$1(config.url)) { request = new window.XDomainRequest(); loadEvent = 'onload'; xDomain = true; request.onprogress = function handleProgress() {}; request.ontimeout = function handleTimeout() {}; } // HTTP basic authentication if (config.auth) { var username = config.auth.username || ''; var password = config.auth.password || ''; requestHeaders.Authorization = 'Basic ' + btoa$3(username + ':' + password); } request.open(config.method.toUpperCase(), buildURL$1(config.url, config.params, config.paramsSerializer), true); // Set the request timeout in MS request.timeout = config.timeout; // Listen for ready state request[loadEvent] = function handleLoad() { if (!request || (request.readyState !== 4 && !xDomain)) { return; } // The request errored out and we didn't get a response, this will be // handled by onerror instead // With one exception: request that using file: protocol, most browsers // will return status as 0 even though it's a successful request if (request.status === 0 && !(request.responseURL && request.responseURL.indexOf('file:') === 0)) { return; } // Prepare the response var responseHeaders = 'getAllResponseHeaders' in request ? parseHeaders$1(request.getAllResponseHeaders()) : null; var responseData = !config.responseType || config.responseType === 'text' ? request.responseText : request.response; var response = { data: responseData, // IE sends 1223 instead of 204 (https://github.com/axios/axios/issues/201) status: request.status === 1223 ? 204 : request.status, statusText: request.status === 1223 ? 'No Content' : request.statusText, headers: responseHeaders, config: config, request: request }; settle$1(resolve, reject, response); // Clean up request request = null; }; // Handle low level network errors request.onerror = function handleError() { // Real errors are hidden from us by the browser // onerror should only fire if it's a network error reject(createError$1('Network Error', config, null, request)); // Clean up request request = null; }; // Handle timeout request.ontimeout = function handleTimeout() { reject(createError$1('timeout of ' + config.timeout + 'ms exceeded', config, 'ECONNABORTED', request)); // Clean up request request = null; }; // Add xsrf header // This is only done if running in a standard browser environment. // Specifically not if we're in a web worker, or react-native. if (utils$1.isStandardBrowserEnv()) { var cookies = cookies$1; // Add xsrf header var xsrfValue = (config.withCredentials || isURLSameOrigin$1(config.url)) && config.xsrfCookieName ? cookies.read(config.xsrfCookieName) : undefined; if (xsrfValue) { requestHeaders[config.xsrfHeaderName] = xsrfValue; } } // Add headers to the request if ('setRequestHeader' in request) { utils$1.forEach(requestHeaders, function setRequestHeader(val, key) { if (typeof requestData === 'undefined' && key.toLowerCase() === 'content-type') { // Remove Content-Type if data is undefined delete requestHeaders[key]; } else { // Otherwise add header to the request request.setRequestHeader(key, val); } }); } // Add withCredentials to request if needed if (config.withCredentials) { request.withCredentials = true; } // Add responseType to request if needed if (config.responseType) { try { request.responseType = config.responseType; } catch (e) { // Expected DOMException thrown by browsers not compatible XMLHttpRequest Level 2. // But, this can be suppressed for 'json' type as it can be parsed by default 'transformResponse' function. if (config.responseType !== 'json') { throw e; } } } // Handle progress if needed if (typeof config.onDownloadProgress === 'function') { request.addEventListener('progress', config.onDownloadProgress); } // Not all browsers support upload events if (typeof config.onUploadProgress === 'function' && request.upload) { request.upload.addEventListener('progress', config.onUploadProgress); } if (config.cancelToken) { // Handle cancellation config.cancelToken.promise.then(function onCanceled(cancel) { if (!request) { return; } request.abort(); reject(cancel); // Clean up request request = null; }); } if (requestData === undefined) { requestData = null; } // Send the request request.send(requestData); }); }; var DEFAULT_CONTENT_TYPE$1 = { 'Content-Type': 'application/x-www-form-urlencoded' }; function setContentTypeIfUnset$1(headers, value) { if (!utils$1.isUndefined(headers) && utils$1.isUndefined(headers['Content-Type'])) { headers['Content-Type'] = value; } } function getDefaultAdapter$1() { var adapter; if (typeof XMLHttpRequest !== 'undefined') { // For browsers use XHR adapter adapter = xhr$1; } else if (typeof process !== 'undefined') { // For node use HTTP adapter adapter = xhr$1; } return adapter; } var defaults$1 = { adapter: getDefaultAdapter$1(), transformRequest: [function transformRequest(data, headers) { normalizeHeaderName$1(headers, 'Content-Type'); if (utils$1.isFormData(data) || utils$1.isArrayBuffer(data) || utils$1.isBuffer(data) || utils$1.isStream(data) || utils$1.isFile(data) || utils$1.isBlob(data) ) { return data; } if (utils$1.isArrayBufferView(data)) { return data.buffer; } if (utils$1.isURLSearchParams(data)) { setContentTypeIfUnset$1(headers, 'application/x-www-form-urlencoded;charset=utf-8'); return data.toString(); } if (utils$1.isObject(data)) { setContentTypeIfUnset$1(headers, 'application/json;charset=utf-8'); return JSON.stringify(data); } return data; }], transformResponse: [function transformResponse(data) { /*eslint no-param-reassign:0*/ if (typeof data === 'string') { try { data = JSON.parse(data); } catch (e) { /* Ignore */ } } return data; }], timeout: 0, xsrfCookieName: 'XSRF-TOKEN', xsrfHeaderName: 'X-XSRF-TOKEN', maxContentLength: -1, validateStatus: function validateStatus(status) { return status >= 200 && status < 300; } }; defaults$1.headers = { common: { 'Accept': 'application/json, text/plain, */*' } }; utils$1.forEach(['delete', 'get', 'head'], function forEachMethodNoData(method) { defaults$1.headers[method] = {}; }); utils$1.forEach(['post', 'put', 'patch'], function forEachMethodWithData(method) { defaults$1.headers[method] = utils$1.merge(DEFAULT_CONTENT_TYPE$1); }); var defaults_1$1 = defaults$1; function InterceptorManager$1() { this.handlers = []; } /** * Add a new interceptor to the stack * * @param {Function} fulfilled The function to handle `then` for a `Promise` * @param {Function} rejected The function to handle `reject` for a `Promise` * * @return {Number} An ID used to remove interceptor later */ InterceptorManager$1.prototype.use = function use(fulfilled, rejected) { this.handlers.push({ fulfilled: fulfilled, rejected: rejected }); return this.handlers.length - 1; }; /** * Remove an interceptor from the stack * * @param {Number} id The ID that was returned by `use` */ InterceptorManager$1.prototype.eject = function eject(id) { if (this.handlers[id]) { this.handlers[id] = null; } }; /** * Iterate over all the registered interceptors * * This method is particularly useful for skipping over any * interceptors that may have become `null` calling `eject`. * * @param {Function} fn The function to call for each interceptor */ InterceptorManager$1.prototype.forEach = function forEach(fn) { utils$1.forEach(this.handlers, function forEachHandler(h) { if (h !== null) { fn(h); } }); }; var InterceptorManager_1$1 = InterceptorManager$1; /** * Transform the data for a request or a response * * @param {Object|String} data The data to be transformed * @param {Array} headers The headers for the request or response * @param {Array|Function} fns A single function or Array of functions * @returns {*} The resulting transformed data */ var transformData$1 = function transformData(data, headers, fns) { /*eslint no-param-reassign:0*/ utils$1.forEach(fns, function transform(fn) { data = fn(data, headers); }); return data; }; var isCancel$1 = function isCancel(value) { return !!(value && value.__CANCEL__); }; /** * Determines whether the specified URL is absolute * * @param {string} url The URL to test * @returns {boolean} True if the specified URL is absolute, otherwise false */ var isAbsoluteURL$1 = function isAbsoluteURL(url) { // A URL is considered absolute if it begins with "<scheme>://" or "//" (protocol-relative URL). // RFC 3986 defines scheme name as a sequence of characters beginning with a letter and followed // by any combination of letters, digits, plus, period, or hyphen. return /^([a-z][a-z\d\+\-\.]*:)?\/\//i.test(url); }; /** * Creates a new URL by combining the specified URLs * * @param {string} baseURL The base URL * @param {string} relativeURL The relative URL * @returns {string} The combined URL */ var combineURLs$1 = function combineURLs(baseURL, relativeURL) { return relativeURL ? baseURL.replace(/\/+$/, '') + '/' + relativeURL.replace(/^\/+/, '') : baseURL; }; /** * Throws a `Cancel` if cancellation has been requested. */ function throwIfCancellationRequested$1(config) { if (config.cancelToken) { config.cancelToken.throwIfRequested(); } } /** * Dispatch a request to the server using the configured adapter. * * @param {object} config The config that is to be used for the request * @returns {Promise} The Promise to be fulfilled */ var dispatchRequest$1 = function dispatchRequest(config) { throwIfCancellationRequested$1(config); // Support baseURL config if (config.baseURL && !isAbsoluteURL$1(config.url)) { config.url = combineURLs$1(config.baseURL, config.url); } // Ensure headers exist config.headers = config.headers || {}; // Transform request data config.data = transformData$1( config.data, config.headers, config.transformRequest ); // Flatten headers config.headers = utils$1.merge( config.headers.common || {}, config.headers[config.method] || {}, config.headers || {} ); utils$1.forEach( ['delete', 'get', 'head', 'post', 'put', 'patch', 'common'], function cleanHeaderConfig(method) { delete config.headers[method]; } ); var adapter = config.adapter || defaults_1$1.adapter; return adapter(config).then(function onAdapterResolution(response) { throwIfCancellationRequested$1(config); // Transform response data response.data = transformData$1( response.data, response.headers, config.transformResponse ); return response; }, function onAdapterRejection(reason) { if (!isCancel$1(reason)) { throwIfCancellationRequested$1(config); // Transform response data if (reason && reason.response) { reason.response.data = transformData$1( reason.response.data, reason.response.headers, config.transformResponse ); } } return Promise.reject(reason); }); }; /** * Create a new instance of Axios * * @param {Object} instanceConfig The default config for the instance */ function Axios$1(instanceConfig) { this.defaults = instanceConfig; this.interceptors = { request: new InterceptorManager_1$1(), response: new InterceptorManager_1$1() }; } /** * Dispatch a request * * @param {Object} config The config specific for this request (merged with this.defaults) */ Axios$1.prototype.request = function request(config) { /*eslint no-param-reassign:0*/ // Allow for axios('example/url'[, config]) a la fetch API if (typeof config === 'string') { config = utils$1.merge({ url: arguments[0] }, arguments[1]); } config = utils$1.merge(defaults_1$1, this.defaults, { method: 'get' }, config); config.method = config.method.toLowerCase(); // Hook up interceptors middleware var chain = [dispatchRequest$1, undefined]; var promise = Promise.resolve(config); this.interceptors.request.forEach(function unshiftRequestInterceptors(interceptor) { chain.unshift(interceptor.fulfilled, interceptor.rejected); }); this.interceptors.response.forEach(function pushResponseInterceptors(interceptor) { chain.push(interceptor.fulfilled, interceptor.rejected); }); while (chain.length) { promise = promise.then(chain.shift(), chain.shift()); } return promise; }; // Provide aliases for supported request methods utils$1.forEach(['delete', 'get', 'head', 'options'], function forEachMethodNoData(method) { /*eslint func-names:0*/ Axios$1.prototype[method] = function(url, config) { return this.request(utils$1.merge(config || {}, { method: method, url: url })); }; }); utils$1.forEach(['post', 'put', 'patch'], function forEachMethodWithData(method) { /*eslint func-names:0*/ Axios$1.prototype[method] = function(url, data, config) { return this.request(utils$1.merge(config || {}, { method: method, url: url, data: data })); }; }); var Axios_1$1 = Axios$1; /** * A `Cancel` is an object that is thrown when an operation is canceled. * * @class * @param {string=} message The message. */ function Cancel$1(message) { this.message = message; } Cancel$1.prototype.toString = function toString() { return 'Cancel' + (this.message ? ': ' + this.message : ''); }; Cancel$1.prototype.__CANCEL__ = true; var Cancel_1$1 = Cancel$1; /** * A `CancelToken` is an object that can be used to request cancellation of an operation. * * @class * @param {Function} executor The executor function. */ function CancelToken$1(executor) { if (typeof executor !== 'function') { throw new TypeError('executor must be a function.'); } var resolvePromise; this.promise = new Promise(function promiseExecutor(resolve) { resolvePromise = resolve; }); var token = this; executor(function cancel(message) { if (token.reason) { // Cancellation has already been requested return; } token.reason = new Cancel_1$1(message); resolvePromise(token.reason); }); } /** * Throws a `Cancel` if cancellation has been requested. */ CancelToken$1.prototype.throwIfRequested = function throwIfRequested() { if (this.reason) { throw this.reason; } }; /** * Returns an object that contains a new `CancelToken` and a function that, when called, * cancels the `CancelToken`. */ CancelToken$1.source = function source() { var cancel; var token = new CancelToken$1(function executor(c) { cancel = c; }); return { token: token, cancel: cancel }; }; var CancelToken_1$1 = CancelToken$1; /** * Syntactic sugar for invoking a function and expanding an array for arguments. * * Common use case would be to use `Function.prototype.apply`. * * ```js * function f(x, y, z) {} * var args = [1, 2, 3]; * f.apply(null, args); * ``` * * With `spread` this example can be re-written. * * ```js * spread(function(x, y, z) {})([1, 2, 3]); * ``` * * @param {Function} callback * @returns {Function} */ var spread$1 = function spread(callback) { return function wrap(arr) { return callback.apply(null, arr); }; }; /** * Create an instance of Axios * * @param {Object} defaultConfig The default config for the instance * @return {Axios} A new instance of Axios */ function createInstance$1(defaultConfig) { var context = new Axios_1$1(defaultConfig); var instance = bind$1(Axios_1$1.prototype.request, context); // Copy axios.prototype to instance utils$1.extend(instance, Axios_1$1.prototype, context); // Copy context to instance utils$1.extend(instance, context); return instance; } // Create the default instance to be exported var axios$2 = createInstance$1(defaults_1$1); // Expose Axios class to allow class inheritance axios$2.Axios = Axios_1$1; // Factory for creating new instances axios$2.create = function create(instanceConfig) { return createInstance$1(utils$1.merge(defaults_1$1, instanceConfig)); }; // Expose Cancel & CancelToken axios$2.Cancel = Cancel_1$1; axios$2.CancelToken = CancelToken_1$1; axios$2.isCancel = isCancel$1; // Expose all/spread axios$2.all = function all(promises) { return Promise.all(promises); }; axios$2.spread = spread$1; var axios_1$1 = axios$2; // Allow use of default import syntax in TypeScript var default_1$1 = axios$2; axios_1$1.default = default_1$1; var axios$3 = axios_1$1; function create(url, tags, level) { var options = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : {}; return new Logstash(url, tags, level, options); } function Logstash(url) { var tags = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : []; var level = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : "info"; var options = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : {}; if (!url) { throw new TypeError("Invalid URL"); } this.url = url; this.tags = tags; this.level = level; this.sendDelay = options.sendDelay || 100; this.retryDelay = options.retryDelay || 2000; this.muteConsole = options.muteConsole === true || false; this.isSending = false; this.queue = []; } Logstash.prototype._trySendEvent = function _trySendEvent() { var _this = this; if (!this.queue.length || this.isSending) { return; } this.isSending = true; var event = this.queue.shift(); var request = { url: this.url, method: 'post', headers: { 'Content-Type': 'application/json' }, data: event }; // HTTP request return axios$3(request).then(function () { _this.isSending = false; _this._trySendEvent(); }).catch(function (err) { console.error(err); // If we could not send the event, // put it back into queue _this.queue.unshift(event); _this.isSending = false; setTimeout(_this._trySendEvent.bind(_this), _this.retryDelay); }); }; Logstash.prototype.log = function log(level, message, fields) { var event = { level: level, fields: fields, message: message }; event['@timestamp'] = new Date().toISOString(); event['@tags'] = this.tags; // Navigator metadata if (typeof navigator !== 'undefined') { event.navigator = { cookieEnabled: navigator.cookieEnabled, geoLocation: navigator.geoLocation, language: navigator.language, languages: navigator.languages, online: navigator.online, userAgent: navigator.userAgent, platform: navigator.platform, vendor: navigator.vendor }; } // Location metadata if (typeof location !== 'undefined') { event.location = { search: location.search, pathname: location.pathname, hostname: location.hostname, protocol: location.protocol, port: location.port, hash: location.hash, href: location.href }; } this.queue.push(event); this._trySendEvent(); if (this.muteConsole) { return; } var fieldsStr = fields ? " - " + JSON.stringify(fields) : ''; switch (level) { case "error": console.error("" + message + fieldsStr); break; case "warn": console.warn("" + message + fieldsStr); break; default: console.info("" + message + fieldsStr); } }; Logstash.prototype.debug = function debug(message, fields) { this.log('debug', message, fields); }; Logstash.prototype.info = function info(message, fields) { this.log('info', message, fields); }; Logstash.prototype.warn = function warn(message, fields) { this.log('warn', message, fields); }; Logstash.prototype.error = function error(err, fields) { if (err instanceof Error) { this.log('error', err.message, Object.assign({ stack: err.stack }, fields)); } else { this.log('error', err, fields); } }; var dist = create; var classCallCheck = function (instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }; var createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }(); var _extends = Object.assign || function (target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) { if (Object.prototype.hasOwnProperty.call(source, key)) { target[key] = source[key]; } } } return target; }; var inherits = function (subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }; var possibleConstructorReturn = function (self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }; var formatUserSettings = function formatUserSettings(userSettings) { return _extends({}, userSettings, { userId: userSettings.userId ? userSettings.userId.toString() : '', subgroupId: userSettings.subgroupId ? userSettings.subgroupId.toString() : '', groupId: userSettings.groupId ? userSettings.groupId.toString() : '' }); }; var LogStash = function LogStash(model, label) { return new Promise(function (resolve, reject) { try { var firstDomainLevel = getFirstLevelDomain(); var url = 'https://videometrics.wyscout' + firstDomainLevel + ':8080'; // optional var tags = ['video', 'metrics']; var level = 'info'; model.userSettings = formatUserSettings(model.userSettings); var options = { muteConsole: true }; // Create logger instance var logger = dist(url, tags, level, options); logger.info(label, model); resolve(logger); } catch (err) { reject(err); } }); }; var RestApi = function RestApi(model) { return axios$1({ method: model.id ? 'PUT' : 'POST', url: model.id ? API_SERVER + ('metrics/' + model.id) : API_SERVER + 'metrics', data: model }); }; var getIpAddress = function getIpAddress() { return axios$1({ method: 'GET', url: 'https://opsapi.wyscout.com/v0.2/get_my_ip' }); }; var Caller = function Caller(model, label) { var transmission = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : TRANSMISSION_TYPE.LOGSTASH; return transmission === TRANSMISSION_TYPE.LOGSTASH ? LogStash(model, label) : RestApi(model, label); }; var getGlobalSwitchStatus = function getGlobalSwitchStatus(accessToken, apiHostname) { return axios$1({ method: 'GET', url: apiHostname + 'media/videometricsconfig/', params: { access_token: accessToken } }); }; var formatBufferedRanges = function formatBufferedRanges(video) { var formattedRanges = []; for (var i = 0; i < video.buffered.length; i++) { formattedRanges.push({ start: video.buffered.start(i), end: video.buffered.end(i) }); } return formattedRanges; }; var formatSeekableRanges = function formatSeekableRanges(video) { var formattedSeekableRanges = []; for (var i = 0; i < video.seekable.length; i++) { formattedSeekableRanges.push({ start: video.seekable.start(i), end: video.seekable.end(i) }); } return formattedSeekableRanges; }; var formatPlayedRanges = function formatPlayedRanges(video) { var formattedPlayedRanges = []; for (var i = 0; i < video.played.length; i++) { formattedPlayedRanges.push({ start: video.played.start(i), end: video.played.end(i) }); } return formattedPlayedRanges; }; var getUrlParams = function getUrlParams(url) { var finalUrl = url; if (!finalUrl.includes('?')) { return { userId: 123456, groupId: 123, subgroupId: 123, userName: 'Tester User' }; } finalUrl = finalUrl.split('?')[1].split('&'); finalUrl = finalUrl.reduce(function (acc, cur) { var key = cur.split('=')[0]; var val = cur.split('=')[1]; acc[key] = val; return acc; }, {}); return finalUrl; }; var getUserParams = function getUserParams() { var result = null; if (window.location.hostname.includes('.wyscout.')) { result = getUrlParams(window.location.href); } else { result = { userId: 123456, groupId: 123, subgroupId: 123, userName: 'Tester User' }; } return result; }; var checkIsEnabledStatus = function checkIsEnabledStatus(accessToken, apiHostname) { var promise = new Promise(function (resolve, reject) { getGlobalSwitchStatus(accessToken, apiHostname).then(function (response) { if (!response.data.isEnabled) return reject(false); return resolve(true); }).catch(function () { return reject(new Error(false)); }); }); return promise; }; var findHTML5Video = function findHTML5Video(userSettings, apiHostname) { var promise = new Promise(function (resolve, reject) { checkIsEnabledStatus(userSettings.accessToken, apiHostname).then(function () { var counter = 0; var seeking = setInterval(function () { var video = document.querySelector('video'); if (video) { clearInterval(seeking); return resolve(video); } else if (counter >= MAX_SEEKING_VIDEO_TAG) { clearInterval(seeking); return reject(new Error('HTML tag video not found')); } counter++; }, 500); }).catch(function () { return reject(new Error('find html5 Video checking problem')); }); }); return promise; }; var getFirstLevelDomain = function getFirstLevelDomain() { if (typeof location !== 'undefined') { if (location.hostname.includes(WYSCOUT_HOSTNAMES_SUFFIX.CN)) { return '.cn'; } } return '.com'; }; var createAnalyticsObject = function createAnalyticsObject(video, detailedAppSource) { return { appSource: ANALYTICS_APP_SOURCE, detailedAppSource: detailedAppSource, actionValue: 1, sessionId: video.sessionId, position: detailedAppSource === ANALYTICS_DETAILED_SOURCE.VIDEO_COMPLETED ? video.duration : video.currentTime, // sometimes on video end, cursor return to position 0 totalLength: video.duration, player: video.playerType || PLAYER_TYPE.APPS, isMuted: video.muted, fullScreen: video.webkitDisplayingFullscreen, isPlaylist: _isPlaylist(video.currentSrc) }; }; var _isPlaylist = function _isPlaylist() { var src = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : 'sometext?vbegin=0'; var params = getUrlParams(src); return params.vbegin && !Number.isNaN(params.vbegin) && params.vbegin > 0; }; var calculateAverageBitRate = function calculateAverageBitRate(snapshots) { return _.meanBy(snapshots, function (p) { return p.decodedBytes; }); }; var calculateAverageFrameRate = function calculateAverageFrameRate(snapshots) { return _.meanBy(snapshots, function (p) { return p.decodedFrames; }); }; var dateStartTimestamp = 0; var canPlayTimeStamp = 0; var totalWaitingSeconds = 0; var startWaitingSeconds = 0; var rebufferingEventsNum = 0; var loadStart = function loadStart(event) { // console.log('loadStart --> ', event); dateStartTimestamp = new Date().getTime(); }; var durationchange = function durationchange(event) { // console.log('durationchange --> ', event); }; var loadedmetadata = function loadedmetadata(event) { // console.log('loadedmetadata --> ', event); }; var ended = function ended(event, session) { // right now we may not have anymore video properties (Es. video is regenerated by client), so we have to use session info. var analyticObj = createAnalyticsObject(event.target, ANALYTICS_DETAILED_SOURCE.VIDEO_COMPLETED); analyticObj.bitrate = calculateAverageBitRate(session.snapshots).toFixed(1); analyticObj.framerate = calculateAverageFrameRate(session.snapshots).toFixed(0); analyticObj.position = session.duration; analyticObj.totalLength = session.duration; }; var loadeddata = function loadeddata(event) { // console.log('loadeddata --> ', event); /* * canplay and others events are also fired after video is completed. So, in order to track on segment * we assume that video is started when video player has loaded all data. This event that's not good in order to track video-metrics */ var analyticObj = createAnalyticsObject(event.target, ANALYTICS_DETAILED_SOURCE.VIDEO_START); }; var progress = function progress(event) { var currentTime = new Date().getTime(); // console.log('progress --> ', event); if (startWaitingSeconds > 0) { totalWaitingSeconds += currentTime - startWaitingSeconds; startWaitingSeconds = 0; } }; var canplay = function canplay(event) { // console.log('canplay --> ', event); canPlayTimeStamp = new Date().getTime(); }; var pause = function pause(event) { if (event.target.networkState === NETWORK_STATE.NO_SOURCE) { var analyticObj = createAnalyticsObject(event.target, 'no audio/video source found'); // track(ANALYTICS_EVENTS.PLAY_INTERRUPTED, analyticObj); } }; var canplaythrough = function canplaythrough(event) { // console.log('canplaythrough --> ', event); }; var waiting = function waiting(event) { // console.log('waiting --> ', event); startWaitingSeconds = new Date().getTime(); rebufferingEventsNum++; }; var getJoinedTime = function getJoinedTime() { return canPlayTimeStamp && dateStartTimestamp ? canPlayTimeStamp - dateStartTimestamp : 0; }; var getTotalRebufferingTime = function getTotalRebufferingTime() { return totalWaitingSeconds; }; var getTotalRebufferingEventsNum = function getTotalRebufferingEventsNum() { return rebufferingEventsNum; }; var convertBytesToBits = function convertBytesToBits(bytes) { return bytes * 8; }; var composeMetric = function composeMetric(startTime, video) { return { startTime: startTime ? startTime : new Date(), decodedFrames: decodedFrameCount(video), droppedFrames: droppedFrameCount(video), decodedBytes: decodedVideoByteCount(video), decodedAudioBytes: decodedAudioByteCount(video), displaySupportFullscreen: displaySupportFullScreen(video), src: currentSrc(video), duration: duration(video), bufferedRanges: formatBufferedRanges(video), playedRanges: formatPlayedRanges(video), seekableRanges: formatSeekableRanges(video) }; }; var Report = function Report() { var _this = this; classCallCheck(this, Report); this.setReportProperties = function (report) { var decodedFrames = report.decodedFrames, droppedFrames = report.droppedFrames, decodedBytes = report.decodedBytes, decodedAudioBytes = report.decodedAudioBytes, src = report.src, duration = report.duration, bufferedRanges = report.bufferedRanges, playedRanges = report.playedRanges, seekableRanges = report.seekableRanges, startTime = report.startTime; _this.startTime = startTime; _this.decodedFrames = decodedFrames; _this.droppedFrames = droppedFrames; _this.decodedBytes = decodedBytes; _this.decodedAudioBytes = decodedAudioBytes; _this.src = src; _this.duration = duration; _this.bufferedRanges = bufferedRanges; _this.playedRanges = playedRanges; _this.seekableRanges = seekableRanges; }; this.setSnapshots = function (snapshots) { _this.snapshots = snapshots; }; this.setSessionId = function (sessionId) { _this.sessionId = sessionId; }; this.setUserSettings = function (userSettings) { _this.userSettings = userSettings; }; this.clearSnapshots = function () { return _this.snapshots = []; }; this.setJoinedTime = function (joinedTime) { return _this.joinedTime = joinedTime; }; this.setRebufferingTime = function (rebufferingTime) { return _this.rebufferingTime = rebufferingTime; }; this.setRebufferingEvents = function (rebufferingEvents) { return _this.rebufferingEvents = rebufferingEvents; }; this.setIpAddress = function (ipAddress) { return _this.ipAddress = ipAddress; }; this.setEndTime = function (endTime) { return _this.endTime = endTime; }; this.setAverageBitrate = function (averageBitrate) { return _this.averageBitrate = averageBitrate; }; }; var Session = function Session() { var _this = this; classCallCheck(this, Session); this.addSnapshot = function (snapshot) { _this.snapshots.push(snapshot); }; this.clearSnapshots = function () { _this.snapshots = []; }; this.setSessionProperties = function (sessionId, duration, currentSrc) { _this.sessionId = sessionId; _this.duration = duration; _this.currentSrc = currentSrc; }; this.snapshots = []; this.sessionId = null; this.duration = 0; }; function createCommonjsModule(fn, module) { return module = { exports: {} }, fn(module, module.exports), module.exports; } var uniqid = createCommonjsModule(function (module) { /* (The MIT License) Copyright (c) 2014 Halász Ãdám <mail@adamhalasz.com> Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ // Unique Hexatridecimal ID Generator // ================================================ // Dependencies // ================================================ var pid = process && process.pid ? process.pid.toString(36) : '' ; var address = ''; if(typeof __webpack_require__ !== 'function'){ var mac = '', networkInterfaces = os.networkInterfaces(); for(interface_key in networkInterfaces){ const networkInterface = networkInterfaces[interface_key]; const length = networkInterface.length; for(var i = 0; i < length; i++){ if(networkInterface[i].mac && networkInterface[i].mac != '00:00:00:00:00:00'){ mac = networkInterface[i].mac; break; } } } address = mac ? parseInt(mac.replace(/\:|\D+/gi, '')).toString(36) : '' ; } // Exports // ================================================ module.exports = module.exports.default = function(prefix){ return (prefix || '') + address + pid + now().toString(36); }; module.exports.process = function(prefix){ return (prefix || '') + pid + now().toString(36); }; module.exports.time = function(prefix){ return (prefix || '') + now().toString(36); }; // Helpers // ================================================ function now(){ var time = Date.now(); var last = now.last || time; return now.last = time > last ? time : last + 1; } }); var uniqid_1 = uniqid.time; var lastDecodedFrames = 0; var lastDroppedFrames = 0; var lastDecodedBytes = 0; var lastDecodedAudioBytes = 0; var lastAudioBitRate = 0; var lastVideoBitRate = 0; var totalAudioBitRate = 0; var totalVideoBitRate = 0; var requestAnimationId = 0; var _timer = void 0; var sessionTransmission = null; var report = new Report(); var session = new Session(); var lastTime = null; var currentTime$1 = null; var video = null; var resetParams = function resetParams(totalReport) { lastDecodedFrames = totalReport.decodedFrames; lastDroppedFrames = totalReport.droppedFrames; lastDecodedBytes = totalReport.decodedBytes; lastDecodedAudioBytes = totalReport.decodedAudioBytes; lastAudioBitRate = totalAudioBitRate; lastVideoBitRate = totalVideoBitRate; }; var resetWithCurrentVideoValues = function resetWithCurrentVideoValues(currentVideo) { lastDecodedFrames = decodedFrameCount(currentVideo); lastDroppedFrames = droppedFrameCount(currentVideo); lastDecodedBytes = decodedVideoByteCount(currentVideo); lastDecodedAudioBytes = decodedAudioByteCount(currentVideo); lastAudioBitRate = convertBytesToBits(lastDecodedAudioBytes); lastVideoBitRate = convertBytesToBits(lastDecodedBytes); }; var resetAll = function resetAll() { lastDecodedFrames = 0; lastDroppedFrames = 0; lastDecodedBytes = 0; lastDecodedAudioBytes = 0; lastAudioBitRate = 0; lastVideoBitRate = 0; totalAudioBitRate = 0; totalVideoBitRate = 0; }; var requestAnimFrame = function () { return window.requestAnimationFrame || window.webkitRequestAnimationFrame || window.mozRequestAnimationFrame || function (callback) { window.setTimeout(callback, 1000 / 60); }; }(); var cancelAnimationFrame = window.cancelAnimationFrame || window.mozCancelAnimationFrame; var closeSession = function closeSession() { report.setJoinedTime(getJoinedTime()); report.setRebufferingTime(getTotalRebufferingTime()); report.setRebufferingEvents(getTotalRebufferingEventsNum()); report.setEndTime(new Date()); Caller(report, 'session', sessionTransmission); }; var startWork = function startWork() { var withReset = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : false; if (withReset) { resetWithCurrentVideoValues(video); currentTime$1 = new Date().getTime(); lastTime = currentTime$1; } if (!requestAnimationId) _timer();else console.log('Profiler is already running'); session = new Session(); }; var stopWork = function stopWork() { var withCloseSession = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : false; cancelAnimationFrame(requestAnimationId); requestAnimationId = 0; if (withCloseSession) closeSession(); }; var onVideoEnded = function onVideoEnded(event) { ended(event, session); // track into analytics stopWork(true); // stopping sniffing resetAll(); // reset all values in order to play the next video }; var onTabVisibilitychange = function onTabVisibilitychange(event) { if (document.visibilityState === 'hidden') stopWork();else startWork(true); }; var onVideoPlaying = function onVideoPlaying(event) { startWork(); }; var stopSniffingVideoMetrics = function stopSniffingVideoMetrics() { console.log('Profiler is going to stop work'); document.removeEventListener('visibilitychange', onTabVisibilitychange); video.removeEventListener('loadstart', loadStart, false); video.removeEventListener('durationchange', durationchange, false); video.removeEventListener('loadedmetadata', loadedmetadata, false); video.removeEventListener('loadeddata', loadeddata, false); video.removeEventListener('progress', progress, false); video.removeEventListener('canplay', canplay, false); video.removeEventListener('canplaythrough', canplaythrough, false); video.removeEventListener('waiting', waiting, false); video.removeEventListener('pause', pause, false); video.removeEventListener('ended', onVideoEnded, false); video.removeEventListener('playing', onVideoPlaying, false); stopWork(); }; var checkStatusInterval = function checkStatusInterval(accessToken, apiHostname) { var interval = setInterval(function () { checkIsEnabledStatus(accessToken, apiHostname).then(function (response) { if (!response) { stopSniffingVideoMetrics(); clearInterval(interval); } if (response && !requestAnimationId) startWork(); }).catch(function () { stopSniffingVideoMetrics(); clearInterval(interval); }); }, ENABLING_STATUS_MILLISECONDS); }; var startSniffingVideoMetrics = function startSniffingVideoMetrics(userSettings, playerType) { var transmission = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : TRANSMISSION_TYPE.LOGSTASH; var apiHostname = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : API_HOSTNAME; findHTML5Video(userSettings, apiHostname).then(function (foundVideo) { video = foundVideo; var sessionId = uniqid(); var profile = !userSettings ? getUserParams() : userSettings; sessionTransmission = transmission; initAnalytics(profile.userId); video.sessionId = sessionId; report.setSessionId(sessionId); document.addEventListener('visibilitychange', onTabVisibilitychange); video.playerType = playerType || PLAYER_TYPE.PLATFROM; video.addEventListener('loadstart', loadStart, false); video.addEventListener('durationchange', durationchange, false); video.addEventListener('loadedmetadata', loadedmetadata, false); video.addEventListener('loadeddata', loadeddata, false); video.addEventListener('progress', progress, false); video.addEventListener('canplay', canplay, false); video.addEventListener('canplaythrough', canplaythrough, false); video.addEventListener('waiting', waiting, false); video.addEventListener('pause', pause, false); video.addEventListener('ended', onVideoEnded, false); video.addEventListener('playing', onVideoPlaying, false); report.setUserSettings(profile); getIpAddress().then(function (call) { if (call && call.data && call.data.response) { report.setIpAddress(call.data.response); } }); lastTime = new Date().getTime(); var numPausedSeconds = 0; currentTime$1 = 0; checkStatusInterval(profile.accessToken, apiHostname); _timer = function timer() { requestAnimationId = requestAnimFrame(_timer); session.setSessionProperties(sessionId, video.duration, video.currentSrc); currentTime$1 = new Date().getTime(); if (currentTime$1 - lastTime >= 1000) { // è passato un secondo lastTime = currentTime$1; if (paused(video)) { numPausedSeconds++; if (numPausedSeconds > MAX_PAUSED_SECONDS) stopWork(true); return; } numPausedSeconds = 0; var metric = composeMetric(report.startTime, video); totalVideoBitRate = convertBytesToBits(metric.decodedBytes); totalAudioBitRate = convertBytesToBits(metric.decodedAudioBytes); report.setReportProperties(metric); var snapshot = { effectiveTime: new Date(), decodedFrames: report.decodedFrames - lastDecodedFrames, droppedFrames: report.droppedFrames - lastDroppedFrames, decodedBytes: report.decodedBytes - lastDecodedBytes, decodedAudioBytes: report.decodedAudioBytes - lastDecodedAudioBytes, displayIsFullscreen: displayIsFullscreen(video), videoBitRate: totalVideoBitRate - lastVideoBitRate, audioBitRate: totalAudioBitRate - lastAudioBitRate, currentTime: currentTime(video).toFixed(2), networkState: networkState(video), sessionId: report.sessionId, userSettings: profile }; session.addSnapshot(snapshot); resetParams(report); Caller(snapshot, 'snapshot', sessionTransmission); } }; }).catch(function () { // console.error(err); }); }; var WyMetricProfiler = function (_Component) { inherits(WyMetricProfiler, _Component); function WyMetricProfiler() { classCallCheck(this, WyMetricProfiler); var _this = possibleConstructorReturn(this, (WyMetricProfiler.__proto__ || Object.getPrototypeOf(WyMetricProfiler)).call(this)); _this.componentDidMount = function () { var _this$props = _this.props, startOnMount = _this$props.startOnMount, userSettings = _this$props.userSettings, playerType = _this$props.playerType, transmitter = _this$props.transmitter, apiHostname = _this$props.apiHostname; if (startOnMount) { startSniffingVideoMetrics(userSettings, playerType, transmitter, apiHostname); } }; _this.state = { running: false, startOnMount: true }; return _this; } createClass(WyMetricProfiler, [{ key: 'render', value: function render() { return React__default.createElement( 'div', null, this.props.children ); } }], [{ key: 'getDerivedStateFromProps', value: function getDerivedStateFromProps(props, state) { var userSettings = props.userSettings, playerType = props.playerType, transmitter = props.transmitter, running = props.running, apiHostname = props.apiHostname; if (running && !state.running) { startSniffingVideoMetrics(userSettings, playerType, transmitter, apiHostname); } else if (!running && state.running) { stopSniffingVideoMetrics(); } return { running: props.running }; } }]); return WyMetricProfiler; }(React.Component); WyMetricProfiler.propTypes = { running: PropTypes.bool.isRequired, startOnMount: PropTypes.bool, userSettings: PropTypes.shape({ userId: PropTypes.number, userName: PropTypes.string, groupId: PropTypes.number, subgroupId: PropTypes.number, accessToken: PropTypes.string }).isRequired, transmitter: PropTypes.oneOf([TRANSMISSION_TYPE.LOGSTASH, TRANSMISSION_TYPE.REST]), playerType: PropTypes.oneOf([PLAYER_TYPE.PLATFORM, PLAYER_TYPE.APPS]), children: PropTypes.node.isRequired, apiHostname: PropTypes.string }; WyMetricProfiler.defaultProps = { startOnMount: true, transmitter: TRANSMISSION_TYPE.LOGSTASH, playerType: PLAYER_TYPE.PLATFORM, apiHostname: API_HOSTNAME }; exports.startSniffingVideoMetrics = startSniffingVideoMetrics; exports.stopSniffingVideoMetrics = stopSniffingVideoMetrics; exports.WyMetricProfiler = WyMetricProfiler; exports.TRANSMISSION_TYPE = TRANSMISSION_TYPE; exports.PLAYER_TYPE = PLAYER_TYPE; return exports; }({}, _, os, React, PropTypes)); //# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoidmlkZW8tbWV0cmljcy5qcyIsInNvdXJjZXMiOlsiLi4vc3JjL2NvcmUvSFRNTDVWaWRlb1Byb3BlcnRpZXMuanMiLCIuLi9zcmMvYW5hbHl0aWNzL2FuYWx5dGljc01hbmFnZXIuanMiLCIuLi9zcmMvY29uZmlnL2NvbmZpZy5qcyIsIi4uL25vZGVfbW9kdWxlcy9heGlvcy9saWIvaGVscGVycy9iaW5kLmpzIiwiLi4vbm9kZV9tb2R1bGVzL2lzLWJ1ZmZlci9pbmRleC5qcyIsIi4uL25vZGVfbW9kdWxlcy9heGlvcy9saWIvdXRpbHMuanMiLCIuLi9ub2RlX21vZHVsZXMvYXhpb3MvbGliL2hlbHBlcnMvbm9ybWFsaXplSGVhZGVyTmFtZS5qcyIsIi4uL25vZGVfbW9kdWxlcy9heGlvcy9saWIvY29yZS9lbmhhbmNlRXJyb3IuanMiLCIuLi9ub2RlX21vZHVsZXMvYXhpb3MvbGliL2NvcmUvY3JlYXRlRXJyb3IuanMiLCIuLi9ub2RlX21vZHVsZXMvYXhpb3MvbGliL2NvcmUvc2V0dGxlLmpzIiwiLi4vbm9kZV9tb2R1bGVzL2F4aW9zL2xpYi9oZWxwZXJzL2J1aWxkVVJMLmpzIiwiLi4vbm9kZV9tb2R1bGVzL2F4aW9zL2xpYi9oZWxwZXJzL3BhcnNlSGVhZGVycy5qcyIsIi4uL25vZGVfbW9kdWxlcy9heGlvcy9saWIvaGVscGVycy9pc1VSTFNhbWVPcmlnaW4uanMiLCIuLi9ub2RlX21vZHVsZXMvYXhpb3MvbGliL2hlbHBlcnMvYnRvYS5qcyIsIi4uL25vZGVfbW9kdWxlcy9heGlvcy9saWIvaGVscGVycy9jb29raWVzLmpzIiwiLi4vbm9kZV9tb2R1bGVzL2F4aW9zL2xpYi9hZGFwdGVycy94aHIuanMiLCIuLi9ub2RlX21vZHVsZXMvYXhpb3MvbGliL2RlZmF1bHRzLmpzIiwiLi4vbm9kZV9tb2R1bGVzL2F4aW9zL2xpYi9jb3JlL0ludGVyY2VwdG9yTWFuYWdlci5qcyIsIi4uL25vZGVfbW9kdWxlcy9heGlvcy9saWIvY29yZS90cmFuc2Zvcm1EYXRhLmpzIiwiLi4vbm9kZV9tb2R1bGVzL2F4aW9zL2xpYi9jYW5jZWwvaXNDYW5jZWwuanMiLCIuLi9ub2RlX21vZHVsZXMvYXhpb3MvbGliL2hlbHBlcnMvaXNBYnNvbHV0ZVVSTC5qcyIsIi4uL25vZGVfbW9kdWxlcy9heGlvcy9saWIvaGVscGVycy9jb21iaW5lVVJMcy5qcyIsIi4uL25vZGVfbW9kdWxlcy9heGlvcy9saWIvY29yZS9kaXNwYXRjaFJlcXVlc3QuanMiLCIuLi9ub2RlX21vZHVsZXMvYXhpb3MvbGliL2NvcmUvQXhpb3MuanMiLCIuLi9ub2RlX21vZHVsZXMvYXhpb3MvbGliL2NhbmNlbC9DYW5jZWwuanMiLCIuLi9ub2RlX21vZHVsZXMvYXhpb3MvbGliL2NhbmNlbC9DYW5jZWxUb2tlbi5qcyIsIi4uL25vZGVfbW9kdWxlcy9heGlvcy9saWIvaGVscGVycy9zcHJlYWQuanMiLCIuLi9ub2RlX21vZHVsZXMvYXhpb3MvbGliL2F4aW9zLmpzIiwiLi4vbm9kZV9tb2R1bGVzL2F4aW9zL2luZGV4LmpzIiwiLi4vbm9kZV9tb2R1bGVzL0B3eXNjb3V0L2xvZ3N0YXNoL25vZGVfbW9kdWxlcy9heGlvcy9saWIvaGVscGVycy9iaW5kLmpzIiwiLi4vbm9kZV9tb2R1bGVzL0B3eXNjb3V0L2xvZ3N0YXNoL25vZGVfbW9kdWxlcy9heGlvcy9saWIvdXRpbHMuanMiLCIuLi9ub2RlX21vZHVsZXMvQHd5c2NvdXQvbG9nc3Rhc2gvbm9kZV9tb2R1bGVzL2F4aW9zL2xpYi9oZWxwZXJzL25vcm1hbGl6ZUhlYWRlck5hbWUuanMiLCIuLi9ub2RlX21vZHVsZXMvQHd5c2NvdXQvbG9nc3Rhc2gvbm9kZV9tb2R1bGVzL2F4aW9zL2xpYi9jb3JlL2VuaGFuY2VFcnJvci5qcyIsIi4uL25vZGVfbW9kdWxlcy9Ad3lzY291dC9sb2dzdGFzaC9ub2RlX21vZHVsZXMvYXhpb3MvbGliL2NvcmUvY3JlYXRlRXJyb3IuanMiLCIuLi9ub2RlX21vZHVsZXMvQHd5c2NvdXQvbG9nc3Rhc2gvbm9kZV9tb2R1bGVzL2F4aW9zL2xpYi9jb3JlL3NldHRsZS5qcyIsIi4uL25vZGVfbW9kdWxlcy9Ad3lzY291dC9sb2dzdGFzaC9ub2RlX21vZHVsZXMvYXhpb3MvbGliL2hlbHBlcnMvYnVpbGRVUkwuanMiLCIuLi9ub2RlX21vZHVsZXMvQHd5c2NvdXQvbG9nc3Rhc2gvbm9kZV9tb2R1bGVzL2F4aW9zL2xpYi9oZWxwZXJzL3BhcnNlSGVhZGVycy5qcyIsIi4uL25vZGVfbW9kdWxlcy9Ad3lzY291dC9sb2dzdGFzaC9ub2RlX21vZHVsZXMvYXhpb3MvbGliL2hlbHBlcnMvaXNVUkxTYW1lT3JpZ2luLmpzIiwiLi4vbm9kZV9tb2R1bGVzL0B3eXNjb3V0L2xvZ3N0YXNoL25vZGVfbW9kdWxlcy9heGlvcy9saWIvaGVscGVycy9idG9hLmpzIiwiLi4vbm9kZV9tb2R1bGVzL0B3eXNjb3V0L2xvZ3N0YXNoL25vZGVfbW9kdWxlcy9heGlvcy9saWIvaGVscGVycy9jb29raWVzLmpzIiwiLi4vbm9kZV9tb2R1bGVzL0B3eXNjb3V0L2xvZ3N0YXNoL25vZGVfbW9kdWxlcy9heGlvcy9saWIvYWRhcHRlcnMveGhyLmpzIiwiLi4vbm9kZV9tb2R1bGVzL0B3eXNjb3V0L2xvZ3N0YXNoL25vZGVfbW9kdWxlcy9heGlvcy9saWIvZGVmYXVsdHMuanMiLCIuLi9ub2RlX21vZHVsZXMvQHd5c2NvdXQvbG9nc3Rhc2gvbm9kZV9tb2R1bGVzL2F4aW9zL2xpYi9jb3JlL0ludGVyY2VwdG9yTWFuYWdlci5qcyIsIi4uL25vZGVfbW9kdWxlcy9Ad3lzY291dC9sb2dzdGFzaC9ub2RlX21vZHVsZXMvYXhpb3MvbGliL2NvcmUvdHJhbnNmb3JtRGF0YS5qcyIsIi4uL25vZGVfbW9kdWxlcy9Ad3lzY291dC9sb2dzdGFzaC9ub2RlX21vZHVsZXMvYXhpb3MvbGliL2NhbmNlbC9pc0NhbmNlbC5qcyIsIi4uL25vZGVfbW9kdWxlcy9Ad3lzY291dC9sb2dzdGFzaC9ub2RlX21vZHVsZXMvYXhpb3MvbGliL2hlbHBlcnMvaXNBYnNvbHV0ZVVSTC5qcyIsIi4uL25vZGVfbW9kdWxlcy9Ad3lzY291dC9sb2dzdGFzaC9ub2RlX21vZHVsZXMvYXhpb3MvbGliL2hlbHBlcnMvY29tYmluZVVSTHMuanMiLCIuLi9ub2RlX21vZHVsZXMvQHd5c2NvdXQvbG9nc3Rhc2gvbm9kZV9tb2R1bGVzL2F4aW9zL2xpYi9jb3JlL2Rpc3BhdGNoUmVxdWVzdC5qcyIsIi4uL25vZGVfbW9kdWxlcy9Ad3lzY291dC9sb2dzdGFzaC9ub2RlX21vZHVsZXMvYXhpb3MvbGliL2NvcmUvQXhpb3MuanMiLCIuLi9ub2RlX21vZHVsZXMvQHd5c2NvdXQvbG9nc3Rhc2gvbm9kZV9tb2R1bGVzL2F4aW9zL2xpYi9jYW5jZWwvQ2FuY2VsLmpzIiwiLi4vbm9kZV9tb2R1bGVzL0B3eXNjb3V0L2xvZ3N0YXNoL25vZGVfbW9kdWxlcy9heGlvcy9saWIvY2FuY2VsL0NhbmNlbFRva2VuLmpzIiwiLi4vbm9kZV9tb2R1bGVzL0B3eXNjb3V0L2xvZ3N0YXNoL25vZGVfbW9kdWxlcy9heGlvcy9saWIvaGVscGVycy9zcHJlYWQuanMiLCIuLi9ub2RlX21vZHVsZXMvQHd5c2NvdXQvbG9nc3Rhc2gvbm9kZV9tb2R1bGVzL2F4aW9zL2xpYi9heGlvcy5qcyIsIi4uL25vZGVfbW9kdWxlcy9Ad3lzY291dC9sb2dzdGFzaC9ub2RlX21vZHVsZXMvYXhpb3MvaW5kZXguanMiLCIuLi9ub2RlX21vZHVsZXMvQHd5c2NvdXQvbG9nc3Rhc2gvZGlzdC9pbmRleC5qcyIsIi4uL3NyYy90cmFuc21pdHRlci9Mb2dTdGFzaC5qcyIsIi4uL3NyYy90cmFuc21pdHRlci9SZXN0QXBpLmpzIiwiLi4vc3JjL2NvcmUvQ2FsbGVyLmpzIiwiLi4vc3JjL3V0aWxpdGllcy91dGlscy5qcyIsIi4uL3NyYy9hbmFseXRpY3MvdXRpbHMuanMiLCIuLi9zcmMvdXRpbGl0aWVzL3N0YXRzLmpzIiwiLi4vc3JjL2NvcmUvRXZlbnRzTWFuYWdlci5qcyIsIi4uL3NyYy91dGlsaXRpZXMvY29udmVydGVyLmpzIiwiLi4vc3JjL3V0aWxpdGllcy92aWRlb1V0aWxzLmpzIiwiLi4vc3JjL21vZGVsL1JlcG9ydC5qcyIsIi4uL3NyYy9tb2RlbC9TZXNzaW9uLmpzIiwiLi4vbm9kZV9tb2R1bGVzL3VuaXFpZC9pbmRleC5qcyIsIi4uL3NyYy9tZXRyaWNzTWFuYWdlci5qcyIsIi4uL3NyYy9tZXRyaWNzTWFuYWdlcldyYXBwZXIuanMiXSwic291cmNlc0NvbnRlbnQiOlsiZXhwb3J0IGNvbnN0IGRlY29kZWRGcmFtZUNvdW50ID0gdmlkZW8gPT4gdmlkZW8ud2Via2l0RGVjb2RlZEZyYW1lQ291bnQ7XG5cbmV4cG9ydCBjb25zdCBkZWNvZGVkVmlkZW9CeXRlQ291bnQgPSB2aWRlbyA9PiB2aWRlby53ZWJraXRWaWRlb0RlY29kZWRCeXRlQ291bnQ7XG5cbmV4cG9ydCBjb25zdCBkZWNvZGVkQXVkaW9CeXRlQ291bnQgPSB2aWRlbyA9PiB2aWRlby53ZWJraXRBdWRpb0RlY29kZWRCeXRlQ291bnQ7XG5cbmV4cG9ydCBjb25zdCBkaXNwbGF5SXNGdWxsc2NyZWVuID0gdmlkZW8gPT4gdmlkZW8ud2Via2l0RGlzcGxheWluZ0Z1bGxzY3JlZW47XG5cbmV4cG9ydCBjb25zdCBkaXNwbGF5U3VwcG9ydEZ1bGxTY3JlZW4gPSB2aWRlbyA9PiB2aWRlby53ZWJraXRTdXBwb3J0c0Z1bGxzY3JlZW47XG5cbmV4cG9ydCBjb25zdCBkcm9wcGVkRnJhbWVDb3VudCA9IHZpZGVvID0+IHZpZGVvLndlYmtpdERyb3BwZWRGcmFtZUNvdW50O1xuXG5leHBvcnQgY29uc3QgZHVyYXRpb24gPSB2aWRlbyA9PiB2aWRlby5kdXJhdGlvbjtcblxuZXhwb3J0IGNvbnN0IHBhdXNlZCA9IHZpZGVvID0+IHZpZGVvLnBhdXNlZDtcblxuZXhwb3J0IGNvbnN0IHNyYyA9IHZpZGVvID0+IHZpZGVvLnNyYztcblxuZXhwb3J0IGNvbnN0IGN1cnJlbnRTcmMgPSB2aWRlbyA9PiB2aWRlby5jdXJyZW50U3JjO1xuXG5leHBvcnQgY29uc3QgbmV0d29ya1N0YXRlID0gdmlkZW8gPT4gdmlkZW8ubmV0d29ya1N0YXRlO1xuXG5leHBvcnQgY29uc3QgY3VycmVudFRpbWUgPSB2aWRlbyA9PiB2aWRlby5jdXJyZW50VGltZTtcbiIsIi8vIGltcG9ydCBXeUFuYWx5dGljcyBmcm9tICdAd3lzY291dC9hbmFseXRpY3MnO1xuXG5sZXQgYW5hbHl0aWNzID0gbnVsbDtcblxuXG5leHBvcnQgY29uc3QgaW5pdEFuYWx5dGljcyA9ICh1c2VySWQsIHByb2Nlc3NFbnYgPSAnZGV2ZWxvcG1lbnQnKSA9PiB7XG4gICAgLy8gYW5hbHl0aWNzID0gbmV3IFd5QW5hbHl0aWNzKHByb2Nlc3NFbnYsIHVzZXJJZCk7XG4gICAgLy8gYW5hbHl0aWNzLmlkZW50aWZ5KCk7XG59O1xuXG5cbmV4cG9ydCBjb25zdCB0cmFjayA9IChldmVudE5hbWUsIG1vZGVsID0ge2FwcFNvdXJjZTogJ3ZpZGVvLW1ldHJpY3MnLCBhcHBEZXRhaWxlZFNvdXJjZTogJ0RlZmF1bHQgRXZlbnQnfSkgPT4ge1xuICAgIC8vIGFuYWx5dGljcy50cmFjayhldmVudE5hbWUsIG1vZGVsKTtcbn07XG4iLCJsZXQgcmVzdEFwaUJhc2VOYW1lID0gbnVsbDtcblxuY29uc3QgZW52ID0gcHJvY2Vzcy5lbnYuUkVBQ1RfQVBQX0VOViB8fCBwcm9jZXNzLmVudi5OT0RFX0VOVjtcblxuc3dpdGNoIChlbnYpIHtcbiAgICBjYXNlICdyYyc6XG4gICAgY2FzZSAncmVsZWFzZSc6XG4gICAgICAgIHJlc3RBcGlCYXNlTmFtZSA9ICdodHRwczovL3Jlc3RyYy53eXNjb3V0LmNvbS8nO1xuICAgICAgICBicmVhaztcbiAgICBjYXNlICdwcmV2aWV3JzpcbiAgICAgICAgcmVzdEFwaUJhc2VOYW1lID0gJ2h0dHBzOi8vcmVzdHByZXZpZXcud3lzY291dC5jb20vJztcbiAgICAgICAgYnJlYWs7XG4gICAgY2FzZSAncHJvZHVjdGlvbic6XG4gICAgICAgIHJlc3RBcGlCYXNlTmFtZSA9ICdodHRwczovL3Jlc3Qud3lzY291dC5jb20vJztcbiAgICAgICAgYnJlYWs7XG4gICAgZGVmYXVsdDpcbiAgICAgICAgcmVzdEFwaUJhc2VOYW1lID0gJ2h0dHBzOi8vcmVzdGJldGEud3lzY291dC5jb20vJztcbiAgICAgICAgYnJlYWs7XG59XG5cbmV4cG9ydCBjb25zdCBBUElfSE9TVE5BTUUgPSByZXN0QXBpQmFzZU5hbWU7XG5cbmV4cG9ydCBjb25zdCBBUElfU0VSVklDRVMgPSB7XG4gICAgdmlkZW9tZXRyaWNzQ29uZmlnOiBgJHtyZXN0QXBpQmFzZU5hbWV9L21lZGlhL3ZpZGVvbWV0cmljc2NvbmZpZy9gLFxufTtcblxuZXhwb3J0IGNvbnN0IEFQSV9TRVJWRVIgPVxuICAgICdodHRwOi8vNWI5MjQ5Y2I0YzgxOGUwMDE0NTZlOGY1Lm1vY2thcGkuaW8vdmlkZW8tbWV0cmljcy92MS8nO1xuXG5leHBvcnQgY29uc3QgTUFYX1NOSUZGSU5HX1NFU1NJT04gPSA2MDtcblxuZXhwb3J0IGNvbnN0IE1BWF9NRVRSSUNTX0NBQ0hFRCA9IDIwO1xuXG5leHBvcnQgY29uc3QgTUFYX1NFRUtJTkdfVklERU9fVEFHID0gMTA7XG5cbmV4cG9ydCBjb25zdCBNQVhfUEFVU0VEX1NFQ09ORFMgPSAyMDtcblxuZXhwb3J0IGNvbnN0IEVOQUJMSU5HX1NUQVRVU19NSUxMSVNFQ09ORFMgPSAxMDAwICogNjAgKiAxMDsgLy8gMTAgbWludXRlc1xuXG5leHBvcnQgY29uc3QgVFJBTlNNSVNTSU9OX1RZUEUgPSB7XG4gICAgUkVTVDogJ3Jlc3QnLFxuICAgIExPR1NUQVNIOiAnbG9nc3Rhc2gnLFxufTtcblxuZXhwb3J0IGNvbnN0IE5FVFdPUktfU1RBVEUgPSB7XG4gICAgRU1QVFk6IDAsXG4gICAgSURMRTogMSxcbiAgICBMT0FESU5HOiAyLFxuICAgIE5PX1NPVVJDRTogMyxcbn07XG5cbmV4cG9ydCBjb25zdCBBTkFMWVRJQ1NfRVZFTlRTID0ge1xuICAgIEJVRkZFUl9TVEFSVEVEOiAnVmlkZW8gUGxheWJhY2sgQnVmZmVyIFN0YXJ0ZWQnLFxuICAgIEJVRkZFUl9DT01QTEVURUQ6ICdWaWRlbyBQbGF5YmFjayBCdWZmZXIgQ29tcGxldGVkJyxcbiAgICBQTEFZX1NUQVJURUQ6ICdWaWRlbyBQbGF5YmFjayBTdGFydGVkJyxcbiAgICBQTEFZX0NPTVBMRVRFRDogJ1ZpZGVvIFBsYXliYWNrIENvbXBsZXRlZCcsXG4gICAgUExBWV9QQVVTRUQ6ICdWaWRlbyBQbGF5YmFjayBQYXVzZWQnLFxuICAgIFBMQVlfSU5URVJSVVBURUQ6ICdWaWRlbyBQbGF5YmFjayBJbnRlcnJ1cHRlZCcsXG59O1xuXG5leHBvcnQgY29uc3QgQU5BTFlUSUNTX0FQUF9TT1VSQ0UgPSAnVmlkZW8gUGxheWVyJztcbmV4cG9ydCBjb25zdCBBTkFMWVRJQ1NfREVUQUlMRURfU09VUkNFID0ge1xuICAgIFZJREVPX1NUQVJUOiAnVmlkZW8gUGxheWVyIEF1dG8gU3RhcnQnLFxuICAgIFZJREVPX0NPTVBMRVRFRDogJ1ZpZGVvIFBsYXllciBDb21wbGV0ZWQnLFxufTtcblxuZXhwb3J0IGNvbnN0IFBMQVlFUl9UWVBFID0ge1xuICAgIFBMQVRGT1JNOiAnQUVWaWRlbycsXG4gICAgQVBQUzogJ1ZQMjAxOCcsXG59O1xuXG5leHBvcnQgY29uc3QgV1lTQ09VVF9IT1NUTkFNRVNfU1VGRklYID0ge1xuICAgIERFRkFVTFQ6ICd3eXNjb3V0LmNvbScsXG4gICAgUlU6ICdwbGF0Zm9ybS1ydS53eXNjb3V0LmNvbScsXG4gICAgQ046ICd3eXNjb3V0LmNuJyxcbn07XG4iLCIndXNlIHN0cmljdCc7XG5cbm1vZHVsZS5leHBvcnRzID0gZnVuY3Rpb24gYmluZChmbiwgdGhpc0FyZykge1xuICByZXR1cm4gZnVuY3Rpb24gd3JhcCgpIHtcbiAgICB2YXIgYXJncyA9IG5ldyBBcnJheShhcmd1bWVudHMubGVuZ3RoKTtcbiAgICBmb3IgKHZhciBpID0gMDsgaSA8IGFyZ3MubGVuZ3RoOyBpKyspIHtcbiAgICAgIGFyZ3NbaV0gPSBhcmd1bWVudHNbaV07XG4gICAgfVxuICAgIHJldHVybiBmbi5hcHBseSh0aGlzQXJnLCBhcmdzKTtcbiAgfTtcbn07XG4iLCIvKiFcbiAqIERldGVybWluZSBpZiBhbiBvYmplY3QgaXMgYSBCdWZmZXJcbiAqXG4gKiBAYXV0aG9yICAgRmVyb3NzIEFib3VraGFkaWplaCA8aHR0cHM6Ly9mZXJvc3Mub3JnPlxuICogQGxpY2Vuc2UgIE1JVFxuICovXG5cbi8vIFRoZSBfaXNCdWZmZXIgY2hlY2sgaXMgZm9yIFNhZmFyaSA1LTcgc3VwcG9ydCwgYmVjYXVzZSBpdCdzIG1pc3Npbmdcbi8vIE9iamVjdC5wcm90b3R5cGUuY29uc3RydWN0b3IuIFJlbW92ZSB0aGlzIGV2ZW50dWFsbHlcbm1vZHVsZS5leHBvcnRzID0gZnVuY3Rpb24gKG9iaikge1xuICByZXR1cm4gb2JqICE9IG51bGwgJiYgKGlzQnVmZmVyKG9iaikgfHwgaXNTbG93QnVmZmVyKG9iaikgfHwgISFvYmouX2lzQnVmZmVyKVxufVxuXG5mdW5jdGlvbiBpc0J1ZmZlciAob2JqKSB7XG4gIHJldHVybiAhIW9iai5jb25zdHJ1Y3RvciAmJiB0eXBlb2Ygb2JqLmNvbnN0cnVjdG9yLmlzQnVmZmVyID09PSAnZnVuY3Rpb24nICYmIG9iai5jb25zdHJ1Y3Rvci5pc0J1ZmZlcihvYmopXG59XG5cbi8vIEZvciBOb2RlIHYwLjEwIHN1cHBvcnQuIFJlbW92ZSB0aGlzIGV2ZW50dWFsbHkuXG5mdW5jdGlvbiBpc1Nsb3dCdWZmZXIgKG9iaikge1xuICByZXR1cm4gdHlwZW9mIG9iai5yZWFkRmxvYXRMRSA9PT0gJ2Z1bmN0aW9uJyAmJiB0eXBlb2Ygb2JqLnNsaWNlID09PSAnZnVuY3Rpb24nICYmIGlzQnVmZmVyKG9iai5zbGljZSgwLCAwKSlcbn1cbiIsIid1c2Ugc3RyaWN0JztcblxudmFyIGJpbmQgPSByZXF1aXJlKCcuL2hlbHBlcnMvYmluZCcpO1xudmFyIGlzQnVmZmVyID0gcmVxdWlyZSgnaXMtYnVmZmVyJyk7XG5cbi8qZ2xvYmFsIHRvU3RyaW5nOnRydWUqL1xuXG4vLyB1dGlscyBpcyBhIGxpYnJhcnkgb2YgZ2VuZXJpYyBoZWxwZXIgZnVuY3Rpb25zIG5vbi1zcGVjaWZpYyB0byBheGlvc1xuXG52YXIgdG9TdHJpbmcgPSBPYmplY3QucHJvdG90eXBlLnRvU3RyaW5nO1xuXG4vKipcbiAqIERldGVybWluZSBpZiBhIHZhbHVlIGlzIGFuIEFycmF5XG4gKlxuICogQHBhcmFtIHtPYmplY3R9IHZhbCBUaGUgdmFsdWUgdG8gdGVzdFxuICogQHJldHVybnMge2Jvb2xlYW59IFRydWUgaWYgdmFsdWUgaXMgYW4gQXJyYXksIG90aGVyd2lzZSBmYWxzZVxuICovXG5mdW5jdGlvbiBpc0FycmF5KHZhbCkge1xuICByZXR1cm4gdG9TdHJpbmcuY2FsbCh2YWwpID09PSAnW29iamVjdCBBcnJheV0nO1xufVxuXG4vKipcbiAqIERldGVybWluZSBpZiBhIHZhbHVlIGlzIGFuIEFycmF5QnVmZmVyXG4gKlxuICogQHBhcmFtIHtPYmplY3R9IHZhbCBUaGUgdmFsdWUgdG8gdGVzdFxuICogQHJldHVybnMge2Jvb2xlYW59IFRydWUgaWYgdmFsdWUgaXMgYW4gQXJyYXlCdWZmZXIsIG90aGVyd2lzZSBmYWxzZVxuICovXG5mdW5jdGlvbiBpc0FycmF5QnVmZmVyKHZhbCkge1xuICByZXR1cm4gdG9TdHJpbmcuY2FsbCh2YWwpID09PSAnW29iamVjdCBBcnJheUJ1ZmZlcl0nO1xufVxuXG4vKipcbiAqIERldGVybWluZSBpZiBhIHZhbHVlIGlzIGEgRm9ybURhdGFcbiAqXG4gKiBAcGFyYW0ge09iamVjdH0gdmFsIFRoZSB2YWx1ZSB0byB0ZXN0XG4gKiBAcmV0dXJucyB7Ym9vbGVhbn0gVHJ1ZSBpZiB2YWx1ZSBpcyBhbiBGb3JtRGF0YSwgb3RoZXJ3aXNlIGZhbHNlXG4gKi9cbmZ1bmN0aW9uIGlzRm9ybURhdGEodmFsKSB7XG4gIHJldHVybiAodHlwZW9mIEZvcm1EYXRhICE9PSAndW5kZWZpbmVkJykgJiYgKHZhbCBpbnN0YW5jZW9mIEZvcm1EYXRhKTtcbn1cblxuLyoqXG4gKiBEZXRlcm1pbmUgaWYgYSB2YWx1ZSBpcyBhIHZpZXcgb24gYW4gQXJyYXlCdWZmZXJcbiAqXG4gKiBAcGFyYW0ge09iamVjdH0gdmFsIFRoZSB2YWx1ZSB0byB0ZXN0XG4gKiBAcmV0dXJucyB7Ym9vbGVhbn0gVHJ1ZSBpZiB2YWx1ZSBpcyBhIHZpZXcgb24gYW4gQXJyYXlCdWZmZXIsIG90aGVyd2lzZSBmYWxzZVxuICovXG5mdW5jdGlvbiBpc0FycmF5QnVmZmVyVmlldyh2YWwpIHtcbiAgdmFyIHJlc3VsdDtcbiAgaWYgKCh0eXBlb2YgQXJyYXlCdWZmZXIgIT09ICd1bmRlZmluZWQnKSAmJiAoQXJyYXlCdWZmZXIuaXNWaWV3KSkge1xuICAgIHJlc3VsdCA9IEFycmF5QnVmZmVyLmlzVmlldyh2YWwpO1xuICB9IGVsc2Uge1xuICAgIHJlc3VsdCA9ICh2YWwpICYmICh2YWwuYnVmZmVyKSAmJiAodmFsLmJ1ZmZlciBpbnN0YW5jZW9mIEFycmF5QnVmZmVyKTtcbiAgfVxuICByZXR1cm4gcmVzdWx0O1xufVxuXG4vKipcbiAqIERldGVybWluZSBpZiBhIHZhbHVlIGlzIGEgU3RyaW5nXG4gKlxuICogQHBhcmFtIHtPYmplY3R9IHZhbCBUaGUgdmFsdWUgdG8gdGVzdFxuICogQHJldHVybnMge2Jvb2xlYW59IFRydWUgaWYgdmFsdWUgaXMgYSBTdHJpbmcsIG90aGVyd2lzZSBmYWxzZVxuICovXG5mdW5jdGlvbiBpc1N0cmluZyh2YWwpIHtcbiAgcmV0dXJuIHR5cGVvZiB2YWwgPT09ICdzdHJpbmcnO1xufVxuXG4vKipcbiAqIERldGVybWluZSBpZiBhIHZhbHVlIGlzIGEgTnVtYmVyXG4gKlxuICogQHBhcmFtIHtPYmplY3R9IHZhbCBUaGUgdmFsdWUgdG8gdGVzdFxuICogQHJldHVybnMge2Jvb2xlYW59IFRydWUgaWYgdmFsdWUgaXMgYSBOdW1iZXIsIG90aGVyd2lzZSBmYWxzZVxuICovXG5mdW5jdGlvbiBpc051bWJlcih2YWwpIHtcbiAgcmV0dXJuIHR5cGVvZiB2YWwgPT09ICdudW1iZXInO1xufVxuXG4vKipcbiAqIERldGVybWluZSBpZiBhIHZhbHVlIGlzIHVuZGVmaW5lZFxuICpcbiAqIEBwYXJhbSB7T2JqZWN0fSB2YWwgVGhlIHZhbHVlIHRvIHRlc3RcbiAqIEByZXR1cm5zIHtib29sZWFufSBUcnVlIGlmIHRoZSB2YWx1ZSBpcyB1bmRlZmluZWQsIG90aGVyd2lzZSBmYWxzZVxuICovXG5mdW5jdGlvbiBpc1VuZGVmaW5lZCh2YWwpIHtcbiAgcmV0dXJuIHR5cGVvZiB2YWwgPT09ICd1bmRlZmluZWQnO1xufVxuXG4vKipcbiAqIERldGVybWluZSBpZiBhIHZhbHVlIGlzIGFuIE9iamVjdFxuICpcbiAqIEBwYXJhbSB7T2JqZWN0fSB2YWwgVGhlIHZhbHVlIHRvIHRlc3RcbiAqIEByZXR1cm5zIHtib29sZWFufSBUcnVlIGlmIHZhbHVlIGlzIGFuIE9iamVjdCwgb3RoZXJ3aXNlIGZhbHNlXG4gKi9cbmZ1bmN0aW9uIGlzT2JqZWN0KHZhbCkge1xuICByZXR1cm4gdmFsICE9PSBudWxsICYmIHR5cGVvZiB2YWwgPT09ICdvYmplY3QnO1xufVxuXG4vKipcbiAqIERldGVybWluZSBpZiBhIHZhbHVlIGlzIGEgRGF0ZVxuICpcbiAqIEBwYXJhbSB7T2JqZWN0fSB2YWwgVGhlIHZhbHVlIHRvIHRlc3RcbiAqIEByZXR1cm5zIHtib29sZWFufSBUcnVlIGlmIHZhbHVlIGlzIGEgRGF0ZSwgb3RoZXJ3aXNlIGZhbHNlXG4gKi9cbmZ1bmN0aW9uIGlzRGF0ZSh2YWwpIHtcbiAgcmV0dXJuIHRvU3RyaW5nLmNhbGwodmFsKSA9PT0gJ1tvYmplY3QgRGF0ZV0nO1xufVxuXG4vKipcbiAqIERldGVybWluZSBpZiBhIHZhbHVlIGlzIGEgRmlsZVxuICpcbiAqIEBwYXJhbSB7T2JqZWN0fSB2YWwgVGhlIHZhbHVlIHRvIHRlc3RcbiAqIEByZXR1cm5zIHtib29sZWFufSBUcnVlIGlmIHZhbHVlIGlzIGEgRmlsZSwgb3RoZXJ3aXNlIGZhbHNlXG4gKi9cbmZ1bmN0aW9uIGlzRmlsZSh2YWwpIHtcbiAgcmV0dXJuIHRvU3RyaW5nLmNhbGwodmFsKSA9PT0gJ1tvYmplY3QgRmlsZV0nO1xufVxuXG4vKipcbiAqIERldGVybWluZSBpZiBhIHZhbHVlIGlzIGEgQmxvYlxuICpcbiAqIEBwYXJhbSB7T2JqZWN0fSB2YWwgVGhlIHZhbHVlIHRvIHRlc3RcbiAqIEByZXR1cm5zIHtib29sZWFufSBUcnVlIGlmIHZhbHVlIGlzIGEgQmxvYiwgb3RoZXJ3aXNlIGZhbHNlXG4gKi9cbmZ1bmN0aW9uIGlzQmxvYih2YWwpIHtcbiAgcmV0dXJuIHRvU3RyaW5nLmNhbGwodmFsKSA9PT0gJ1tvYmplY3QgQmxvYl0nO1xufVxuXG4vKipcbiAqIERldGVybWluZSBpZiBhIHZhbHVlIGlzIGEgRnVuY3Rpb25cbiAqXG4gKiBAcGFyYW0ge09iamVjdH0gdmFsIFRoZSB2YWx1ZSB0byB0ZXN0XG4gKiBAcmV0dXJucyB7Ym9vbGVhbn0gVHJ1ZSBpZiB2YWx1ZSBpcyBhIEZ1bmN0aW9uLCBvdGhlcndpc2UgZmFsc2VcbiAqL1xuZnVuY3Rpb24gaXNGdW5jdGlvbih2YWwpIHtcbiAgcmV0dXJuIHRvU3RyaW5nLmNhbGwodmFsKSA9PT0gJ1tvYmplY3QgRnVuY3Rpb25dJztcbn1cblxuLyoqXG4gKiBEZXRlcm1pbmUgaWYgYSB2YWx1ZSBpcyBhIFN0cmVhbVxuICpcbiAqIEBwYXJhbSB7T2JqZWN0fSB2YWwgVGhlIHZhbHVlIHRvIHRlc3RcbiAqIEByZXR1cm5zIHtib29sZWFufSBUcnVlIGlmIHZhbHVlIGlzIGEgU3RyZWFtLCBvdGhlcndpc2UgZmFsc2VcbiAqL1xuZnVuY3Rpb24gaXNTdHJlYW0odmFsKSB7XG4gIHJldHVybiBpc09iamVjdCh2YWwpICYmIGlzRnVuY3Rpb24odmFsLnBpcGUpO1xufVxuXG4vKipcbiAqIERldGVybWluZSBpZiBhIHZhbHVlIGlzIGEgVVJMU2VhcmNoUGFyYW1zIG9iamVjdFxuICpcbiAqIEBwYXJhbSB7T2JqZWN0fSB2YWwgVGhlIHZhbHVlIHRvIHRlc3RcbiAqIEByZXR1cm5zIHtib29sZWFufSBUcnVlIGlmIHZhbHVlIGlzIGEgVVJMU2VhcmNoUGFyYW1zIG9iamVjdCwgb3RoZXJ3aXNlIGZhbHNlXG4gKi9cbmZ1bmN0aW9uIGlzVVJMU2VhcmNoUGFyYW1zKHZhbCkge1xuICByZXR1cm4gdHlwZW9mIFVSTFNlYXJjaFBhcmFtcyAhPT0gJ3VuZGVmaW5lZCcgJiYgdmFsIGluc3RhbmNlb2YgVVJMU2VhcmNoUGFyYW1zO1xufVxuXG4vKipcbiAqIFRyaW0gZXhjZXNzIHdoaXRlc3BhY2Ugb2ZmIHRoZSBiZWdpbm5pbmcgYW5kIGVuZCBvZiBhIHN0cmluZ1xuICpcbiAqIEBwYXJhbSB7U3RyaW5nfSBzdHIgVGhlIFN0cmluZyB0byB0cmltXG4gKiBAcmV0dXJucyB7U3RyaW5nfSBUaGUgU3RyaW5nIGZyZWVkIG9mIGV4Y2VzcyB3aGl0ZXNwYWNlXG4gKi9cbmZ1bmN0aW9uIHRyaW0oc3RyKSB7XG4gIHJldHVybiBzdHIucmVwbGFjZSgvXlxccyovLCAnJykucmVwbGFjZSgvXFxzKiQvLCAnJyk7XG59XG5cbi8qKlxuICogRGV0ZXJtaW5lIGlmIHdlJ3JlIHJ1bm5pbmcgaW4gYSBzdGFuZGFyZCBicm93c2VyIGVudmlyb25tZW50XG4gKlxuICogVGhpcyBhbGxvd3MgYXhpb3MgdG8gcnVuIGluIGEgd2ViIHdvcmtlciwgYW5kIHJlYWN0LW5hdGl2ZS5cbiAqIEJvdGggZW52aXJvbm1lbnRzIHN1cHBvcnQgWE1MSHR0cFJlcXVlc3QsIGJ1dCBub3QgZnVsbHkgc3RhbmRhcmQgZ2xvYmFscy5cbiAqXG4gKiB3ZWIgd29ya2VyczpcbiAqICB0eXBlb2Ygd2luZG93IC0+IHVuZGVmaW5lZFxuICogIHR5cGVvZiBkb2N1bWVudCAtPiB1bmRlZmluZWRcbiAqXG4gKiByZWFjdC1uYXRpdmU6XG4gKiAgbmF2aWdhdG9yLnByb2R1Y3QgLT4gJ1JlYWN0TmF0aXZlJ1xuICovXG5mdW5jdGlvbiBpc1N0YW5kYXJkQnJvd3NlckVudigpIHtcbiAgaWYgKHR5cGVvZiBuYXZpZ2F0b3IgIT09ICd1bmRlZmluZWQnICYmIG5hdmlnYXRvci5wcm9kdWN0ID09PSAnUmVhY3ROYXRpdmUnKSB7XG4gICAgcmV0dXJuIGZhbHNlO1xuICB9XG4gIHJldHVybiAoXG4gICAgdHlwZW9mIHdpbmRvdyAhPT0gJ3VuZGVmaW5lZCcgJiZcbiAgICB0eXBlb2YgZG9jdW1lbnQgIT09ICd1bmRlZmluZWQnXG4gICk7XG59XG5cbi8qKlxuICogSXRlcmF0ZSBvdmVyIGFuIEFycmF5IG9yIGFuIE9iamVjdCBpbnZva2luZyBhIGZ1bmN0aW9uIGZvciBlYWNoIGl0ZW0uXG4gKlxuICogSWYgYG9iamAgaXMgYW4gQXJyYXkgY2FsbGJhY2sgd2lsbCBiZSBjYWxsZWQgcGFzc2luZ1xuICogdGhlIHZhbHVlLCBpbmRleCwgYW5kIGNvbXBsZXRlIGFycmF5IGZvciBlYWNoIGl0ZW0uXG4gKlxuICogSWYgJ29iaicgaXMgYW4gT2JqZWN0IGNhbGxiYWNrIHdpbGwgYmUgY2FsbGVkIHBhc3NpbmdcbiAqIHRoZSB2YWx1ZSwga2V5LCBhbmQgY29tcGxldGUgb2JqZWN0IGZvciBlYWNoIHByb3BlcnR5LlxuICpcbiAqIEBwYXJhbSB7T2JqZWN0fEFycmF5fSBvYmogVGhlIG9iamVjdCB0byBpdGVyYXRlXG4gKiBAcGFyYW0ge0Z1bmN0aW9ufSBmbiBUaGUgY2FsbGJhY2sgdG8gaW52b2tlIGZvciBlYWNoIGl0ZW1cbiAqL1xuZnVuY3Rpb24gZm9yRWFjaChvYmosIGZuKSB7XG4gIC8vIERvbid0IGJvdGhlciBpZiBubyB2YWx1ZSBwcm92aWRlZFxuICBpZiAob2JqID09PSBudWxsIHx8IHR5cGVvZiBvYmogPT09ICd1bmRlZmluZWQnKSB7XG4gICAgcmV0dXJuO1xuICB9XG5cbiAgLy8gRm9yY2UgYW4gYXJyYXkgaWYgbm90IGFscmVhZHkgc29tZXRoaW5nIGl0ZXJhYmxlXG4gIGlmICh0eXBlb2Ygb2JqICE9PSAnb2JqZWN0Jykge1xuICAgIC8qZXNsaW50IG5vLXBhcmFtLXJlYXNzaWduOjAqL1xuICAgIG9iaiA9IFtvYmpdO1xuICB9XG5cbiAgaWYgKGlzQXJyYXkob2JqKSkge1xuICAgIC8vIEl0ZXJhdGUgb3ZlciBhcnJheSB2YWx1ZXNcbiAgICBmb3IgKHZhciBpID0gMCwgbCA9IG9iai5sZW5ndGg7IGkgPCBsOyBpKyspIHtcbiAgICAgIGZuLmNhbGwobnVsbCwgb2JqW2ldLCBpLCBvYmopO1xuICAgIH1cbiAgfSBlbHNlIHtcbiAgICAvLyBJdGVyYXRlIG92ZXIgb2JqZWN0IGtleXNcbiAgICBmb3IgKHZhciBrZXkgaW4gb2JqKSB7XG4gICAgICBpZiAoT2JqZWN0LnByb3RvdHlwZS5oYXNPd25Qcm9wZXJ0eS5jYWxsKG9iaiwga2V5KSkge1xuICAgICAgICBmbi5jYWxsKG51bGwsIG9ialtrZXldLCBrZXksIG9iaik7XG4gICAgICB9XG4gICAgfVxuICB9XG59XG5cbi8qKlxuICogQWNjZXB0cyB2YXJhcmdzIGV4cGVjdGluZyBlYWNoIGFyZ3VtZW50IHRvIGJlIGFuIG9iamVjdCwgdGhlblxuICogaW1tdXRhYmx5IG1lcmdlcyB0aGUgcHJvcGVydGllcyBvZiBlYWNoIG9iamVjdCBhbmQgcmV0dXJucyByZXN1bHQuXG4gKlxuICogV2hlbiBtdWx0aXBsZSBvYmplY3RzIGNvbnRhaW4gdGhlIHNhbWUga2V5IHRoZSBsYXRlciBvYmplY3QgaW5cbiAqIHRoZSBhcmd1bWVudHMgbGlzdCB3aWxsIHRha2UgcHJlY2VkZW5jZS5cbiAqXG4gKiBFeGFtcGxlOlxuICpcbiAqIGBgYGpzXG4gKiB2YXIgcmVzdWx0ID0gbWVyZ2Uoe2ZvbzogMTIzfSwge2ZvbzogNDU2fSk7XG4gKiBjb25zb2xlLmxvZyhyZXN1bHQuZm9vKTsgLy8gb3V0cHV0cyA0NTZcbiAqIGBgYFxuICpcbiAqIEBwYXJhbSB7T2JqZWN0fSBvYmoxIE9iamVjdCB0byBtZXJnZVxuICogQHJldHVybnMge09iamVjdH0gUmVzdWx0IG9mIGFsbCBtZXJnZSBwcm9wZXJ0aWVzXG4gKi9cbmZ1bmN0aW9uIG1lcmdlKC8qIG9iajEsIG9iajIsIG9iajMsIC4uLiAqLykge1xuICB2YXIgcmVzdWx0ID0ge307XG4gIGZ1bmN0aW9uIGFzc2lnblZhbHVlKHZhbCwga2V5KSB7XG4gICAgaWYgKHR5cGVvZiByZXN1bHRba2V5XSA9PT0gJ29iamVjdCcgJiYgdHlwZW9mIHZhbCA9PT0gJ29iamVjdCcpIHtcbiAgICAgIHJlc3VsdFtrZXldID0gbWVyZ2UocmVzdWx0W2tleV0sIHZhbCk7XG4gICAgfSBlbHNlIHtcbiAgICAgIHJlc3VsdFtrZXldID0gdmFsO1xuICAgIH1cbiAgfVxuXG4gIGZvciAodmFyIGkgPSAwLCBsID0gYXJndW1lbnRzLmxlbmd0aDsgaSA8IGw7IGkrKykge1xuICAgIGZvckVhY2goYXJndW1lbnRzW2ldLCBhc3NpZ25WYWx1ZSk7XG4gIH1cbiAgcmV0dXJuIHJlc3VsdDtcbn1cblxuLyoqXG4gKiBFeHRlbmRzIG9iamVjdCBhIGJ5IG11dGFibHkgYWRkaW5nIHRvIGl0IHRoZSBwcm9wZXJ0aWVzIG9mIG9iamVjdCBiLlxuICpcbiAqIEBwYXJhbSB7T2JqZWN0fSBhIFRoZSBvYmplY3QgdG8gYmUgZXh0ZW5kZWRcbiAqIEBwYXJhbSB7T2JqZWN0fSBiIFRoZSBvYmplY3QgdG8gY29weSBwcm9wZXJ0aWVzIGZyb21cbiAqIEBwYXJhbSB7T2JqZWN0fSB0aGlzQXJnIFRoZSBvYmplY3QgdG8gYmluZCBmdW5jdGlvbiB0b1xuICogQHJldHVybiB7T2JqZWN0fSBUaGUgcmVzdWx0aW5nIHZhbHVlIG9mIG9iamVjdCBhXG4gKi9cbmZ1bmN0aW9uIGV4dGVuZChhLCBiLCB0aGlzQXJnKSB7XG4gIGZvckVhY2goYiwgZnVuY3Rpb24gYXNzaWduVmFsdWUodmFsLCBrZXkpIHtcbiAgICBpZiAodGhpc0FyZyAmJiB0eXBlb2YgdmFsID09PSAnZnVuY3Rpb24nKSB7XG4gICAgICBhW2tleV0gPSBiaW5kKHZhbCwgdGhpc0FyZyk7XG4gICAgfSBlbHNlIHtcbiAgICAgIGFba2V5XSA9IHZhbDtcbiAgICB9XG4gIH0pO1xuICByZXR1cm4gYTtcbn1cblxubW9kdWxlLmV4cG9ydHMgPSB7XG4gIGlzQXJyYXk6IGlzQXJyYXksXG4gIGlzQXJyYXlCdWZmZXI6IGlzQXJyYXlCdWZmZXIsXG4gIGlzQnVmZmVyOiBpc0J1ZmZlcixcbiAgaXNGb3JtRGF0YTogaXNGb3JtRGF0YSxcbiAgaXNBcnJheUJ1ZmZlclZpZXc6IGlzQXJyYXlCdWZmZXJWaWV3LFxuICBpc1N0cmluZzogaXNTdHJpbmcsXG4gIGlzTnVtYmVyOiBpc051bWJlcixcbiAgaXNPYmplY3Q6IGlzT2JqZWN0LFxuICBpc1VuZGVmaW5lZDogaXNVbmRlZmluZWQsXG4gIGlzRGF0ZTogaXNEYXRlLFxuICBpc0ZpbGU6IGlzRmlsZSxcbiAgaXNCbG9iOiBpc0Jsb2IsXG4gIGlzRnVuY3Rpb246IGlzRnVuY3Rpb24sXG4gIGlzU3RyZWFtOiBpc1N0cmVhbSxcbiAgaXNVUkxTZWFyY2hQYXJhbXM6IGlzVVJMU2VhcmNoUGFyYW1zLFxuICBpc1N0YW5kYXJkQnJvd3NlckVudjogaXNTdGFuZGFyZEJyb3dzZXJFbnYsXG4gIGZvckVhY2g6IGZvckVhY2gsXG4gIG1lcmdlOiBtZXJnZSxcbiAgZXh0ZW5kOiBleHRlbmQsXG4gIHRyaW06IHRyaW1cbn07XG4iLCIndXNlIHN0cmljdCc7XG5cbnZhciB1dGlscyA9IHJlcXVpcmUoJy4uL3V0aWxzJyk7XG5cbm1vZHVsZS5leHBvcnRzID0gZnVuY3Rpb24gbm9ybWFsaXplSGVhZGVyTmFtZShoZWFkZXJzLCBub3JtYWxpemVkTmFtZSkge1xuICB1dGlscy5mb3JFYWNoKGhlYWRlcnMsIGZ1bmN0aW9uIHByb2Nlc3NIZWFkZXIodmFsdWUsIG5hbWUpIHtcbiAgICBpZiAobmFtZSAhPT0gbm9ybWFsaXplZE5hbWUgJiYgbmFtZS50b1VwcGVyQ2FzZSgpID09PSBub3JtYWxpemVkTmFtZS50b1VwcGVyQ2FzZSgpKSB7XG4gICAgICBoZWFkZXJzW25vcm1hbGl6ZWROYW1lXSA9IHZhbHVlO1xuICAgICAgZGVsZXRlIGhlYWRlcnNbbmFtZV07XG4gICAgfVxuICB9KTtcbn07XG4iLCIndXNlIHN0cmljdCc7XG5cbi8qKlxuICogVXBkYXRlIGFuIEVycm9yIHdpdGggdGhlIHNwZWNpZmllZCBjb25maWcsIGVycm9yIGNvZGUsIGFuZCByZXNwb25zZS5cbiAqXG4gKiBAcGFyYW0ge0Vycm9yfSBlcnJvciBUaGUgZXJyb3IgdG8gdXBkYXRlLlxuICogQHBhcmFtIHtPYmplY3R9IGNvbmZpZyBUaGUgY29uZmlnLlxuICogQHBhcmFtIHtzdHJpbmd9IFtjb2RlXSBUaGUgZXJyb3IgY29kZSAoZm9yIGV4YW1wbGUsICdFQ09OTkFCT1JURUQnKS5cbiAqIEBwYXJhbSB7T2JqZWN0fSBbcmVxdWVzdF0gVGhlIHJlcXVlc3QuXG4gKiBAcGFyYW0ge09iamVjdH0gW3Jlc3BvbnNlXSBUaGUgcmVzcG9uc2UuXG4gKiBAcmV0dXJucyB7RXJyb3J9IFRoZSBlcnJvci5cbiAqL1xubW9kdWxlLmV4cG9ydHMgPSBmdW5jdGlvbiBlbmhhbmNlRXJyb3IoZXJyb3IsIGNvbmZpZywgY29kZSwgcmVxdWVzdCwgcmVzcG9uc2UpIHtcbiAgZXJyb3IuY29uZmlnID0gY29uZmlnO1xuICBpZiAoY29kZSkge1xuICAgIGVycm9yLmNvZGUgPSBjb2RlO1xuICB9XG4gIGVycm9yLnJlcXVlc3QgPSByZXF1ZXN0O1xuICBlcnJvci5yZXNwb25zZSA9IHJlc3BvbnNlO1xuICByZXR1cm4gZXJyb3I7XG59O1xuIiwiJ3VzZSBzdHJpY3QnO1xuXG52YXIgZW5oYW5jZUVycm9yID0gcmVxdWlyZSgnLi9lbmhhbmNlRXJyb3InKTtcblxuLyoqXG4gKiBDcmVhdGUgYW4gRXJyb3Igd2l0aCB0aGUgc3BlY2lmaWVkIG1lc3NhZ2UsIGNvbmZpZywgZXJyb3IgY29kZSwgcmVxdWVzdCBhbmQgcmVzcG9uc2UuXG4gKlxuICogQHBhcmFtIHtzdHJpbmd9IG1lc3NhZ2UgVGhlIGVycm9yIG1lc3NhZ2UuXG4gKiBAcGFyYW0ge09iamVjdH0gY29uZmlnIFRoZSBjb25maWcuXG4gKiBAcGFyYW0ge3N0cmluZ30gW2NvZGVdIFRoZSBlcnJvciBjb2RlIChmb3IgZXhhbXBsZSwgJ0VDT05OQUJPUlRFRCcpLlxuICogQHBhcmFtIHtPYmplY3R9IFtyZXF1ZXN0XSBUaGUgcmVxdWVzdC5cbiAqIEBwYXJhbSB7T2JqZWN0fSBbcmVzcG9uc2VdIFRoZSByZXNwb25zZS5cbiAqIEByZXR1cm5zIHtFcnJvcn0gVGhlIGNyZWF0ZWQgZXJyb3IuXG4gKi9cbm1vZHVsZS5leHBvcnRzID0gZnVuY3Rpb24gY3JlYXRlRXJyb3IobWVzc2FnZSwgY29uZmlnLCBjb2RlLCByZXF1ZXN0LCByZXNwb25zZSkge1xuICB2YXIgZXJyb3IgPSBuZXcgRXJyb3IobWVzc2FnZSk7XG4gIHJldHVybiBlbmhhbmNlRXJyb3IoZXJyb3IsIGNvbmZpZywgY29kZSwgcmVxdWVzdCwgcmVzcG9uc2UpO1xufTtcbiIsIid1c2Ugc3RyaWN0JztcblxudmFyIGNyZWF0ZUVycm9yID0gcmVxdWlyZSgnLi9jcmVhdGVFcnJvcicpO1xuXG4vKipcbiAqIFJlc29sdmUgb3IgcmVqZWN0IGEgUHJvbWlzZSBiYXNlZCBvbiByZXNwb25zZSBzdGF0dXMuXG4gKlxuICogQHBhcmFtIHtGdW5jdGlvbn0gcmVzb2x2ZSBBIGZ1bmN0aW9uIHRoYXQgcmVzb2x2ZXMgdGhlIHByb21pc2UuXG4gKiBAcGFyYW0ge0Z1bmN0aW9ufSByZWplY3QgQSBmdW5jdGlvbiB0aGF0IHJlamVjdHMgdGhlIHByb21pc2UuXG4gKiBAcGFyYW0ge29iamVjdH0gcmVzcG9uc2UgVGhlIHJlc3BvbnNlLlxuICovXG5tb2R1bGUuZXhwb3J0cyA9IGZ1bmN0aW9uIHNldHRsZShyZXNvbHZlLCByZWplY3QsIHJlc3BvbnNlKSB7XG4gIHZhciB2YWxpZGF0ZVN0YXR1cyA9IHJlc3BvbnNlLmNvbmZpZy52YWxpZGF0ZVN0YXR1cztcbiAgLy8gTm90ZTogc3RhdHVzIGlzIG5vdCBleHBvc2VkIGJ5IFhEb21haW5SZXF1ZXN0XG4gIGlmICghcmVzcG9uc2Uuc3RhdHVzIHx8ICF2YWxpZGF0ZVN0YXR1cyB8fCB2YWxpZGF0ZVN0YXR1cyhyZXNwb25zZS5zdGF0dXMpKSB7XG4gICAgcmVzb2x2ZShyZXNwb25zZSk7XG4gIH0gZWxzZSB7XG4gICAgcmVqZWN0KGNyZWF0ZUVycm9yKFxuICAgICAgJ1JlcXVlc3QgZmFpbGVkIHdpdGggc3RhdHVzIGNvZGUgJyArIHJlc3BvbnNlLnN0YXR1cyxcbiAgICAgIHJlc3BvbnNlLmNvbmZpZyxcbiAgICAgIG51bGwsXG4gICAgICByZXNwb25zZS5yZXF1ZXN0LFxuICAgICAgcmVzcG9uc2VcbiAgICApKTtcbiAgfVxufTtcbiIsIid1c2Ugc3RyaWN0JztcblxudmFyIHV0aWxzID0gcmVxdWlyZSgnLi8uLi91dGlscycpO1xuXG5mdW5jdGlvbiBlbmNvZGUodmFsKSB7XG4gIHJldHVybiBlbmNvZGVVUklDb21wb25lbnQodmFsKS5cbiAgICByZXBsYWNlKC8lNDAvZ2ksICdAJykuXG4gICAgcmVwbGFjZSgvJTNBL2dpLCAnOicpLlxuICAgIHJlcGxhY2UoLyUyNC9nLCAnJCcpLlxuICAgIHJlcGxhY2UoLyUyQy9naSwgJywnKS5cbiAgICByZXBsYWNlKC8lMjAvZywgJysnKS5cbiAgICByZXBsYWNlKC8lNUIvZ2ksICdbJykuXG4gICAgcmVwbGFjZSgvJTVEL2dpLCAnXScpO1xufVxuXG4vKipcbiAqIEJ1aWxkIGEgVVJMIGJ5IGFwcGVuZGluZyBwYXJhbXMgdG8gdGhlIGVuZFxuICpcbiAqIEBwYXJhbSB7c3RyaW5nfSB1cmwgVGhlIGJhc2Ugb2YgdGhlIHVybCAoZS5nLiwgaHR0cDovL3d3dy5nb29nbGUuY29tKVxuICogQHBhcmFtIHtvYmplY3R9IFtwYXJhbXNdIFRoZSBwYXJhbXMgdG8gYmUgYXBwZW5kZWRcbiAqIEByZXR1cm5zIHtzdHJpbmd9IFRoZSBmb3JtYXR0ZWQgdXJsXG4gKi9cbm1vZHVsZS5leHBvcnRzID0gZnVuY3Rpb24gYnVpbGRVUkwodXJsLCBwYXJhbXMsIHBhcmFtc1NlcmlhbGl6ZXIpIHtcbiAgLyplc2xpbnQgbm8tcGFyYW0tcmVhc3NpZ246MCovXG4gIGlmICghcGFyYW1zKSB7XG4gICAgcmV0dXJuIHVybDtcbiAgfVxuXG4gIHZhciBzZXJpYWxpemVkUGFyYW1zO1xuICBpZiAocGFyYW1zU2VyaWFsaXplcikge1xuICAgIHNlcmlhbGl6ZWRQYXJhbXMgPSBwYXJhbXNTZXJpYWxpemVyKHBhcmFtcyk7XG4gIH0gZWxzZSBpZiAodXRpbHMuaXNVUkxTZWFyY2hQYXJhbXMocGFyYW1zKSkge1xuICAgIHNlcmlhbGl6ZWRQYXJhbXMgPSBwYXJhbXMudG9TdHJpbmcoKTtcbiAgfSBlbHNlIHtcbiAgICB2YXIgcGFydHMgPSBbXTtcblxuICAgIHV0aWxzLmZvckVhY2gocGFyYW1zLCBmdW5jdGlvbiBzZXJpYWxpemUodmFsLCBrZXkpIHtcbiAgICAgIGlmICh2YWwgPT09IG51bGwgfHwgdHlwZW9mIHZhbCA9PT0gJ3VuZGVmaW5lZCcpIHtcbiAgICAgICAgcmV0dXJuO1xuICAgICAgfVxuXG4gICAgICBpZiAodXRpbHMuaXNBcnJheSh2YWwpKSB7XG4gICAgICAgIGtleSA9IGtleSArICdbXSc7XG4gICAgICB9IGVsc2Uge1xuICAgICAgICB2YWwgPSBbdmFsXTtcbiAgICAgIH1cblxuICAgICAgdXRpbHMuZm9yRWFjaCh2YWwsIGZ1bmN0aW9uIHBhcnNlVmFsdWUodikge1xuICAgICAgICBpZiAodXRpbHMuaXNEYXRlKHYpKSB7XG4gICAgICAgICAgdiA9IHYudG9JU09TdHJpbmcoKTtcbiAgICAgICAgfSBlbHNlIGlmICh1dGlscy5pc09iamVjdCh2KSkge1xuICAgICAgICAgIHYgPSBKU09OLnN0cmluZ2lmeSh2KTtcbiAgICAgICAgfVxuICAgICAgICBwYXJ0cy5wdXNoKGVuY29kZShrZXkpICsgJz0nICsgZW5jb2RlKHYpKTtcbiAgICAgIH0pO1xuICAgIH0pO1xuXG4gICAgc2VyaWFsaXplZFBhcmFtcyA9IHBhcnRzLmpvaW4oJyYnKTtcbiAgfVxuXG4gIGlmIChzZXJpYWxpemVkUGFyYW1zKSB7XG4gICAgdXJsICs9ICh1cmwuaW5kZXhPZignPycpID09PSAtMSA/ICc/JyA6ICcmJykgKyBzZXJpYWxpemVkUGFyYW1zO1xuICB9XG5cbiAgcmV0dXJuIHVybDtcbn07XG4iLCIndXNlIHN0cmljdCc7XG5cbnZhciB1dGlscyA9IHJlcXVpcmUoJy4vLi4vdXRpbHMnKTtcblxuLy8gSGVhZGVycyB3aG9zZSBkdXBsaWNhdGVzIGFyZSBpZ25vcmVkIGJ5IG5vZGVcbi8vIGMuZi4gaHR0cHM6Ly9ub2RlanMub3JnL2FwaS9odHRwLmh0bWwjaHR0cF9tZXNzYWdlX2hlYWRlcnNcbnZhciBpZ25vcmVEdXBsaWNhdGVPZiA9IFtcbiAgJ2FnZScsICdhdXRob3JpemF0aW9uJywgJ2NvbnRlbnQtbGVuZ3RoJywgJ2NvbnRlbnQtdHlwZScsICdldGFnJyxcbiAgJ2V4cGlyZXMnLCAnZnJvbScsICdob3N0JywgJ2lmLW1vZGlmaWVkLXNpbmNlJywgJ2lmLXVubW9kaWZpZWQtc2luY2UnLFxuICAnbGFzdC1tb2RpZmllZCcsICdsb2NhdGlvbicsICdtYXgtZm9yd2FyZHMnLCAncHJveHktYXV0aG9yaXphdGlvbicsXG4gICdyZWZlcmVyJywgJ3JldHJ5LWFmdGVyJywgJ3VzZXItYWdlbnQnXG5dO1xuXG4vKipcbiAqIFBhcnNlIGhlYWRlcnMgaW50byBhbiBvYmplY3RcbiAqXG4gKiBgYGBcbiAqIERhdGU6IFdlZCwgMjcgQXVnIDIwMTQgMDg6NTg6NDkgR01UXG4gKiBDb250ZW50LVR5cGU6IGFwcGxpY2F0aW9uL2pzb25cbiAqIENvbm5lY3Rpb246IGtlZXAtYWxpdmVcbiAqIFRyYW5zZmVyLUVuY29kaW5nOiBjaHVua2VkXG4gKiBgYGBcbiAqXG4gKiBAcGFyYW0ge1N0cmluZ30gaGVhZGVycyBIZWFkZXJzIG5lZWRpbmcgdG8gYmUgcGFyc2VkXG4gKiBAcmV0dXJucyB7T2JqZWN0fSBIZWFkZXJzIHBhcnNlZCBpbnRvIGFuIG9iamVjdFxuICovXG5tb2R1bGUuZXhwb3J0cyA9IGZ1bmN0aW9uIHBhcnNlSGVhZGVycyhoZWFkZXJzKSB7XG4gIHZhciBwYXJzZWQgPSB7fTtcbiAgdmFyIGtleTtcbiAgdmFyIHZhbDtcbiAgdmFyIGk7XG5cbiAgaWYgKCFoZWFkZXJzKSB7IHJldHVybiBwYXJzZWQ7IH1cblxuICB1dGlscy5mb3JFYWNoKGhlYWRlcnMuc3BsaXQoJ1xcbicpLCBmdW5jdGlvbiBwYXJzZXIobGluZSkge1xuICAgIGkgPSBsaW5lLmluZGV4T2YoJzonKTtcbiAgICBrZXkgPSB1dGlscy50cmltKGxpbmUuc3Vic3RyKDAsIGkpKS50b0xvd2VyQ2FzZSgpO1xuICAgIHZhbCA9IHV0aWxzLnRyaW0obGluZS5zdWJzdHIoaSArIDEpKTtcblxuICAgIGlmIChrZXkpIHtcbiAgICAgIGlmIChwYXJzZWRba2V5XSAmJiBpZ25vcmVEdXBsaWNhdGVPZi5pbmRleE9mKGtleSkgPj0gMCkge1xuICAgICAgICByZXR1cm47XG4gICAgICB9XG4gICAgICBpZiAoa2V5ID09PSAnc2V0LWNvb2tpZScpIHtcbiAgICAgICAgcGFyc2VkW2tleV0gPSAocGFyc2VkW2tleV0gPyBwYXJzZWRba2V5XSA6IFtdKS5jb25jYXQoW3ZhbF0pO1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgcGFyc2VkW2tleV0gPSBwYXJzZWRba2V5XSA/IHBhcnNlZFtrZXldICsgJywgJyArIHZhbCA6IHZhbDtcbiAgICAgIH1cbiAgICB9XG4gIH0pO1xuXG4gIHJldHVybiBwYXJzZWQ7XG59O1xuIiwiJ3VzZSBzdHJpY3QnO1xuXG52YXIgdXRpbHMgPSByZXF1aXJlKCcuLy4uL3V0aWxzJyk7XG5cbm1vZHVsZS5leHBvcnRzID0gKFxuICB1dGlscy5pc1N0YW5kYXJkQnJvd3NlckVudigpID9cblxuICAvLyBTdGFuZGFyZCBicm93c2VyIGVudnMgaGF2ZSBmdWxsIHN1cHBvcnQgb2YgdGhlIEFQSXMgbmVlZGVkIHRvIHRlc3RcbiAgLy8gd2hldGhlciB0aGUgcmVxdWVzdCBVUkwgaXMgb2YgdGhlIHNhbWUgb3JpZ2luIGFzIGN1cnJlbnQgbG9jYXRpb24uXG4gIChmdW5jdGlvbiBzdGFuZGFyZEJyb3dzZXJFbnYoKSB7XG4gICAgdmFyIG1zaWUgPSAvKG1zaWV8dHJpZGVudCkvaS50ZXN0KG5hdmlnYXRvci51c2VyQWdlbnQpO1xuICAgIHZhciB1cmxQYXJzaW5nTm9kZSA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoJ2EnKTtcbiAgICB2YXIgb3JpZ2luVVJMO1xuXG4gICAgLyoqXG4gICAgKiBQYXJzZSBhIFVSTCB0byBkaXNjb3ZlciBpdCdzIGNvbXBvbmVudHNcbiAgICAqXG4gICAgKiBAcGFyYW0ge1N0cmluZ30gdXJsIFRoZSBVUkwgdG8gYmUgcGFyc2VkXG4gICAgKiBAcmV0dXJucyB7T2JqZWN0fVxuICAgICovXG4gICAgZnVuY3Rpb24gcmVzb2x2ZVVSTCh1cmwpIHtcbiAgICAgIHZhciBocmVmID0gdXJsO1xuXG4gICAgICBpZiAobXNpZSkge1xuICAgICAgICAvLyBJRSBuZWVkcyBhdHRyaWJ1dGUgc2V0IHR3aWNlIHRvIG5vcm1hbGl6ZSBwcm9wZXJ0aWVzXG4gICAgICAgIHVybFBhcnNpbmdOb2RlLnNldEF0dHJpYnV0ZSgnaHJlZicsIGhyZWYpO1xuICAgICAgICBocmVmID0gdXJsUGFyc2luZ05vZGUuaHJlZjtcbiAgICAgIH1cblxuICAgICAgdXJsUGFyc2luZ05vZGUuc2V0QXR0cmlidXRlKCdocmVmJywgaHJlZik7XG5cbiAgICAgIC8vIHVybFBhcnNpbmdOb2RlIHByb3ZpZGVzIHRoZSBVcmxVdGlscyBpbnRlcmZhY2UgLSBodHRwOi8vdXJsLnNwZWMud2hhdHdnLm9yZy8jdXJsdXRpbHNcbiAgICAgIHJldHVybiB7XG4gICAgICAgIGhyZWY6IHVybFBhcnNpbmdOb2RlLmhyZWYsXG4gICAgICAgIHByb3RvY29sOiB1cmxQYXJzaW5nTm9kZS5wcm90b2NvbCA/IHVybFBhcnNpbmdOb2RlLnByb3RvY29sLnJlcGxhY2UoLzokLywgJycpIDogJycsXG4gICAgICAgIGhvc3Q6IHVybFBhcnNpbmdOb2RlLmhvc3QsXG4gICAgICAgIHNlYXJjaDogdXJsUGFyc2luZ05vZGUuc2VhcmNoID8gdXJsUGFyc2luZ05vZGUuc2VhcmNoLnJlcGxhY2UoL15cXD8vLCAnJykgOiAnJyxcbiAgICAgICAgaGFzaDogdXJsUGFyc2luZ05vZGUuaGFzaCA/IHVybFBhcnNpbmdOb2RlLmhhc2gucmVwbGFjZSgvXiMvLCAnJykgOiAnJyxcbiAgICAgICAgaG9zdG5hbWU6IHVybFBhcnNpbmdOb2RlLmhvc3RuYW1lLFxuICAgICAgICBwb3J0OiB1cmxQYXJzaW5nTm9kZS5wb3J0LFxuICAgICAgICBwYXRobmFtZTogKHVybFBhcnNpbmdOb2RlLnBhdGhuYW1lLmNoYXJBdCgwKSA9PT0gJy8nKSA/XG4gICAgICAgICAgICAgICAgICB1cmxQYXJzaW5nTm9kZS5wYXRobmFtZSA6XG4gICAgICAgICAgICAgICAgICAnLycgKyB1cmxQYXJzaW5nTm9kZS5wYXRobmFtZVxuICAgICAgfTtcbiAgICB9XG5cbiAgICBvcmlnaW5VUkwgPSByZXNvbHZlVVJMKHdpbmRvdy5sb2NhdGlvbi5ocmVmKTtcblxuICAgIC8qKlxuICAgICogRGV0ZXJtaW5lIGlmIGEgVVJMIHNoYXJlcyB0aGUgc2FtZSBvcmlnaW4gYXMgdGhlIGN1cnJlbnQgbG9jYXRpb25cbiAgICAqXG4gICAgKiBAcGFyYW0ge1N0cmluZ30gcmVxdWVzdFVSTCBUaGUgVVJMIHRvIHRlc3RcbiAgICAqIEByZXR1cm5zIHtib29sZWFufSBUcnVlIGlmIFVSTCBzaGFyZXMgdGhlIHNhbWUgb3JpZ2luLCBvdGhlcndpc2UgZmFsc2VcbiAgICAqL1xuICAgIHJldHVybiBmdW5jdGlvbiBpc1VSTFNhbWVPcmlnaW4ocmVxdWVzdFVSTCkge1xuICAgICAgdmFyIHBhcnNlZCA9ICh1dGlscy5pc1N0cmluZyhyZXF1ZXN0VVJMKSkgPyByZXNvbHZlVVJMKHJlcXVlc3RVUkwpIDogcmVxdWVzdFVSTDtcbiAgICAgIHJldHVybiAocGFyc2VkLnByb3RvY29sID09PSBvcmlnaW5VUkwucHJvdG9jb2wgJiZcbiAgICAgICAgICAgIHBhcnNlZC5ob3N0ID09PSBvcmlnaW5VUkwuaG9zdCk7XG4gICAgfTtcbiAgfSkoKSA6XG5cbiAgLy8gTm9uIHN0YW5kYXJkIGJyb3dzZXIgZW52cyAod2ViIHdvcmtlcnMsIHJlYWN0LW5hdGl2ZSkgbGFjayBuZWVkZWQgc3VwcG9ydC5cbiAgKGZ1bmN0aW9uIG5vblN0YW5kYXJkQnJvd3NlckVudigpIHtcbiAgICByZXR1cm4gZnVuY3Rpb24gaXNVUkxTYW1lT3JpZ2luKCkge1xuICAgICAgcmV0dXJuIHRydWU7XG4gICAgfTtcbiAgfSkoKVxuKTtcbiIsIid1c2Ugc3RyaWN0JztcblxuLy8gYnRvYSBwb2x5ZmlsbCBmb3IgSUU8MTAgY291cnRlc3kgaHR0cHM6Ly9naXRodWIuY29tL2RhdmlkY2hhbWJlcnMvQmFzZTY0LmpzXG5cbnZhciBjaGFycyA9ICdBQkNERUZHSElKS0xNTk9QUVJTVFVWV1hZWmFiY2RlZmdoaWprbG1ub3BxcnN0dXZ3eHl6MDEyMzQ1Njc4OSsvPSc7XG5cbmZ1bmN0aW9uIEUoKSB7XG4gIHRoaXMubWVzc2FnZSA9ICdTdHJpbmcgY29udGFpbnMgYW4gaW52YWxpZCBjaGFyYWN0ZXInO1xufVxuRS5wcm90b3R5cGUgPSBuZXcgRXJyb3I7XG5FLnByb3RvdHlwZS5jb2RlID0gNTtcbkUucHJvdG90eXBlLm5hbWUgPSAnSW52YWxpZENoYXJhY3RlckVycm9yJztcblxuZnVuY3Rpb24gYnRvYShpbnB1dCkge1xuICB2YXIgc3RyID0gU3RyaW5nKGlucHV0KTtcbiAgdmFyIG91dHB1dCA9ICcnO1xuICBmb3IgKFxuICAgIC8vIGluaXRpYWxpemUgcmVzdWx0IGFuZCBjb3VudGVyXG4gICAgdmFyIGJsb2NrLCBjaGFyQ29kZSwgaWR4ID0gMCwgbWFwID0gY2hhcnM7XG4gICAgLy8gaWYgdGhlIG5leHQgc3RyIGluZGV4IGRvZXMgbm90IGV4aXN0OlxuICAgIC8vICAgY2hhbmdlIHRoZSBtYXBwaW5nIHRhYmxlIHRvIFwiPVwiXG4gICAgLy8gICBjaGVjayBpZiBkIGhhcyBubyBmcmFjdGlvbmFsIGRpZ2l0c1xuICAgIHN0ci5jaGFyQXQoaWR4IHwgMCkgfHwgKG1hcCA9ICc9JywgaWR4ICUgMSk7XG4gICAgLy8gXCI4IC0gaWR4ICUgMSAqIDhcIiBnZW5lcmF0ZXMgdGhlIHNlcXVlbmNlIDIsIDQsIDYsIDhcbiAgICBvdXRwdXQgKz0gbWFwLmNoYXJBdCg2MyAmIGJsb2NrID4+IDggLSBpZHggJSAxICogOClcbiAgKSB7XG4gICAgY2hhckNvZGUgPSBzdHIuY2hhckNvZGVBdChpZHggKz0gMyAvIDQpO1xuICAgIGlmIChjaGFyQ29kZSA+IDB4RkYpIHtcbiAgICAgIHRocm93IG5ldyBFKCk7XG4gICAgfVxuICAgIGJsb2NrID0gYmxvY2sgPDwgOCB8IGNoYXJDb2RlO1xuICB9XG4gIHJldHVybiBvdXRwdXQ7XG59XG5cbm1vZHVsZS5leHBvcnRzID0gYnRvYTtcbiIsIid1c2Ugc3RyaWN0JztcblxudmFyIHV0aWxzID0gcmVxdWlyZSgnLi8uLi91dGlscycpO1xuXG5tb2R1bGUuZXhwb3J0cyA9IChcbiAgdXRpbHMuaXNTdGFuZGFyZEJyb3dzZXJFbnYoKSA/XG5cbiAgLy8gU3RhbmRhcmQgYnJvd3NlciBlbnZzIHN1cHBvcnQgZG9jdW1lbnQuY29va2llXG4gIChmdW5jdGlvbiBzdGFuZGFyZEJyb3dzZXJFbnYoKSB7XG4gICAgcmV0dXJuIHtcbiAgICAgIHdyaXRlOiBmdW5jdGlvbiB3cml0ZShuYW1lLCB2YWx1ZSwgZXhwaXJlcywgcGF0aCwgZG9tYWluLCBzZWN1cmUpIHtcbiAgICAgICAgdmFyIGNvb2tpZSA9IFtdO1xuICAgICAgICBjb29raWUucHVzaChuYW1lICsgJz0nICsgZW5jb2RlVVJJQ29tcG9uZW50KHZhbHVlKSk7XG5cbiAgICAgICAgaWYgKHV0aWxzLmlzTnVtYmVyKGV4cGlyZXMpKSB7XG4gICAgICAgICAgY29va2llLnB1c2goJ2V4cGlyZXM9JyArIG5ldyBEYXRlKGV4cGlyZXMpLnRvR01UU3RyaW5nKCkpO1xuICAgICAgICB9XG5cbiAgICAgICAgaWYgKHV0aWxzLmlzU3RyaW5nKHBhdGgpKSB7XG4gICAgICAgICAgY29va2llLnB1c2goJ3BhdGg9JyArIHBhdGgpO1xuICAgICAgICB9XG5cbiAgICAgICAgaWYgKHV0aWxzLmlzU3RyaW5nKGRvbWFpbikpIHtcbiAgICAgICAgICBjb29raWUucHVzaCgnZG9tYWluPScgKyBkb21haW4pO1xuICAgICAgICB9XG5cbiAgICAgICAgaWYgKHNlY3VyZSA9PT0gdHJ1ZSkge1xuICAgICAgICAgIGNvb2tpZS5wdXNoKCdzZWN1cmUnKTtcbiAgICAgICAgfVxuXG4gICAgICAgIGRvY3VtZW50LmNvb2tpZSA9IGNvb2tpZS5qb2luKCc7ICcpO1xuICAgICAgfSxcblxuICAgICAgcmVhZDogZnVuY3Rpb24gcmVhZChuYW1lKSB7XG4gICAgICAgIHZhciBtYXRjaCA9IGRvY3VtZW50LmNvb2tpZS5tYXRjaChuZXcgUmVnRXhwKCcoXnw7XFxcXHMqKSgnICsgbmFtZSArICcpPShbXjtdKiknKSk7XG4gICAgICAgIHJldHVybiAobWF0Y2ggPyBkZWNvZGVVUklDb21wb25lbnQobWF0Y2hbM10pIDogbnVsbCk7XG4gICAgICB9LFxuXG4gICAgICByZW1vdmU6IGZ1bmN0aW9uIHJlbW92ZShuYW1lKSB7XG4gICAgICAgIHRoaXMud3JpdGUobmFtZSwgJycsIERhdGUubm93KCkgLSA4NjQwMDAwMCk7XG4gICAgICB9XG4gICAgfTtcbiAgfSkoKSA6XG5cbiAgLy8gTm9uIHN0YW5kYXJkIGJyb3dzZXIgZW52ICh3ZWIgd29ya2VycywgcmVhY3QtbmF0aXZlKSBsYWNrIG5lZWRlZCBzdXBwb3J0LlxuICAoZnVuY3Rpb24gbm9uU3RhbmRhcmRCcm93c2VyRW52KCkge1xuICAgIHJldHVybiB7XG4gICAgICB3cml0ZTogZnVuY3Rpb24gd3JpdGUoKSB7fSxcbiAgICAgIHJlYWQ6IGZ1bmN0aW9uIHJlYWQoKSB7IHJldHVybiBudWxsOyB9LFxuICAgICAgcmVtb3ZlOiBmdW5jdGlvbiByZW1vdmUoKSB7fVxuICAgIH07XG4gIH0pKClcbik7XG4iLCIndXNlIHN0cmljdCc7XG5cbnZhciB1dGlscyA9IHJlcXVpcmUoJy4vLi4vdXRpbHMnKTtcbnZhciBzZXR0bGUgPSByZXF1aXJlKCcuLy4uL2NvcmUvc2V0dGxlJyk7XG52YXIgYnVpbGRVUkwgPSByZXF1aXJlKCcuLy4uL2hlbHBlcnMvYnVpbGRVUkwnKTtcbnZhciBwYXJzZUhlYWRlcnMgPSByZXF1aXJlKCcuLy4uL2hlbHBlcnMvcGFyc2VIZWFkZXJzJyk7XG52YXIgaXNVUkxTYW1lT3JpZ2luID0gcmVxdWlyZSgnLi8uLi9oZWxwZXJzL2lzVVJMU2FtZU9yaWdpbicpO1xudmFyIGNyZWF0ZUVycm9yID0gcmVxdWlyZSgnLi4vY29yZS9jcmVhdGVFcnJvcicpO1xudmFyIGJ0b2EgPSAodHlwZW9mIHdpbmRvdyAhPT0gJ3VuZGVmaW5lZCcgJiYgd2luZG93LmJ0b2EgJiYgd2luZG93LmJ0b2EuYmluZCh3aW5kb3cpKSB8fCByZXF1aXJlKCcuLy4uL2hlbHBlcnMvYnRvYScpO1xuXG5tb2R1bGUuZXhwb3J0cyA9IGZ1bmN0aW9uIHhockFkYXB0ZXIoY29uZmlnKSB7XG4gIHJldHVybiBuZXcgUHJvbWlzZShmdW5jdGlvbiBkaXNwYXRjaFhoclJlcXVlc3QocmVzb2x2ZSwgcmVqZWN0KSB7XG4gICAgdmFyIHJlcXVlc3REYXRhID0gY29uZmlnLmRhdGE7XG4gICAgdmFyIHJlcXVlc3RIZWFkZXJzID0gY29uZmlnLmhlYWRlcnM7XG5cbiAgICBpZiAodXRpbHMuaXNGb3JtRGF0YShyZXF1ZXN0RGF0YSkpIHtcbiAgICAgIGRlbGV0ZSByZXF1ZXN0SGVhZGVyc1snQ29udGVudC1UeXBlJ107IC8vIExldCB0aGUgYnJvd3NlciBzZXQgaXRcbiAgICB9XG5cbiAgICB2YXIgcmVxdWVzdCA9IG5ldyBYTUxIdHRwUmVxdWVzdCgpO1xuICAgIHZhciBsb2FkRXZlbnQgPSAnb25yZWFkeXN0YXRlY2hhbmdlJztcbiAgICB2YXIgeERvbWFpbiA9IGZhbHNlO1xuXG4gICAgLy8gRm9yIElFIDgvOSBDT1JTIHN1cHBvcnRcbiAgICAvLyBPbmx5IHN1cHBvcnRzIFBPU1QgYW5kIEdFVCBjYWxscyBhbmQgZG9lc24ndCByZXR1cm5zIHRoZSByZXNwb25zZSBoZWFkZXJzLlxuICAgIC8vIERPTidUIGRvIHRoaXMgZm9yIHRlc3RpbmcgYi9jIFhNTEh0dHBSZXF1ZXN0IGlzIG1vY2tlZCwgbm90IFhEb21haW5SZXF1ZXN0LlxuICAgIGlmIChwcm9jZXNzLmVudi5OT0RFX0VOViAhPT0gJ3Rlc3QnICYmXG4gICAgICAgIHR5cGVvZiB3aW5kb3cgIT09ICd1bmRlZmluZWQnICYmXG4gICAgICAgIHdpbmRvdy5YRG9tYWluUmVxdWVzdCAmJiAhKCd3aXRoQ3JlZGVudGlhbHMnIGluIHJlcXVlc3QpICYmXG4gICAgICAgICFpc1VSTFNhbWVPcmlnaW4oY29uZmlnLnVybCkpIHtcbiAgICAgIHJlcXVlc3QgPSBuZXcgd2luZG93LlhEb21haW5SZXF1ZXN0KCk7XG4gICAgICBsb2FkRXZlbnQgPSAnb25sb2FkJztcbiAgICAgIHhEb21haW4gPSB0cnVlO1xuICAgICAgcmVxdWVzdC5vbnByb2dyZXNzID0gZnVuY3Rpb24gaGFuZGxlUHJvZ3Jlc3MoKSB7fTtcbiAgICAgIHJlcXVlc3Qub250aW1lb3V0ID0gZnVuY3Rpb24gaGFuZGxlVGltZW91dCgpIHt9O1xuICAgIH1cblxuICAgIC8vIEhUVFAgYmFzaWMgYXV0aGVudGljYXRpb25cbiAgICBpZiAoY29uZmlnLmF1dGgpIHtcbiAgICAgIHZhciB1c2VybmFtZSA9IGNvbmZpZy5hdXRoLnVzZXJuYW1lIHx8ICcnO1xuICAgICAgdmFyIHBhc3N3b3JkID0gY29uZmlnLmF1dGgucGFzc3dvcmQgfHwgJyc7XG4gICAgICByZXF1ZXN0SGVhZGVycy5BdXRob3JpemF0aW9uID0gJ0Jhc2ljICcgKyBidG9hKHVzZXJuYW1lICsgJzonICsgcGFzc3dvcmQpO1xuICAgIH1cblxuICAgIHJlcXVlc3Qub3Blbihjb25maWcubWV0aG9kLnRvVXBwZXJDYXNlKCksIGJ1aWxkVVJMKGNvbmZpZy51cmwsIGNvbmZpZy5wYXJhbXMsIGNvbmZpZy5wYXJhbXNTZXJpYWxpemVyKSwgdHJ1ZSk7XG5cbiAgICAvLyBTZXQgdGhlIHJlcXVlc3QgdGltZW91dCBpbiBNU1xuICAgIHJlcXVlc3QudGltZW91dCA9IGNvbmZpZy50aW1lb3V0O1xuXG4gICAgLy8gTGlzdGVuIGZvciByZWFkeSBzdGF0ZVxuICAgIHJlcXVlc3RbbG9hZEV2ZW50XSA9IGZ1bmN0aW9uIGhhbmRsZUxvYWQoKSB7XG4gICAgICBpZiAoIXJlcXVlc3QgfHwgKHJlcXVlc3QucmVhZHlTdGF0ZSAhPT0gNCAmJiAheERvbWFpbikpIHtcbiAgICAgICAgcmV0dXJuO1xuICAgICAgfVxuXG4gICAgICAvLyBUaGUgcmVxdWVzdCBlcnJvcmVkIG91dCBhbmQgd2UgZGlkbid0IGdldCBhIHJlc3BvbnNlLCB0aGlzIHdpbGwgYmVcbiAgICAgIC8vIGhhbmRsZWQgYnkgb25lcnJvciBpbnN0ZWFkXG4gICAgICAvLyBXaXRoIG9uZSBleGNlcHRpb246IHJlcXVlc3QgdGhhdCB1c2luZyBmaWxlOiBwcm90b2NvbCwgbW9zdCBicm93c2Vyc1xuICAgICAgLy8gd2lsbCByZXR1cm4gc3RhdHVzIGFzIDAgZXZlbiB0aG91Z2ggaXQncyBhIHN1Y2Nlc3NmdWwgcmVxdWVzdFxuICAgICAgaWYgKHJlcXVlc3Quc3RhdHVzID09PSAwICYmICEocmVxdWVzdC5yZXNwb25zZVVSTCAmJiByZXF1ZXN0LnJlc3BvbnNlVVJMLmluZGV4T2YoJ2ZpbGU6JykgPT09IDApKSB7XG4gICAgICAgIHJldHVybjtcbiAgICAgIH1cblxuICAgICAgLy8gUHJlcGFyZSB0aGUgcmVzcG9uc2VcbiAgICAgIHZhciByZXNwb25zZUhlYWRlcnMgPSAnZ2V0QWxsUmVzcG9uc2VIZWFkZXJzJyBpbiByZXF1ZXN0ID8gcGFyc2VIZWFkZXJzKHJlcXVlc3QuZ2V0QWxsUmVzcG9uc2VIZWFkZXJzKCkpIDogbnVsbDtcbiAgICAgIHZhciByZXNwb25zZURhdGEgPSAhY29uZmlnLnJlc3BvbnNlVHlwZSB8fCBjb25maWcucmVzcG9uc2VUeXBlID09PSAndGV4dCcgPyByZXF1ZXN0LnJlc3BvbnNlVGV4dCA6IHJlcXVlc3QucmVzcG9uc2U7XG4gICAgICB2YXIgcmVzcG9uc2UgPSB7XG4gICAgICAgIGRhdGE6IHJlc3BvbnNlRGF0YSxcbiAgICAgICAgLy8gSUUgc2VuZHMgMTIyMyBpbnN0ZWFkIG9mIDIwNCAoaHR0cHM6Ly9naXRodWIuY29tL2F4aW9zL2F4aW9zL2lzc3Vlcy8yMDEpXG4gICAgICAgIHN0YXR1czogcmVxdWVzdC5zdGF0dXMgPT09IDEyMjMgPyAyMDQgOiByZXF1ZXN0LnN0YXR1cyxcbiAgICAgICAgc3RhdHVzVGV4dDogcmVxdWVzdC5zdGF0dXMgPT09IDEyMjMgPyAnTm8gQ29udGVudCcgOiByZXF1ZXN0LnN0YXR1c1RleHQsXG4gICAgICAgIGhlYWRlcnM6IHJlc3BvbnNlSGVhZGVycyxcbiAgICAgICAgY29uZmlnOiBjb25maWcsXG4gICAgICAgIHJlcXVlc3Q6IHJlcXVlc3RcbiAgICAgIH07XG5cbiAgICAgIHNldHRsZShyZXNvbHZlLCByZWplY3QsIHJlc3BvbnNlKTtcblxuICAgICAgLy8gQ2xlYW4gdXAgcmVxdWVzdFxuICAgICAgcmVxdWVzdCA9IG51bGw7XG4gICAgfTtcblxuICAgIC8vIEhhbmRsZSBsb3cgbGV2ZWwgbmV0d29yayBlcnJvcnNcbiAgICByZXF1ZXN0Lm9uZXJyb3IgPSBmdW5jdGlvbiBoYW5kbGVFcnJvcigpIHtcbiAgICAgIC8vIFJlYWwgZXJyb3JzIGFyZSBoaWRkZW4gZnJvbSB1cyBieSB0aGUgYnJvd3NlclxuICAgICAgLy8gb25lcnJvciBzaG91bGQgb25seSBmaXJlIGlmIGl0J3MgYSBuZXR3b3JrIGVycm9yXG4gICAgICByZWplY3QoY3JlYXRlRXJyb3IoJ05ldHdvcmsgRXJyb3InLCBjb25maWcsIG51bGwsIHJlcXVlc3QpKTtcblxuICAgICAgLy8gQ2xlYW4gdXAgcmVxdWVzdFxuICAgICAgcmVxdWVzdCA9IG51bGw7XG4gICAgfTtcblxuICAgIC8vIEhhbmRsZSB0aW1lb3V0XG4gICAgcmVxdWVzdC5vbnRpbWVvdXQgPSBmdW5jdGlvbiBoYW5kbGVUaW1lb3V0KCkge1xuICAgICAgcmVqZWN0KGNyZWF0ZUVycm9yKCd0aW1lb3V0IG9mICcgKyBjb25maWcudGltZW91dCArICdtcyBleGNlZWRlZCcsIGNvbmZpZywgJ0VDT05OQUJPUlRFRCcsXG4gICAgICAgIHJlcXVlc3QpKTtcblxuICAgICAgLy8gQ2xlYW4gdXAgcmVxdWVzdFxuICAgICAgcmVxdWVzdCA9IG51bGw7XG4gICAgfTtcblxuICAgIC8vIEFkZCB4c3JmIGhlYWRlclxuICAgIC8vIFRoaXMgaXMgb25seSBkb25lIGlmIHJ1bm5pbmcgaW4gYSBzdGFuZGFyZCBicm93c2VyIGVudmlyb25tZW50LlxuICAgIC8vIFNwZWNpZmljYWxseSBub3QgaWYgd2UncmUgaW4gYSB3ZWIgd29ya2VyLCBvciByZWFjdC1uYXRpdmUuXG4gICAgaWYgKHV0aWxzLmlzU3RhbmRhcmRCcm93c2VyRW52KCkpIHtcbiAgICAgIHZhciBjb29raWVzID0gcmVxdWlyZSgnLi8uLi9oZWxwZXJzL2Nvb2tpZXMnKTtcblxuICAgICAgLy8gQWRkIHhzcmYgaGVhZGVyXG4gICAgICB2YXIgeHNyZlZhbHVlID0gKGNvbmZpZy53aXRoQ3JlZGVudGlhbHMgfHwgaXNVUkxTYW1lT3JpZ2luKGNvbmZpZy51cmwpKSAmJiBjb25maWcueHNyZkNvb2tpZU5hbWUgP1xuICAgICAgICAgIGNvb2tpZXMucmVhZChjb25maWcueHNyZkNvb2tpZU5hbWUpIDpcbiAgICAgICAgICB1bmRlZmluZWQ7XG5cbiAgICAgIGlmICh4c3JmVmFsdWUpIHtcbiAgICAgICAgcmVxdWVzdEhlYWRlcnNbY29uZmlnLnhzcmZIZWFkZXJOYW1lXSA9IHhzcmZWYWx1ZTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICAvLyBBZGQgaGVhZGVycyB0byB0aGUgcmVxdWVzdFxuICAgIGlmICgnc2V0UmVxdWVzdEhlYWRlcicgaW4gcmVxdWVzdCkge1xuICAgICAgdXRpbHMuZm9yRWFjaChyZXF1ZXN0SGVhZGVycywgZnVuY3Rpb24gc2V0UmVxdWVzdEhlYWRlcih2YWwsIGtleSkge1xuICAgICAgICBpZiAodHlwZW9mIHJlcXVlc3REYXRhID09PSAndW5kZWZpbmVkJyAmJiBrZXkudG9Mb3dlckNhc2UoKSA9PT0gJ2NvbnRlbnQtdHlwZScpIHtcbiAgICAgICAgICAvLyBSZW1vdmUgQ29udGVudC1UeXBlIGlmIGRhdGEgaXMgdW5kZWZpbmVkXG4gICAgICAgICAgZGVsZXRlIHJlcXVlc3RIZWFkZXJzW2tleV07XG4gICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgLy8gT3RoZXJ3aXNlIGFkZCBoZWFkZXIgdG8gdGhlIHJlcXVlc3RcbiAgICAgICAgICByZXF1ZXN0LnNldFJlcXVlc3RIZWFkZXIoa2V5LCB2YWwpO1xuICAgICAgICB9XG4gICAgICB9KTtcbiAgICB9XG5cbiAgICAvLyBBZGQgd2l0aENyZWRlbnRpYWxzIHRvIHJlcXVlc3QgaWYgbmVlZGVkXG4gICAgaWYgKGNvbmZpZy53aXRoQ3JlZGVudGlhbHMpIHtcbiAgICAgIHJlcXVlc3Qud2l0aENyZWRlbnRpYWxzID0gdHJ1ZTtcbiAgICB9XG5cbiAgICAvLyBBZGQgcmVzcG9uc2VUeXBlIHRvIHJlcXVlc3QgaWYgbmVlZGVkXG4gICAgaWYgKGNvbmZpZy5yZXNwb25zZVR5cGUpIHtcbiAgICAgIHRyeSB7XG4gICAgICAgIHJlcXVlc3QucmVzcG9uc2VUeXBlID0gY29uZmlnLnJlc3BvbnNlVHlwZTtcbiAgICAgIH0gY2F0Y2ggKGUpIHtcbiAgICAgICAgLy8gRXhwZWN0ZWQgRE9NRXhjZXB0aW9uIHRocm93biBieSBicm93c2VycyBub3QgY29tcGF0aWJsZSBYTUxIdHRwUmVxdWVzdCBMZXZlbCAyLlxuICAgICAgICAvLyBCdXQsIHRoaXMgY2FuIGJlIHN1cHByZXNzZWQgZm9yICdqc29uJyB0eXBlIGFzIGl0IGNhbiBiZSBwYXJzZWQgYnkgZGVmYXVsdCAndHJhbnNmb3JtUmVzcG9uc2UnIGZ1bmN0aW9uLlxuICAgICAgICBpZiAoY29uZmlnLnJlc3BvbnNlVHlwZSAhPT0gJ2pzb24nKSB7XG4gICAgICAgICAgdGhyb3cgZTtcbiAgICAgICAgfVxuICAgICAgfVxuICAgIH1cblxuICAgIC8vIEhhbmRsZSBwcm9ncmVzcyBpZiBuZWVkZWRcbiAgICBpZiAodHlwZW9mIGNvbmZpZy5vbkRvd25sb2FkUHJvZ3Jlc3MgPT09ICdmdW5jdGlvbicpIHtcbiAgICAgIHJlcXVlc3QuYWRkRXZlbnRMaXN0ZW5lcigncHJvZ3Jlc3MnLCBjb25maWcub25Eb3dubG9hZFByb2dyZXNzKTtcbiAgICB9XG5cbiAgICAvLyBOb3QgYWxsIGJyb3dzZXJzIHN1cHBvcnQgdXBsb2FkIGV2ZW50c1xuICAgIGlmICh0eXBlb2YgY29uZmlnLm9uVXBsb2FkUHJvZ3Jlc3MgPT09ICdmdW5jdGlvbicgJiYgcmVxdWVzdC51cGxvYWQpIHtcbiAgICAgIHJlcXVlc3QudXBsb2FkLmFkZEV2ZW50TGlzdGVuZXIoJ3Byb2dyZXNzJywgY29uZmlnLm9uVXBsb2FkUHJvZ3Jlc3MpO1xuICAgIH1cblxuICAgIGlmIChjb25maWcuY2FuY2VsVG9rZW4pIHtcbiAgICAgIC8vIEhhbmRsZSBjYW5jZWxsYXRpb25cbiAgICAgIGNvbmZpZy5jYW5jZWxUb2tlbi5wcm9taXNlLnRoZW4oZnVuY3Rpb24gb25DYW5jZWxlZChjYW5jZWwpIHtcbiAgICAgICAgaWYgKCFyZXF1ZXN0KSB7XG4gICAgICAgICAgcmV0dXJuO1xuICAgICAgICB9XG5cbiAgICAgICAgcmVxdWVzdC5hYm9ydCgpO1xuICAgICAgICByZWplY3QoY2FuY2VsKTtcbiAgICAgICAgLy8gQ2xlYW4gdXAgcmVxdWVzdFxuICAgICAgICByZXF1ZXN0ID0gbnVsbDtcbiAgICAgIH0pO1xuICAgIH1cblxuICAgIGlmIChyZXF1ZXN0RGF0YSA9PT0gdW5kZWZpbmVkKSB7XG4gICAgICByZXF1ZXN0RGF0YSA9IG51bGw7XG4gICAgfVxuXG4gICAgLy8gU2VuZCB0aGUgcmVxdWVzdFxuICAgIHJlcXVlc3Quc2VuZChyZXF1ZXN0RGF0YSk7XG4gIH0pO1xufTtcbiIsIid1c2Ugc3RyaWN0JztcblxudmFyIHV0aWxzID0gcmVxdWlyZSgnLi91dGlscycpO1xudmFyIG5vcm1hbGl6ZUhlYWRlck5hbWUgPSByZXF1aXJlKCcuL2hlbHBlcnMvbm9ybWFsaXplSGVhZGVyTmFtZScpO1xuXG52YXIgREVGQVVMVF9DT05URU5UX1RZUEUgPSB7XG4gICdDb250ZW50LVR5cGUnOiAnYXBwbGljYXRpb24veC13d3ctZm9ybS11cmxlbmNvZGVkJ1xufTtcblxuZnVuY3Rpb24gc2V0Q29udGVudFR5cGVJZlVuc2V0KGhlYWRlcnMsIHZhbHVlKSB7XG4gIGlmICghdXRpbHMuaXNVbmRlZmluZWQoaGVhZGVycykgJiYgdXRpbHMuaXNVbmRlZmluZWQoaGVhZGVyc1snQ29udGVudC1UeXBlJ10pKSB7XG4gICAgaGVhZGVyc1snQ29udGVudC1UeXBlJ10gPSB2YWx1ZTtcbiAgfVxufVxuXG5mdW5jdGlvbiBnZXREZWZhdWx0QWRhcHRlcigpIHtcbiAgdmFyIGFkYXB0ZXI7XG4gIGlmICh0eXBlb2YgWE1MSHR0cFJlcXVlc3QgIT09ICd1bmRlZmluZWQnKSB7XG4gICAgLy8gRm9yIGJyb3dzZXJzIHVzZSBYSFIgYWRhcHRlclxuICAgIGFkYXB0ZXIgPSByZXF1aXJlKCcuL2FkYXB0ZXJzL3hocicpO1xuICB9IGVsc2UgaWYgKHR5cGVvZiBwcm9jZXNzICE9PSAndW5kZWZpbmVkJykge1xuICAgIC8vIEZvciBub2RlIHVzZSBIVFRQIGFkYXB0ZXJcbiAgICBhZGFwdGVyID0gcmVxdWlyZSgnLi9hZGFwdGVycy9odHRwJyk7XG4gIH1cbiAgcmV0dXJuIGFkYXB0ZXI7XG59XG5cbnZhciBkZWZhdWx0cyA9IHtcbiAgYWRhcHRlcjogZ2V0RGVmYXVsdEFkYXB0ZXIoKSxcblxuICB0cmFuc2Zvcm1SZXF1ZXN0OiBbZnVuY3Rpb24gdHJhbnNmb3JtUmVxdWVzdChkYXRhLCBoZWFkZXJzKSB7XG4gICAgbm9ybWFsaXplSGVhZGVyTmFtZShoZWFkZXJzLCAnQ29udGVudC1UeXBlJyk7XG4gICAgaWYgKHV0aWxzLmlzRm9ybURhdGEoZGF0YSkgfHxcbiAgICAgIHV0aWxzLmlzQXJyYXlCdWZmZXIoZGF0YSkgfHxcbiAgICAgIHV0aWxzLmlzQnVmZmVyKGRhdGEpIHx8XG4gICAgICB1dGlscy5pc1N0cmVhbShkYXRhKSB8fFxuICAgICAgdXRpbHMuaXNGaWxlKGRhdGEpIHx8XG4gICAgICB1dGlscy5pc0Jsb2IoZGF0YSlcbiAgICApIHtcbiAgICAgIHJldHVybiBkYXRhO1xuICAgIH1cbiAgICBpZiAodXRpbHMuaXNBcnJheUJ1ZmZlclZpZXcoZGF0YSkpIHtcbiAgICAgIHJldHVybiBkYXRhLmJ1ZmZlcjtcbiAgICB9XG4gICAgaWYgKHV0aWxzLmlzVVJMU2VhcmNoUGFyYW1zKGRhdGEpKSB7XG4gICAgICBzZXRDb250ZW50VHlwZUlmVW5zZXQoaGVhZGVycywgJ2FwcGxpY2F0aW9uL3gtd3d3LWZvcm0tdXJsZW5jb2RlZDtjaGFyc2V0PXV0Zi04Jyk7XG4gICAgICByZXR1cm4gZGF0YS50b1N0cmluZygpO1xuICAgIH1cbiAgICBpZiAodXRpbHMuaXNPYmplY3QoZGF0YSkpIHtcbiAgICAgIHNldENvbnRlbnRUeXBlSWZVbnNldChoZWFkZXJzLCAnYXBwbGljYXRpb24vanNvbjtjaGFyc2V0PXV0Zi04Jyk7XG4gICAgICByZXR1cm4gSlNPTi5zdHJpbmdpZnkoZGF0YSk7XG4gICAgfVxuICAgIHJldHVybiBkYXRhO1xuICB9XSxcblxuICB0cmFuc2Zvcm1SZXNwb25zZTogW2Z1bmN0aW9uIHRyYW5zZm9ybVJlc3BvbnNlKGRhdGEpIHtcbiAgICAvKmVzbGludCBuby1wYXJhbS1yZWFzc2lnbjowKi9cbiAgICBpZiAodHlwZW9mIGRhdGEgPT09ICdzdHJpbmcnKSB7XG4gICAgICB0cnkge1xuICAgICAgICBkYXRhID0gSlNPTi5wYXJzZShkYXRhKTtcbiAgICAgIH0gY2F0Y2ggKGUpIHsgLyogSWdub3JlICovIH1cbiAgICB9XG4gICAgcmV0dXJuIGRhdGE7XG4gIH1dLFxuXG4gIC8qKlxuICAgKiBBIHRpbWVvdXQgaW4gbWlsbGlzZWNvbmRzIHRvIGFib3J0IGEgcmVxdWVzdC4gSWYgc2V0IHRvIDAgKGRlZmF1bHQpIGFcbiAgICogdGltZW91dCBpcyBub3QgY3JlYXRlZC5cbiAgICovXG4gIHRpbWVvdXQ6IDAsXG5cbiAgeHNyZkNvb2tpZU5hbWU6ICdYU1JGLVRPS0VOJyxcbiAgeHNyZkhlYWRlck5hbWU6ICdYLVhTUkYtVE9LRU4nLFxuXG4gIG1heENvbnRlbnRMZW5ndGg6IC0xLFxuXG4gIHZhbGlkYXRlU3RhdHVzOiBmdW5jdGlvbiB2YWxpZGF0ZVN0YXR1cyhzdGF0dXMpIHtcbiAgICByZXR1cm4gc3RhdHVzID49IDIwMCAmJiBzdGF0dXMgPCAzMDA7XG4gIH1cbn07XG5cbmRlZmF1bHRzLmhlYWRlcnMgPSB7XG4gIGNvbW1vbjoge1xuICAgICdBY2NlcHQnOiAnYXBwbGljYXRpb24vanNvbiwgdGV4dC9wbGFpbiwgKi8qJ1xuICB9XG59O1xuXG51dGlscy5mb3JFYWNoKFsnZGVsZXRlJywgJ2dldCcsICdoZWFkJ10sIGZ1bmN0aW9uIGZvckVhY2hNZXRob2ROb0RhdGEobWV0aG9kKSB7XG4gIGRlZmF1bHRzLmhlYWRlcnNbbWV0aG9kXSA9IHt9O1xufSk7XG5cbnV0aWxzLmZvckVhY2goWydwb3N0JywgJ3B1dCcsICdwYXRjaCddLCBmdW5jdGlvbiBmb3JFYWNoTWV0aG9kV2l0aERhdGEobWV0aG9kKSB7XG4gIGRlZmF1bHRzLmhlYWRlcnNbbWV0aG9kXSA9IHV0aWxzLm1lcmdlKERFRkFVTFRfQ09OVEVOVF9UWVBFKTtcbn0pO1xuXG5tb2R1bGUuZXhwb3J0cyA9IGRlZmF1bHRzO1xuIiwiJ3VzZSBzdHJpY3QnO1xuXG52YXIgdXRpbHMgPSByZXF1aXJlKCcuLy4uL3V0aWxzJyk7XG5cbmZ1bmN0aW9uIEludGVyY2VwdG9yTWFuYWdlcigpIHtcbiAgdGhpcy5oYW5kbGVycyA9IFtdO1xufVxuXG4vKipcbiAqIEFkZCBhIG5ldyBpbnRlcmNlcHRvciB0byB0aGUgc3RhY2tcbiAqXG4gKiBAcGFyYW0ge0Z1bmN0aW9ufSBmdWxmaWxsZWQgVGhlIGZ1bmN0aW9uIHRvIGhhbmRsZSBgdGhlbmAgZm9yIGEgYFByb21pc2VgXG4gKiBAcGFyYW0ge0Z1bmN0aW9ufSByZWplY3RlZCBUaGUgZnVuY3Rpb24gdG8gaGFuZGxlIGByZWplY3RgIGZvciBhIGBQcm9taXNlYFxuICpcbiAqIEByZXR1cm4ge051bWJlcn0gQW4gSUQgdXNlZCB0byByZW1vdmUgaW50ZXJjZXB0b3IgbGF0ZXJcbiAqL1xuSW50ZXJjZXB0b3JNYW5hZ2VyLnByb3RvdHlwZS51c2UgPSBmdW5jdGlvbiB1c2UoZnVsZmlsbGVkLCByZWplY3RlZCkge1xuICB0aGlzLmhhbmRsZXJzLnB1c2goe1xuICAgIGZ1bGZpbGxlZDogZnVsZmlsbGVkLFxuICAgIHJlamVjdGVkOiByZWplY3RlZFxuICB9KTtcbiAgcmV0dXJuIHRoaXMuaGFuZGxlcnMubGVuZ3RoIC0gMTtcbn07XG5cbi8qKlxuICogUmVtb3ZlIGFuIGludGVyY2VwdG9yIGZyb20gdGhlIHN0YWNrXG4gKlxuICogQHBhcmFtIHtOdW1iZXJ9IGlkIFRoZSBJRCB0aGF0IHdhcyByZXR1cm5lZCBieSBgdXNlYFxuICovXG5JbnRlcmNlcHRvck1hbmFnZXIucHJvdG90eXBlLmVqZWN0ID0gZnVuY3Rpb24gZWplY3QoaWQpIHtcbiAgaWYgKHRoaXMuaGFuZGxlcnNbaWRdKSB7XG4gICAgdGhpcy5oYW5kbGVyc1tpZF0gPSBudWxsO1xuICB9XG59O1xuXG4vKipcbiAqIEl0ZXJhdGUgb3ZlciBhbGwgdGhlIHJlZ2lzdGVyZWQgaW50ZXJjZXB0b3JzXG4gKlxuICogVGhpcyBtZXRob2QgaXMgcGFydGljdWxhcmx5IHVzZWZ1bCBmb3Igc2tpcHBpbmcgb3ZlciBhbnlcbiAqIGludGVyY2VwdG9ycyB0aGF0IG1heSBoYXZlIGJlY29tZSBgbnVsbGAgY2FsbGluZyBgZWplY3RgLlxuICpcbiAqIEBwYXJhbSB7RnVuY3Rpb259IGZuIFRoZSBmdW5jdGlvbiB0byBjYWxsIGZvciBlYWNoIGludGVyY2VwdG9yXG4gKi9cbkludGVyY2VwdG9yTWFuYWdlci5wcm90b3R5cGUuZm9yRWFjaCA9IGZ1bmN0aW9uIGZvckVhY2goZm4pIHtcbiAgdXRpbHMuZm9yRWFjaCh0aGlzLmhhbmRsZXJzLCBmdW5jdGlvbiBmb3JFYWNoSGFuZGxlcihoKSB7XG4gICAgaWYgKGggIT09IG51bGwpIHtcbiAgICAgIGZuKGgpO1xuICAgIH1cbiAgfSk7XG59O1xuXG5tb2R1bGUuZXhwb3J0cyA9IEludGVyY2VwdG9yTWFuYWdlcjtcbiIsIid1c2Ugc3RyaWN0JztcblxudmFyIHV0aWxzID0gcmVxdWlyZSgnLi8uLi91dGlscycpO1xuXG4vKipcbiAqIFRyYW5zZm9ybSB0aGUgZGF0YSBmb3IgYSByZXF1ZXN0IG9yIGEgcmVzcG9uc2VcbiAqXG4gKiBAcGFyYW0ge09iamVjdHxTdHJpbmd9IGRhdGEgVGhlIGRhdGEgdG8gYmUgdHJhbnNmb3JtZWRcbiAqIEBwYXJhbSB7QXJyYXl9IGhlYWRlcnMgVGhlIGhlYWRlcnMgZm9yIHRoZSByZXF1ZXN0IG9yIHJlc3BvbnNlXG4gKiBAcGFyYW0ge0FycmF5fEZ1bmN0aW9ufSBmbnMgQSBzaW5nbGUgZnVuY3Rpb24gb3IgQXJyYXkgb2YgZnVuY3Rpb25zXG4gKiBAcmV0dXJucyB7Kn0gVGhlIHJlc3VsdGluZyB0cmFuc2Zvcm1lZCBkYXRhXG4gKi9cbm1vZHVsZS5leHBvcnRzID0gZnVuY3Rpb24gdHJhbnNmb3JtRGF0YShkYXRhLCBoZWFkZXJzLCBmbnMpIHtcbiAgLyplc2xpbnQgbm8tcGFyYW0tcmVhc3NpZ246MCovXG4gIHV0aWxzLmZvckVhY2goZm5zLCBmdW5jdGlvbiB0cmFuc2Zvcm0oZm4pIHtcbiAgICBkYXRhID0gZm4oZGF0YSwgaGVhZGVycyk7XG4gIH0pO1xuXG4gIHJldHVybiBkYXRhO1xufTtcbiIsIid1c2Ugc3RyaWN0JztcblxubW9kdWxlLmV4cG9ydHMgPSBmdW5jdGlvbiBpc0NhbmNlbCh2YWx1ZSkge1xuICByZXR1cm4gISEodmFsdWUgJiYgdmFsdWUuX19DQU5DRUxfXyk7XG59O1xuIiwiJ3VzZSBzdHJpY3QnO1xuXG4vKipcbiAqIERldGVybWluZXMgd2hldGhlciB0aGUgc3BlY2lmaWVkIFVSTCBpcyBhYnNvbHV0ZVxuICpcbiAqIEBwYXJhbSB7c3RyaW5nfSB1cmwgVGhlIFVSTCB0byB0ZXN0XG4gKiBAcmV0dXJucyB7Ym9vbGVhbn0gVHJ1ZSBpZiB0aGUgc3BlY2lmaWVkIFVSTCBpcyBhYnNvbHV0ZSwgb3RoZXJ3aXNlIGZhbHNlXG4gKi9cbm1vZHVsZS5leHBvcnRzID0gZnVuY3Rpb24gaXNBYnNvbHV0ZVVSTCh1cmwpIHtcbiAgLy8gQSBVUkwgaXMgY29uc2lkZXJlZCBhYnNvbHV0ZSBpZiBpdCBiZWdpbnMgd2l0aCBcIjxzY2hlbWU+Oi8vXCIgb3IgXCIvL1wiIChwcm90b2NvbC1yZWxhdGl2ZSBVUkwpLlxuICAvLyBSRkMgMzk4NiBkZWZpbmVzIHNjaGVtZSBuYW1lIGFzIGEgc2VxdWVuY2Ugb2YgY2hhcmFjdGVycyBiZWdpbm5pbmcgd2l0aCBhIGxldHRlciBhbmQgZm9sbG93ZWRcbiAgLy8gYnkgYW55IGNvbWJpbmF0aW9uIG9mIGxldHRlcnMsIGRpZ2l0cywgcGx1cywgcGVyaW9kLCBvciBoeXBoZW4uXG4gIHJldHVybiAvXihbYS16XVthLXpcXGRcXCtcXC1cXC5dKjopP1xcL1xcLy9pLnRlc3QodXJsKTtcbn07XG4iLCIndXNlIHN0cmljdCc7XG5cbi8qKlxuICogQ3JlYXRlcyBhIG5ldyBVUkwgYnkgY29tYmluaW5nIHRoZSBzcGVjaWZpZWQgVVJMc1xuICpcbiAqIEBwYXJhbSB7c3RyaW5nfSBiYXNlVVJMIFRoZSBiYXNlIFVSTFxuICogQHBhcmFtIHtzdHJpbmd9IHJlbGF0aXZlVVJMIFRoZSByZWxhdGl2ZSBVUkxcbiAqIEByZXR1cm5zIHtzdHJpbmd9IFRoZSBjb21iaW5lZCBVUkxcbiAqL1xubW9kdWxlLmV4cG9ydHMgPSBmdW5jdGlvbiBjb21iaW5lVVJMcyhiYXNlVVJMLCByZWxhdGl2ZVVSTCkge1xuICByZXR1cm4gcmVsYXRpdmVVUkxcbiAgICA/IGJhc2VVUkwucmVwbGFjZSgvXFwvKyQvLCAnJykgKyAnLycgKyByZWxhdGl2ZVVSTC5yZXBsYWNlKC9eXFwvKy8sICcnKVxuICAgIDogYmFzZVVSTDtcbn07XG4iLCIndXNlIHN0cmljdCc7XG5cbnZhciB1dGlscyA9IHJlcXVpcmUoJy4vLi4vdXRpbHMnKTtcbnZhciB0cmFuc2Zvcm1EYXRhID0gcmVxdWlyZSgnLi90cmFuc2Zvcm1EYXRhJyk7XG52YXIgaXNDYW5jZWwgPSByZXF1aXJlKCcuLi9jYW5jZWwvaXNDYW5jZWwnKTtcbnZhciBkZWZhdWx0cyA9IHJlcXVpcmUoJy4uL2RlZmF1bHRzJyk7XG52YXIgaXNBYnNvbHV0ZVVSTCA9IHJlcXVpcmUoJy4vLi4vaGVscGVycy9pc0Fic29sdXRlVVJMJyk7XG52YXIgY29tYmluZVVSTHMgPSByZXF1aXJlKCcuLy4uL2hlbHBlcnMvY29tYmluZVVSTHMnKTtcblxuLyoqXG4gKiBUaHJvd3MgYSBgQ2FuY2VsYCBpZiBjYW5jZWxsYXRpb24gaGFzIGJlZW4gcmVxdWVzdGVkLlxuICovXG5mdW5jdGlvbiB0aHJvd0lmQ2FuY2VsbGF0aW9uUmVxdWVzdGVkKGNvbmZpZykge1xuICBpZiAoY29uZmlnLmNhbmNlbFRva2VuKSB7XG4gICAgY29uZmlnLmNhbmNlbFRva2VuLnRocm93SWZSZXF1ZXN0ZWQoKTtcbiAgfVxufVxuXG4vKipcbiAqIERpc3BhdGNoIGEgcmVxdWVzdCB0byB0aGUgc2VydmVyIHVzaW5nIHRoZSBjb25maWd1cmVkIGFkYXB0ZXIuXG4gKlxuICogQHBhcmFtIHtvYmplY3R9IGNvbmZpZyBUaGUgY29uZmlnIHRoYXQgaXMgdG8gYmUgdXNlZCBmb3IgdGhlIHJlcXVlc3RcbiAqIEByZXR1cm5zIHtQcm9taXNlfSBUaGUgUHJvbWlzZSB0byBiZSBmdWxmaWxsZWRcbiAqL1xubW9kdWxlLmV4cG9ydHMgPSBmdW5jdGlvbiBkaXNwYXRjaFJlcXVlc3QoY29uZmlnKSB7XG4gIHRocm93SWZDYW5jZWxsYXRpb25SZXF1ZXN0ZWQoY29uZmlnKTtcblxuICAvLyBTdXBwb3J0IGJhc2VVUkwgY29uZmlnXG4gIGlmIChjb25maWcuYmFzZVVSTCAmJiAhaXNBYnNvbHV0ZVVSTChjb25maWcudXJsKSkge1xuICAgIGNvbmZpZy51cmwgPSBjb21iaW5lVVJMcyhjb25maWcuYmFzZVVSTCwgY29uZmlnLnVybCk7XG4gIH1cblxuICAvLyBFbnN1cmUgaGVhZGVycyBleGlzdFxuICBjb25maWcuaGVhZGVycyA9IGNvbmZpZy5oZWFkZXJzIHx8IHt9O1xuXG4gIC8vIFRyYW5zZm9ybSByZXF1ZXN0IGRhdGFcbiAgY29uZmlnLmRhdGEgPSB0cmFuc2Zvcm1EYXRhKFxuICAgIGNvbmZpZy5kYXRhLFxuICAgIGNvbmZpZy5oZWFkZXJzLFxuICAgIGNvbmZpZy50cmFuc2Zvcm1SZXF1ZXN0XG4gICk7XG5cbiAgLy8gRmxhdHRlbiBoZWFkZXJzXG4gIGNvbmZpZy5oZWFkZXJzID0gdXRpbHMubWVyZ2UoXG4gICAgY29uZmlnLmhlYWRlcnMuY29tbW9uIHx8IHt9LFxuICAgIGNvbmZpZy5oZWFkZXJzW2NvbmZpZy5tZXRob2RdIHx8IHt9LFxuICAgIGNvbmZpZy5oZWFkZXJzIHx8IHt9XG4gICk7XG5cbiAgdXRpbHMuZm9yRWFjaChcbiAgICBbJ2RlbGV0ZScsICdnZXQnLCAnaGVhZCcsICdwb3N0JywgJ3B1dCcsICdwYXRjaCcsICdjb21tb24nXSxcbiAgICBmdW5jdGlvbiBjbGVhbkhlYWRlckNvbmZpZyhtZXRob2QpIHtcbiAgICAgIGRlbGV0ZSBjb25maWcuaGVhZGVyc1ttZXRob2RdO1xuICAgIH1cbiAgKTtcblxuICB2YXIgYWRhcHRlciA9IGNvbmZpZy5hZGFwdGVyIHx8IGRlZmF1bHRzLmFkYXB0ZXI7XG5cbiAgcmV0dXJuIGFkYXB0ZXIoY29uZmlnKS50aGVuKGZ1bmN0aW9uIG9uQWRhcHRlclJlc29sdXRpb24ocmVzcG9uc2UpIHtcbiAgICB0aHJvd0lmQ2FuY2VsbGF0aW9uUmVxdWVzdGVkKGNvbmZpZyk7XG5cbiAgICAvLyBUcmFuc2Zvcm0gcmVzcG9uc2UgZGF0YVxuICAgIHJlc3BvbnNlLmRhdGEgPSB0cmFuc2Zvcm1EYXRhKFxuICAgICAgcmVzcG9uc2UuZGF0YSxcbiAgICAgIHJlc3BvbnNlLmhlYWRlcnMsXG4gICAgICBjb25maWcudHJhbnNmb3JtUmVzcG9uc2VcbiAgICApO1xuXG4gICAgcmV0dXJuIHJlc3BvbnNlO1xuICB9LCBmdW5jdGlvbiBvbkFkYXB0ZXJSZWplY3Rpb24ocmVhc29uKSB7XG4gICAgaWYgKCFpc0NhbmNlbChyZWFzb24pKSB7XG4gICAgICB0aHJvd0lmQ2FuY2VsbGF0aW9uUmVxdWVzdGVkKGNvbmZpZyk7XG5cbiAgICAgIC8vIFRyYW5zZm9ybSByZXNwb25zZSBkYXRhXG4gICAgICBpZiAocmVhc29uICYmIHJlYXNvbi5yZXNwb25zZSkge1xuICAgICAgICByZWFzb24ucmVzcG9uc2UuZGF0YSA9IHRyYW5zZm9ybURhdGEoXG4gICAgICAgICAgcmVhc29uLnJlc3BvbnNlLmRhdGEsXG4gICAgICAgICAgcmVhc29uLnJlc3BvbnNlLmhlYWRlcnMsXG4gICAgICAgICAgY29uZmlnLnRyYW5zZm9ybVJlc3BvbnNlXG4gICAgICAgICk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgcmV0dXJuIFByb21pc2UucmVqZWN0KHJlYXNvbik7XG4gIH0pO1xufTtcbiIsIid1c2Ugc3RyaWN0JztcblxudmFyIGRlZmF1bHRzID0gcmVxdWlyZSgnLi8uLi9kZWZhdWx0cycpO1xudmFyIHV0aWxzID0gcmVxdWlyZSgnLi8uLi91dGlscycpO1xudmFyIEludGVyY2VwdG9yTWFuYWdlciA9IHJlcXVpcmUoJy4vSW50ZXJjZXB0b3JNYW5hZ2VyJyk7XG52YXIgZGlzcGF0Y2hSZXF1ZXN0ID0gcmVxdWlyZSgnLi9kaXNwYXRjaFJlcXVlc3QnKTtcblxuLyoqXG4gKiBDcmVhdGUgYSBuZXcgaW5zdGFuY2Ugb2YgQXhpb3NcbiAqXG4gKiBAcGFyYW0ge09iamVjdH0gaW5zdGFuY2VDb25maWcgVGhlIGRlZmF1bHQgY29uZmlnIGZvciB0aGUgaW5zdGFuY2VcbiAqL1xuZnVuY3Rpb24gQXhpb3MoaW5zdGFuY2VDb25maWcpIHtcbiAgdGhpcy5kZWZhdWx0cyA9IGluc3RhbmNlQ29uZmlnO1xuICB0aGlzLmludGVyY2VwdG9ycyA9IHtcbiAgICByZXF1ZXN0OiBuZXcgSW50ZXJjZXB0b3JNYW5hZ2VyKCksXG4gICAgcmVzcG9uc2U6IG5ldyBJbnRlcmNlcHRvck1hbmFnZXIoKVxuICB9O1xufVxuXG4vKipcbiAqIERpc3BhdGNoIGEgcmVxdWVzdFxuICpcbiAqIEBwYXJhbSB7T2JqZWN0fSBjb25maWcgVGhlIGNvbmZpZyBzcGVjaWZpYyBmb3IgdGhpcyByZXF1ZXN0IChtZXJnZWQgd2l0aCB0aGlzLmRlZmF1bHRzKVxuICovXG5BeGlvcy5wcm90b3R5cGUucmVxdWVzdCA9IGZ1bmN0aW9uIHJlcXVlc3QoY29uZmlnKSB7XG4gIC8qZXNsaW50IG5vLXBhcmFtLXJlYXNzaWduOjAqL1xuICAvLyBBbGxvdyBmb3IgYXhpb3MoJ2V4YW1wbGUvdXJsJ1ssIGNvbmZpZ10pIGEgbGEgZmV0Y2ggQVBJXG4gIGlmICh0eXBlb2YgY29uZmlnID09PSAnc3RyaW5nJykge1xuICAgIGNvbmZpZyA9IHV0aWxzLm1lcmdlKHtcbiAgICAgIHVybDogYXJndW1lbnRzWzBdXG4gICAgfSwgYXJndW1lbnRzWzFdKTtcbiAgfVxuXG4gIGNvbmZpZyA9IHV0aWxzLm1lcmdlKGRlZmF1bHRzLCB7bWV0aG9kOiAnZ2V0J30sIHRoaXMuZGVmYXVsdHMsIGNvbmZpZyk7XG4gIGNvbmZpZy5tZXRob2QgPSBjb25maWcubWV0aG9kLnRvTG93ZXJDYXNlKCk7XG5cbiAgLy8gSG9vayB1cCBpbnRlcmNlcHRvcnMgbWlkZGxld2FyZVxuICB2YXIgY2hhaW4gPSBbZGlzcGF0Y2hSZXF1ZXN0LCB1bmRlZmluZWRdO1xuICB2YXIgcHJvbWlzZSA9IFByb21pc2UucmVzb2x2ZShjb25maWcpO1xuXG4gIHRoaXMuaW50ZXJjZXB0b3JzLnJlcXVlc3QuZm9yRWFjaChmdW5jdGlvbiB1bnNoaWZ0UmVxdWVzdEludGVyY2VwdG9ycyhpbnRlcmNlcHRvcikge1xuICAgIGNoYWluLnVuc2hpZnQoaW50ZXJjZXB0b3IuZnVsZmlsbGVkLCBpbnRlcmNlcHRvci5yZWplY3RlZCk7XG4gIH0pO1xuXG4gIHRoaXMuaW50ZXJjZXB0b3JzLnJlc3BvbnNlLmZvckVhY2goZnVuY3Rpb24gcHVzaFJlc3BvbnNlSW50ZXJjZXB0b3JzKGludGVyY2VwdG9yKSB7XG4gICAgY2hhaW4ucHVzaChpbnRlcmNlcHRvci5mdWxmaWxsZWQsIGludGVyY2VwdG9yLnJlamVjdGVkKTtcbiAgfSk7XG5cbiAgd2hpbGUgKGNoYWluLmxlbmd0aCkge1xuICAgIHByb21pc2UgPSBwcm9taXNlLnRoZW4oY2hhaW4uc2hpZnQoKSwgY2hhaW4uc2hpZnQoKSk7XG4gIH1cblxuICByZXR1cm4gcHJvbWlzZTtcbn07XG5cbi8vIFByb3ZpZGUgYWxpYXNlcyBmb3Igc3VwcG9ydGVkIHJlcXVlc3QgbWV0aG9kc1xudXRpbHMuZm9yRWFjaChbJ2RlbGV0ZScsICdnZXQnLCAnaGVhZCcsICdvcHRpb25zJ10sIGZ1bmN0aW9uIGZvckVhY2hNZXRob2ROb0RhdGEobWV0aG9kKSB7XG4gIC8qZXNsaW50IGZ1bmMtbmFtZXM6MCovXG4gIEF4aW9zLnByb3RvdHlwZVttZXRob2RdID0gZnVuY3Rpb24odXJsLCBjb25maWcpIHtcbiAgICByZXR1cm4gdGhpcy5yZXF1ZXN0KHV0aWxzLm1lcmdlKGNvbmZpZyB8fCB7fSwge1xuICAgICAgbWV0aG9kOiBtZXRob2QsXG4gICAgICB1cmw6IHVybFxuICAgIH0pKTtcbiAgfTtcbn0pO1xuXG51dGlscy5mb3JFYWNoKFsncG9zdCcsICdwdXQnLCAncGF0Y2gnXSwgZnVuY3Rpb24gZm9yRWFjaE1ldGhvZFdpdGhEYXRhKG1ldGhvZCkge1xuICAvKmVzbGludCBmdW5jLW5hbWVzOjAqL1xuICBBeGlvcy5wcm90b3R5cGVbbWV0aG9kXSA9IGZ1bmN0aW9uKHVybCwgZGF0YSwgY29uZmlnKSB7XG4gICAgcmV0dXJuIHRoaXMucmVxdWVzdCh1dGlscy5tZXJnZShjb25maWcgfHwge30sIHtcbiAgICAgIG1ldGhvZDogbWV0aG9kLFxuICAgICAgdXJsOiB1cmwsXG4gICAgICBkYXRhOiBkYXRhXG4gICAgfSkpO1xuICB9O1xufSk7XG5cbm1vZHVsZS5leHBvcnRzID0gQXhpb3M7XG4iLCIndXNlIHN0cmljdCc7XG5cbi8qKlxuICogQSBgQ2FuY2VsYCBpcyBhbiBvYmplY3QgdGhhdCBpcyB0aHJvd24gd2hlbiBhbiBvcGVyYXRpb24gaXMgY2FuY2VsZWQuXG4gKlxuICogQGNsYXNzXG4gKiBAcGFyYW0ge3N0cmluZz19IG1lc3NhZ2UgVGhlIG1lc3NhZ2UuXG4gKi9cbmZ1bmN0aW9uIENhbmNlbChtZXNzYWdlKSB7XG4gIHRoaXMubWVzc2FnZSA9IG1lc3NhZ2U7XG59XG5cbkNhbmNlbC5wcm90b3R5cGUudG9TdHJpbmcgPSBmdW5jdGlvbiB0b1N0cmluZygpIHtcbiAgcmV0dXJuICdDYW5jZWwnICsgKHRoaXMubWVzc2FnZSA/ICc6ICcgKyB0aGlzLm1lc3NhZ2UgOiAnJyk7XG59O1xuXG5DYW5jZWwucHJvdG90eXBlLl9fQ0FOQ0VMX18gPSB0cnVlO1xuXG5tb2R1bGUuZXhwb3J0cyA9IENhbmNlbDtcbiIsIid1c2Ugc3RyaWN0JztcblxudmFyIENhbmNlbCA9IHJlcXVpcmUoJy4vQ2FuY2VsJyk7XG5cbi8qKlxuICogQSBgQ2FuY2VsVG9rZW5gIGlzIGFuIG9iamVjdCB0aGF0IGNhbiBiZSB1c2VkIHRvIHJlcXVlc3QgY2FuY2VsbGF0aW9uIG9mIGFuIG9wZXJhdGlvbi5cbiAqXG4gKiBAY2xhc3NcbiAqIEBwYXJhbSB7RnVuY3Rpb259IGV4ZWN1dG9yIFRoZSBleGVjdXRvciBmdW5jdGlvbi5cbiAqL1xuZnVuY3Rpb24gQ2FuY2VsVG9rZW4oZXhlY3V0b3IpIHtcbiAgaWYgKHR5cGVvZiBleGVjdXRvciAhPT0gJ2Z1bmN0aW9uJykge1xuICAgIHRocm93IG5ldyBUeXBlRXJyb3IoJ2V4ZWN1dG9yIG11c3QgYmUgYSBmdW5jdGlvbi4nKTtcbiAgfVxuXG4gIHZhciByZXNvbHZlUHJvbWlzZTtcbiAgdGhpcy5wcm9taXNlID0gbmV3IFByb21pc2UoZnVuY3Rpb24gcHJvbWlzZUV4ZWN1dG9yKHJlc29sdmUpIHtcbiAgICByZXNvbHZlUHJvbWlzZSA9IHJlc29sdmU7XG4gIH0pO1xuXG4gIHZhciB0b2tlbiA9IHRoaXM7XG4gIGV4ZWN1dG9yKGZ1bmN0aW9uIGNhbmNlbChtZXNzYWdlKSB7XG4gICAgaWYgKHRva2VuLnJlYXNvbikge1xuICAgICAgLy8gQ2FuY2VsbGF0aW9uIGhhcyBhbHJlYWR5IGJlZW4gcmVxdWVzdGVkXG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgdG9rZW4ucmVhc29uID0gbmV3IENhbmNlbChtZXNzYWdlKTtcbiAgICByZXNvbHZlUHJvbWlzZSh0b2tlbi5yZWFzb24pO1xuICB9KTtcbn1cblxuLyoqXG4gKiBUaHJvd3MgYSBgQ2FuY2VsYCBpZiBjYW5jZWxsYXRpb24gaGFzIGJlZW4gcmVxdWVzdGVkLlxuICovXG5DYW5jZWxUb2tlbi5wcm90b3R5cGUudGhyb3dJZlJlcXVlc3RlZCA9IGZ1bmN0aW9uIHRocm93SWZSZXF1ZXN0ZWQoKSB7XG4gIGlmICh0aGlzLnJlYXNvbikge1xuICAgIHRocm93IHRoaXMucmVhc29uO1xuICB9XG59O1xuXG4vKipcbiAqIFJldHVybnMgYW4gb2JqZWN0IHRoYXQgY29udGFpbnMgYSBuZXcgYENhbmNlbFRva2VuYCBhbmQgYSBmdW5jdGlvbiB0aGF0LCB3aGVuIGNhbGxlZCxcbiAqIGNhbmNlbHMgdGhlIGBDYW5jZWxUb2tlbmAuXG4gKi9cbkNhbmNlbFRva2VuLnNvdXJjZSA9IGZ1bmN0aW9uIHNvdXJjZSgpIHtcbiAgdmFyIGNhbmNlbDtcbiAgdmFyIHRva2VuID0gbmV3IENhbmNlbFRva2VuKGZ1bmN0aW9uIGV4ZWN1dG9yKGMpIHtcbiAgICBjYW5jZWwgPSBjO1xuICB9KTtcbiAgcmV0dXJuIHtcbiAgICB0b2tlbjogdG9rZW4sXG4gICAgY2FuY2VsOiBjYW5jZWxcbiAgfTtcbn07XG5cbm1vZHVsZS5leHBvcnRzID0gQ2FuY2VsVG9rZW47XG4iLCIndXNlIHN0cmljdCc7XG5cbi8qKlxuICogU3ludGFjdGljIHN1Z2FyIGZvciBpbnZva2luZyBhIGZ1bmN0aW9uIGFuZCBleHBhbmRpbmcgYW4gYXJyYXkgZm9yIGFyZ3VtZW50cy5cbiAqXG4gKiBDb21tb24gdXNlIGNhc2Ugd291bGQgYmUgdG8gdXNlIGBGdW5jdGlvbi5wcm90b3R5cGUuYXBwbHlgLlxuICpcbiAqICBgYGBqc1xuICogIGZ1bmN0aW9uIGYoeCwgeSwgeikge31cbiAqICB2YXIgYXJncyA9IFsxLCAyLCAzXTtcbiAqICBmLmFwcGx5KG51bGwsIGFyZ3MpO1xuICogIGBgYFxuICpcbiAqIFdpdGggYHNwcmVhZGAgdGhpcyBleGFtcGxlIGNhbiBiZSByZS13cml0dGVuLlxuICpcbiAqICBgYGBqc1xuICogIHNwcmVhZChmdW5jdGlvbih4LCB5LCB6KSB7fSkoWzEsIDIsIDNdKTtcbiAqICBgYGBcbiAqXG4gKiBAcGFyYW0ge0Z1bmN0aW9ufSBjYWxsYmFja1xuICogQHJldHVybnMge0Z1bmN0aW9ufVxuICovXG5tb2R1bGUuZXhwb3J0cyA9IGZ1bmN0aW9uIHNwcmVhZChjYWxsYmFjaykge1xuICByZXR1cm4gZnVuY3Rpb24gd3JhcChhcnIpIHtcbiAgICByZXR1cm4gY2FsbGJhY2suYXBwbHkobnVsbCwgYXJyKTtcbiAgfTtcbn07XG4iLCIndXNlIHN0cmljdCc7XG5cbnZhciB1dGlscyA9IHJlcXVpcmUoJy4vdXRpbHMnKTtcbnZhciBiaW5kID0gcmVxdWlyZSgnLi9oZWxwZXJzL2JpbmQnKTtcbnZhciBBeGlvcyA9IHJlcXVpcmUoJy4vY29yZS9BeGlvcycpO1xudmFyIGRlZmF1bHRzID0gcmVxdWlyZSgnLi9kZWZhdWx0cycpO1xuXG4vKipcbiAqIENyZWF0ZSBhbiBpbnN0YW5jZSBvZiBBeGlvc1xuICpcbiAqIEBwYXJhbSB7T2JqZWN0fSBkZWZhdWx0Q29uZmlnIFRoZSBkZWZhdWx0IGNvbmZpZyBmb3IgdGhlIGluc3RhbmNlXG4gKiBAcmV0dXJuIHtBeGlvc30gQSBuZXcgaW5zdGFuY2Ugb2YgQXhpb3NcbiAqL1xuZnVuY3Rpb24gY3JlYXRlSW5zdGFuY2UoZGVmYXVsdENvbmZpZykge1xuICB2YXIgY29udGV4dCA9IG5ldyBBeGlvcyhkZWZhdWx0Q29uZmlnKTtcbiAgdmFyIGluc3RhbmNlID0gYmluZChBeGlvcy5wcm90b3R5cGUucmVxdWVzdCwgY29udGV4dCk7XG5cbiAgLy8gQ29weSBheGlvcy5wcm90b3R5cGUgdG8gaW5zdGFuY2VcbiAgdXRpbHMuZXh0ZW5kKGluc3RhbmNlLCBBeGlvcy5wcm90b3R5cGUsIGNvbnRleHQpO1xuXG4gIC8vIENvcHkgY29udGV4dCB0byBpbnN0YW5jZVxuICB1dGlscy5leHRlbmQoaW5zdGFuY2UsIGNvbnRleHQpO1xuXG4gIHJldHVybiBpbnN0YW5jZTtcbn1cblxuLy8gQ3JlYXRlIHRoZSBkZWZhdWx0IGluc3RhbmNlIHRvIGJlIGV4cG9ydGVkXG52YXIgYXhpb3MgPSBjcmVhdGVJbnN0YW5jZShkZWZhdWx0cyk7XG5cbi8vIEV4cG9zZSBBeGlvcyBjbGFzcyB0byBhbGxvdyBjbGFzcyBpbmhlcml0YW5jZVxuYXhpb3MuQXhpb3MgPSBBeGlvcztcblxuLy8gRmFjdG9yeSBmb3IgY3JlYXRpbmcgbmV3IGluc3RhbmNlc1xuYXhpb3MuY3JlYXRlID0gZnVuY3Rpb24gY3JlYXRlKGluc3RhbmNlQ29uZmlnKSB7XG4gIHJldHVybiBjcmVhdGVJbnN0YW5jZSh1dGlscy5tZXJnZShkZWZhdWx0cywgaW5zdGFuY2VDb25maWcpKTtcbn07XG5cbi8vIEV4cG9zZSBDYW5jZWwgJiBDYW5jZWxUb2tlblxuYXhpb3MuQ2FuY2VsID0gcmVxdWlyZSgnLi9jYW5jZWwvQ2FuY2VsJyk7XG5heGlvcy5DYW5jZWxUb2tlbiA9IHJlcXVpcmUoJy4vY2FuY2VsL0NhbmNlbFRva2VuJyk7XG5heGlvcy5pc0NhbmNlbCA9IHJlcXVpcmUoJy4vY2FuY2VsL2lzQ2FuY2VsJyk7XG5cbi8vIEV4cG9zZSBhbGwvc3ByZWFkXG5heGlvcy5hbGwgPSBmdW5jdGlvbiBhbGwocHJvbWlzZXMpIHtcbiAgcmV0dXJuIFByb21pc2UuYWxsKHByb21pc2VzKTtcbn07XG5heGlvcy5zcHJlYWQgPSByZXF1aXJlKCcuL2hlbHBlcnMvc3ByZWFkJyk7XG5cbm1vZHVsZS5leHBvcnRzID0gYXhpb3M7XG5cbi8vIEFsbG93IHVzZSBvZiBkZWZhdWx0IGltcG9ydCBzeW50YXggaW4gVHlwZVNjcmlwdFxubW9kdWxlLmV4cG9ydHMuZGVmYXVsdCA9IGF4aW9zO1xuIiwibW9kdWxlLmV4cG9ydHMgPSByZXF1aXJlKCcuL2xpYi9heGlvcycpOyIsIid1c2Ugc3RyaWN0JztcblxubW9kdWxlLmV4cG9ydHMgPSBmdW5jdGlvbiBiaW5kKGZuLCB0aGlzQXJnKSB7XG4gIHJldHVybiBmdW5jdGlvbiB3cmFwKCkge1xuICAgIHZhciBhcmdzID0gbmV3IEFycmF5KGFyZ3VtZW50cy5sZW5ndGgpO1xuICAgIGZvciAodmFyIGkgPSAwOyBpIDwgYXJncy5sZW5ndGg7IGkrKykge1xuICAgICAgYXJnc1tpXSA9IGFyZ3VtZW50c1tpXTtcbiAgICB9XG4gICAgcmV0dXJuIGZuLmFwcGx5KHRoaXNBcmcsIGFyZ3MpO1xuICB9O1xufTtcbiIsIid1c2Ugc3RyaWN0JztcblxudmFyIGJpbmQgPSByZXF1aXJlKCcuL2hlbHBlcnMvYmluZCcpO1xudmFyIGlzQnVmZmVyID0gcmVxdWlyZSgnaXMtYnVmZmVyJyk7XG5cbi8qZ2xvYmFsIHRvU3RyaW5nOnRydWUqL1xuXG4vLyB1dGlscyBpcyBhIGxpYnJhcnkgb2YgZ2VuZXJpYyBoZWxwZXIgZnVuY3Rpb25zIG5vbi1zcGVjaWZpYyB0byBheGlvc1xuXG52YXIgdG9TdHJpbmcgPSBPYmplY3QucHJvdG90eXBlLnRvU3RyaW5nO1xuXG4vKipcbiAqIERldGVybWluZSBpZiBhIHZhbHVlIGlzIGFuIEFycmF5XG4gKlxuICogQHBhcmFtIHtPYmplY3R9IHZhbCBUaGUgdmFsdWUgdG8gdGVzdFxuICogQHJldHVybnMge2Jvb2xlYW59IFRydWUgaWYgdmFsdWUgaXMgYW4gQXJyYXksIG90aGVyd2lzZSBmYWxzZVxuICovXG5mdW5jdGlvbiBpc0FycmF5KHZhbCkge1xuICByZXR1cm4gdG9TdHJpbmcuY2FsbCh2YWwpID09PSAnW29iamVjdCBBcnJheV0nO1xufVxuXG4vKipcbiAqIERldGVybWluZSBpZiBhIHZhbHVlIGlzIGFuIEFycmF5QnVmZmVyXG4gKlxuICogQHBhcmFtIHtPYmplY3R9IHZhbCBUaGUgdmFsdWUgdG8gdGVzdFxuICogQHJldHVybnMge2Jvb2xlYW59IFRydWUgaWYgdmFsdWUgaXMgYW4gQXJyYXlCdWZmZXIsIG90aGVyd2lzZSBmYWxzZVxuICovXG5mdW5jdGlvbiBpc0FycmF5QnVmZmVyKHZhbCkge1xuICByZXR1cm4gdG9TdHJpbmcuY2FsbCh2YWwpID09PSAnW29iamVjdCBBcnJheUJ1ZmZlcl0nO1xufVxuXG4vKipcbiAqIERldGVybWluZSBpZiBhIHZhbHVlIGlzIGEgRm9ybURhdGFcbiAqXG4gKiBAcGFyYW0ge09iamVjdH0gdmFsIFRoZSB2YWx1ZSB0byB0ZXN0XG4gKiBAcmV0dXJucyB7Ym9vbGVhbn0gVHJ1ZSBpZiB2YWx1ZSBpcyBhbiBGb3JtRGF0YSwgb3RoZXJ3aXNlIGZhbHNlXG4gKi9cbmZ1bmN0aW9uIGlzRm9ybURhdGEodmFsKSB7XG4gIHJldHVybiAodHlwZW9mIEZvcm1EYXRhICE9PSAndW5kZWZpbmVkJykgJiYgKHZhbCBpbnN0YW5jZW9mIEZvcm1EYXRhKTtcbn1cblxuLyoqXG4gKiBEZXRlcm1pbmUgaWYgYSB2YWx1ZSBpcyBhIHZpZXcgb24gYW4gQXJyYXlCdWZmZXJcbiAqXG4gKiBAcGFyYW0ge09iamVjdH0gdmFsIFRoZSB2YWx1ZSB0byB0ZXN0XG4gKiBAcmV0dXJucyB7Ym9vbGVhbn0gVHJ1ZSBpZiB2YWx1ZSBpcyBhIHZpZXcgb24gYW4gQXJyYXlCdWZmZXIsIG90aGVyd2lzZSBmYWxzZVxuICovXG5mdW5jdGlvbiBpc0FycmF5QnVmZmVyVmlldyh2YWwpIHtcbiAgdmFyIHJlc3VsdDtcbiAgaWYgKCh0eXBlb2YgQXJyYXlCdWZmZXIgIT09ICd1bmRlZmluZWQnKSAmJiAoQXJyYXlCdWZmZXIuaXNWaWV3KSkge1xuICAgIHJlc3VsdCA9IEFycmF5QnVmZmVyLmlzVmlldyh2YWwpO1xuICB9IGVsc2Uge1xuICAgIHJlc3VsdCA9ICh2YWwpICYmICh2YWwuYnVmZmVyKSAmJiAodmFsLmJ1ZmZlciBpbnN0YW5jZW9mIEFycmF5QnVmZmVyKTtcbiAgfVxuICByZXR1cm4gcmVzdWx0O1xufVxuXG4vKipcbiAqIERldGVybWluZSBpZiBhIHZhbHVlIGlzIGEgU3RyaW5nXG4gKlxuICogQHBhcmFtIHtPYmplY3R9IHZhbCBUaGUgdmFsdWUgdG8gdGVzdFxuICogQHJldHVybnMge2Jvb2xlYW59IFRydWUgaWYgdmFsdWUgaXMgYSBTdHJpbmcsIG90aGVyd2lzZSBmYWxzZVxuICovXG5mdW5jdGlvbiBpc1N0cmluZyh2YWwpIHtcbiAgcmV0dXJuIHR5cGVvZiB2YWwgPT09ICdzdHJpbmcnO1xufVxuXG4vKipcbiAqIERldGVybWluZSBpZiBhIHZhbHVlIGlzIGEgTnVtYmVyXG4gKlxuICogQHBhcmFtIHtPYmplY3R9IHZhbCBUaGUgdmFsdWUgdG8gdGVzdFxuICogQHJldHVybnMge2Jvb2xlYW59IFRydWUgaWYgdmFsdWUgaXMgYSBOdW1iZXIsIG90aGVyd2lzZSBmYWxzZVxuICovXG5mdW5jdGlvbiBpc051bWJlcih2YWwpIHtcbiAgcmV0dXJuIHR5cGVvZiB2YWwgPT09ICdudW1iZXInO1xufVxuXG4vKipcbiAqIERldGVybWluZSBpZiBhIHZhbHVlIGlzIHVuZGVmaW5lZFxuICpcbiAqIEBwYXJhbSB7T2JqZWN0fSB2YWwgVGhlIHZhbHVlIHRvIHRlc3RcbiAqIEByZXR1cm5zIHtib29sZWFufSBUcnVlIGlmIHRoZSB2YWx1ZSBpcyB1bmRlZmluZWQsIG90aGVyd2lzZSBmYWxzZVxuICovXG5mdW5jdGlvbiBpc1VuZGVmaW5lZCh2YWwpIHtcbiAgcmV0dXJuIHR5cGVvZiB2YWwgPT09ICd1bmRlZmluZWQnO1xufVxuXG4vKipcbiAqIERldGVybWluZSBpZiBhIHZhbHVlIGlzIGFuIE9iamVjdFxuICpcbiAqIEBwYXJhbSB7T2JqZWN0fSB2YWwgVGhlIHZhbHVlIHRvIHRlc3RcbiAqIEByZXR1cm5zIHtib29sZWFufSBUcnVlIGlmIHZhbHVlIGlzIGFuIE9iamVjdCwgb3RoZXJ3aXNlIGZhbHNlXG4gKi9cbmZ1bmN0aW9uIGlzT2JqZWN0KHZhbCkge1xuICByZXR1cm4gdmFsICE9PSBudWxsICYmIHR5cGVvZiB2YWwgPT09ICdvYmplY3QnO1xufVxuXG4vKipcbiAqIERldGVybWluZSBpZiBhIHZhbHVlIGlzIGEgRGF0ZVxuICpcbiAqIEBwYXJhbSB7T2JqZWN0fSB2YWwgVGhlIHZhbHVlIHRvIHRlc3RcbiAqIEByZXR1cm5zIHtib29sZWFufSBUcnVlIGlmIHZhbHVlIGlzIGEgRGF0ZSwgb3RoZXJ3aXNlIGZhbHNlXG4gKi9cbmZ1bmN0aW9uIGlzRGF0ZSh2YWwpIHtcbiAgcmV0dXJuIHRvU3RyaW5nLmNhbGwodmFsKSA9PT0gJ1tvYmplY3QgRGF0ZV0nO1xufVxuXG4vKipcbiAqIERldGVybWluZSBpZiBhIHZhbHVlIGlzIGEgRmlsZVxuICpcbiAqIEBwYXJhbSB7T2JqZWN0fSB2YWwgVGhlIHZhbHVlIHRvIHRlc3RcbiAqIEByZXR1cm5zIHtib29sZWFufSBUcnVlIGlmIHZhbHVlIGlzIGEgRmlsZSwgb3RoZXJ3aXNlIGZhbHNlXG4gKi9cbmZ1bmN0aW9uIGlzRmlsZSh2YWwpIHtcbiAgcmV0dXJuIHRvU3RyaW5nLmNhbGwodmFsKSA9PT0gJ1tvYmplY3QgRmlsZV0nO1xufVxuXG4vKipcbiAqIERldGVybWluZSBpZiBhIHZhbHVlIGlzIGEgQmxvYlxuICpcbiAqIEBwYXJhbSB7T2JqZWN0fSB2YWwgVGhlIHZhbHVlIHRvIHRlc3RcbiAqIEByZXR1cm5zIHtib29sZWFufSBUcnVlIGlmIHZhbHVlIGlzIGEgQmxvYiwgb3RoZXJ3aXNlIGZhbHNlXG4gKi9cbmZ1bmN0aW9uIGlzQmxvYih2YWwpIHtcbiAgcmV0dXJuIHRvU3RyaW5nLmNhbGwodmFsKSA9PT0gJ1tvYmplY3QgQmxvYl0nO1xufVxuXG4vKipcbiAqIERldGVybWluZSBpZiBhIHZhbHVlIGlzIGEgRnVuY3Rpb25cbiAqXG4gKiBAcGFyYW0ge09iamVjdH0gdmFsIFRoZSB2YWx1ZSB0byB0ZXN0XG4gKiBAcmV0dXJucyB7Ym9vbGVhbn0gVHJ1ZSBpZiB2YWx1ZSBpcyBhIEZ1bmN0aW9uLCBvdGhlcndpc2UgZmFsc2VcbiAqL1xuZnVuY3Rpb24gaXNGdW5jdGlvbih2YWwpIHtcbiAgcmV0dXJuIHRvU3RyaW5nLmNhbGwodmFsKSA9PT0gJ1tvYmplY3QgRnVuY3Rpb25dJztcbn1cblxuLyoqXG4gKiBEZXRlcm1pbmUgaWYgYSB2YWx1ZSBpcyBhIFN0cmVhbVxuICpcbiAqIEBwYXJhbSB7T2JqZWN0fSB2YWwgVGhlIHZhbHVlIHRvIHRlc3RcbiAqIEByZXR1cm5zIHtib29sZWFufSBUcnVlIGlmIHZhbHVlIGlzIGEgU3RyZWFtLCBvdGhlcndpc2UgZmFsc2VcbiAqL1xuZnVuY3Rpb24gaXNTdHJlYW0odmFsKSB7XG4gIHJldHVybiBpc09iamVjdCh2YWwpICYmIGlzRnVuY3Rpb24odmFsLnBpcGUpO1xufVxuXG4vKipcbiAqIERldGVybWluZSBpZiBhIHZhbHVlIGlzIGEgVVJMU2VhcmNoUGFyYW1zIG9iamVjdFxuICpcbiAqIEBwYXJhbSB7T2JqZWN0fSB2YWwgVGhlIHZhbHVlIHRvIHRlc3RcbiAqIEByZXR1cm5zIHtib29sZWFufSBUcnVlIGlmIHZhbHVlIGlzIGEgVVJMU2VhcmNoUGFyYW1zIG9iamVjdCwgb3RoZXJ3aXNlIGZhbHNlXG4gKi9cbmZ1bmN0aW9uIGlzVVJMU2VhcmNoUGFyYW1zKHZhbCkge1xuICByZXR1cm4gdHlwZW9mIFVSTFNlYXJjaFBhcmFtcyAhPT0gJ3VuZGVmaW5lZCcgJiYgdmFsIGluc3RhbmNlb2YgVVJMU2VhcmNoUGFyYW1zO1xufVxuXG4vKipcbiAqIFRyaW0gZXhjZXNzIHdoaXRlc3BhY2Ugb2ZmIHRoZSBiZWdpbm5pbmcgYW5kIGVuZCBvZiBhIHN0cmluZ1xuICpcbiAqIEBwYXJhbSB7U3RyaW5nfSBzdHIgVGhlIFN0cmluZyB0byB0cmltXG4gKiBAcmV0dXJucyB7U3RyaW5nfSBUaGUgU3RyaW5nIGZyZWVkIG9mIGV4Y2VzcyB3aGl0ZXNwYWNlXG4gKi9cbmZ1bmN0aW9uIHRyaW0oc3RyKSB7XG4gIHJldHVybiBzdHIucmVwbGFjZSgvXlxccyovLCAnJykucmVwbGFjZSgvXFxzKiQvLCAnJyk7XG59XG5cbi8qKlxuICogRGV0ZXJtaW5lIGlmIHdlJ3JlIHJ1bm5pbmcgaW4gYSBzdGFuZGFyZCBicm93c2VyIGVudmlyb25tZW50XG4gKlxuICogVGhpcyBhbGxvd3MgYXhpb3MgdG8gcnVuIGluIGEgd2ViIHdvcmtlciwgYW5kIHJlYWN0LW5hdGl2ZS5cbiAqIEJvdGggZW52aXJvbm1lbnRzIHN1cHBvcnQgWE1MSHR0cFJlcXVlc3QsIGJ1dCBub3QgZnVsbHkgc3RhbmRhcmQgZ2xvYmFscy5cbiAqXG4gKiB3ZWIgd29ya2VyczpcbiAqICB0eXBlb2Ygd2luZG93IC0+IHVuZGVmaW5lZFxuICogIHR5cGVvZiBkb2N1bWVudCAtPiB1bmRlZmluZWRcbiAqXG4gKiByZWFjdC1uYXRpdmU6XG4gKiAgbmF2aWdhdG9yLnByb2R1Y3QgLT4gJ1JlYWN0TmF0aXZlJ1xuICovXG5mdW5jdGlvbiBpc1N0YW5kYXJkQnJvd3NlckVudigpIHtcbiAgaWYgKHR5cGVvZiBuYXZpZ2F0b3IgIT09ICd1bmRlZmluZWQnICYmIG5hdmlnYXRvci5wcm9kdWN0ID09PSAnUmVhY3ROYXRpdmUnKSB7XG4gICAgcmV0dXJuIGZhbHNlO1xuICB9XG4gIHJldHVybiAoXG4gICAgdHlwZW9mIHdpbmRvdyAhPT0gJ3VuZGVmaW5lZCcgJiZcbiAgICB0eXBlb2YgZG9jdW1lbnQgIT09ICd1bmRlZmluZWQnXG4gICk7XG59XG5cbi8qKlxuICogSXRlcmF0ZSBvdmVyIGFuIEFycmF5IG9yIGFuIE9iamVjdCBpbnZva2luZyBhIGZ1bmN0aW9uIGZvciBlYWNoIGl0ZW0uXG4gKlxuICogSWYgYG9iamAgaXMgYW4gQXJyYXkgY2FsbGJhY2sgd2lsbCBiZSBjYWxsZWQgcGFzc2luZ1xuICogdGhlIHZhbHVlLCBpbmRleCwgYW5kIGNvbXBsZXRlIGFycmF5IGZvciBlYWNoIGl0ZW0uXG4gKlxuICogSWYgJ29iaicgaXMgYW4gT2JqZWN0IGNhbGxiYWNrIHdpbGwgYmUgY2FsbGVkIHBhc3NpbmdcbiAqIHRoZSB2YWx1ZSwga2V5LCBhbmQgY29tcGxldGUgb2JqZWN0IGZvciBlYWNoIHByb3BlcnR5LlxuICpcbiAqIEBwYXJhbSB7T2JqZWN0fEFycmF5fSBvYmogVGhlIG9iamVjdCB0byBpdGVyYXRlXG4gKiBAcGFyYW0ge0Z1bmN0aW9ufSBmbiBUaGUgY2FsbGJhY2sgdG8gaW52b2tlIGZvciBlYWNoIGl0ZW1cbiAqL1xuZnVuY3Rpb24gZm9yRWFjaChvYmosIGZuKSB7XG4gIC8vIERvbid0IGJvdGhlciBpZiBubyB2YWx1ZSBwcm92aWRlZFxuICBpZiAob2JqID09PSBudWxsIHx8IHR5cGVvZiBvYmogPT09ICd1bmRlZmluZWQnKSB7XG4gICAgcmV0dXJuO1xuICB9XG5cbiAgLy8gRm9yY2UgYW4gYXJyYXkgaWYgbm90IGFscmVhZHkgc29tZXRoaW5nIGl0ZXJhYmxlXG4gIGlmICh0eXBlb2Ygb2JqICE9PSAnb2JqZWN0Jykge1xuICAgIC8qZXNsaW50IG5vLXBhcmFtLXJlYXNzaWduOjAqL1xuICAgIG9iaiA9IFtvYmpdO1xuICB9XG5cbiAgaWYgKGlzQXJyYXkob2JqKSkge1xuICAgIC8vIEl0ZXJhdGUgb3ZlciBhcnJheSB2YWx1ZXNcbiAgICBmb3IgKHZhciBpID0gMCwgbCA9IG9iai5sZW5ndGg7IGkgPCBsOyBpKyspIHtcbiAgICAgIGZuLmNhbGwobnVsbCwgb2JqW2ldLCBpLCBvYmopO1xuICAgIH1cbiAgfSBlbHNlIHtcbiAgICAvLyBJdGVyYXRlIG92ZXIgb2JqZWN0IGtleXNcbiAgICBmb3IgKHZhciBrZXkgaW4gb2JqKSB7XG4gICAgICBpZiAoT2JqZWN0LnByb3RvdHlwZS5oYXNPd25Qcm9wZXJ0eS5jYWxsKG9iaiwga2V5KSkge1xuICAgICAgICBmbi5jYWxsKG51bGwsIG9ialtrZXldLCBrZXksIG9iaik7XG4gICAgICB9XG4gICAgfVxuICB9XG59XG5cbi8qKlxuICogQWNjZXB0cyB2YXJhcmdzIGV4cGVjdGluZyBlYWNoIGFyZ3VtZW50IHRvIGJlIGFuIG9iamVjdCwgdGhlblxuICogaW1tdXRhYmx5IG1lcmdlcyB0aGUgcHJvcGVydGllcyBvZiBlYWNoIG9iamVjdCBhbmQgcmV0dXJucyByZXN1bHQuXG4gKlxuICogV2hlbiBtdWx0aXBsZSBvYmplY3RzIGNvbnRhaW4gdGhlIHNhbWUga2V5IHRoZSBsYXRlciBvYmplY3QgaW5cbiAqIHRoZSBhcmd1bWVudHMgbGlzdCB3aWxsIHRha2UgcHJlY2VkZW5jZS5cbiAqXG4gKiBFeGFtcGxlOlxuICpcbiAqIGBgYGpzXG4gKiB2YXIgcmVzdWx0ID0gbWVyZ2Uoe2ZvbzogMTIzfSwge2ZvbzogNDU2fSk7XG4gKiBjb25zb2xlLmxvZyhyZXN1bHQuZm9vKTsgLy8gb3V0cHV0cyA0NTZcbiAqIGBgYFxuICpcbiAqIEBwYXJhbSB7T2JqZWN0fSBvYmoxIE9iamVjdCB0byBtZXJnZVxuICogQHJldHVybnMge09iamVjdH0gUmVzdWx0IG9mIGFsbCBtZXJnZSBwcm9wZXJ0aWVzXG4gKi9cbmZ1bmN0aW9uIG1lcmdlKC8qIG9iajEsIG9iajIsIG9iajMsIC4uLiAqLykge1xuICB2YXIgcmVzdWx0ID0ge307XG4gIGZ1bmN0aW9uIGFzc2lnblZhbHVlKHZhbCwga2V5KSB7XG4gICAgaWYgKHR5cGVvZiByZXN1bHRba2V5XSA9PT0gJ29iamVjdCcgJiYgdHlwZW9mIHZhbCA9PT0gJ29iamVjdCcpIHtcbiAgICAgIHJlc3VsdFtrZXldID0gbWVyZ2UocmVzdWx0W2tleV0sIHZhbCk7XG4gICAgfSBlbHNlIHtcbiAgICAgIHJlc3VsdFtrZXldID0gdmFsO1xuICAgIH1cbiAgfVxuXG4gIGZvciAodmFyIGkgPSAwLCBsID0gYXJndW1lbnRzLmxlbmd0aDsgaSA8IGw7IGkrKykge1xuICAgIGZvckVhY2goYXJndW1lbnRzW2ldLCBhc3NpZ25WYWx1ZSk7XG4gIH1cbiAgcmV0dXJuIHJlc3VsdDtcbn1cblxuLyoqXG4gKiBFeHRlbmRzIG9iamVjdCBhIGJ5IG11dGFibHkgYWRkaW5nIHRvIGl0IHRoZSBwcm9wZXJ0aWVzIG9mIG9iamVjdCBiLlxuICpcbiAqIEBwYXJhbSB7T2JqZWN0fSBhIFRoZSBvYmplY3QgdG8gYmUgZXh0ZW5kZWRcbiAqIEBwYXJhbSB7T2JqZWN0fSBiIFRoZSBvYmplY3QgdG8gY29weSBwcm9wZXJ0aWVzIGZyb21cbiAqIEBwYXJhbSB7T2JqZWN0fSB0aGlzQXJnIFRoZSBvYmplY3QgdG8gYmluZCBmdW5jdGlvbiB0b1xuICogQHJldHVybiB7T2JqZWN0fSBUaGUgcmVzdWx0aW5nIHZhbHVlIG9mIG9iamVjdCBhXG4gKi9cbmZ1bmN0aW9uIGV4dGVuZChhLCBiLCB0aGlzQXJnKSB7XG4gIGZvckVhY2goYiwgZnVuY3Rpb24gYXNzaWduVmFsdWUodmFsLCBrZXkpIHtcbiAgICBpZiAodGhpc0FyZyAmJiB0eXBlb2YgdmFsID09PSAnZnVuY3Rpb24nKSB7XG4gICAgICBhW2tleV0gPSBiaW5kKHZhbCwgdGhpc0FyZyk7XG4gICAgfSBlbHNlIHtcbiAgICAgIGFba2V5XSA9IHZhbDtcbiAgICB9XG4gIH0pO1xuICByZXR1cm4gYTtcbn1cblxubW9kdWxlLmV4cG9ydHMgPSB7XG4gIGlzQXJyYXk6IGlzQXJyYXksXG4gIGlzQXJyYXlCdWZmZXI6IGlzQXJyYXlCdWZmZXIsXG4gIGlzQnVmZmVyOiBpc0J1ZmZlcixcbiAgaXNGb3JtRGF0YTogaXNGb3JtRGF0YSxcbiAgaXNBcnJheUJ1ZmZlclZpZXc6IGlzQXJyYXlCdWZmZXJWaWV3LFxuICBpc1N0cmluZzogaXNTdHJpbmcsXG4gIGlzTnVtYmVyOiBpc051bWJlcixcbiAgaXNPYmplY3Q6IGlzT2JqZWN0LFxuICBpc1VuZGVmaW5lZDogaXNVbmRlZmluZWQsXG4gIGlzRGF0ZTogaXNEYXRlLFxuICBpc0ZpbGU6IGlzRmlsZSxcbiAgaXNCbG9iOiBpc0Jsb2IsXG4gIGlzRnVuY3Rpb246IGlzRnVuY3Rpb24sXG4gIGlzU3RyZWFtOiBpc1N0cmVhbSxcbiAgaXNVUkxTZWFyY2hQYXJhbXM6IGlzVVJMU2VhcmNoUGFyYW1zLFxuICBpc1N0YW5kYXJkQnJvd3NlckVudjogaXNTdGFuZGFyZEJyb3dzZXJFbnYsXG4gIGZvckVhY2g6IGZvckVhY2gsXG4gIG1lcmdlOiBtZXJnZSxcbiAgZXh0ZW5kOiBleHRlbmQsXG4gIHRyaW06IHRyaW1cbn07XG4iLCIndXNlIHN0cmljdCc7XG5cbnZhciB1dGlscyA9IHJlcXVpcmUoJy4uL3V0aWxzJyk7XG5cbm1vZHVsZS5leHBvcnRzID0gZnVuY3Rpb24gbm9ybWFsaXplSGVhZGVyTmFtZShoZWFkZXJzLCBub3JtYWxpemVkTmFtZSkge1xuICB1dGlscy5mb3JFYWNoKGhlYWRlcnMsIGZ1bmN0aW9uIHByb2Nlc3NIZWFkZXIodmFsdWUsIG5hbWUpIHtcbiAgICBpZiAobmFtZSAhPT0gbm9ybWFsaXplZE5hbWUgJiYgbmFtZS50b1VwcGVyQ2FzZSgpID09PSBub3JtYWxpemVkTmFtZS50b1VwcGVyQ2FzZSgpKSB7XG4gICAgICBoZWFkZXJzW25vcm1hbGl6ZWROYW1lXSA9IHZhbHVlO1xuICAgICAgZGVsZXRlIGhlYWRlcnNbbmFtZV07XG4gICAgfVxuICB9KTtcbn07XG4iLCIndXNlIHN0cmljdCc7XG5cbi8qKlxuICogVXBkYXRlIGFuIEVycm9yIHdpdGggdGhlIHNwZWNpZmllZCBjb25maWcsIGVycm9yIGNvZGUsIGFuZCByZXNwb25zZS5cbiAqXG4gKiBAcGFyYW0ge0Vycm9yfSBlcnJvciBUaGUgZXJyb3IgdG8gdXBkYXRlLlxuICogQHBhcmFtIHtPYmplY3R9IGNvbmZpZyBUaGUgY29uZmlnLlxuICogQHBhcmFtIHtzdHJpbmd9IFtjb2RlXSBUaGUgZXJyb3IgY29kZSAoZm9yIGV4YW1wbGUsICdFQ09OTkFCT1JURUQnKS5cbiAqIEBwYXJhbSB7T2JqZWN0fSBbcmVxdWVzdF0gVGhlIHJlcXVlc3QuXG4gKiBAcGFyYW0ge09iamVjdH0gW3Jlc3BvbnNlXSBUaGUgcmVzcG9uc2UuXG4gKiBAcmV0dXJucyB7RXJyb3J9IFRoZSBlcnJvci5cbiAqL1xubW9kdWxlLmV4cG9ydHMgPSBmdW5jdGlvbiBlbmhhbmNlRXJyb3IoZXJyb3IsIGNvbmZpZywgY29kZSwgcmVxdWVzdCwgcmVzcG9uc2UpIHtcbiAgZXJyb3IuY29uZmlnID0gY29uZmlnO1xuICBpZiAoY29kZSkge1xuICAgIGVycm9yLmNvZGUgPSBjb2RlO1xuICB9XG4gIGVycm9yLnJlcXVlc3QgPSByZXF1ZXN0O1xuICBlcnJvci5yZXNwb25zZSA9IHJlc3BvbnNlO1xuICByZXR1cm4gZXJyb3I7XG59O1xuIiwiJ3VzZSBzdHJpY3QnO1xuXG52YXIgZW5oYW5jZUVycm9yID0gcmVxdWlyZSgnLi9lbmhhbmNlRXJyb3InKTtcblxuLyoqXG4gKiBDcmVhdGUgYW4gRXJyb3Igd2l0aCB0aGUgc3BlY2lmaWVkIG1lc3NhZ2UsIGNvbmZpZywgZXJyb3IgY29kZSwgcmVxdWVzdCBhbmQgcmVzcG9uc2UuXG4gKlxuICogQHBhcmFtIHtzdHJpbmd9IG1lc3NhZ2UgVGhlIGVycm9yIG1lc3NhZ2UuXG4gKiBAcGFyYW0ge09iamVjdH0gY29uZmlnIFRoZSBjb25maWcuXG4gKiBAcGFyYW0ge3N0cmluZ30gW2NvZGVdIFRoZSBlcnJvciBjb2RlIChmb3IgZXhhbXBsZSwgJ0VDT05OQUJPUlRFRCcpLlxuICogQHBhcmFtIHtPYmplY3R9IFtyZXF1ZXN0XSBUaGUgcmVxdWVzdC5cbiAqIEBwYXJhbSB7T2JqZWN0fSBbcmVzcG9uc2VdIFRoZSByZXNwb25zZS5cbiAqIEByZXR1cm5zIHtFcnJvcn0gVGhlIGNyZWF0ZWQgZXJyb3IuXG4gKi9cbm1vZHVsZS5leHBvcnRzID0gZnVuY3Rpb24gY3JlYXRlRXJyb3IobWVzc2FnZSwgY29uZmlnLCBjb2RlLCByZXF1ZXN0LCByZXNwb25zZSkge1xuICB2YXIgZXJyb3IgPSBuZXcgRXJyb3IobWVzc2FnZSk7XG4gIHJldHVybiBlbmhhbmNlRXJyb3IoZXJyb3IsIGNvbmZpZywgY29kZSwgcmVxdWVzdCwgcmVzcG9uc2UpO1xufTtcbiIsIid1c2Ugc3RyaWN0JztcblxudmFyIGNyZWF0ZUVycm9yID0gcmVxdWlyZSgnLi9jcmVhdGVFcnJvcicpO1xuXG4vKipcbiAqIFJlc29sdmUgb3IgcmVqZWN0IGEgUHJvbWlzZSBiYXNlZCBvbiByZXNwb25zZSBzdGF0dXMuXG4gKlxuICogQHBhcmFtIHtGdW5jdGlvbn0gcmVzb2x2ZSBBIGZ1bmN0aW9uIHRoYXQgcmVzb2x2ZXMgdGhlIHByb21pc2UuXG4gKiBAcGFyYW0ge0Z1bmN0aW9ufSByZWplY3QgQSBmdW5jdGlvbiB0aGF0IHJlamVjdHMgdGhlIHByb21pc2UuXG4gKiBAcGFyYW0ge29iamVjdH0gcmVzcG9uc2UgVGhlIHJlc3BvbnNlLlxuICovXG5tb2R1bGUuZXhwb3J0cyA9IGZ1bmN0aW9uIHNldHRsZShyZXNvbHZlLCByZWplY3QsIHJlc3BvbnNlKSB7XG4gIHZhciB2YWxpZGF0ZVN0YXR1cyA9IHJlc3BvbnNlLmNvbmZpZy52YWxpZGF0ZVN0YXR1cztcbiAgLy8gTm90ZTogc3RhdHVzIGlzIG5vdCBleHBvc2VkIGJ5IFhEb21haW5SZXF1ZXN0XG4gIGlmICghcmVzcG9uc2Uuc3RhdHVzIHx8ICF2YWxpZGF0ZVN0YXR1cyB8fCB2YWxpZGF0ZVN0YXR1cyhyZXNwb25zZS5zdGF0dXMpKSB7XG4gICAgcmVzb2x2ZShyZXNwb25zZSk7XG4gIH0gZWxzZSB7XG4gICAgcmVqZWN0KGNyZWF0ZUVycm9yKFxuICAgICAgJ1JlcXVlc3QgZmFpbGVkIHdpdGggc3RhdHVzIGNvZGUgJyArIHJlc3BvbnNlLnN0YXR1cyxcbiAgICAgIHJlc3BvbnNlLmNvbmZpZyxcbiAgICAgIG51bGwsXG4gICAgICByZXNwb25zZS5yZXF1ZXN0LFxuICAgICAgcmVzcG9uc2VcbiAgICApKTtcbiAgfVxufTtcbiIsIid1c2Ugc3RyaWN0JztcblxudmFyIHV0aWxzID0gcmVxdWlyZSgnLi8uLi91dGlscycpO1xuXG5mdW5jdGlvbiBlbmNvZGUodmFsKSB7XG4gIHJldHVybiBlbmNvZGVVUklDb21wb25lbnQodmFsKS5cbiAgICByZXBsYWNlKC8lNDAvZ2ksICdAJykuXG4gICAgcmVwbGFjZSgvJTNBL2dpLCAnOicpLlxuICAgIHJlcGxhY2UoLyUyNC9nLCAnJCcpLlxuICAgIHJlcGxhY2UoLyUyQy9naSwgJywnKS5cbiAgICByZXBsYWNlKC8lMjAvZywgJysnKS5cbiAgICByZXBsYWNlKC8lNUIvZ2ksICdbJykuXG4gICAgcmVwbGFjZSgvJTVEL2dpLCAnXScpO1xufVxuXG4vKipcbiAqIEJ1aWxkIGEgVVJMIGJ5IGFwcGVuZGluZyBwYXJhbXMgdG8gdGhlIGVuZFxuICpcbiAqIEBwYXJhbSB7c3RyaW5nfSB1cmwgVGhlIGJhc2Ugb2YgdGhlIHVybCAoZS5nLiwgaHR0cDovL3d3dy5nb29nbGUuY29tKVxuICogQHBhcmFtIHtvYmplY3R9IFtwYXJhbXNdIFRoZSBwYXJhbXMgdG8gYmUgYXBwZW5kZWRcbiAqIEByZXR1cm5zIHtzdHJpbmd9IFRoZSBmb3JtYXR0ZWQgdXJsXG4gKi9cbm1vZHVsZS5leHBvcnRzID0gZnVuY3Rpb24gYnVpbGRVUkwodXJsLCBwYXJhbXMsIHBhcmFtc1NlcmlhbGl6ZXIpIHtcbiAgLyplc2xpbnQgbm8tcGFyYW0tcmVhc3NpZ246MCovXG4gIGlmICghcGFyYW1zKSB7XG4gICAgcmV0dXJuIHVybDtcbiAgfVxuXG4gIHZhciBzZXJpYWxpemVkUGFyYW1zO1xuICBpZiAocGFyYW1zU2VyaWFsaXplcikge1xuICAgIHNlcmlhbGl6ZWRQYXJhbXMgPSBwYXJhbXNTZXJpYWxpemVyKHBhcmFtcyk7XG4gIH0gZWxzZSBpZiAodXRpbHMuaXNVUkxTZWFyY2hQYXJhbXMocGFyYW1zKSkge1xuICAgIHNlcmlhbGl6ZWRQYXJhbXMgPSBwYXJhbXMudG9TdHJpbmcoKTtcbiAgfSBlbHNlIHtcbiAgICB2YXIgcGFydHMgPSBbXTtcblxuICAgIHV0aWxzLmZvckVhY2gocGFyYW1zLCBmdW5jdGlvbiBzZXJpYWxpemUodmFsLCBrZXkpIHtcbiAgICAgIGlmICh2YWwgPT09IG51bGwgfHwgdHlwZW9mIHZhbCA9PT0gJ3VuZGVmaW5lZCcpIHtcbiAgICAgICAgcmV0dXJuO1xuICAgICAgfVxuXG4gICAgICBpZiAodXRpbHMuaXNBcnJheSh2YWwpKSB7XG4gICAgICAgIGtleSA9IGtleSArICdbXSc7XG4gICAgICB9XG5cbiAgICAgIGlmICghdXRpbHMuaXNBcnJheSh2YWwpKSB7XG4gICAgICAgIHZhbCA9IFt2YWxdO1xuICAgICAgfVxuXG4gICAgICB1dGlscy5mb3JFYWNoKHZhbCwgZnVuY3Rpb24gcGFyc2VWYWx1ZSh2KSB7XG4gICAgICAgIGlmICh1dGlscy5pc0RhdGUodikpIHtcbiAgICAgICAgICB2ID0gdi50b0lTT1N0cmluZygpO1xuICAgICAgICB9IGVsc2UgaWYgKHV0aWxzLmlzT2JqZWN0KHYpKSB7XG4gICAgICAgICAgdiA9IEpTT04uc3RyaW5naWZ5KHYpO1xuICAgICAgICB9XG4gICAgICAgIHBhcnRzLnB1c2goZW5jb2RlKGtleSkgKyAnPScgKyBlbmNvZGUodikpO1xuICAgICAgfSk7XG4gICAgfSk7XG5cbiAgICBzZXJpYWxpemVkUGFyYW1zID0gcGFydHMuam9pbignJicpO1xuICB9XG5cbiAgaWYgKHNlcmlhbGl6ZWRQYXJhbXMpIHtcbiAgICB1cmwgKz0gKHVybC5pbmRleE9mKCc/JykgPT09IC0xID8gJz8nIDogJyYnKSArIHNlcmlhbGl6ZWRQYXJhbXM7XG4gIH1cblxuICByZXR1cm4gdXJsO1xufTtcbiIsIid1c2Ugc3RyaWN0JztcblxudmFyIHV0aWxzID0gcmVxdWlyZSgnLi8uLi91dGlscycpO1xuXG4vLyBIZWFkZXJzIHdob3NlIGR1cGxpY2F0ZXMgYXJlIGlnbm9yZWQgYnkgbm9kZVxuLy8gYy5mLiBodHRwczovL25vZGVqcy5vcmcvYXBpL2h0dHAuaHRtbCNodHRwX21lc3NhZ2VfaGVhZGVyc1xudmFyIGlnbm9yZUR1cGxpY2F0ZU9mID0gW1xuICAnYWdlJywgJ2F1dGhvcml6YXRpb24nLCAnY29udGVudC1sZW5ndGgnLCAnY29udGVudC10eXBlJywgJ2V0YWcnLFxuICAnZXhwaXJlcycsICdmcm9tJywgJ2hvc3QnLCAnaWYtbW9kaWZpZWQtc2luY2UnLCAnaWYtdW5tb2RpZmllZC1zaW5jZScsXG4gICdsYXN0LW1vZGlmaWVkJywgJ2xvY2F0aW9uJywgJ21heC1mb3J3YXJkcycsICdwcm94eS1hdXRob3JpemF0aW9uJyxcbiAgJ3JlZmVyZXInLCAncmV0cnktYWZ0ZXInLCAndXNlci1hZ2VudCdcbl07XG5cbi8qKlxuICogUGFyc2UgaGVhZGVycyBpbnRvIGFuIG9iamVjdFxuICpcbiAqIGBgYFxuICogRGF0ZTogV2VkLCAyNyBBdWcgMjAxNCAwODo1ODo0OSBHTVRcbiAqIENvbnRlbnQtVHlwZTogYXBwbGljYXRpb24vanNvblxuICogQ29ubmVjdGlvbjoga2VlcC1hbGl2ZVxuICogVHJhbnNmZXItRW5jb2Rpbmc6IGNodW5rZWRcbiAqIGBgYFxuICpcbiAqIEBwYXJhbSB7U3RyaW5nfSBoZWFkZXJzIEhlYWRlcnMgbmVlZGluZyB0byBiZSBwYXJzZWRcbiAqIEByZXR1cm5zIHtPYmplY3R9IEhlYWRlcnMgcGFyc2VkIGludG8gYW4gb2JqZWN0XG4gKi9cbm1vZHVsZS5leHBvcnRzID0gZnVuY3Rpb24gcGFyc2VIZWFkZXJzKGhlYWRlcnMpIHtcbiAgdmFyIHBhcnNlZCA9IHt9O1xuICB2YXIga2V5O1xuICB2YXIgdmFsO1xuICB2YXIgaTtcblxuICBpZiAoIWhlYWRlcnMpIHsgcmV0dXJuIHBhcnNlZDsgfVxuXG4gIHV0aWxzLmZvckVhY2goaGVhZGVycy5zcGxpdCgnXFxuJyksIGZ1bmN0aW9uIHBhcnNlcihsaW5lKSB7XG4gICAgaSA9IGxpbmUuaW5kZXhPZignOicpO1xuICAgIGtleSA9IHV0aWxzLnRyaW0obGluZS5zdWJzdHIoMCwgaSkpLnRvTG93ZXJDYXNlKCk7XG4gICAgdmFsID0gdXRpbHMudHJpbShsaW5lLnN1YnN0cihpICsgMSkpO1xuXG4gICAgaWYgKGtleSkge1xuICAgICAgaWYgKHBhcnNlZFtrZXldICYmIGlnbm9yZUR1cGxpY2F0ZU9mLmluZGV4T2Yoa2V5KSA+PSAwKSB7XG4gICAgICAgIHJldHVybjtcbiAgICAgIH1cbiAgICAgIGlmIChrZXkgPT09ICdzZXQtY29va2llJykge1xuICAgICAgICBwYXJzZWRba2V5XSA9IChwYXJzZWRba2V5XSA/IHBhcnNlZFtrZXldIDogW10pLmNvbmNhdChbdmFsXSk7XG4gICAgICB9IGVsc2Uge1xuICAgICAgICBwYXJzZWRba2V5XSA9IHBhcnNlZFtrZXldID8gcGFyc2VkW2tleV0gKyAnLCAnICsgdmFsIDogdmFsO1xuICAgICAgfVxuICAgIH1cbiAgfSk7XG5cbiAgcmV0dXJuIHBhcnNlZDtcbn07XG4iLCIndXNlIHN0cmljdCc7XG5cbnZhciB1dGlscyA9IHJlcXVpcmUoJy4vLi4vdXRpbHMnKTtcblxubW9kdWxlLmV4cG9ydHMgPSAoXG4gIHV0aWxzLmlzU3RhbmRhcmRCcm93c2VyRW52KCkgP1xuXG4gIC8vIFN0YW5kYXJkIGJyb3dzZXIgZW52cyBoYXZlIGZ1bGwgc3VwcG9ydCBvZiB0aGUgQVBJcyBuZWVkZWQgdG8gdGVzdFxuICAvLyB3aGV0aGVyIHRoZSByZXF1ZXN0IFVSTCBpcyBvZiB0aGUgc2FtZSBvcmlnaW4gYXMgY3VycmVudCBsb2NhdGlvbi5cbiAgKGZ1bmN0aW9uIHN0YW5kYXJkQnJvd3NlckVudigpIHtcbiAgICB2YXIgbXNpZSA9IC8obXNpZXx0cmlkZW50KS9pLnRlc3QobmF2aWdhdG9yLnVzZXJBZ2VudCk7XG4gICAgdmFyIHVybFBhcnNpbmdOb2RlID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnYScpO1xuICAgIHZhciBvcmlnaW5VUkw7XG5cbiAgICAvKipcbiAgICAqIFBhcnNlIGEgVVJMIHRvIGRpc2NvdmVyIGl0J3MgY29tcG9uZW50c1xuICAgICpcbiAgICAqIEBwYXJhbSB7U3RyaW5nfSB1cmwgVGhlIFVSTCB0byBiZSBwYXJzZWRcbiAgICAqIEByZXR1cm5zIHtPYmplY3R9XG4gICAgKi9cbiAgICBmdW5jdGlvbiByZXNvbHZlVVJMKHVybCkge1xuICAgICAgdmFyIGhyZWYgPSB1cmw7XG5cbiAgICAgIGlmIChtc2llKSB7XG4gICAgICAgIC8vIElFIG5lZWRzIGF0dHJpYnV0ZSBzZXQgdHdpY2UgdG8gbm9ybWFsaXplIHByb3BlcnRpZXNcbiAgICAgICAgdXJsUGFyc2luZ05vZGUuc2V0QXR0cmlidXRlKCdocmVmJywgaHJlZik7XG4gICAgICAgIGhyZWYgPSB1cmxQYXJzaW5nTm9kZS5ocmVmO1xuICAgICAgfVxuXG4gICAgICB1cmxQYXJzaW5nTm9kZS5zZXRBdHRyaWJ1dGUoJ2hyZWYnLCBocmVmKTtcblxuICAgICAgLy8gdXJsUGFyc2luZ05vZGUgcHJvdmlkZXMgdGhlIFVybFV0aWxzIGludGVyZmFjZSAtIGh0dHA6Ly91cmwuc3BlYy53aGF0d2cub3JnLyN1cmx1dGlsc1xuICAgICAgcmV0dXJuIHtcbiAgICAgICAgaHJlZjogdXJsUGFyc2luZ05vZGUuaHJlZixcbiAgICAgICAgcHJvdG9jb2w6IHVybFBhcnNpbmdOb2RlLnByb3RvY29sID8gdXJsUGFyc2luZ05vZGUucHJvdG9jb2wucmVwbGFjZSgvOiQvLCAnJykgOiAnJyxcbiAgICAgICAgaG9zdDogdXJsUGFyc2luZ05vZGUuaG9zdCxcbiAgICAgICAgc2VhcmNoOiB1cmxQYXJzaW5nTm9kZS5zZWFyY2ggPyB1cmxQYXJzaW5nTm9kZS5zZWFyY2gucmVwbGFjZSgvXlxcPy8sICcnKSA6ICcnLFxuICAgICAgICBoYXNoOiB1cmxQYXJzaW5nTm9kZS5oYXNoID8gdXJsUGFyc2luZ05vZGUuaGFzaC5yZXBsYWNlKC9eIy8sICcnKSA6ICcnLFxuICAgICAgICBob3N0bmFtZTogdXJsUGFyc2luZ05vZGUuaG9zdG5hbWUsXG4gICAgICAgIHBvcnQ6IHVybFBhcnNpbmdOb2RlLnBvcnQsXG4gICAgICAgIHBhdGhuYW1lOiAodXJsUGFyc2luZ05vZGUucGF0aG5hbWUuY2hhckF0KDApID09PSAnLycpID9cbiAgICAgICAgICAgICAgICAgIHVybFBhcnNpbmdOb2RlLnBhdGhuYW1lIDpcbiAgICAgICAgICAgICAgICAgICcvJyArIHVybFBhcnNpbmdOb2RlLnBhdGhuYW1lXG4gICAgICB9O1xuICAgIH1cblxuICAgIG9yaWdpblVSTCA9IHJlc29sdmVVUkwod2luZG93LmxvY2F0aW9uLmhyZWYpO1xuXG4gICAgLyoqXG4gICAgKiBEZXRlcm1pbmUgaWYgYSBVUkwgc2hhcmVzIHRoZSBzYW1lIG9yaWdpbiBhcyB0aGUgY3VycmVudCBsb2NhdGlvblxuICAgICpcbiAgICAqIEBwYXJhbSB7U3RyaW5nfSByZXF1ZXN0VVJMIFRoZSBVUkwgdG8gdGVzdFxuICAgICogQHJldHVybnMge2Jvb2xlYW59IFRydWUgaWYgVVJMIHNoYXJlcyB0aGUgc2FtZSBvcmlnaW4sIG90aGVyd2lzZSBmYWxzZVxuICAgICovXG4gICAgcmV0dXJuIGZ1bmN0aW9uIGlzVVJMU2FtZU9yaWdpbihyZXF1ZXN0VVJMKSB7XG4gICAgICB2YXIgcGFyc2VkID0gKHV0aWxzLmlzU3RyaW5nKHJlcXVlc3RVUkwpKSA/IHJlc29sdmVVUkwocmVxdWVzdFVSTCkgOiByZXF1ZXN0VVJMO1xuICAgICAgcmV0dXJuIChwYXJzZWQucHJvdG9jb2wgPT09IG9yaWdpblVSTC5wcm90b2NvbCAmJlxuICAgICAgICAgICAgcGFyc2VkLmhvc3QgPT09IG9yaWdpblVSTC5ob3N0KTtcbiAgICB9O1xuICB9KSgpIDpcblxuICAvLyBOb24gc3RhbmRhcmQgYnJvd3NlciBlbnZzICh3ZWIgd29ya2VycywgcmVhY3QtbmF0aXZlKSBsYWNrIG5lZWRlZCBzdXBwb3J0LlxuICAoZnVuY3Rpb24gbm9uU3RhbmRhcmRCcm93c2VyRW52KCkge1xuICAgIHJldHVybiBmdW5jdGlvbiBpc1VSTFNhbWVPcmlnaW4oKSB7XG4gICAgICByZXR1cm4gdHJ1ZTtcbiAgICB9O1xuICB9KSgpXG4pO1xuIiwiJ3VzZSBzdHJpY3QnO1xuXG4vLyBidG9hIHBvbHlmaWxsIGZvciBJRTwxMCBjb3VydGVzeSBodHRwczovL2dpdGh1Yi5jb20vZGF2aWRjaGFtYmVycy9CYXNlNjQuanNcblxudmFyIGNoYXJzID0gJ0FCQ0RFRkdISUpLTE1OT1BRUlNUVVZXWFlaYWJjZGVmZ2hpamtsbW5vcHFyc3R1dnd4eXowMTIzNDU2Nzg5Ky89JztcblxuZnVuY3Rpb24gRSgpIHtcbiAgdGhpcy5tZXNzYWdlID0gJ1N0cmluZyBjb250YWlucyBhbiBpbnZhbGlkIGNoYXJhY3Rlcic7XG59XG5FLnByb3RvdHlwZSA9IG5ldyBFcnJvcjtcbkUucHJvdG90eXBlLmNvZGUgPSA1O1xuRS5wcm90b3R5cGUubmFtZSA9ICdJbnZhbGlkQ2hhcmFjdGVyRXJyb3InO1xuXG5mdW5jdGlvbiBidG9hKGlucHV0KSB7XG4gIHZhciBzdHIgPSBTdHJpbmcoaW5wdXQpO1xuICB2YXIgb3V0cHV0ID0gJyc7XG4gIGZvciAoXG4gICAgLy8gaW5pdGlhbGl6ZSByZXN1bHQgYW5kIGNvdW50ZXJcbiAgICB2YXIgYmxvY2ssIGNoYXJDb2RlLCBpZHggPSAwLCBtYXAgPSBjaGFycztcbiAgICAvLyBpZiB0aGUgbmV4dCBzdHIgaW5kZXggZG9lcyBub3QgZXhpc3Q6XG4gICAgLy8gICBjaGFuZ2UgdGhlIG1hcHBpbmcgdGFibGUgdG8gXCI9XCJcbiAgICAvLyAgIGNoZWNrIGlmIGQgaGFzIG5vIGZyYWN0aW9uYWwgZGlnaXRzXG4gICAgc3RyLmNoYXJBdChpZHggfCAwKSB8fCAobWFwID0gJz0nLCBpZHggJSAxKTtcbiAgICAvLyBcIjggLSBpZHggJSAxICogOFwiIGdlbmVyYXRlcyB0aGUgc2VxdWVuY2UgMiwgNCwgNiwgOFxuICAgIG91dHB1dCArPSBtYXAuY2hhckF0KDYzICYgYmxvY2sgPj4gOCAtIGlkeCAlIDEgKiA4KVxuICApIHtcbiAgICBjaGFyQ29kZSA9IHN0ci5jaGFyQ29kZUF0KGlkeCArPSAzIC8gNCk7XG4gICAgaWYgKGNoYXJDb2RlID4gMHhGRikge1xuICAgICAgdGhyb3cgbmV3IEUoKTtcbiAgICB9XG4gICAgYmxvY2sgPSBibG9jayA8PCA4IHwgY2hhckNvZGU7XG4gIH1cbiAgcmV0dXJuIG91dHB1dDtcbn1cblxubW9kdWxlLmV4cG9ydHMgPSBidG9hO1xuIiwiJ3VzZSBzdHJpY3QnO1xuXG52YXIgdXRpbHMgPSByZXF1aXJlKCcuLy4uL3V0aWxzJyk7XG5cbm1vZHVsZS5leHBvcnRzID0gKFxuICB1dGlscy5pc1N0YW5kYXJkQnJvd3NlckVudigpID9cblxuICAvLyBTdGFuZGFyZCBicm93c2VyIGVudnMgc3VwcG9ydCBkb2N1bWVudC5jb29raWVcbiAgKGZ1bmN0aW9uIHN0YW5kYXJkQnJvd3NlckVudigpIHtcbiAgICByZXR1cm4ge1xuICAgICAgd3JpdGU6IGZ1bmN0aW9uIHdyaXRlKG5hbWUsIHZhbHVlLCBleHBpcmVzLCBwYXRoLCBkb21haW4sIHNlY3VyZSkge1xuICAgICAgICB2YXIgY29va2llID0gW107XG4gICAgICAgIGNvb2tpZS5wdXNoKG5hbWUgKyAnPScgKyBlbmNvZGVVUklDb21wb25lbnQodmFsdWUpKTtcblxuICAgICAgICBpZiAodXRpbHMuaXNOdW1iZXIoZXhwaXJlcykpIHtcbiAgICAgICAgICBjb29raWUucHVzaCgnZXhwaXJlcz0nICsgbmV3IERhdGUoZXhwaXJlcykudG9HTVRTdHJpbmcoKSk7XG4gICAgICAgIH1cblxuICAgICAgICBpZiAodXRpbHMuaXNTdHJpbmcocGF0aCkpIHtcbiAgICAgICAgICBjb29raWUucHVzaCgncGF0aD0nICsgcGF0aCk7XG4gICAgICAgIH1cblxuICAgICAgICBpZiAodXRpbHMuaXNTdHJpbmcoZG9tYWluKSkge1xuICAgICAgICAgIGNvb2tpZS5wdXNoKCdkb21haW49JyArIGRvbWFpbik7XG4gICAgICAgIH1cblxuICAgICAgICBpZiAoc2VjdXJlID09PSB0cnVlKSB7XG4gICAgICAgICAgY29va2llLnB1c2goJ3NlY3VyZScpO1xuICAgICAgICB9XG5cbiAgICAgICAgZG9jdW1lbnQuY29va2llID0gY29va2llLmpvaW4oJzsgJyk7XG4gICAgICB9LFxuXG4gICAgICByZWFkOiBmdW5jdGlvbiByZWFkKG5hbWUpIHtcbiAgICAgICAgdmFyIG1hdGNoID0gZG9jdW1lbnQuY29va2llLm1hdGNoKG5ldyBSZWdFeHAoJyhefDtcXFxccyopKCcgKyBuYW1lICsgJyk9KFteO10qKScpKTtcbiAgICAgICAgcmV0dXJuIChtYXRjaCA/IGRlY29kZVVSSUNvbXBvbmVudChtYXRjaFszXSkgOiBudWxsKTtcbiAgICAgIH0sXG5cbiAgICAgIHJlbW92ZTogZnVuY3Rpb24gcmVtb3ZlKG5hbWUpIHtcbiAgICAgICAgdGhpcy53cml0ZShuYW1lLCAnJywgRGF0ZS5ub3coKSAtIDg2NDAwMDAwKTtcbiAgICAgIH1cbiAgICB9O1xuICB9KSgpIDpcblxuICAvLyBOb24gc3RhbmRhcmQgYnJvd3NlciBlbnYgKHdlYiB3b3JrZXJzLCByZWFjdC1uYXRpdmUpIGxhY2sgbmVlZGVkIHN1cHBvcnQuXG4gIChmdW5jdGlvbiBub25TdGFuZGFyZEJyb3dzZXJFbnYoKSB7XG4gICAgcmV0dXJuIHtcbiAgICAgIHdyaXRlOiBmdW5jdGlvbiB3cml0ZSgpIHt9LFxuICAgICAgcmVhZDogZnVuY3Rpb24gcmVhZCgpIHsgcmV0dXJuIG51bGw7IH0sXG4gICAgICByZW1vdmU6IGZ1bmN0aW9uIHJlbW92ZSgpIHt9XG4gICAgfTtcbiAgfSkoKVxuKTtcbiIsIid1c2Ugc3RyaWN0JztcblxudmFyIHV0aWxzID0gcmVxdWlyZSgnLi8uLi91dGlscycpO1xudmFyIHNldHRsZSA9IHJlcXVpcmUoJy4vLi4vY29yZS9zZXR0bGUnKTtcbnZhciBidWlsZFVSTCA9IHJlcXVpcmUoJy4vLi4vaGVscGVycy9idWlsZFVSTCcpO1xudmFyIHBhcnNlSGVhZGVycyA9IHJlcXVpcmUoJy4vLi4vaGVscGVycy9wYXJzZUhlYWRlcnMnKTtcbnZhciBpc1VSTFNhbWVPcmlnaW4gPSByZXF1aXJlKCcuLy4uL2hlbHBlcnMvaXNVUkxTYW1lT3JpZ2luJyk7XG52YXIgY3JlYXRlRXJyb3IgPSByZXF1aXJlKCcuLi9jb3JlL2NyZWF0ZUVycm9yJyk7XG52YXIgYnRvYSA9ICh0eXBlb2Ygd2luZG93ICE9PSAndW5kZWZpbmVkJyAmJiB3aW5kb3cuYnRvYSAmJiB3aW5kb3cuYnRvYS5iaW5kKHdpbmRvdykpIHx8IHJlcXVpcmUoJy4vLi4vaGVscGVycy9idG9hJyk7XG5cbm1vZHVsZS5leHBvcnRzID0gZnVuY3Rpb24geGhyQWRhcHRlcihjb25maWcpIHtcbiAgcmV0dXJuIG5ldyBQcm9taXNlKGZ1bmN0aW9uIGRpc3BhdGNoWGhyUmVxdWVzdChyZXNvbHZlLCByZWplY3QpIHtcbiAgICB2YXIgcmVxdWVzdERhdGEgPSBjb25maWcuZGF0YTtcbiAgICB2YXIgcmVxdWVzdEhlYWRlcnMgPSBjb25maWcuaGVhZGVycztcblxuICAgIGlmICh1dGlscy5pc0Zvcm1EYXRhKHJlcXVlc3REYXRhKSkge1xuICAgICAgZGVsZXRlIHJlcXVlc3RIZWFkZXJzWydDb250ZW50LVR5cGUnXTsgLy8gTGV0IHRoZSBicm93c2VyIHNldCBpdFxuICAgIH1cblxuICAgIHZhciByZXF1ZXN0ID0gbmV3IFhNTEh0dHBSZXF1ZXN0KCk7XG4gICAgdmFyIGxvYWRFdmVudCA9ICdvbnJlYWR5c3RhdGVjaGFuZ2UnO1xuICAgIHZhciB4RG9tYWluID0gZmFsc2U7XG5cbiAgICAvLyBGb3IgSUUgOC85IENPUlMgc3VwcG9ydFxuICAgIC8vIE9ubHkgc3VwcG9ydHMgUE9TVCBhbmQgR0VUIGNhbGxzIGFuZCBkb2Vzbid0IHJldHVybnMgdGhlIHJlc3BvbnNlIGhlYWRlcnMuXG4gICAgLy8gRE9OJ1QgZG8gdGhpcyBmb3IgdGVzdGluZyBiL2MgWE1MSHR0cFJlcXVlc3QgaXMgbW9ja2VkLCBub3QgWERvbWFpblJlcXVlc3QuXG4gICAgaWYgKHByb2Nlc3MuZW52Lk5PREVfRU5WICE9PSAndGVzdCcgJiZcbiAgICAgICAgdHlwZW9mIHdpbmRvdyAhPT0gJ3VuZGVmaW5lZCcgJiZcbiAgICAgICAgd2luZG93LlhEb21haW5SZXF1ZXN0ICYmICEoJ3dpdGhDcmVkZW50aWFscycgaW4gcmVxdWVzdCkgJiZcbiAgICAgICAgIWlzVVJMU2FtZU9yaWdpbihjb25maWcudXJsKSkge1xuICAgICAgcmVxdWVzdCA9IG5ldyB3aW5kb3cuWERvbWFpblJlcXVlc3QoKTtcbiAgICAgIGxvYWRFdmVudCA9ICdvbmxvYWQnO1xuICAgICAgeERvbWFpbiA9IHRydWU7XG4gICAgICByZXF1ZXN0Lm9ucHJvZ3Jlc3MgPSBmdW5jdGlvbiBoYW5kbGVQcm9ncmVzcygpIHt9O1xuICAgICAgcmVxdWVzdC5vbnRpbWVvdXQgPSBmdW5jdGlvbiBoYW5kbGVUaW1lb3V0KCkge307XG4gICAgfVxuXG4gICAgLy8gSFRUUCBiYXNpYyBhdXRoZW50aWNhdGlvblxuICAgIGlmIChjb25maWcuYXV0aCkge1xuICAgICAgdmFyIHVzZXJuYW1lID0gY29uZmlnLmF1dGgudXNlcm5hbWUgfHwgJyc7XG4gICAgICB2YXIgcGFzc3dvcmQgPSBjb25maWcuYXV0aC5wYXNzd29yZCB8fCAnJztcbiAgICAgIHJlcXVlc3RIZWFkZXJzLkF1dGhvcml6YXRpb24gPSAnQmFzaWMgJyArIGJ0b2EodXNlcm5hbWUgKyAnOicgKyBwYXNzd29yZCk7XG4gICAgfVxuXG4gICAgcmVxdWVzdC5vcGVuKGNvbmZpZy5tZXRob2QudG9VcHBlckNhc2UoKSwgYnVpbGRVUkwoY29uZmlnLnVybCwgY29uZmlnLnBhcmFtcywgY29uZmlnLnBhcmFtc1NlcmlhbGl6ZXIpLCB0cnVlKTtcblxuICAgIC8vIFNldCB0aGUgcmVxdWVzdCB0aW1lb3V0IGluIE1TXG4gICAgcmVxdWVzdC50aW1lb3V0ID0gY29uZmlnLnRpbWVvdXQ7XG5cbiAgICAvLyBMaXN0ZW4gZm9yIHJlYWR5IHN0YXRlXG4gICAgcmVxdWVzdFtsb2FkRXZlbnRdID0gZnVuY3Rpb24gaGFuZGxlTG9hZCgpIHtcbiAgICAgIGlmICghcmVxdWVzdCB8fCAocmVxdWVzdC5yZWFkeVN0YXRlICE9PSA0ICYmICF4RG9tYWluKSkge1xuICAgICAgICByZXR1cm47XG4gICAgICB9XG5cbiAgICAgIC8vIFRoZSByZXF1ZXN0IGVycm9yZWQgb3V0IGFuZCB3ZSBkaWRuJ3QgZ2V0IGEgcmVzcG9uc2UsIHRoaXMgd2lsbCBiZVxuICAgICAgLy8gaGFuZGxlZCBieSBvbmVycm9yIGluc3RlYWRcbiAgICAgIC8vIFdpdGggb25lIGV4Y2VwdGlvbjogcmVxdWVzdCB0aGF0IHVzaW5nIGZpbGU6IHByb3RvY29sLCBtb3N0IGJyb3dzZXJzXG4gICAgICAvLyB3aWxsIHJldHVybiBzdGF0dXMgYXMgMCBldmVuIHRob3VnaCBpdCdzIGEgc3VjY2Vzc2Z1bCByZXF1ZXN0XG4gICAgICBpZiAocmVxdWVzdC5zdGF0dXMgPT09IDAgJiYgIShyZXF1ZXN0LnJlc3BvbnNlVVJMICYmIHJlcXVlc3QucmVzcG9uc2VVUkwuaW5kZXhPZignZmlsZTonKSA9PT0gMCkpIHtcbiAgICAgICAgcmV0dXJuO1xuICAgICAgfVxuXG4gICAgICAvLyBQcmVwYXJlIHRoZSByZXNwb25zZVxuICAgICAgdmFyIHJlc3BvbnNlSGVhZGVycyA9ICdnZXRBbGxSZXNwb25zZUhlYWRlcnMnIGluIHJlcXVlc3QgPyBwYXJzZUhlYWRlcnMocmVxdWVzdC5nZXRBbGxSZXNwb25zZUhlYWRlcnMoKSkgOiBudWxsO1xuICAgICAgdmFyIHJlc3BvbnNlRGF0YSA9ICFjb25maWcucmVzcG9uc2VUeXBlIHx8IGNvbmZpZy5yZXNwb25zZVR5cGUgPT09ICd0ZXh0JyA/IHJlcXVlc3QucmVzcG9uc2VUZXh0IDogcmVxdWVzdC5yZXNwb25zZTtcbiAgICAgIHZhciByZXNwb25zZSA9IHtcbiAgICAgICAgZGF0YTogcmVzcG9uc2VEYXRhLFxuICAgICAgICAvLyBJRSBzZW5kcyAxMjIzIGluc3RlYWQgb2YgMjA0IChodHRwczovL2dpdGh1Yi5jb20vYXhpb3MvYXhpb3MvaXNzdWVzLzIwMSlcbiAgICAgICAgc3RhdHVzOiByZXF1ZXN0LnN0YXR1cyA9PT0gMTIyMyA/IDIwNCA6IHJlcXVlc3Quc3RhdHVzLFxuICAgICAgICBzdGF0dXNUZXh0OiByZXF1ZXN0LnN0YXR1cyA9PT0gMTIyMyA/ICdObyBDb250ZW50JyA6IHJlcXVlc3Quc3RhdHVzVGV4dCxcbiAgICAgICAgaGVhZGVyczogcmVzcG9uc2VIZWFkZXJzLFxuICAgICAgICBjb25maWc6IGNvbmZpZyxcbiAgICAgICAgcmVxdWVzdDogcmVxdWVzdFxuICAgICAgfTtcblxuICAgICAgc2V0dGxlKHJlc29sdmUsIHJlamVjdCwgcmVzcG9uc2UpO1xuXG4gICAgICAvLyBDbGVhbiB1cCByZXF1ZXN0XG4gICAgICByZXF1ZXN0ID0gbnVsbDtcbiAgICB9O1xuXG4gICAgLy8gSGFuZGxlIGxvdyBsZXZlbCBuZXR3b3JrIGVycm9yc1xuICAgIHJlcXVlc3Qub25lcnJvciA9IGZ1bmN0aW9uIGhhbmRsZUVycm9yKCkge1xuICAgICAgLy8gUmVhbCBlcnJvcnMgYXJlIGhpZGRlbiBmcm9tIHVzIGJ5IHRoZSBicm93c2VyXG4gICAgICAvLyBvbmVycm9yIHNob3VsZCBvbmx5IGZpcmUgaWYgaXQncyBhIG5ldHdvcmsgZXJyb3JcbiAgICAgIHJlamVjdChjcmVhdGVFcnJvcignTmV0d29yayBFcnJvcicsIGNvbmZpZywgbnVsbCwgcmVxdWVzdCkpO1xuXG4gICAgICAvLyBDbGVhbiB1cCByZXF1ZXN0XG4gICAgICByZXF1ZXN0ID0gbnVsbDtcbiAgICB9O1xuXG4gICAgLy8gSGFuZGxlIHRpbWVvdXRcbiAgICByZXF1ZXN0Lm9udGltZW91dCA9IGZ1bmN0aW9uIGhhbmRsZVRpbWVvdXQoKSB7XG4gICAgICByZWplY3QoY3JlYXRlRXJyb3IoJ3RpbWVvdXQgb2YgJyArIGNvbmZpZy50aW1lb3V0ICsgJ21zIGV4Y2VlZGVkJywgY29uZmlnLCAnRUNPTk5BQk9SVEVEJyxcbiAgICAgICAgcmVxdWVzdCkpO1xuXG4gICAgICAvLyBDbGVhbiB1cCByZXF1ZXN0XG4gICAgICByZXF1ZXN0ID0gbnVsbDtcbiAgICB9O1xuXG4gICAgLy8gQWRkIHhzcmYgaGVhZGVyXG4gICAgLy8gVGhpcyBpcyBvbmx5IGRvbmUgaWYgcnVubmluZyBpbiBhIHN0YW5kYXJkIGJyb3dzZXIgZW52aXJvbm1lbnQuXG4gICAgLy8gU3BlY2lmaWNhbGx5IG5vdCBpZiB3ZSdyZSBpbiBhIHdlYiB3b3JrZXIsIG9yIHJlYWN0LW5hdGl2ZS5cbiAgICBpZiAodXRpbHMuaXNTdGFuZGFyZEJyb3dzZXJFbnYoKSkge1xuICAgICAgdmFyIGNvb2tpZXMgPSByZXF1aXJlKCcuLy4uL2hlbHBlcnMvY29va2llcycpO1xuXG4gICAgICAvLyBBZGQgeHNyZiBoZWFkZXJcbiAgICAgIHZhciB4c3JmVmFsdWUgPSAoY29uZmlnLndpdGhDcmVkZW50aWFscyB8fCBpc1VSTFNhbWVPcmlnaW4oY29uZmlnLnVybCkpICYmIGNvbmZpZy54c3JmQ29va2llTmFtZSA/XG4gICAgICAgICAgY29va2llcy5yZWFkKGNvbmZpZy54c3JmQ29va2llTmFtZSkgOlxuICAgICAgICAgIHVuZGVmaW5lZDtcblxuICAgICAgaWYgKHhzcmZWYWx1ZSkge1xuICAgICAgICByZXF1ZXN0SGVhZGVyc1tjb25maWcueHNyZkhlYWRlck5hbWVdID0geHNyZlZhbHVlO1xuICAgICAgfVxuICAgIH1cblxuICAgIC8vIEFkZCBoZWFkZXJzIHRvIHRoZSByZXF1ZXN0XG4gICAgaWYgKCdzZXRSZXF1ZXN0SGVhZGVyJyBpbiByZXF1ZXN0KSB7XG4gICAgICB1dGlscy5mb3JFYWNoKHJlcXVlc3RIZWFkZXJzLCBmdW5jdGlvbiBzZXRSZXF1ZXN0SGVhZGVyKHZhbCwga2V5KSB7XG4gICAgICAgIGlmICh0eXBlb2YgcmVxdWVzdERhdGEgPT09ICd1bmRlZmluZWQnICYmIGtleS50b0xvd2VyQ2FzZSgpID09PSAnY29udGVudC10eXBlJykge1xuICAgICAgICAgIC8vIFJlbW92ZSBDb250ZW50LVR5cGUgaWYgZGF0YSBpcyB1bmRlZmluZWRcbiAgICAgICAgICBkZWxldGUgcmVxdWVzdEhlYWRlcnNba2V5XTtcbiAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICAvLyBPdGhlcndpc2UgYWRkIGhlYWRlciB0byB0aGUgcmVxdWVzdFxuICAgICAgICAgIHJlcXVlc3Quc2V0UmVxdWVzdEhlYWRlcihrZXksIHZhbCk7XG4gICAgICAgIH1cbiAgICAgIH0pO1xuICAgIH1cblxuICAgIC8vIEFkZCB3aXRoQ3JlZGVudGlhbHMgdG8gcmVxdWVzdCBpZiBuZWVkZWRcbiAgICBpZiAoY29uZmlnLndpdGhDcmVkZW50aWFscykge1xuICAgICAgcmVxdWVzdC53aXRoQ3JlZGVudGlhbHMgPSB0cnVlO1xuICAgIH1cblxuICAgIC8vIEFkZCByZXNwb25zZVR5cGUgdG8gcmVxdWVzdCBpZiBuZWVkZWRcbiAgICBpZiAoY29uZmlnLnJlc3BvbnNlVHlwZSkge1xuICAgICAgdHJ5IHtcbiAgICAgICAgcmVxdWVzdC5yZXNwb25zZVR5cGUgPSBjb25maWcucmVzcG9uc2VUeXBlO1xuICAgICAgfSBjYXRjaCAoZSkge1xuICAgICAgICAvLyBFeHBlY3RlZCBET01FeGNlcHRpb24gdGhyb3duIGJ5IGJyb3dzZXJzIG5vdCBjb21wYXRpYmxlIFhNTEh0dHBSZXF1ZXN0IExldmVsIDIuXG4gICAgICAgIC8vIEJ1dCwgdGhpcyBjYW4gYmUgc3VwcHJlc3NlZCBmb3IgJ2pzb24nIHR5cGUgYXMgaXQgY2FuIGJlIHBhcnNlZCBieSBkZWZhdWx0ICd0cmFuc2Zvcm1SZXNwb25zZScgZnVuY3Rpb24uXG4gICAgICAgIGlmIChjb25maWcucmVzcG9uc2VUeXBlICE9PSAnanNvbicpIHtcbiAgICAgICAgICB0aHJvdyBlO1xuICAgICAgICB9XG4gICAgICB9XG4gICAgfVxuXG4gICAgLy8gSGFuZGxlIHByb2dyZXNzIGlmIG5lZWRlZFxuICAgIGlmICh0eXBlb2YgY29uZmlnLm9uRG93bmxvYWRQcm9ncmVzcyA9PT0gJ2Z1bmN0aW9uJykge1xuICAgICAgcmVxdWVzdC5hZGRFdmVudExpc3RlbmVyKCdwcm9ncmVzcycsIGNvbmZpZy5vbkRvd25sb2FkUHJvZ3Jlc3MpO1xuICAgIH1cblxuICAgIC8vIE5vdCBhbGwgYnJvd3NlcnMgc3VwcG9ydCB1cGxvYWQgZXZlbnRzXG4gICAgaWYgKHR5cGVvZiBjb25maWcub25VcGxvYWRQcm9ncmVzcyA9PT0gJ2Z1bmN0aW9uJyAmJiByZXF1ZXN0LnVwbG9hZCkge1xuICAgICAgcmVxdWVzdC51cGxvYWQuYWRkRXZlbnRMaXN0ZW5lcigncHJvZ3Jlc3MnLCBjb25maWcub25VcGxvYWRQcm9ncmVzcyk7XG4gICAgfVxuXG4gICAgaWYgKGNvbmZpZy5jYW5jZWxUb2tlbikge1xuICAgICAgLy8gSGFuZGxlIGNhbmNlbGxhdGlvblxuICAgICAgY29uZmlnLmNhbmNlbFRva2VuLnByb21pc2UudGhlbihmdW5jdGlvbiBvbkNhbmNlbGVkKGNhbmNlbCkge1xuICAgICAgICBpZiAoIXJlcXVlc3QpIHtcbiAgICAgICAgICByZXR1cm47XG4gICAgICAgIH1cblxuICAgICAgICByZXF1ZXN0LmFib3J0KCk7XG4gICAgICAgIHJlamVjdChjYW5jZWwpO1xuICAgICAgICAvLyBDbGVhbiB1cCByZXF1ZXN0XG4gICAgICAgIHJlcXVlc3QgPSBudWxsO1xuICAgICAgfSk7XG4gICAgfVxuXG4gICAgaWYgKHJlcXVlc3REYXRhID09PSB1bmRlZmluZWQpIHtcbiAgICAgIHJlcXVlc3REYXRhID0gbnVsbDtcbiAgICB9XG5cbiAgICAvLyBTZW5kIHRoZSByZXF1ZXN0XG4gICAgcmVxdWVzdC5zZW5kKHJlcXVlc3REYXRhKTtcbiAgfSk7XG59O1xuIiwiJ3VzZSBzdHJpY3QnO1xuXG52YXIgdXRpbHMgPSByZXF1aXJlKCcuL3V0aWxzJyk7XG52YXIgbm9ybWFsaXplSGVhZGVyTmFtZSA9IHJlcXVpcmUoJy4vaGVscGVycy9ub3JtYWxpemVIZWFkZXJOYW1lJyk7XG5cbnZhciBERUZBVUxUX0NPTlRFTlRfVFlQRSA9IHtcbiAgJ0NvbnRlbnQtVHlwZSc6ICdhcHBsaWNhdGlvbi94LXd3dy1mb3JtLXVybGVuY29kZWQnXG59O1xuXG5mdW5jdGlvbiBzZXRDb250ZW50VHlwZUlmVW5zZXQoaGVhZGVycywgdmFsdWUpIHtcbiAgaWYgKCF1dGlscy5pc1VuZGVmaW5lZChoZWFkZXJzKSAmJiB1dGlscy5pc1VuZGVmaW5lZChoZWFkZXJzWydDb250ZW50LVR5cGUnXSkpIHtcbiAgICBoZWFkZXJzWydDb250ZW50LVR5cGUnXSA9IHZhbHVlO1xuICB9XG59XG5cbmZ1bmN0aW9uIGdldERlZmF1bHRBZGFwdGVyKCkge1xuICB2YXIgYWRhcHRlcjtcbiAgaWYgKHR5cGVvZiBYTUxIdHRwUmVxdWVzdCAhPT0gJ3VuZGVmaW5lZCcpIHtcbiAgICAvLyBGb3IgYnJvd3NlcnMgdXNlIFhIUiBhZGFwdGVyXG4gICAgYWRhcHRlciA9IHJlcXVpcmUoJy4vYWRhcHRlcnMveGhyJyk7XG4gIH0gZWxzZSBpZiAodHlwZW9mIHByb2Nlc3MgIT09ICd1bmRlZmluZWQnKSB7XG4gICAgLy8gRm9yIG5vZGUgdXNlIEhUVFAgYWRhcHRlclxuICAgIGFkYXB0ZXIgPSByZXF1aXJlKCcuL2FkYXB0ZXJzL2h0dHAnKTtcbiAgfVxuICByZXR1cm4gYWRhcHRlcjtcbn1cblxudmFyIGRlZmF1bHRzID0ge1xuICBhZGFwdGVyOiBnZXREZWZhdWx0QWRhcHRlcigpLFxuXG4gIHRyYW5zZm9ybVJlcXVlc3Q6IFtmdW5jdGlvbiB0cmFuc2Zvcm1SZXF1ZXN0KGRhdGEsIGhlYWRlcnMpIHtcbiAgICBub3JtYWxpemVIZWFkZXJOYW1lKGhlYWRlcnMsICdDb250ZW50LVR5cGUnKTtcbiAgICBpZiAodXRpbHMuaXNGb3JtRGF0YShkYXRhKSB8fFxuICAgICAgdXRpbHMuaXNBcnJheUJ1ZmZlcihkYXRhKSB8fFxuICAgICAgdXRpbHMuaXNCdWZmZXIoZGF0YSkgfHxcbiAgICAgIHV0aWxzLmlzU3RyZWFtKGRhdGEpIHx8XG4gICAgICB1dGlscy5pc0ZpbGUoZGF0YSkgfHxcbiAgICAgIHV0aWxzLmlzQmxvYihkYXRhKVxuICAgICkge1xuICAgICAgcmV0dXJuIGRhdGE7XG4gICAgfVxuICAgIGlmICh1dGlscy5pc0FycmF5QnVmZmVyVmlldyhkYXRhKSkge1xuICAgICAgcmV0dXJuIGRhdGEuYnVmZmVyO1xuICAgIH1cbiAgICBpZiAodXRpbHMuaXNVUkxTZWFyY2hQYXJhbXMoZGF0YSkpIHtcbiAgICAgIHNldENvbnRlbnRUeXBlSWZVbnNldChoZWFkZXJzLCAnYXBwbGljYXRpb24veC13d3ctZm9ybS11cmxlbmNvZGVkO2NoYXJzZXQ9dXRmLTgnKTtcbiAgICAgIHJldHVybiBkYXRhLnRvU3RyaW5nKCk7XG4gICAgfVxuICAgIGlmICh1dGlscy5pc09iamVjdChkYXRhKSkge1xuICAgICAgc2V0Q29udGVudFR5cGVJZlVuc2V0KGhlYWRlcnMsICdhcHBsaWNhdGlvbi9qc29uO2NoYXJzZXQ9dXRmLTgnKTtcbiAgICAgIHJldHVybiBKU09OLnN0cmluZ2lmeShkYXRhKTtcbiAgICB9XG4gICAgcmV0dXJuIGRhdGE7XG4gIH1dLFxuXG4gIHRyYW5zZm9ybVJlc3BvbnNlOiBbZnVuY3Rpb24gdHJhbnNmb3JtUmVzcG9uc2UoZGF0YSkge1xuICAgIC8qZXNsaW50IG5vLXBhcmFtLXJlYXNzaWduOjAqL1xuICAgIGlmICh0eXBlb2YgZGF0YSA9PT0gJ3N0cmluZycpIHtcbiAgICAgIHRyeSB7XG4gICAgICAgIGRhdGEgPSBKU09OLnBhcnNlKGRhdGEpO1xuICAgICAgfSBjYXRjaCAoZSkgeyAvKiBJZ25vcmUgKi8gfVxuICAgIH1cbiAgICByZXR1cm4gZGF0YTtcbiAgfV0sXG5cbiAgdGltZW91dDogMCxcblxuICB4c3JmQ29va2llTmFtZTogJ1hTUkYtVE9LRU4nLFxuICB4c3JmSGVhZGVyTmFtZTogJ1gtWFNSRi1UT0tFTicsXG5cbiAgbWF4Q29udGVudExlbmd0aDogLTEsXG5cbiAgdmFsaWRhdGVTdGF0dXM6IGZ1bmN0aW9uIHZhbGlkYXRlU3RhdHVzKHN0YXR1cykge1xuICAgIHJldHVybiBzdGF0dXMgPj0gMjAwICYmIHN0YXR1cyA8IDMwMDtcbiAgfVxufTtcblxuZGVmYXVsdHMuaGVhZGVycyA9IHtcbiAgY29tbW9uOiB7XG4gICAgJ0FjY2VwdCc6ICdhcHBsaWNhdGlvbi9qc29uLCB0ZXh0L3BsYWluLCAqLyonXG4gIH1cbn07XG5cbnV0aWxzLmZvckVhY2goWydkZWxldGUnLCAnZ2V0JywgJ2hlYWQnXSwgZnVuY3Rpb24gZm9yRWFjaE1ldGhvZE5vRGF0YShtZXRob2QpIHtcbiAgZGVmYXVsdHMuaGVhZGVyc1ttZXRob2RdID0ge307XG59KTtcblxudXRpbHMuZm9yRWFjaChbJ3Bvc3QnLCAncHV0JywgJ3BhdGNoJ10sIGZ1bmN0aW9uIGZvckVhY2hNZXRob2RXaXRoRGF0YShtZXRob2QpIHtcbiAgZGVmYXVsdHMuaGVhZGVyc1ttZXRob2RdID0gdXRpbHMubWVyZ2UoREVGQVVMVF9DT05URU5UX1RZUEUpO1xufSk7XG5cbm1vZHVsZS5leHBvcnRzID0gZGVmYXVsdHM7XG4iLCIndXNlIHN0cmljdCc7XG5cbnZhciB1dGlscyA9IHJlcXVpcmUoJy4vLi4vdXRpbHMnKTtcblxuZnVuY3Rpb24gSW50ZXJjZXB0b3JNYW5hZ2VyKCkge1xuICB0aGlzLmhhbmRsZXJzID0gW107XG59XG5cbi8qKlxuICogQWRkIGEgbmV3IGludGVyY2VwdG9yIHRvIHRoZSBzdGFja1xuICpcbiAqIEBwYXJhbSB7RnVuY3Rpb259IGZ1bGZpbGxlZCBUaGUgZnVuY3Rpb24gdG8gaGFuZGxlIGB0aGVuYCBmb3IgYSBgUHJvbWlzZWBcbiAqIEBwYXJhbSB7RnVuY3Rpb259IHJlamVjdGVkIFRoZSBmdW5jdGlvbiB0byBoYW5kbGUgYHJlamVjdGAgZm9yIGEgYFByb21pc2VgXG4gKlxuICogQHJldHVybiB7TnVtYmVyfSBBbiBJRCB1c2VkIHRvIHJlbW92ZSBpbnRlcmNlcHRvciBsYXRlclxuICovXG5JbnRlcmNlcHRvck1hbmFnZXIucHJvdG90eXBlLnVzZSA9IGZ1bmN0aW9uIHVzZShmdWxmaWxsZWQsIHJlamVjdGVkKSB7XG4gIHRoaXMuaGFuZGxlcnMucHVzaCh7XG4gICAgZnVsZmlsbGVkOiBmdWxmaWxsZWQsXG4gICAgcmVqZWN0ZWQ6IHJlamVjdGVkXG4gIH0pO1xuICByZXR1cm4gdGhpcy5oYW5kbGVycy5sZW5ndGggLSAxO1xufTtcblxuLyoqXG4gKiBSZW1vdmUgYW4gaW50ZXJjZXB0b3IgZnJvbSB0aGUgc3RhY2tcbiAqXG4gKiBAcGFyYW0ge051bWJlcn0gaWQgVGhlIElEIHRoYXQgd2FzIHJldHVybmVkIGJ5IGB1c2VgXG4gKi9cbkludGVyY2VwdG9yTWFuYWdlci5wcm90b3R5cGUuZWplY3QgPSBmdW5jdGlvbiBlamVjdChpZCkge1xuICBpZiAodGhpcy5oYW5kbGVyc1tpZF0pIHtcbiAgICB0aGlzLmhhbmRsZXJzW2lkXSA9IG51bGw7XG4gIH1cbn07XG5cbi8qKlxuICogSXRlcmF0ZSBvdmVyIGFsbCB0aGUgcmVnaXN0ZXJlZCBpbnRlcmNlcHRvcnNcbiAqXG4gKiBUaGlzIG1ldGhvZCBpcyBwYXJ0aWN1bGFybHkgdXNlZnVsIGZvciBza2lwcGluZyBvdmVyIGFueVxuICogaW50ZXJjZXB0b3JzIHRoYXQgbWF5IGhhdmUgYmVjb21lIGBudWxsYCBjYWxsaW5nIGBlamVjdGAuXG4gKlxuICogQHBhcmFtIHtGdW5jdGlvbn0gZm4gVGhlIGZ1bmN0aW9uIHRvIGNhbGwgZm9yIGVhY2ggaW50ZXJjZXB0b3JcbiAqL1xuSW50ZXJjZXB0b3JNYW5hZ2VyLnByb3RvdHlwZS5mb3JFYWNoID0gZnVuY3Rpb24gZm9yRWFjaChmbikge1xuICB1dGlscy5mb3JFYWNoKHRoaXMuaGFuZGxlcnMsIGZ1bmN0aW9uIGZvckVhY2hIYW5kbGVyKGgpIHtcbiAgICBpZiAoaCAhPT0gbnVsbCkge1xuICAgICAgZm4oaCk7XG4gICAgfVxuICB9KTtcbn07XG5cbm1vZHVsZS5leHBvcnRzID0gSW50ZXJjZXB0b3JNYW5hZ2VyO1xuIiwiJ3VzZSBzdHJpY3QnO1xuXG52YXIgdXRpbHMgPSByZXF1aXJlKCcuLy4uL3V0aWxzJyk7XG5cbi8qKlxuICogVHJhbnNmb3JtIHRoZSBkYXRhIGZvciBhIHJlcXVlc3Qgb3IgYSByZXNwb25zZVxuICpcbiAqIEBwYXJhbSB7T2JqZWN0fFN0cmluZ30gZGF0YSBUaGUgZGF0YSB0byBiZSB0cmFuc2Zvcm1lZFxuICogQHBhcmFtIHtBcnJheX0gaGVhZGVycyBUaGUgaGVhZGVycyBmb3IgdGhlIHJlcXVlc3Qgb3IgcmVzcG9uc2VcbiAqIEBwYXJhbSB7QXJyYXl8RnVuY3Rpb259IGZucyBBIHNpbmdsZSBmdW5jdGlvbiBvciBBcnJheSBvZiBmdW5jdGlvbnNcbiAqIEByZXR1cm5zIHsqfSBUaGUgcmVzdWx0aW5nIHRyYW5zZm9ybWVkIGRhdGFcbiAqL1xubW9kdWxlLmV4cG9ydHMgPSBmdW5jdGlvbiB0cmFuc2Zvcm1EYXRhKGRhdGEsIGhlYWRlcnMsIGZucykge1xuICAvKmVzbGludCBuby1wYXJhbS1yZWFzc2lnbjowKi9cbiAgdXRpbHMuZm9yRWFjaChmbnMsIGZ1bmN0aW9uIHRyYW5zZm9ybShmbikge1xuICAgIGRhdGEgPSBmbihkYXRhLCBoZWFkZXJzKTtcbiAgfSk7XG5cbiAgcmV0dXJuIGRhdGE7XG59O1xuIiwiJ3VzZSBzdHJpY3QnO1xuXG5tb2R1bGUuZXhwb3J0cyA9IGZ1bmN0aW9uIGlzQ2FuY2VsKHZhbHVlKSB7XG4gIHJldHVybiAhISh2YWx1ZSAmJiB2YWx1ZS5fX0NBTkNFTF9fKTtcbn07XG4iLCIndXNlIHN0cmljdCc7XG5cbi8qKlxuICogRGV0ZXJtaW5lcyB3aGV0aGVyIHRoZSBzcGVjaWZpZWQgVVJMIGlzIGFic29sdXRlXG4gKlxuICogQHBhcmFtIHtzdHJpbmd9IHVybCBUaGUgVVJMIHRvIHRlc3RcbiAqIEByZXR1cm5zIHtib29sZWFufSBUcnVlIGlmIHRoZSBzcGVjaWZpZWQgVVJMIGlzIGFic29sdXRlLCBvdGhlcndpc2UgZmFsc2VcbiAqL1xubW9kdWxlLmV4cG9ydHMgPSBmdW5jdGlvbiBpc0Fic29sdXRlVVJMKHVybCkge1xuICAvLyBBIFVSTCBpcyBjb25zaWRlcmVkIGFic29sdXRlIGlmIGl0IGJlZ2lucyB3aXRoIFwiPHNjaGVtZT46Ly9cIiBvciBcIi8vXCIgKHByb3RvY29sLXJlbGF0aXZlIFVSTCkuXG4gIC8vIFJGQyAzOTg2IGRlZmluZXMgc2NoZW1lIG5hbWUgYXMgYSBzZXF1ZW5jZSBvZiBjaGFyYWN0ZXJzIGJlZ2lubmluZyB3aXRoIGEgbGV0dGVyIGFuZCBmb2xsb3dlZFxuICAvLyBieSBhbnkgY29tYmluYXRpb24gb2YgbGV0dGVycywgZGlnaXRzLCBwbHVzLCBwZXJpb2QsIG9yIGh5cGhlbi5cbiAgcmV0dXJuIC9eKFthLXpdW2EtelxcZFxcK1xcLVxcLl0qOik/XFwvXFwvL2kudGVzdCh1cmwpO1xufTtcbiIsIid1c2Ugc3RyaWN0JztcblxuLyoqXG4gKiBDcmVhdGVzIGEgbmV3IFVSTCBieSBjb21iaW5pbmcgdGhlIHNwZWNpZmllZCBVUkxzXG4gKlxuICogQHBhcmFtIHtzdHJpbmd9IGJhc2VVUkwgVGhlIGJhc2UgVVJMXG4gKiBAcGFyYW0ge3N0cmluZ30gcmVsYXRpdmVVUkwgVGhlIHJlbGF0aXZlIFVSTFxuICogQHJldHVybnMge3N0cmluZ30gVGhlIGNvbWJpbmVkIFVSTFxuICovXG5tb2R1bGUuZXhwb3J0cyA9IGZ1bmN0aW9uIGNvbWJpbmVVUkxzKGJhc2VVUkwsIHJlbGF0aXZlVVJMKSB7XG4gIHJldHVybiByZWxhdGl2ZVVSTFxuICAgID8gYmFzZVVSTC5yZXBsYWNlKC9cXC8rJC8sICcnKSArICcvJyArIHJlbGF0aXZlVVJMLnJlcGxhY2UoL15cXC8rLywgJycpXG4gICAgOiBiYXNlVVJMO1xufTtcbiIsIid1c2Ugc3RyaWN0JztcblxudmFyIHV0aWxzID0gcmVxdWlyZSgnLi8uLi91dGlscycpO1xudmFyIHRyYW5zZm9ybURhdGEgPSByZXF1aXJlKCcuL3RyYW5zZm9ybURhdGEnKTtcbnZhciBpc0NhbmNlbCA9IHJlcXVpcmUoJy4uL2NhbmNlbC9pc0NhbmNlbCcpO1xudmFyIGRlZmF1bHRzID0gcmVxdWlyZSgnLi4vZGVmYXVsdHMnKTtcbnZhciBpc0Fic29sdXRlVVJMID0gcmVxdWlyZSgnLi8uLi9oZWxwZXJzL2lzQWJzb2x1dGVVUkwnKTtcbnZhciBjb21iaW5lVVJMcyA9IHJlcXVpcmUoJy4vLi4vaGVscGVycy9jb21iaW5lVVJMcycpO1xuXG4vKipcbiAqIFRocm93cyBhIGBDYW5jZWxgIGlmIGNhbmNlbGxhdGlvbiBoYXMgYmVlbiByZXF1ZXN0ZWQuXG4gKi9cbmZ1bmN0aW9uIHRocm93SWZDYW5jZWxsYXRpb25SZXF1ZXN0ZWQoY29uZmlnKSB7XG4gIGlmIChjb25maWcuY2FuY2VsVG9rZW4pIHtcbiAgICBjb25maWcuY2FuY2VsVG9rZW4udGhyb3dJZlJlcXVlc3RlZCgpO1xuICB9XG59XG5cbi8qKlxuICogRGlzcGF0Y2ggYSByZXF1ZXN0IHRvIHRoZSBzZXJ2ZXIgdXNpbmcgdGhlIGNvbmZpZ3VyZWQgYWRhcHRlci5cbiAqXG4gKiBAcGFyYW0ge29iamVjdH0gY29uZmlnIFRoZSBjb25maWcgdGhhdCBpcyB0byBiZSB1c2VkIGZvciB0aGUgcmVxdWVzdFxuICogQHJldHVybnMge1Byb21pc2V9IFRoZSBQcm9taXNlIHRvIGJlIGZ1bGZpbGxlZFxuICovXG5tb2R1bGUuZXhwb3J0cyA9IGZ1bmN0aW9uIGRpc3BhdGNoUmVxdWVzdChjb25maWcpIHtcbiAgdGhyb3dJZkNhbmNlbGxhdGlvblJlcXVlc3RlZChjb25maWcpO1xuXG4gIC8vIFN1cHBvcnQgYmFzZVVSTCBjb25maWdcbiAgaWYgKGNvbmZpZy5iYXNlVVJMICYmICFpc0Fic29sdXRlVVJMKGNvbmZpZy51cmwpKSB7XG4gICAgY29uZmlnLnVybCA9IGNvbWJpbmVVUkxzKGNvbmZpZy5iYXNlVVJMLCBjb25maWcudXJsKTtcbiAgfVxuXG4gIC8vIEVuc3VyZSBoZWFkZXJzIGV4aXN0XG4gIGNvbmZpZy5oZWFkZXJzID0gY29uZmlnLmhlYWRlcnMgfHwge307XG5cbiAgLy8gVHJhbnNmb3JtIHJlcXVlc3QgZGF0YVxuICBjb25maWcuZGF0YSA9IHRyYW5zZm9ybURhdGEoXG4gICAgY29uZmlnLmRhdGEsXG4gICAgY29uZmlnLmhlYWRlcnMsXG4gICAgY29uZmlnLnRyYW5zZm9ybVJlcXVlc3RcbiAgKTtcblxuICAvLyBGbGF0dGVuIGhlYWRlcnNcbiAgY29uZmlnLmhlYWRlcnMgPSB1dGlscy5tZXJnZShcbiAgICBjb25maWcuaGVhZGVycy5jb21tb24gfHwge30sXG4gICAgY29uZmlnLmhlYWRlcnNbY29uZmlnLm1ldGhvZF0gfHwge30sXG4gICAgY29uZmlnLmhlYWRlcnMgfHwge31cbiAgKTtcblxuICB1dGlscy5mb3JFYWNoKFxuICAgIFsnZGVsZXRlJywgJ2dldCcsICdoZWFkJywgJ3Bvc3QnLCAncHV0JywgJ3BhdGNoJywgJ2NvbW1vbiddLFxuICAgIGZ1bmN0aW9uIGNsZWFuSGVhZGVyQ29uZmlnKG1ldGhvZCkge1xuICAgICAgZGVsZXRlIGNvbmZpZy5oZWFkZXJzW21ldGhvZF07XG4gICAgfVxuICApO1xuXG4gIHZhciBhZGFwdGVyID0gY29uZmlnLmFkYXB0ZXIgfHwgZGVmYXVsdHMuYWRhcHRlcjtcblxuICByZXR1cm4gYWRhcHRlcihjb25maWcpLnRoZW4oZnVuY3Rpb24gb25BZGFwdGVyUmVzb2x1dGlvbihyZXNwb25zZSkge1xuICAgIHRocm93SWZDYW5jZWxsYXRpb25SZXF1ZXN0ZWQoY29uZmlnKTtcblxuICAgIC8vIFRyYW5zZm9ybSByZXNwb25zZSBkYXRhXG4gICAgcmVzcG9uc2UuZGF0YSA9IHRyYW5zZm9ybURhdGEoXG4gICAgICByZXNwb25zZS5kYXRhLFxuICAgICAgcmVzcG9uc2UuaGVhZGVycyxcbiAgICAgIGNvbmZpZy50cmFuc2Zvcm1SZXNwb25zZVxuICAgICk7XG5cbiAgICByZXR1cm4gcmVzcG9uc2U7XG4gIH0sIGZ1bmN0aW9uIG9uQWRhcHRlclJlamVjdGlvbihyZWFzb24pIHtcbiAgICBpZiAoIWlzQ2FuY2VsKHJlYXNvbikpIHtcbiAgICAgIHRocm93SWZDYW5jZWxsYXRpb25SZXF1ZXN0ZWQoY29uZmlnKTtcblxuICAgICAgLy8gVHJhbnNmb3JtIHJlc3BvbnNlIGRhdGFcbiAgICAgIGlmIChyZWFzb24gJiYgcmVhc29uLnJlc3BvbnNlKSB7XG4gICAgICAgIHJlYXNvbi5yZXNwb25zZS5kYXRhID0gdHJhbnNmb3JtRGF0YShcbiAgICAgICAgICByZWFzb24ucmVzcG9uc2UuZGF0YSxcbiAgICAgICAgICByZWFzb24ucmVzcG9uc2UuaGVhZGVycyxcbiAgICAgICAgICBjb25maWcudHJhbnNmb3JtUmVzcG9uc2VcbiAgICAgICAgKTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICByZXR1cm4gUHJvbWlzZS5yZWplY3QocmVhc29uKTtcbiAgfSk7XG59O1xuIiwiJ3VzZSBzdHJpY3QnO1xuXG52YXIgZGVmYXVsdHMgPSByZXF1aXJlKCcuLy4uL2RlZmF1bHRzJyk7XG52YXIgdXRpbHMgPSByZXF1aXJlKCcuLy4uL3V0aWxzJyk7XG52YXIgSW50ZXJjZXB0b3JNYW5hZ2VyID0gcmVxdWlyZSgnLi9JbnRlcmNlcHRvck1hbmFnZXInKTtcbnZhciBkaXNwYXRjaFJlcXVlc3QgPSByZXF1aXJlKCcuL2Rpc3BhdGNoUmVxdWVzdCcpO1xuXG4vKipcbiAqIENyZWF0ZSBhIG5ldyBpbnN0YW5jZSBvZiBBeGlvc1xuICpcbiAqIEBwYXJhbSB7T2JqZWN0fSBpbnN0YW5jZUNvbmZpZyBUaGUgZGVmYXVsdCBjb25maWcgZm9yIHRoZSBpbnN0YW5jZVxuICovXG5mdW5jdGlvbiBBeGlvcyhpbnN0YW5jZUNvbmZpZykge1xuICB0aGlzLmRlZmF1bHRzID0gaW5zdGFuY2VDb25maWc7XG4gIHRoaXMuaW50ZXJjZXB0b3JzID0ge1xuICAgIHJlcXVlc3Q6IG5ldyBJbnRlcmNlcHRvck1hbmFnZXIoKSxcbiAgICByZXNwb25zZTogbmV3IEludGVyY2VwdG9yTWFuYWdlcigpXG4gIH07XG59XG5cbi8qKlxuICogRGlzcGF0Y2ggYSByZXF1ZXN0XG4gKlxuICogQHBhcmFtIHtPYmplY3R9IGNvbmZpZyBUaGUgY29uZmlnIHNwZWNpZmljIGZvciB0aGlzIHJlcXVlc3QgKG1lcmdlZCB3aXRoIHRoaXMuZGVmYXVsdHMpXG4gKi9cbkF4aW9zLnByb3RvdHlwZS5yZXF1ZXN0ID0gZnVuY3Rpb24gcmVxdWVzdChjb25maWcpIHtcbiAgLyplc2xpbnQgbm8tcGFyYW0tcmVhc3NpZ246MCovXG4gIC8vIEFsbG93IGZvciBheGlvcygnZXhhbXBsZS91cmwnWywgY29uZmlnXSkgYSBsYSBmZXRjaCBBUElcbiAgaWYgKHR5cGVvZiBjb25maWcgPT09ICdzdHJpbmcnKSB7XG4gICAgY29uZmlnID0gdXRpbHMubWVyZ2Uoe1xuICAgICAgdXJsOiBhcmd1bWVudHNbMF1cbiAgICB9LCBhcmd1bWVudHNbMV0pO1xuICB9XG5cbiAgY29uZmlnID0gdXRpbHMubWVyZ2UoZGVmYXVsdHMsIHRoaXMuZGVmYXVsdHMsIHsgbWV0aG9kOiAnZ2V0JyB9LCBjb25maWcpO1xuICBjb25maWcubWV0aG9kID0gY29uZmlnLm1ldGhvZC50b0xvd2VyQ2FzZSgpO1xuXG4gIC8vIEhvb2sgdXAgaW50ZXJjZXB0b3JzIG1pZGRsZXdhcmVcbiAgdmFyIGNoYWluID0gW2Rpc3BhdGNoUmVxdWVzdCwgdW5kZWZpbmVkXTtcbiAgdmFyIHByb21pc2UgPSBQcm9taXNlLnJlc29sdmUoY29uZmlnKTtcblxuICB0aGlzLmludGVyY2VwdG9ycy5yZXF1ZXN0LmZvckVhY2goZnVuY3Rpb24gdW5zaGlmdFJlcXVlc3RJbnRlcmNlcHRvcnMoaW50ZXJjZXB0b3IpIHtcbiAgICBjaGFpbi51bnNoaWZ0KGludGVyY2VwdG9yLmZ1bGZpbGxlZCwgaW50ZXJjZXB0b3IucmVqZWN0ZWQpO1xuICB9KTtcblxuICB0aGlzLmludGVyY2VwdG9ycy5yZXNwb25zZS5mb3JFYWNoKGZ1bmN0aW9uIHB1c2hSZXNwb25zZUludGVyY2VwdG9ycyhpbnRlcmNlcHRvcikge1xuICAgIGNoYWluLnB1c2goaW50ZXJjZXB0b3IuZnVsZmlsbGVkLCBpbnRlcmNlcHRvci5yZWplY3RlZCk7XG4gIH0pO1xuXG4gIHdoaWxlIChjaGFpbi5sZW5ndGgpIHtcbiAgICBwcm9taXNlID0gcHJvbWlzZS50aGVuKGNoYWluLnNoaWZ0KCksIGNoYWluLnNoaWZ0KCkpO1xuICB9XG5cbiAgcmV0dXJuIHByb21pc2U7XG59O1xuXG4vLyBQcm92aWRlIGFsaWFzZXMgZm9yIHN1cHBvcnRlZCByZXF1ZXN0IG1ldGhvZHNcbnV0aWxzLmZvckVhY2goWydkZWxldGUnLCAnZ2V0JywgJ2hlYWQnLCAnb3B0aW9ucyddLCBmdW5jdGlvbiBmb3JFYWNoTWV0aG9kTm9EYXRhKG1ldGhvZCkge1xuICAvKmVzbGludCBmdW5jLW5hbWVzOjAqL1xuICBBeGlvcy5wcm90b3R5cGVbbWV0aG9kXSA9IGZ1bmN0aW9uKHVybCwgY29uZmlnKSB7XG4gICAgcmV0dXJuIHRoaXMucmVxdWVzdCh1dGlscy5tZXJnZShjb25maWcgfHwge30sIHtcbiAgICAgIG1ldGhvZDogbWV0aG9kLFxuICAgICAgdXJsOiB1cmxcbiAgICB9KSk7XG4gIH07XG59KTtcblxudXRpbHMuZm9yRWFjaChbJ3Bvc3QnLCAncHV0JywgJ3BhdGNoJ10sIGZ1bmN0aW9uIGZvckVhY2hNZXRob2RXaXRoRGF0YShtZXRob2QpIHtcbiAgLyplc2xpbnQgZnVuYy1uYW1lczowKi9cbiAgQXhpb3MucHJvdG90eXBlW21ldGhvZF0gPSBmdW5jdGlvbih1cmwsIGRhdGEsIGNvbmZpZykge1xuICAgIHJldHVybiB0aGlzLnJlcXVlc3QodXRpbHMubWVyZ2UoY29uZmlnIHx8IHt9LCB7XG4gICAgICBtZXRob2Q6IG1ldGhvZCxcbiAgICAgIHVybDogdXJsLFxuICAgICAgZGF0YTogZGF0YVxuICAgIH0pKTtcbiAgfTtcbn0pO1xuXG5tb2R1bGUuZXhwb3J0cyA9IEF4aW9zO1xuIiwiJ3VzZSBzdHJpY3QnO1xuXG4vKipcbiAqIEEgYENhbmNlbGAgaXMgYW4gb2JqZWN0IHRoYXQgaXMgdGhyb3duIHdoZW4gYW4gb3BlcmF0aW9uIGlzIGNhbmNlbGVkLlxuICpcbiAqIEBjbGFzc1xuICogQHBhcmFtIHtzdHJpbmc9fSBtZXNzYWdlIFRoZSBtZXNzYWdlLlxuICovXG5mdW5jdGlvbiBDYW5jZWwobWVzc2FnZSkge1xuICB0aGlzLm1lc3NhZ2UgPSBtZXNzYWdlO1xufVxuXG5DYW5jZWwucHJvdG90eXBlLnRvU3RyaW5nID0gZnVuY3Rpb24gdG9TdHJpbmcoKSB7XG4gIHJldHVybiAnQ2FuY2VsJyArICh0aGlzLm1lc3NhZ2UgPyAnOiAnICsgdGhpcy5tZXNzYWdlIDogJycpO1xufTtcblxuQ2FuY2VsLnByb3RvdHlwZS5fX0NBTkNFTF9fID0gdHJ1ZTtcblxubW9kdWxlLmV4cG9ydHMgPSBDYW5jZWw7XG4iLCIndXNlIHN0cmljdCc7XG5cbnZhciBDYW5jZWwgPSByZXF1aXJlKCcuL0NhbmNlbCcpO1xuXG4vKipcbiAqIEEgYENhbmNlbFRva2VuYCBpcyBhbiBvYmplY3QgdGhhdCBjYW4gYmUgdXNlZCB0byByZXF1ZXN0IGNhbmNlbGxhdGlvbiBvZiBhbiBvcGVyYXRpb24uXG4gKlxuICogQGNsYXNzXG4gKiBAcGFyYW0ge0Z1bmN0aW9ufSBleGVjdXRvciBUaGUgZXhlY3V0b3IgZnVuY3Rpb24uXG4gKi9cbmZ1bmN0aW9uIENhbmNlbFRva2VuKGV4ZWN1dG9yKSB7XG4gIGlmICh0eXBlb2YgZXhlY3V0b3IgIT09ICdmdW5jdGlvbicpIHtcbiAgICB0aHJvdyBuZXcgVHlwZUVycm9yKCdleGVjdXRvciBtdXN0IGJlIGEgZnVuY3Rpb24uJyk7XG4gIH1cblxuICB2YXIgcmVzb2x2ZVByb21pc2U7XG4gIHRoaXMucHJvbWlzZSA9IG5ldyBQcm9taXNlKGZ1bmN0aW9uIHByb21pc2VFeGVjdXRvcihyZXNvbHZlKSB7XG4gICAgcmVzb2x2ZVByb21pc2UgPSByZXNvbHZlO1xuICB9KTtcblxuICB2YXIgdG9rZW4gPSB0aGlzO1xuICBleGVjdXRvcihmdW5jdGlvbiBjYW5jZWwobWVzc2FnZSkge1xuICAgIGlmICh0b2tlbi5yZWFzb24pIHtcbiAgICAgIC8vIENhbmNlbGxhdGlvbiBoYXMgYWxyZWFkeSBiZWVuIHJlcXVlc3RlZFxuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIHRva2VuLnJlYXNvbiA9IG5ldyBDYW5jZWwobWVzc2FnZSk7XG4gICAgcmVzb2x2ZVByb21pc2UodG9rZW4ucmVhc29uKTtcbiAgfSk7XG59XG5cbi8qKlxuICogVGhyb3dzIGEgYENhbmNlbGAgaWYgY2FuY2VsbGF0aW9uIGhhcyBiZWVuIHJlcXVlc3RlZC5cbiAqL1xuQ2FuY2VsVG9rZW4ucHJvdG90eXBlLnRocm93SWZSZXF1ZXN0ZWQgPSBmdW5jdGlvbiB0aHJvd0lmUmVxdWVzdGVkKCkge1xuICBpZiAodGhpcy5yZWFzb24pIHtcbiAgICB0aHJvdyB0aGlzLnJlYXNvbjtcbiAgfVxufTtcblxuLyoqXG4gKiBSZXR1cm5zIGFuIG9iamVjdCB0aGF0IGNvbnRhaW5zIGEgbmV3IGBDYW5jZWxUb2tlbmAgYW5kIGEgZnVuY3Rpb24gdGhhdCwgd2hlbiBjYWxsZWQsXG4gKiBjYW5jZWxzIHRoZSBgQ2FuY2VsVG9rZW5gLlxuICovXG5DYW5jZWxUb2tlbi5zb3VyY2UgPSBmdW5jdGlvbiBzb3VyY2UoKSB7XG4gIHZhciBjYW5jZWw7XG4gIHZhciB0b2tlbiA9IG5ldyBDYW5jZWxUb2tlbihmdW5jdGlvbiBleGVjdXRvcihjKSB7XG4gICAgY2FuY2VsID0gYztcbiAgfSk7XG4gIHJldHVybiB7XG4gICAgdG9rZW46IHRva2VuLFxuICAgIGNhbmNlbDogY2FuY2VsXG4gIH07XG59O1xuXG5tb2R1bGUuZXhwb3J0cyA9IENhbmNlbFRva2VuO1xuIiwiJ3VzZSBzdHJpY3QnO1xuXG4vKipcbiAqIFN5bnRhY3RpYyBzdWdhciBmb3IgaW52b2tpbmcgYSBmdW5jdGlvbiBhbmQgZXhwYW5kaW5nIGFuIGFycmF5IGZvciBhcmd1bWVudHMuXG4gKlxuICogQ29tbW9uIHVzZSBjYXNlIHdvdWxkIGJlIHRvIHVzZSBgRnVuY3Rpb24ucHJvdG90eXBlLmFwcGx5YC5cbiAqXG4gKiAgYGBganNcbiAqICBmdW5jdGlvbiBmKHgsIHksIHopIHt9XG4gKiAgdmFyIGFyZ3MgPSBbMSwgMiwgM107XG4gKiAgZi5hcHBseShudWxsLCBhcmdzKTtcbiAqICBgYGBcbiAqXG4gKiBXaXRoIGBzcHJlYWRgIHRoaXMgZXhhbXBsZSBjYW4gYmUgcmUtd3JpdHRlbi5cbiAqXG4gKiAgYGBganNcbiAqICBzcHJlYWQoZnVuY3Rpb24oeCwgeSwgeikge30pKFsxLCAyLCAzXSk7XG4gKiAgYGBgXG4gKlxuICogQHBhcmFtIHtGdW5jdGlvbn0gY2FsbGJhY2tcbiAqIEByZXR1cm5zIHtGdW5jdGlvbn1cbiAqL1xubW9kdWxlLmV4cG9ydHMgPSBmdW5jdGlvbiBzcHJlYWQoY2FsbGJhY2spIHtcbiAgcmV0dXJuIGZ1bmN0aW9uIHdyYXAoYXJyKSB7XG4gICAgcmV0dXJuIGNhbGxiYWNrLmFwcGx5KG51bGwsIGFycik7XG4gIH07XG59O1xuIiwiJ3VzZSBzdHJpY3QnO1xuXG52YXIgdXRpbHMgPSByZXF1aXJlKCcuL3V0aWxzJyk7XG52YXIgYmluZCA9IHJlcXVpcmUoJy4vaGVscGVycy9iaW5kJyk7XG52YXIgQXhpb3MgPSByZXF1aXJlKCcuL2NvcmUvQXhpb3MnKTtcbnZhciBkZWZhdWx0cyA9IHJlcXVpcmUoJy4vZGVmYXVsdHMnKTtcblxuLyoqXG4gKiBDcmVhdGUgYW4gaW5zdGFuY2Ugb2YgQXhpb3NcbiAqXG4gKiBAcGFyYW0ge09iamVjdH0gZGVmYXVsdENvbmZpZyBUaGUgZGVmYXVsdCBjb25maWcgZm9yIHRoZSBpbnN0YW5jZVxuICogQHJldHVybiB7QXhpb3N9IEEgbmV3IGluc3RhbmNlIG9mIEF4aW9zXG4gKi9cbmZ1bmN0aW9uIGNyZWF0ZUluc3RhbmNlKGRlZmF1bHRDb25maWcpIHtcbiAgdmFyIGNvbnRleHQgPSBuZXcgQXhpb3MoZGVmYXVsdENvbmZpZyk7XG4gIHZhciBpbnN0YW5jZSA9IGJpbmQoQXhpb3MucHJvdG90eXBlLnJlcXVlc3QsIGNvbnRleHQpO1xuXG4gIC8vIENvcHkgYXhpb3MucHJvdG90eXBlIHRvIGluc3RhbmNlXG4gIHV0aWxzLmV4dGVuZChpbnN0YW5jZSwgQXhpb3MucHJvdG90eXBlLCBjb250ZXh0KTtcblxuICAvLyBDb3B5IGNvbnRleHQgdG8gaW5zdGFuY2VcbiAgdXRpbHMuZXh0ZW5kKGluc3RhbmNlLCBjb250ZXh0KTtcblxuICByZXR1cm4gaW5zdGFuY2U7XG59XG5cbi8vIENyZWF0ZSB0aGUgZGVmYXVsdCBpbnN0YW5jZSB0byBiZSBleHBvcnRlZFxudmFyIGF4aW9zID0gY3JlYXRlSW5zdGFuY2UoZGVmYXVsdHMpO1xuXG4vLyBFeHBvc2UgQXhpb3MgY2xhc3MgdG8gYWxsb3cgY2xhc3MgaW5oZXJpdGFuY2VcbmF4aW9zLkF4aW9zID0gQXhpb3M7XG5cbi8vIEZhY3RvcnkgZm9yIGNyZWF0aW5nIG5ldyBpbnN0YW5jZXNcbmF4aW9zLmNyZWF0ZSA9IGZ1bmN0aW9uIGNyZWF0ZShpbnN0YW5jZUNvbmZpZykge1xuICByZXR1cm4gY3JlYXRlSW5zdGFuY2UodXRpbHMubWVyZ2UoZGVmYXVsdHMsIGluc3RhbmNlQ29uZmlnKSk7XG59O1xuXG4vLyBFeHBvc2UgQ2FuY2VsICYgQ2FuY2VsVG9rZW5cbmF4aW9zLkNhbmNlbCA9IHJlcXVpcmUoJy4vY2FuY2VsL0NhbmNlbCcpO1xuYXhpb3MuQ2FuY2VsVG9rZW4gPSByZXF1aXJlKCcuL2NhbmNlbC9DYW5jZWxUb2tlbicpO1xuYXhpb3MuaXNDYW5jZWwgPSByZXF1aXJlKCcuL2NhbmNlbC9pc0NhbmNlbCcpO1xuXG4vLyBFeHBvc2UgYWxsL3NwcmVhZFxuYXhpb3MuYWxsID0gZnVuY3Rpb24gYWxsKHByb21pc2VzKSB7XG4gIHJldHVybiBQcm9taXNlLmFsbChwcm9taXNlcyk7XG59O1xuYXhpb3Muc3ByZWFkID0gcmVxdWlyZSgnLi9oZWxwZXJzL3NwcmVhZCcpO1xuXG5tb2R1bGUuZXhwb3J0cyA9IGF4aW9zO1xuXG4vLyBBbGxvdyB1c2Ugb2YgZGVmYXVsdCBpbXBvcnQgc3ludGF4IGluIFR5cGVTY3JpcHRcbm1vZHVsZS5leHBvcnRzLmRlZmF1bHQgPSBheGlvcztcbiIsIm1vZHVsZS5leHBvcnRzID0gcmVxdWlyZSgnLi9saWIvYXhpb3MnKTsiLCJcInVzZSBzdHJpY3RcIjtcblxudmFyIGF4aW9zID0gcmVxdWlyZSgnYXhpb3MnKTtcbnZhciBsb2dnZXJzID0gW107XG5cbmZ1bmN0aW9uIGNyZWF0ZSh1cmwsIHRhZ3MsIGxldmVsKSB7XG4gIHZhciBvcHRpb25zID0gYXJndW1lbnRzLmxlbmd0aCA+IDMgJiYgYXJndW1lbnRzWzNdICE9PSB1bmRlZmluZWQgPyBhcmd1bWVudHNbM10gOiB7fTtcblxuICByZXR1cm4gbmV3IExvZ3N0YXNoKHVybCwgdGFncywgbGV2ZWwsIG9wdGlvbnMpO1xufVxuXG5mdW5jdGlvbiBMb2dzdGFzaCh1cmwpIHtcbiAgdmFyIHRhZ3MgPSBhcmd1bWVudHMubGVuZ3RoID4gMSAmJiBhcmd1bWVudHNbMV0gIT09IHVuZGVmaW5lZCA/IGFyZ3VtZW50c1sxXSA6IFtdO1xuICB2YXIgbGV2ZWwgPSBhcmd1bWVudHMubGVuZ3RoID4gMiAmJiBhcmd1bWVudHNbMl0gIT09IHVuZGVmaW5lZCA/IGFyZ3VtZW50c1syXSA6IFwiaW5mb1wiO1xuICB2YXIgb3B0aW9ucyA9IGFyZ3VtZW50cy5sZW5ndGggPiAzICYmIGFyZ3VtZW50c1szXSAhPT0gdW5kZWZpbmVkID8gYXJndW1lbnRzWzNdIDoge307XG5cbiAgaWYgKCF1cmwpIHtcbiAgICB0aHJvdyBuZXcgVHlwZUVycm9yKFwiSW52YWxpZCBVUkxcIik7XG4gIH1cblxuICB0aGlzLnVybCA9IHVybDtcbiAgdGhpcy50YWdzID0gdGFncztcbiAgdGhpcy5sZXZlbCA9IGxldmVsO1xuICB0aGlzLnNlbmREZWxheSA9IG9wdGlvbnMuc2VuZERlbGF5IHx8IDEwMDtcbiAgdGhpcy5yZXRyeURlbGF5ID0gb3B0aW9ucy5yZXRyeURlbGF5IHx8IDIwMDA7XG4gIHRoaXMubXV0ZUNvbnNvbGUgPSBvcHRpb25zLm11dGVDb25zb2xlID09PSB0cnVlIHx8IGZhbHNlO1xuICB0aGlzLmlzU2VuZGluZyA9IGZhbHNlO1xuICB0aGlzLnF1ZXVlID0gW107XG59XG5cbkxvZ3N0YXNoLnByb3RvdHlwZS5fdHJ5U2VuZEV2ZW50ID0gZnVuY3Rpb24gX3RyeVNlbmRFdmVudCgpIHtcbiAgdmFyIF90aGlzID0gdGhpcztcblxuICBpZiAoIXRoaXMucXVldWUubGVuZ3RoIHx8IHRoaXMuaXNTZW5kaW5nKSB7XG4gICAgcmV0dXJuO1xuICB9XG5cbiAgdGhpcy5pc1NlbmRpbmcgPSB0cnVlO1xuICB2YXIgZXZlbnQgPSB0aGlzLnF1ZXVlLnNoaWZ0KCk7XG5cbiAgdmFyIHJlcXVlc3QgPSB7XG4gICAgdXJsOiB0aGlzLnVybCxcbiAgICBtZXRob2Q6ICdwb3N0JyxcbiAgICBoZWFkZXJzOiB7ICdDb250ZW50LVR5cGUnOiAnYXBwbGljYXRpb24vanNvbicgfSxcbiAgICBkYXRhOiBldmVudFxuICB9O1xuXG4gIC8vIEhUVFAgcmVxdWVzdFxuICByZXR1cm4gYXhpb3MocmVxdWVzdCkudGhlbihmdW5jdGlvbiAoKSB7XG4gICAgX3RoaXMuaXNTZW5kaW5nID0gZmFsc2U7XG4gICAgX3RoaXMuX3RyeVNlbmRFdmVudCgpO1xuICB9KS5jYXRjaChmdW5jdGlvbiAoZXJyKSB7XG4gICAgY29uc29sZS5lcnJvcihlcnIpO1xuXG4gICAgLy8gSWYgd2UgY291bGQgbm90IHNlbmQgdGhlIGV2ZW50LFxuICAgIC8vIHB1dCBpdCBiYWNrIGludG8gcXVldWVcbiAgICBfdGhpcy5xdWV1ZS51bnNoaWZ0KGV2ZW50KTtcblxuICAgIF90aGlzLmlzU2VuZGluZyA9IGZhbHNlO1xuICAgIHNldFRpbWVvdXQoX3RoaXMuX3RyeVNlbmRFdmVudC5iaW5kKF90aGlzKSwgX3RoaXMucmV0cnlEZWxheSk7XG4gIH0pO1xufTtcblxuTG9nc3Rhc2gucHJvdG90eXBlLmxvZyA9IGZ1bmN0aW9uIGxvZyhsZXZlbCwgbWVzc2FnZSwgZmllbGRzKSB7XG4gIHZhciBldmVudCA9IHsgbGV2ZWw6IGxldmVsLCBmaWVsZHM6IGZpZWxkcywgbWVzc2FnZTogbWVzc2FnZSB9O1xuXG4gIGV2ZW50WydAdGltZXN0YW1wJ10gPSBuZXcgRGF0ZSgpLnRvSVNPU3RyaW5nKCk7XG4gIGV2ZW50WydAdGFncyddID0gdGhpcy50YWdzO1xuXG4gIC8vIE5hdmlnYXRvciBtZXRhZGF0YVxuICBpZiAodHlwZW9mIG5hdmlnYXRvciAhPT0gJ3VuZGVmaW5lZCcpIHtcbiAgICBldmVudC5uYXZpZ2F0b3IgPSB7XG4gICAgICBjb29raWVFbmFibGVkOiBuYXZpZ2F0b3IuY29va2llRW5hYmxlZCxcbiAgICAgIGdlb0xvY2F0aW9uOiBuYXZpZ2F0b3IuZ2VvTG9jYXRpb24sXG4gICAgICBsYW5ndWFnZTogbmF2aWdhdG9yLmxhbmd1YWdlLFxuICAgICAgbGFuZ3VhZ2VzOiBuYXZpZ2F0b3IubGFuZ3VhZ2VzLFxuICAgICAgb25saW5lOiBuYXZpZ2F0b3Iub25saW5lLFxuICAgICAgdXNlckFnZW50OiBuYXZpZ2F0b3IudXNlckFnZW50LFxuICAgICAgcGxhdGZvcm06IG5hdmlnYXRvci5wbGF0Zm9ybSxcbiAgICAgIHZlbmRvcjogbmF2aWdhdG9yLnZlbmRvclxuICAgIH07XG4gIH1cblxuICAvLyBMb2NhdGlvbiBtZXRhZGF0YVxuICBpZiAodHlwZW9mIGxvY2F0aW9uICE9PSAndW5kZWZpbmVkJykge1xuICAgIGV2ZW50LmxvY2F0aW9uID0ge1xuICAgICAgc2VhcmNoOiBsb2NhdGlvbi5zZWFyY2gsXG4gICAgICBwYXRobmFtZTogbG9jYXRpb24ucGF0aG5hbWUsXG4gICAgICBob3N0bmFtZTogbG9jYXRpb24uaG9zdG5hbWUsXG4gICAgICBwcm90b2NvbDogbG9jYXRpb24ucHJvdG9jb2wsXG4gICAgICBwb3J0OiBsb2NhdGlvbi5wb3J0LFxuICAgICAgaGFzaDogbG9jYXRpb24uaGFzaCxcbiAgICAgIGhyZWY6IGxvY2F0aW9uLmhyZWZcbiAgICB9O1xuICB9XG5cbiAgdGhpcy5xdWV1ZS5wdXNoKGV2ZW50KTtcbiAgdGhpcy5fdHJ5U2VuZEV2ZW50KCk7XG5cbiAgaWYgKHRoaXMubXV0ZUNvbnNvbGUpIHtcbiAgICByZXR1cm47XG4gIH1cblxuICB2YXIgZmllbGRzU3RyID0gZmllbGRzID8gXCIgLSBcIiArIEpTT04uc3RyaW5naWZ5KGZpZWxkcykgOiAnJztcblxuICBzd2l0Y2ggKGxldmVsKSB7XG4gICAgY2FzZSBcImVycm9yXCI6XG4gICAgICBjb25zb2xlLmVycm9yKFwiXCIgKyBtZXNzYWdlICsgZmllbGRzU3RyKTtcbiAgICAgIGJyZWFrO1xuICAgIGNhc2UgXCJ3YXJuXCI6XG4gICAgICBjb25zb2xlLndhcm4oXCJcIiArIG1lc3NhZ2UgKyBmaWVsZHNTdHIpO1xuICAgICAgYnJlYWs7XG4gICAgZGVmYXVsdDpcbiAgICAgIGNvbnNvbGUuaW5mbyhcIlwiICsgbWVzc2FnZSArIGZpZWxkc1N0cik7XG4gIH1cbn07XG5cbkxvZ3N0YXNoLnByb3RvdHlwZS5kZWJ1ZyA9IGZ1bmN0aW9uIGRlYnVnKG1lc3NhZ2UsIGZpZWxkcykge1xuICB0aGlzLmxvZygnZGVidWcnLCBtZXNzYWdlLCBmaWVsZHMpO1xufTtcblxuTG9nc3Rhc2gucHJvdG90eXBlLmluZm8gPSBmdW5jdGlvbiBpbmZvKG1lc3NhZ2UsIGZpZWxkcykge1xuICB0aGlzLmxvZygnaW5mbycsIG1lc3NhZ2UsIGZpZWxkcyk7XG59O1xuXG5Mb2dzdGFzaC5wcm90b3R5cGUud2FybiA9IGZ1bmN0aW9uIHdhcm4obWVzc2FnZSwgZmllbGRzKSB7XG4gIHRoaXMubG9nKCd3YXJuJywgbWVzc2FnZSwgZmllbGRzKTtcbn07XG5cbkxvZ3N0YXNoLnByb3RvdHlwZS5lcnJvciA9IGZ1bmN0aW9uIGVycm9yKGVyciwgZmllbGRzKSB7XG4gIGlmIChlcnIgaW5zdGFuY2VvZiBFcnJvcikge1xuICAgIHRoaXMubG9nKCdlcnJvcicsIGVyci5tZXNzYWdlLCBPYmplY3QuYXNzaWduKHsgc3RhY2s6IGVyci5zdGFjayB9LCBmaWVsZHMpKTtcbiAgfSBlbHNlIHtcbiAgICB0aGlzLmxvZygnZXJyb3InLCBlcnIsIGZpZWxkcyk7XG4gIH1cbn07XG5cbm1vZHVsZS5leHBvcnRzID0gY3JlYXRlOyIsImltcG9ydCBjcmVhdGUgZnJvbSAnQHd5c2NvdXQvbG9nc3Rhc2gnO1xuaW1wb3J0IHsgZ2V0Rmlyc3RMZXZlbERvbWFpbiB9IGZyb20gJy4uL3V0aWxpdGllcy91dGlscyc7XG5cbmNvbnN0IGZvcm1hdFVzZXJTZXR0aW5ncyA9ICh1c2VyU2V0dGluZ3MpID0+IHtcbiAgICByZXR1cm4ge1xuICAgICAgICAuLi51c2VyU2V0dGluZ3MsXG4gICAgICAgIHVzZXJJZDogdXNlclNldHRpbmdzLnVzZXJJZCA/IHVzZXJTZXR0aW5ncy51c2VySWQudG9TdHJpbmcoKSA6ICcnLFxuICAgICAgICBzdWJncm91cElkOiB1c2VyU2V0dGluZ3Muc3ViZ3JvdXBJZCA/IHVzZXJTZXR0aW5ncy5zdWJncm91cElkLnRvU3RyaW5nKCkgOiAnJyxcbiAgICAgICAgZ3JvdXBJZDogdXNlclNldHRpbmdzLmdyb3VwSWQgPyB1c2VyU2V0dGluZ3MuZ3JvdXBJZC50b1N0cmluZygpIDogJycsXG4gICAgfTtcbn07XG5cbmNvbnN0IExvZ1N0YXNoID0gKG1vZGVsLCBsYWJlbCkgPT4ge1xuICAgIHJldHVybiBuZXcgUHJvbWlzZSgocmVzb2x2ZSwgcmVqZWN0KSA9PiB7XG4gICAgICAgIHRyeSB7XG4gICAgICAgICAgICBjb25zdCBmaXJzdERvbWFpbkxldmVsID0gZ2V0Rmlyc3RMZXZlbERvbWFpbigpO1xuICAgICAgICAgICAgY29uc3QgdXJsID0gYGh0dHBzOi8vdmlkZW9tZXRyaWNzLnd5c2NvdXQke2ZpcnN0RG9tYWluTGV2ZWx9OjgwODBgO1xuICAgICAgICAgICAgLy8gb3B0aW9uYWxcbiAgICAgICAgICAgIGNvbnN0IHRhZ3MgPSBbJ3ZpZGVvJywgJ21ldHJpY3MnXTtcbiAgICAgICAgICAgIGNvbnN0IGxldmVsID0gJ2luZm8nO1xuICAgICAgICAgICAgbW9kZWwudXNlclNldHRpbmdzID0gZm9ybWF0VXNlclNldHRpbmdzKG1vZGVsLnVzZXJTZXR0aW5ncyk7XG4gICAgICAgICAgICBjb25zdCBvcHRpb25zID0ge1xuICAgICAgICAgICAgICAgIG11dGVDb25zb2xlOiB0cnVlLFxuICAgICAgICAgICAgfTtcbiAgICAgICAgICAgIC8vIENyZWF0ZSBsb2dnZXIgaW5zdGFuY2VcbiAgICAgICAgICAgIGNvbnN0IGxvZ2dlciA9IGNyZWF0ZSh1cmwsIHRhZ3MsIGxldmVsLCBvcHRpb25zKTtcblxuICAgICAgICAgICAgbG9nZ2VyLmluZm8obGFiZWwsIG1vZGVsKTtcbiAgICAgICAgICAgIHJlc29sdmUobG9nZ2VyKTtcbiAgICAgICAgfSBjYXRjaCAoZXJyKSB7XG4gICAgICAgICAgICByZWplY3QoZXJyKTtcbiAgICAgICAgfVxuICAgIH0pO1xufTtcblxuXG5leHBvcnQgZGVmYXVsdCBMb2dTdGFzaDtcbiIsImltcG9ydCBheGlvcyBmcm9tICdheGlvcyc7XG5pbXBvcnQgeyBBUElfU0VSVkVSIH0gZnJvbSAnLi4vY29uZmlnL2NvbmZpZy5qcyc7XG5cbmNvbnN0IFJlc3RBcGkgPSAobW9kZWwpID0+IHtcbiAgICByZXR1cm4gYXhpb3Moe1xuICAgICAgICBtZXRob2Q6IG1vZGVsLmlkID8gJ1BVVCcgOiAnUE9TVCcsXG4gICAgICAgIHVybDogbW9kZWwuaWRcbiAgICAgICAgICAgID8gQVBJX1NFUlZFUiArIGBtZXRyaWNzLyR7bW9kZWwuaWR9YFxuICAgICAgICAgICAgOiBBUElfU0VSVkVSICsgJ21ldHJpY3MnLFxuICAgICAgICBkYXRhOiBtb2RlbCxcbiAgICB9KTtcbn07XG5cbmV4cG9ydCBkZWZhdWx0IFJlc3RBcGk7XG4iLCJpbXBvcnQgYXhpb3MgZnJvbSAnYXhpb3MnO1xuaW1wb3J0IHsgVFJBTlNNSVNTSU9OX1RZUEUgfSBmcm9tICcuLi9jb25maWcvY29uZmlnLmpzJztcbmltcG9ydCBMb2dTdGFzaCBmcm9tICcuLi90cmFuc21pdHRlci9Mb2dTdGFzaCc7XG5pbXBvcnQgUmVzdEFwaSBmcm9tICcuLi90cmFuc21pdHRlci9SZXN0QXBpJztcblxuZXhwb3J0IGNvbnN0IGdldElwQWRkcmVzcyA9ICgpID0+IHtcbiAgICByZXR1cm4gYXhpb3Moe1xuICAgICAgICBtZXRob2Q6ICdHRVQnLFxuICAgICAgICB1cmw6ICdodHRwczovL29wc2FwaS53eXNjb3V0LmNvbS92MC4yL2dldF9teV9pcCcsXG4gICAgfSk7XG59O1xuXG5leHBvcnQgY29uc3QgQ2FsbGVyID0gKG1vZGVsLCBsYWJlbCwgdHJhbnNtaXNzaW9uID0gVFJBTlNNSVNTSU9OX1RZUEUuTE9HU1RBU0gpID0+IHtcbiAgICByZXR1cm4gdHJhbnNtaXNzaW9uID09PSBUUkFOU01JU1NJT05fVFlQRS5MT0dTVEFTSCA/IExvZ1N0YXNoKG1vZGVsLCBsYWJlbCkgOiBSZXN0QXBpKG1vZGVsLCBsYWJlbCk7XG59O1xuXG5leHBvcnQgY29uc3QgZ2V0R2xvYmFsU3dpdGNoU3RhdHVzID0gKGFjY2Vzc1Rva2VuLCBhcGlIb3N0bmFtZSkgPT4ge1xuICAgIHJldHVybiBheGlvcyh7XG4gICAgICAgIG1ldGhvZDogJ0dFVCcsXG4gICAgICAgIHVybDogYXBpSG9zdG5hbWUgKyAnbWVkaWEvdmlkZW9tZXRyaWNzY29uZmlnLycsXG4gICAgICAgIHBhcmFtczoge1xuICAgICAgICAgICAgYWNjZXNzX3Rva2VuOiBhY2Nlc3NUb2tlbixcbiAgICAgICAgfSxcbiAgICB9KTtcbn07XG4iLCJpbXBvcnQgeyBnZXRHbG9iYWxTd2l0Y2hTdGF0dXMgfSBmcm9tICcuLi9jb3JlL0NhbGxlcic7XG5pbXBvcnQgeyBNQVhfU0VFS0lOR19WSURFT19UQUcsIFdZU0NPVVRfSE9TVE5BTUVTX1NVRkZJWCB9IGZyb20gJy4uL2NvbmZpZy9jb25maWcnO1xuXG5cbmV4cG9ydCBjb25zdCBmb3JtYXRCdWZmZXJlZFJhbmdlcyA9IHZpZGVvID0+IHtcbiAgICBsZXQgZm9ybWF0dGVkUmFuZ2VzID0gW107XG4gICAgZm9yIChsZXQgaSA9IDA7IGkgPCB2aWRlby5idWZmZXJlZC5sZW5ndGg7IGkrKykge1xuICAgICAgICBmb3JtYXR0ZWRSYW5nZXMucHVzaCh7XG4gICAgICAgICAgICBzdGFydDogdmlkZW8uYnVmZmVyZWQuc3RhcnQoaSksXG4gICAgICAgICAgICBlbmQ6IHZpZGVvLmJ1ZmZlcmVkLmVuZChpKSxcbiAgICAgICAgfSk7XG4gICAgfVxuICAgIHJldHVybiBmb3JtYXR0ZWRSYW5nZXM7XG59O1xuXG5leHBvcnQgY29uc3QgZm9ybWF0U2Vla2FibGVSYW5nZXMgPSB2aWRlbyA9PiB7XG4gICAgbGV0IGZvcm1hdHRlZFNlZWthYmxlUmFuZ2VzID0gW107XG4gICAgZm9yIChsZXQgaSA9IDA7IGkgPCB2aWRlby5zZWVrYWJsZS5sZW5ndGg7IGkrKykge1xuICAgICAgICBmb3JtYXR0ZWRTZWVrYWJsZVJhbmdlcy5wdXNoKHtcbiAgICAgICAgICAgIHN0YXJ0OiB2aWRlby5zZWVrYWJsZS5zdGFydChpKSxcbiAgICAgICAgICAgIGVuZDogdmlkZW8uc2Vla2FibGUuZW5kKGkpLFxuICAgICAgICB9KTtcbiAgICB9XG4gICAgcmV0dXJuIGZvcm1hdHRlZFNlZWthYmxlUmFuZ2VzO1xufTtcblxuZXhwb3J0IGNvbnN0IGZvcm1hdFBsYXllZFJhbmdlcyA9IHZpZGVvID0+IHtcbiAgICBsZXQgZm9ybWF0dGVkUGxheWVkUmFuZ2VzID0gW107XG4gICAgZm9yIChsZXQgaSA9IDA7IGkgPCB2aWRlby5wbGF5ZWQubGVuZ3RoOyBpKyspIHtcbiAgICAgICAgZm9ybWF0dGVkUGxheWVkUmFuZ2VzLnB1c2goe1xuICAgICAgICAgICAgc3RhcnQ6IHZpZGVvLnBsYXllZC5zdGFydChpKSxcbiAgICAgICAgICAgIGVuZDogdmlkZW8ucGxheWVkLmVuZChpKSxcbiAgICAgICAgfSk7XG4gICAgfVxuICAgIHJldHVybiBmb3JtYXR0ZWRQbGF5ZWRSYW5nZXM7XG59O1xuXG5leHBvcnQgY29uc3QgZ2V0VXJsUGFyYW1zID0gdXJsID0+IHtcbiAgICBsZXQgZmluYWxVcmwgPSB1cmw7XG4gICAgaWYgKCFmaW5hbFVybC5pbmNsdWRlcygnPycpKSB7XG4gICAgICAgIHJldHVybiB7XG4gICAgICAgICAgICB1c2VySWQ6IDEyMzQ1NixcbiAgICAgICAgICAgIGdyb3VwSWQ6IDEyMyxcbiAgICAgICAgICAgIHN1Ymdyb3VwSWQ6IDEyMyxcbiAgICAgICAgICAgIHVzZXJOYW1lOiAnVGVzdGVyIFVzZXInLFxuICAgICAgICB9O1xuICAgIH1cblxuICAgIGZpbmFsVXJsID0gZmluYWxVcmwuc3BsaXQoJz8nKVsxXS5zcGxpdCgnJicpO1xuICAgIGZpbmFsVXJsID0gZmluYWxVcmwucmVkdWNlKChhY2MsIGN1cikgPT4ge1xuICAgICAgICBsZXQga2V5ID0gY3VyLnNwbGl0KCc9JylbMF07XG4gICAgICAgIGxldCB2YWwgPSBjdXIuc3BsaXQoJz0nKVsxXTtcbiAgICAgICAgYWNjW2tleV0gPSB2YWw7XG4gICAgICAgIHJldHVybiBhY2M7XG4gICAgfSwge30pO1xuICAgIHJldHVybiBmaW5hbFVybDtcbn07XG5cbmV4cG9ydCBjb25zdCBnZXRVc2VyUGFyYW1zID0gKCkgPT4ge1xuICAgIGxldCByZXN1bHQgPSBudWxsO1xuICAgIGlmICh3aW5kb3cubG9jYXRpb24uaG9zdG5hbWUuaW5jbHVkZXMoJy53eXNjb3V0LicpKSB7XG4gICAgICAgIHJlc3VsdCA9IGdldFVybFBhcmFtcyh3aW5kb3cubG9jYXRpb24uaHJlZik7XG4gICAgfSBlbHNlIHtcbiAgICAgICAgcmVzdWx0ID0ge1xuICAgICAgICAgICAgdXNlcklkOiAxMjM0NTYsXG4gICAgICAgICAgICBncm91cElkOiAxMjMsXG4gICAgICAgICAgICBzdWJncm91cElkOiAxMjMsXG4gICAgICAgICAgICB1c2VyTmFtZTogJ1Rlc3RlciBVc2VyJyxcbiAgICAgICAgfTtcbiAgICB9XG4gICAgcmV0dXJuIHJlc3VsdDtcbn07XG5cbmV4cG9ydCBjb25zdCBjaGVja0lzRW5hYmxlZFN0YXR1cyA9IChhY2Nlc3NUb2tlbiwgYXBpSG9zdG5hbWUpID0+IHtcbiAgICBjb25zdCBwcm9taXNlID0gbmV3IFByb21pc2UoKHJlc29sdmUsIHJlamVjdCkgPT4ge1xuICAgICAgICBnZXRHbG9iYWxTd2l0Y2hTdGF0dXMoYWNjZXNzVG9rZW4sIGFwaUhvc3RuYW1lKS50aGVuKChyZXNwb25zZSkgPT4ge1xuICAgICAgICAgICAgaWYgKCFyZXNwb25zZS5kYXRhLmlzRW5hYmxlZCkgcmV0dXJuIHJlamVjdChmYWxzZSk7XG4gICAgICAgICAgICByZXR1cm4gcmVzb2x2ZSh0cnVlKTtcbiAgICAgICAgfSkuY2F0Y2goKCkgPT4ge1xuICAgICAgICAgICAgcmV0dXJuIHJlamVjdChuZXcgRXJyb3IoZmFsc2UpKTtcbiAgICAgICAgfSk7XG4gICAgfSk7XG5cbiAgICByZXR1cm4gcHJvbWlzZTtcbn07XG5cbmV4cG9ydCBjb25zdCBmaW5kSFRNTDVWaWRlbyA9ICh1c2VyU2V0dGluZ3MsIGFwaUhvc3RuYW1lKSA9PiB7XG4gICAgY29uc3QgcHJvbWlzZSA9IG5ldyBQcm9taXNlKChyZXNvbHZlLCByZWplY3QpID0+IHtcbiAgICAgICAgY2hlY2tJc0VuYWJsZWRTdGF0dXModXNlclNldHRpbmdzLmFjY2Vzc1Rva2VuLCBhcGlIb3N0bmFtZSkudGhlbigoKSA9PiB7XG4gICAgICAgICAgICBsZXQgY291bnRlciA9IDA7XG4gICAgICAgICAgICBsZXQgc2Vla2luZyA9IHNldEludGVydmFsKCgpID0+IHtcbiAgICAgICAgICAgICAgICBsZXQgdmlkZW8gPSBkb2N1bWVudC5xdWVyeVNlbGVjdG9yKCd2aWRlbycpO1xuICAgICAgICAgICAgICAgIGlmICh2aWRlbykge1xuICAgICAgICAgICAgICAgICAgICBjbGVhckludGVydmFsKHNlZWtpbmcpO1xuICAgICAgICAgICAgICAgICAgICByZXR1cm4gcmVzb2x2ZSh2aWRlbyk7XG4gICAgICAgICAgICAgICAgfSBlbHNlIGlmIChjb3VudGVyID49IE1BWF9TRUVLSU5HX1ZJREVPX1RBRykge1xuICAgICAgICAgICAgICAgICAgICBjbGVhckludGVydmFsKHNlZWtpbmcpO1xuICAgICAgICAgICAgICAgICAgICByZXR1cm4gcmVqZWN0KG5ldyBFcnJvcignSFRNTCB0YWcgdmlkZW8gbm90IGZvdW5kJykpO1xuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgICBjb3VudGVyKys7XG4gICAgICAgICAgICB9LCA1MDApO1xuICAgICAgICB9KS5jYXRjaCgoKSA9PiB7XG4gICAgICAgICAgICByZXR1cm4gcmVqZWN0KG5ldyBFcnJvcignZmluZCBodG1sNSBWaWRlbyBjaGVja2luZyBwcm9ibGVtJykpO1xuICAgICAgICB9KTtcbiAgICB9KTtcblxuICAgIHJldHVybiBwcm9taXNlO1xufTtcblxuXG5leHBvcnQgY29uc3QgZ2V0Rmlyc3RMZXZlbERvbWFpbiA9ICgpID0+IHtcbiAgICBpZiAodHlwZW9mIGxvY2F0aW9uICE9PSAndW5kZWZpbmVkJykge1xuICAgICAgICBpZiAobG9jYXRpb24uaG9zdG5hbWUuaW5jbHVkZXMoV1lTQ09VVF9IT1NUTkFNRVNfU1VGRklYLkNOKSkge1xuICAgICAgICAgICAgcmV0dXJuICcuY24nO1xuICAgICAgICB9XG4gICAgfVxuXG4gICAgcmV0dXJuICcuY29tJztcbn07XG4iLCJpbXBvcnQgeyBBTkFMWVRJQ1NfQVBQX1NPVVJDRSwgQU5BTFlUSUNTX0RFVEFJTEVEX1NPVVJDRSwgUExBWUVSX1RZUEUgfSBmcm9tICcuLi9jb25maWcvY29uZmlnJztcbmltcG9ydCB7IGdldFVybFBhcmFtcyB9IGZyb20gJy4uL3V0aWxpdGllcy91dGlscyc7XG5cbmV4cG9ydCBjb25zdCBjcmVhdGVBbmFseXRpY3NPYmplY3QgPSAodmlkZW8sIGRldGFpbGVkQXBwU291cmNlKSA9PiB7XG4gICAgcmV0dXJuIHtcbiAgICAgICAgYXBwU291cmNlOiBBTkFMWVRJQ1NfQVBQX1NPVVJDRSxcbiAgICAgICAgZGV0YWlsZWRBcHBTb3VyY2U6IGRldGFpbGVkQXBwU291cmNlLFxuICAgICAgICBhY3Rpb25WYWx1ZTogMSxcbiAgICAgICAgc2Vzc2lvbklkOiB2aWRlby5zZXNzaW9uSWQsXG4gICAgICAgIHBvc2l0aW9uOiBkZXRhaWxlZEFwcFNvdXJjZSA9PT0gQU5BTFlUSUNTX0RFVEFJTEVEX1NPVVJDRS5WSURFT19DT01QTEVURUQgPyB2aWRlby5kdXJhdGlvbiA6IHZpZGVvLmN1cnJlbnRUaW1lLCAvLyBzb21ldGltZXMgb24gdmlkZW8gZW5kLCBjdXJzb3IgcmV0dXJuIHRvIHBvc2l0aW9uIDBcbiAgICAgICAgdG90YWxMZW5ndGg6IHZpZGVvLmR1cmF0aW9uLFxuICAgICAgICBwbGF5ZXI6IHZpZGVvLnBsYXllclR5cGUgfHwgUExBWUVSX1RZUEUuQVBQUyxcbiAgICAgICAgaXNNdXRlZDogdmlkZW8ubXV0ZWQsXG4gICAgICAgIGZ1bGxTY3JlZW46IHZpZGVvLndlYmtpdERpc3BsYXlpbmdGdWxsc2NyZWVuLFxuICAgICAgICBpc1BsYXlsaXN0OiBfaXNQbGF5bGlzdCh2aWRlby5jdXJyZW50U3JjKSxcbiAgICB9O1xufTtcblxuXG5jb25zdCBfaXNQbGF5bGlzdCA9IChzcmMgPSAnc29tZXRleHQ/dmJlZ2luPTAnKSA9PiB7XG4gICAgY29uc3QgcGFyYW1zID0gZ2V0VXJsUGFyYW1zKHNyYyk7XG4gICAgcmV0dXJuIHBhcmFtcy52YmVnaW4gJiYgIU51bWJlci5pc05hTihwYXJhbXMudmJlZ2luKSAmJiBwYXJhbXMudmJlZ2luID4gMDtcbn07XG4iLCJpbXBvcnQgXyBmcm9tICdsb2Rhc2gnO1xuXG5leHBvcnQgY29uc3QgY2FsY3VsYXRlQXZlcmFnZUJpdFJhdGUgPSBzbmFwc2hvdHMgPT4ge1xuICAgIHJldHVybiBfLm1lYW5CeShzbmFwc2hvdHMsIHAgPT4gcC5kZWNvZGVkQnl0ZXMpO1xufTtcblxuZXhwb3J0IGNvbnN0IGNhbGN1bGF0ZUF2ZXJhZ2VGcmFtZVJhdGUgPSBzbmFwc2hvdHMgPT4ge1xuICAgIHJldHVybiBfLm1lYW5CeShzbmFwc2hvdHMsIHAgPT4gcC5kZWNvZGVkRnJhbWVzKTtcbn07XG4iLCJpbXBvcnQgeyB0cmFjayB9IGZyb20gJy4uL2FuYWx5dGljcy9hbmFseXRpY3NNYW5hZ2VyJztcbmltcG9ydCB7IGNyZWF0ZUFuYWx5dGljc09iamVjdCB9IGZyb20gJy4uL2FuYWx5dGljcy91dGlscyc7XG5pbXBvcnQgeyBBTkFMWVRJQ1NfRVZFTlRTLCBORVRXT1JLX1NUQVRFLCBBTkFMWVRJQ1NfREVUQUlMRURfU09VUkNFIH0gZnJvbSAnLi4vY29uZmlnL2NvbmZpZyc7XG5pbXBvcnQgeyBjYWxjdWxhdGVBdmVyYWdlQml0UmF0ZSwgY2FsY3VsYXRlQXZlcmFnZUZyYW1lUmF0ZSB9IGZyb20gJy4uL3V0aWxpdGllcy9zdGF0cyc7XG5cbmxldCBkYXRlU3RhcnRUaW1lc3RhbXAgPSAwO1xubGV0IGNhblBsYXlUaW1lU3RhbXAgPSAwO1xubGV0IHRvdGFsV2FpdGluZ1NlY29uZHMgPSAwO1xubGV0IHN0YXJ0V2FpdGluZ1NlY29uZHMgPSAwO1xubGV0IHJlYnVmZmVyaW5nRXZlbnRzTnVtID0gMDtcblxuZXhwb3J0IGNvbnN0IGxvYWRTdGFydCA9IChldmVudCkgPT4ge1xuICAgIC8vIGNvbnNvbGUubG9nKCdsb2FkU3RhcnQgLS0+ICcsIGV2ZW50KTtcbiAgICBkYXRlU3RhcnRUaW1lc3RhbXAgPSBuZXcgRGF0ZSgpLmdldFRpbWUoKTtcbn07XG5cbmV4cG9ydCBjb25zdCBkdXJhdGlvbmNoYW5nZSA9IChldmVudCkgPT4ge1xuICAgIC8vIGNvbnNvbGUubG9nKCdkdXJhdGlvbmNoYW5nZSAtLT4gJywgZXZlbnQpO1xufTtcblxuZXhwb3J0IGNvbnN0IGxvYWRlZG1ldGFkYXRhID0gKGV2ZW50KSA9PiB7XG4gICAgLy8gY29uc29sZS5sb2coJ2xvYWRlZG1ldGFkYXRhIC0tPiAnLCBldmVudCk7XG59O1xuXG5leHBvcnQgY29uc3QgZW5kZWQgPSAoZXZlbnQsIHNlc3Npb24pID0+IHtcbiAgICAvLyByaWdodCBub3cgd2UgbWF5IG5vdCBoYXZlIGFueW1vcmUgdmlkZW8gcHJvcGVydGllcyAoRXMuIHZpZGVvIGlzIHJlZ2VuZXJhdGVkIGJ5IGNsaWVudCksIHNvIHdlIGhhdmUgdG8gdXNlIHNlc3Npb24gaW5mby5cbiAgICBsZXQgYW5hbHl0aWNPYmogPSBjcmVhdGVBbmFseXRpY3NPYmplY3QoZXZlbnQudGFyZ2V0LCBBTkFMWVRJQ1NfREVUQUlMRURfU09VUkNFLlZJREVPX0NPTVBMRVRFRCk7XG4gICAgYW5hbHl0aWNPYmouYml0cmF0ZSA9IGNhbGN1bGF0ZUF2ZXJhZ2VCaXRSYXRlKHNlc3Npb24uc25hcHNob3RzKS50b0ZpeGVkKDEpO1xuICAgIGFuYWx5dGljT2JqLmZyYW1lcmF0ZSA9IGNhbGN1bGF0ZUF2ZXJhZ2VGcmFtZVJhdGUoc2Vzc2lvbi5zbmFwc2hvdHMpLnRvRml4ZWQoMCk7XG4gICAgYW5hbHl0aWNPYmoucG9zaXRpb24gPSBzZXNzaW9uLmR1cmF0aW9uO1xuICAgIGFuYWx5dGljT2JqLnRvdGFsTGVuZ3RoID0gc2Vzc2lvbi5kdXJhdGlvbjtcbiAgICB0cmFjayhBTkFMWVRJQ1NfRVZFTlRTLlBMQVlfQ09NUExFVEVELCBhbmFseXRpY09iaik7XG59O1xuXG5leHBvcnQgY29uc3QgbG9hZGVkZGF0YSA9IChldmVudCkgPT4ge1xuICAgIC8vIGNvbnNvbGUubG9nKCdsb2FkZWRkYXRhIC0tPiAnLCBldmVudCk7XG4gICAgLypcbiAgICAqIGNhbnBsYXkgYW5kIG90aGVycyBldmVudHMgYXJlIGFsc28gZmlyZWQgIGFmdGVyIHZpZGVvIGlzIGNvbXBsZXRlZC4gU28sIGluIG9yZGVyIHRvIHRyYWNrIG9uIHNlZ21lbnRcbiAgICAqIHdlIGFzc3VtZSB0aGF0IHZpZGVvIGlzIHN0YXJ0ZWQgd2hlbiB2aWRlbyBwbGF5ZXIgaGFzIGxvYWRlZCBhbGwgZGF0YS4gVGhpcyBldmVudCB0aGF0J3Mgbm90IGdvb2QgaW4gb3JkZXIgdG8gdHJhY2sgdmlkZW8tbWV0cmljc1xuICAgICovXG4gICAgY29uc3QgYW5hbHl0aWNPYmogPSBjcmVhdGVBbmFseXRpY3NPYmplY3QoZXZlbnQudGFyZ2V0LCBBTkFMWVRJQ1NfREVUQUlMRURfU09VUkNFLlZJREVPX1NUQVJUKTtcbiAgICB0cmFjayhBTkFMWVRJQ1NfRVZFTlRTLlBMQVlfU1RBUlRFRCwgYW5hbHl0aWNPYmopO1xufTtcblxuZXhwb3J0IGNvbnN0IHByb2dyZXNzID0gKGV2ZW50KSA9PiB7XG4gICAgY29uc3QgY3VycmVudFRpbWUgPSBuZXcgRGF0ZSgpLmdldFRpbWUoKTtcbiAgICAvLyBjb25zb2xlLmxvZygncHJvZ3Jlc3MgLS0+ICcsIGV2ZW50KTtcbiAgICBpZiAoc3RhcnRXYWl0aW5nU2Vjb25kcyA+IDApIHtcbiAgICAgICAgdG90YWxXYWl0aW5nU2Vjb25kcyArPSBjdXJyZW50VGltZSAtIHN0YXJ0V2FpdGluZ1NlY29uZHM7XG4gICAgICAgIHN0YXJ0V2FpdGluZ1NlY29uZHMgPSAwO1xuICAgIH1cbn07XG5cbmV4cG9ydCBjb25zdCBjYW5wbGF5ID0gKGV2ZW50KSA9PiB7XG4gICAgLy8gY29uc29sZS5sb2coJ2NhbnBsYXkgLS0+ICcsIGV2ZW50KTtcbiAgICBjYW5QbGF5VGltZVN0YW1wID0gbmV3IERhdGUoKS5nZXRUaW1lKCk7XG59O1xuXG5leHBvcnQgY29uc3QgcGF1c2UgPSAoZXZlbnQpID0+IHtcbiAgICBpZiAoZXZlbnQudGFyZ2V0Lm5ldHdvcmtTdGF0ZSA9PT0gTkVUV09SS19TVEFURS5OT19TT1VSQ0UpIHtcbiAgICAgICAgY29uc3QgYW5hbHl0aWNPYmogPSBjcmVhdGVBbmFseXRpY3NPYmplY3QoZXZlbnQudGFyZ2V0LCAnbm8gYXVkaW8vdmlkZW8gc291cmNlIGZvdW5kJyk7XG4gICAgICAgIC8vIHRyYWNrKEFOQUxZVElDU19FVkVOVFMuUExBWV9JTlRFUlJVUFRFRCwgYW5hbHl0aWNPYmopO1xuICAgIH1cbn07XG5cbmV4cG9ydCBjb25zdCBjYW5wbGF5dGhyb3VnaCA9IChldmVudCkgPT4ge1xuICAgIC8vIGNvbnNvbGUubG9nKCdjYW5wbGF5dGhyb3VnaCAtLT4gJywgZXZlbnQpO1xufTtcblxuZXhwb3J0IGNvbnN0IHdhaXRpbmcgPSAoZXZlbnQpID0+IHtcbiAgICAvLyBjb25zb2xlLmxvZygnd2FpdGluZyAtLT4gJywgZXZlbnQpO1xuICAgIHN0YXJ0V2FpdGluZ1NlY29uZHMgPSBuZXcgRGF0ZSgpLmdldFRpbWUoKTtcbiAgICByZWJ1ZmZlcmluZ0V2ZW50c051bSsrO1xufTtcblxuZXhwb3J0IGNvbnN0IGdldEpvaW5lZFRpbWUgPSAoKSA9PiB7XG4gICAgcmV0dXJuIGNhblBsYXlUaW1lU3RhbXAgJiYgZGF0ZVN0YXJ0VGltZXN0YW1wXG4gICAgICAgID8gY2FuUGxheVRpbWVTdGFtcCAtIGRhdGVTdGFydFRpbWVzdGFtcFxuICAgICAgICA6IDA7XG59O1xuXG5leHBvcnQgY29uc3QgZ2V0VG90YWxSZWJ1ZmZlcmluZ1RpbWUgPSAoKSA9PiB7XG4gICAgcmV0dXJuIHRvdGFsV2FpdGluZ1NlY29uZHM7XG59O1xuXG5leHBvcnQgY29uc3QgZ2V0VG90YWxSZWJ1ZmZlcmluZ0V2ZW50c051bSA9ICgpID0+IHtcbiAgICByZXR1cm4gcmVidWZmZXJpbmdFdmVudHNOdW07XG59O1xuIiwiZXhwb3J0IGNvbnN0IGNvbnZlcnRCeXRlc1RvQml0cyA9IGJ5dGVzID0+IGJ5dGVzICogODtcbiIsImltcG9ydCB7XG4gICAgZGVjb2RlZEZyYW1lQ291bnQsXG4gICAgZGVjb2RlZFZpZGVvQnl0ZUNvdW50LFxuICAgIGRlY29kZWRBdWRpb0J5dGVDb3VudCxcbiAgICBkaXNwbGF5U3VwcG9ydEZ1bGxTY3JlZW4sXG4gICAgZHJvcHBlZEZyYW1lQ291bnQsXG4gICAgZHVyYXRpb24sXG4gICAgY3VycmVudFNyYyxcbn0gZnJvbSAnLi4vY29yZS9IVE1MNVZpZGVvUHJvcGVydGllcyc7XG5cbmltcG9ydCB7XG4gICAgZm9ybWF0QnVmZmVyZWRSYW5nZXMsXG4gICAgZm9ybWF0U2Vla2FibGVSYW5nZXMsXG4gICAgZm9ybWF0UGxheWVkUmFuZ2VzLFxufSBmcm9tICcuLi91dGlsaXRpZXMvdXRpbHMuanMnO1xuXG5leHBvcnQgY29uc3QgY29tcG9zZU1ldHJpYyA9IChzdGFydFRpbWUsIHZpZGVvKSA9PiB7XG4gICAgcmV0dXJuIHtcbiAgICAgICAgc3RhcnRUaW1lOiBzdGFydFRpbWUgPyBzdGFydFRpbWUgOiBuZXcgRGF0ZSgpLFxuICAgICAgICBkZWNvZGVkRnJhbWVzOiBkZWNvZGVkRnJhbWVDb3VudCh2aWRlbyksXG4gICAgICAgIGRyb3BwZWRGcmFtZXM6IGRyb3BwZWRGcmFtZUNvdW50KHZpZGVvKSxcbiAgICAgICAgZGVjb2RlZEJ5dGVzOiBkZWNvZGVkVmlkZW9CeXRlQ291bnQodmlkZW8pLFxuICAgICAgICBkZWNvZGVkQXVkaW9CeXRlczogZGVjb2RlZEF1ZGlvQnl0ZUNvdW50KHZpZGVvKSxcbiAgICAgICAgZGlzcGxheVN1cHBvcnRGdWxsc2NyZWVuOiBkaXNwbGF5U3VwcG9ydEZ1bGxTY3JlZW4odmlkZW8pLFxuICAgICAgICBzcmM6IGN1cnJlbnRTcmModmlkZW8pLFxuICAgICAgICBkdXJhdGlvbjogZHVyYXRpb24odmlkZW8pLFxuICAgICAgICBidWZmZXJlZFJhbmdlczogZm9ybWF0QnVmZmVyZWRSYW5nZXModmlkZW8pLFxuICAgICAgICBwbGF5ZWRSYW5nZXM6IGZvcm1hdFBsYXllZFJhbmdlcyh2aWRlbyksXG4gICAgICAgIHNlZWthYmxlUmFuZ2VzOiBmb3JtYXRTZWVrYWJsZVJhbmdlcyh2aWRlbyksXG4gICAgfTtcbn07XG4iLCJleHBvcnQgZGVmYXVsdCBjbGFzcyBSZXBvcnQge1xuICAgIHNldFJlcG9ydFByb3BlcnRpZXMgPSByZXBvcnQgPT4ge1xuICAgICAgICBjb25zdCB7XG4gICAgICAgICAgICBkZWNvZGVkRnJhbWVzLFxuICAgICAgICAgICAgZHJvcHBlZEZyYW1lcyxcbiAgICAgICAgICAgIGRlY29kZWRCeXRlcyxcbiAgICAgICAgICAgIGRlY29kZWRBdWRpb0J5dGVzLFxuICAgICAgICAgICAgc3JjLFxuICAgICAgICAgICAgZHVyYXRpb24sXG4gICAgICAgICAgICBidWZmZXJlZFJhbmdlcyxcbiAgICAgICAgICAgIHBsYXllZFJhbmdlcyxcbiAgICAgICAgICAgIHNlZWthYmxlUmFuZ2VzLFxuICAgICAgICAgICAgc3RhcnRUaW1lLFxuICAgICAgICB9ID0gcmVwb3J0O1xuICAgICAgICB0aGlzLnN0YXJ0VGltZSA9IHN0YXJ0VGltZTtcbiAgICAgICAgdGhpcy5kZWNvZGVkRnJhbWVzID0gZGVjb2RlZEZyYW1lcztcbiAgICAgICAgdGhpcy5kcm9wcGVkRnJhbWVzID0gZHJvcHBlZEZyYW1lcztcbiAgICAgICAgdGhpcy5kZWNvZGVkQnl0ZXMgPSBkZWNvZGVkQnl0ZXM7XG4gICAgICAgIHRoaXMuZGVjb2RlZEF1ZGlvQnl0ZXMgPSBkZWNvZGVkQXVkaW9CeXRlcztcbiAgICAgICAgdGhpcy5zcmMgPSBzcmM7XG4gICAgICAgIHRoaXMuZHVyYXRpb24gPSBkdXJhdGlvbjtcbiAgICAgICAgdGhpcy5idWZmZXJlZFJhbmdlcyA9IGJ1ZmZlcmVkUmFuZ2VzO1xuICAgICAgICB0aGlzLnBsYXllZFJhbmdlcyA9IHBsYXllZFJhbmdlcztcbiAgICAgICAgdGhpcy5zZWVrYWJsZVJhbmdlcyA9IHNlZWthYmxlUmFuZ2VzO1xuICAgIH07XG5cbiAgICBzZXRTbmFwc2hvdHMgPSBzbmFwc2hvdHMgPT4ge1xuICAgICAgICB0aGlzLnNuYXBzaG90cyA9IHNuYXBzaG90cztcbiAgICB9O1xuXG4gICAgc2V0U2Vzc2lvbklkID0gc2Vzc2lvbklkID0+IHtcbiAgICAgICAgdGhpcy5zZXNzaW9uSWQgPSBzZXNzaW9uSWQ7XG4gICAgfTtcblxuICAgIHNldFVzZXJTZXR0aW5ncyA9IHVzZXJTZXR0aW5ncyA9PiB7XG4gICAgICAgIHRoaXMudXNlclNldHRpbmdzID0gdXNlclNldHRpbmdzO1xuICAgIH07XG5cbiAgICBjbGVhclNuYXBzaG90cyA9ICgpID0+ICh0aGlzLnNuYXBzaG90cyA9IFtdKTtcblxuICAgIHNldEpvaW5lZFRpbWUgPSBqb2luZWRUaW1lID0+ICh0aGlzLmpvaW5lZFRpbWUgPSBqb2luZWRUaW1lKTtcblxuICAgIHNldFJlYnVmZmVyaW5nVGltZSA9IHJlYnVmZmVyaW5nVGltZSA9PlxuICAgICAgICAodGhpcy5yZWJ1ZmZlcmluZ1RpbWUgPSByZWJ1ZmZlcmluZ1RpbWUpO1xuXG4gICAgc2V0UmVidWZmZXJpbmdFdmVudHMgPSByZWJ1ZmZlcmluZ0V2ZW50cyA9PlxuICAgICAgICAodGhpcy5yZWJ1ZmZlcmluZ0V2ZW50cyA9IHJlYnVmZmVyaW5nRXZlbnRzKTtcblxuICAgIHNldElwQWRkcmVzcyA9IGlwQWRkcmVzcyA9PiAodGhpcy5pcEFkZHJlc3MgPSBpcEFkZHJlc3MpO1xuXG4gICAgc2V0RW5kVGltZSA9IGVuZFRpbWUgPT4gKHRoaXMuZW5kVGltZSA9IGVuZFRpbWUpO1xuXG4gICAgc2V0QXZlcmFnZUJpdHJhdGUgPSBhdmVyYWdlQml0cmF0ZSA9PlxuICAgICAgICAodGhpcy5hdmVyYWdlQml0cmF0ZSA9IGF2ZXJhZ2VCaXRyYXRlKTtcbn1cbiIsImV4cG9ydCBkZWZhdWx0IGNsYXNzIFNlc3Npb24ge1xuICAgIGNvbnN0cnVjdG9yKCkge1xuICAgICAgICB0aGlzLnNuYXBzaG90cyA9IFtdO1xuICAgICAgICB0aGlzLnNlc3Npb25JZCA9IG51bGw7XG4gICAgICAgIHRoaXMuZHVyYXRpb24gPSAwO1xuICAgIH1cblxuICAgIGFkZFNuYXBzaG90ID0gKHNuYXBzaG90KSA9PiB7XG4gICAgICAgIHRoaXMuc25hcHNob3RzLnB1c2goc25hcHNob3QpO1xuICAgIH1cblxuICAgIGNsZWFyU25hcHNob3RzID0gKCkgPT4ge1xuICAgICAgICB0aGlzLnNuYXBzaG90cyA9IFtdO1xuICAgIH1cblxuICAgIHNldFNlc3Npb25Qcm9wZXJ0aWVzID0gKHNlc3Npb25JZCwgZHVyYXRpb24sIGN1cnJlbnRTcmMpID0+IHtcbiAgICAgICAgdGhpcy5zZXNzaW9uSWQgPSBzZXNzaW9uSWQ7XG4gICAgICAgIHRoaXMuZHVyYXRpb24gPSBkdXJhdGlvbjtcbiAgICAgICAgdGhpcy5jdXJyZW50U3JjID0gY3VycmVudFNyYztcbiAgICB9XG59XG4iLCIvKiBcbihUaGUgTUlUIExpY2Vuc2UpXG5Db3B5cmlnaHQgKGMpIDIwMTQgSGFsw6FzeiDDgWTDoW0gPG1haWxAYWRhbWhhbGFzei5jb20+XG5QZXJtaXNzaW9uIGlzIGhlcmVieSBncmFudGVkLCBmcmVlIG9mIGNoYXJnZSwgdG8gYW55IHBlcnNvbiBvYnRhaW5pbmcgYSBjb3B5IG9mIHRoaXMgc29mdHdhcmUgYW5kIGFzc29jaWF0ZWQgZG9jdW1lbnRhdGlvbiBmaWxlcyAodGhlIFwiU29mdHdhcmVcIiksIHRvIGRlYWwgaW4gdGhlIFNvZnR3YXJlIHdpdGhvdXQgcmVzdHJpY3Rpb24sIGluY2x1ZGluZyB3aXRob3V0IGxpbWl0YXRpb24gdGhlIHJpZ2h0cyB0byB1c2UsIGNvcHksIG1vZGlmeSwgbWVyZ2UsIHB1Ymxpc2gsIGRpc3RyaWJ1dGUsIHN1YmxpY2Vuc2UsIGFuZC9vciBzZWxsIGNvcGllcyBvZiB0aGUgU29mdHdhcmUsIGFuZCB0byBwZXJtaXQgcGVyc29ucyB0byB3aG9tIHRoZSBTb2Z0d2FyZSBpcyBmdXJuaXNoZWQgdG8gZG8gc28sIHN1YmplY3QgdG8gdGhlIGZvbGxvd2luZyBjb25kaXRpb25zOlxuVGhlIGFib3ZlIGNvcHlyaWdodCBub3RpY2UgYW5kIHRoaXMgcGVybWlzc2lvbiBub3RpY2Ugc2hhbGwgYmUgaW5jbHVkZWQgaW4gYWxsIGNvcGllcyBvciBzdWJzdGFudGlhbCBwb3J0aW9ucyBvZiB0aGUgU29mdHdhcmUuXG5USEUgU09GVFdBUkUgSVMgUFJPVklERUQgXCJBUyBJU1wiLCBXSVRIT1VUIFdBUlJBTlRZIE9GIEFOWSBLSU5ELCBFWFBSRVNTIE9SIElNUExJRUQsIElOQ0xVRElORyBCVVQgTk9UIExJTUlURUQgVE8gVEhFIFdBUlJBTlRJRVMgT0YgTUVSQ0hBTlRBQklMSVRZLCBGSVRORVNTIEZPUiBBIFBBUlRJQ1VMQVIgUFVSUE9TRSBBTkQgTk9OSU5GUklOR0VNRU5ULiBJTiBOTyBFVkVOVCBTSEFMTCBUSEUgQVVUSE9SUyBPUiBDT1BZUklHSFQgSE9MREVSUyBCRSBMSUFCTEUgRk9SIEFOWSBDTEFJTSwgREFNQUdFUyBPUiBPVEhFUiBMSUFCSUxJVFksIFdIRVRIRVIgSU4gQU4gQUNUSU9OIE9GIENPTlRSQUNULCBUT1JUIE9SIE9USEVSV0lTRSwgQVJJU0lORyBGUk9NLCBPVVQgT0YgT1IgSU4gQ09OTkVDVElPTiBXSVRIIFRIRSBTT0ZUV0FSRSBPUiBUSEUgVVNFIE9SIE9USEVSIERFQUxJTkdTIElOIFRIRSBTT0ZUV0FSRS5cbiovXG5cbi8vICBVbmlxdWUgSGV4YXRyaWRlY2ltYWwgSUQgR2VuZXJhdG9yXG4vLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT1cblxuLy8gIERlcGVuZGVuY2llc1xuLy8gPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09XG52YXIgcGlkID0gcHJvY2VzcyAmJiBwcm9jZXNzLnBpZCA/IHByb2Nlc3MucGlkLnRvU3RyaW5nKDM2KSA6ICcnIDtcbnZhciBhZGRyZXNzID0gJyc7XG5pZih0eXBlb2YgX193ZWJwYWNrX3JlcXVpcmVfXyAhPT0gJ2Z1bmN0aW9uJyl7XG4gICAgdmFyIG1hYyA9ICcnLCBuZXR3b3JrSW50ZXJmYWNlcyA9IHJlcXVpcmUoJ29zJykubmV0d29ya0ludGVyZmFjZXMoKTtcbiAgICBmb3IoaW50ZXJmYWNlX2tleSBpbiBuZXR3b3JrSW50ZXJmYWNlcyl7XG4gICAgICAgIGNvbnN0IG5ldHdvcmtJbnRlcmZhY2UgPSBuZXR3b3JrSW50ZXJmYWNlc1tpbnRlcmZhY2Vfa2V5XTtcbiAgICAgICAgY29uc3QgbGVuZ3RoID0gbmV0d29ya0ludGVyZmFjZS5sZW5ndGg7XG4gICAgICAgIGZvcih2YXIgaSA9IDA7IGkgPCBsZW5ndGg7IGkrKyl7XG4gICAgICAgICAgICBpZihuZXR3b3JrSW50ZXJmYWNlW2ldLm1hYyAmJiBuZXR3b3JrSW50ZXJmYWNlW2ldLm1hYyAhPSAnMDA6MDA6MDA6MDA6MDA6MDAnKXtcbiAgICAgICAgICAgICAgICBtYWMgPSBuZXR3b3JrSW50ZXJmYWNlW2ldLm1hYzsgYnJlYWs7XG4gICAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICB9XG4gICAgYWRkcmVzcyA9IG1hYyA/IHBhcnNlSW50KG1hYy5yZXBsYWNlKC9cXDp8XFxEKy9naSwgJycpKS50b1N0cmluZygzNikgOiAnJyA7XG59IFxuXG4vLyAgRXhwb3J0c1xuLy8gPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09XG5tb2R1bGUuZXhwb3J0cyA9IG1vZHVsZS5leHBvcnRzLmRlZmF1bHQgPSBmdW5jdGlvbihwcmVmaXgpeyByZXR1cm4gKHByZWZpeCB8fCAnJykgKyBhZGRyZXNzICsgcGlkICsgbm93KCkudG9TdHJpbmcoMzYpOyB9XG5tb2R1bGUuZXhwb3J0cy5wcm9jZXNzID0gZnVuY3Rpb24ocHJlZml4KXsgcmV0dXJuIChwcmVmaXggfHwgJycpICsgcGlkICsgbm93KCkudG9TdHJpbmcoMzYpOyB9XG5tb2R1bGUuZXhwb3J0cy50aW1lICAgID0gZnVuY3Rpb24ocHJlZml4KXsgcmV0dXJuIChwcmVmaXggfHwgJycpICsgbm93KCkudG9TdHJpbmcoMzYpOyB9XG5cbi8vICBIZWxwZXJzXG4vLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT1cbmZ1bmN0aW9uIG5vdygpe1xuICAgIHZhciB0aW1lID0gRGF0ZS5ub3coKTtcbiAgICB2YXIgbGFzdCA9IG5vdy5sYXN0IHx8IHRpbWU7XG4gICAgcmV0dXJuIG5vdy5sYXN0ID0gdGltZSA+IGxhc3QgPyB0aW1lIDogbGFzdCArIDE7XG59XG4iLCJpbXBvcnQge1xuICAgIGRlY29kZWRGcmFtZUNvdW50LFxuICAgIGRlY29kZWRWaWRlb0J5dGVDb3VudCxcbiAgICBkZWNvZGVkQXVkaW9CeXRlQ291bnQsXG4gICAgZGlzcGxheUlzRnVsbHNjcmVlbixcbiAgICBkcm9wcGVkRnJhbWVDb3VudCxcbiAgICBwYXVzZWQsXG4gICAgbmV0d29ya1N0YXRlLFxuICAgIGN1cnJlbnRUaW1lIGFzIGN1cnJlbnRWaWRlb1RpbWUsXG59IGZyb20gJy4vY29yZS9IVE1MNVZpZGVvUHJvcGVydGllcyc7XG5cbmltcG9ydCB7XG4gICAgbG9hZFN0YXJ0LFxuICAgIGR1cmF0aW9uY2hhbmdlLFxuICAgIGxvYWRlZG1ldGFkYXRhLFxuICAgIGxvYWRlZGRhdGEsXG4gICAgcHJvZ3Jlc3MsXG4gICAgY2FucGxheSxcbiAgICBjYW5wbGF5dGhyb3VnaCxcbiAgICB3YWl0aW5nLFxuICAgIGdldEpvaW5lZFRpbWUsXG4gICAgZ2V0VG90YWxSZWJ1ZmZlcmluZ1RpbWUsXG4gICAgZ2V0VG90YWxSZWJ1ZmZlcmluZ0V2ZW50c051bSxcbiAgICBwYXVzZSxcbiAgICBlbmRlZCxcbn0gZnJvbSAnLi9jb3JlL0V2ZW50c01hbmFnZXInO1xuXG5pbXBvcnQge1xuICAgIGdldFVzZXJQYXJhbXMsXG4gICAgZmluZEhUTUw1VmlkZW8sXG4gICAgY29udmVydEJ5dGVzVG9CaXRzLFxuICAgIGNvbXBvc2VNZXRyaWMsXG4gICAgY2hlY2tJc0VuYWJsZWRTdGF0dXMsXG59IGZyb20gJy4vdXRpbGl0aWVzJztcblxuaW1wb3J0IHsgQ2FsbGVyLCBnZXRJcEFkZHJlc3MgfSBmcm9tICcuL2NvcmUvQ2FsbGVyJztcblxuaW1wb3J0IHtcbiAgICBNQVhfUEFVU0VEX1NFQ09ORFMsXG4gICAgVFJBTlNNSVNTSU9OX1RZUEUsXG4gICAgUExBWUVSX1RZUEUsXG4gICAgQVBJX0hPU1ROQU1FLFxuICAgIEVOQUJMSU5HX1NUQVRVU19NSUxMSVNFQ09ORFMsXG59IGZyb20gJy4vY29uZmlnL2NvbmZpZyc7XG5cbmltcG9ydCBSZXBvcnQgZnJvbSAnLi9tb2RlbC9SZXBvcnQnO1xuaW1wb3J0IFNlc3Npb24gZnJvbSAnLi9tb2RlbC9TZXNzaW9uJztcbmltcG9ydCB1bmlxaWQgZnJvbSAndW5pcWlkJztcbmltcG9ydCB7IGluaXRBbmFseXRpY3MgfSBmcm9tICcuL2FuYWx5dGljcy9hbmFseXRpY3NNYW5hZ2VyJztcblxubGV0IGxhc3REZWNvZGVkRnJhbWVzID0gMDtcbmxldCBsYXN0RHJvcHBlZEZyYW1lcyA9IDA7XG5sZXQgbGFzdERlY29kZWRCeXRlcyA9IDA7XG5sZXQgbGFzdERlY29kZWRBdWRpb0J5dGVzID0gMDtcbmxldCBsYXN0QXVkaW9CaXRSYXRlID0gMDtcbmxldCBsYXN0VmlkZW9CaXRSYXRlID0gMDtcbmxldCB0b3RhbEF1ZGlvQml0UmF0ZSA9IDA7XG5sZXQgdG90YWxWaWRlb0JpdFJhdGUgPSAwO1xubGV0IHJlcXVlc3RBbmltYXRpb25JZCA9IDA7XG5sZXQgdGltZXI7XG5sZXQgc2Vzc2lvblRyYW5zbWlzc2lvbiA9IG51bGw7XG5sZXQgcmVwb3J0ID0gbmV3IFJlcG9ydCgpO1xubGV0IHNlc3Npb24gPSBuZXcgU2Vzc2lvbigpO1xubGV0IGxhc3RUaW1lID0gbnVsbDtcbmxldCBjdXJyZW50VGltZSA9IG51bGw7XG5sZXQgdmlkZW8gPSBudWxsO1xuXG5jb25zdCByZXNldFBhcmFtcyA9ICh0b3RhbFJlcG9ydCkgPT4ge1xuICAgIGxhc3REZWNvZGVkRnJhbWVzID0gdG90YWxSZXBvcnQuZGVjb2RlZEZyYW1lcztcbiAgICBsYXN0RHJvcHBlZEZyYW1lcyA9IHRvdGFsUmVwb3J0LmRyb3BwZWRGcmFtZXM7XG4gICAgbGFzdERlY29kZWRCeXRlcyA9IHRvdGFsUmVwb3J0LmRlY29kZWRCeXRlcztcbiAgICBsYXN0RGVjb2RlZEF1ZGlvQnl0ZXMgPSB0b3RhbFJlcG9ydC5kZWNvZGVkQXVkaW9CeXRlcztcbiAgICBsYXN0QXVkaW9CaXRSYXRlID0gdG90YWxBdWRpb0JpdFJhdGU7XG4gICAgbGFzdFZpZGVvQml0UmF0ZSA9IHRvdGFsVmlkZW9CaXRSYXRlO1xufTtcblxuY29uc3QgcmVzZXRXaXRoQ3VycmVudFZpZGVvVmFsdWVzID0gKGN1cnJlbnRWaWRlbykgPT4ge1xuICAgIGxhc3REZWNvZGVkRnJhbWVzID0gZGVjb2RlZEZyYW1lQ291bnQoY3VycmVudFZpZGVvKTtcbiAgICBsYXN0RHJvcHBlZEZyYW1lcyA9IGRyb3BwZWRGcmFtZUNvdW50KGN1cnJlbnRWaWRlbyk7XG4gICAgbGFzdERlY29kZWRCeXRlcyA9IGRlY29kZWRWaWRlb0J5dGVDb3VudChjdXJyZW50VmlkZW8pO1xuICAgIGxhc3REZWNvZGVkQXVkaW9CeXRlcyA9IGRlY29kZWRBdWRpb0J5dGVDb3VudChjdXJyZW50VmlkZW8pO1xuICAgIGxhc3RBdWRpb0JpdFJhdGUgPSBjb252ZXJ0Qnl0ZXNUb0JpdHMobGFzdERlY29kZWRBdWRpb0J5dGVzKTtcbiAgICBsYXN0VmlkZW9CaXRSYXRlID0gY29udmVydEJ5dGVzVG9CaXRzKGxhc3REZWNvZGVkQnl0ZXMpO1xufTtcblxuY29uc3QgcmVzZXRBbGwgPSAoKSA9PiB7XG4gICAgbGFzdERlY29kZWRGcmFtZXMgPSAwO1xuICAgIGxhc3REcm9wcGVkRnJhbWVzID0gMDtcbiAgICBsYXN0RGVjb2RlZEJ5dGVzID0gMDtcbiAgICBsYXN0RGVjb2RlZEF1ZGlvQnl0ZXMgPSAwO1xuICAgIGxhc3RBdWRpb0JpdFJhdGUgPSAwO1xuICAgIGxhc3RWaWRlb0JpdFJhdGUgPSAwO1xuICAgIHRvdGFsQXVkaW9CaXRSYXRlID0gMDtcbiAgICB0b3RhbFZpZGVvQml0UmF0ZSA9IDA7XG59O1xuXG5jb25zdCByZXF1ZXN0QW5pbUZyYW1lID0gKCgpID0+IHtcbiAgICByZXR1cm4gKFxuICAgICAgICB3aW5kb3cucmVxdWVzdEFuaW1hdGlvbkZyYW1lIHx8XG4gICAgICAgIHdpbmRvdy53ZWJraXRSZXF1ZXN0QW5pbWF0aW9uRnJhbWUgfHxcbiAgICAgICAgd2luZG93Lm1velJlcXVlc3RBbmltYXRpb25GcmFtZSB8fFxuICAgICAgICBmdW5jdGlvbihjYWxsYmFjaykge1xuICAgICAgICAgICAgd2luZG93LnNldFRpbWVvdXQoY2FsbGJhY2ssIDEwMDAgLyA2MCk7XG4gICAgICAgIH1cbiAgICApO1xufSkoKTtcblxuY29uc3QgY2FuY2VsQW5pbWF0aW9uRnJhbWUgPSB3aW5kb3cuY2FuY2VsQW5pbWF0aW9uRnJhbWUgfHwgd2luZG93Lm1vekNhbmNlbEFuaW1hdGlvbkZyYW1lO1xuXG5jb25zdCBjbG9zZVNlc3Npb24gPSAoKSA9PiB7XG4gICAgcmVwb3J0LnNldEpvaW5lZFRpbWUoZ2V0Sm9pbmVkVGltZSgpKTtcbiAgICByZXBvcnQuc2V0UmVidWZmZXJpbmdUaW1lKGdldFRvdGFsUmVidWZmZXJpbmdUaW1lKCkpO1xuICAgIHJlcG9ydC5zZXRSZWJ1ZmZlcmluZ0V2ZW50cyhnZXRUb3RhbFJlYnVmZmVyaW5nRXZlbnRzTnVtKCkpO1xuICAgIHJlcG9ydC5zZXRFbmRUaW1lKG5ldyBEYXRlKCkpO1xuICAgIENhbGxlcihyZXBvcnQsICdzZXNzaW9uJywgc2Vzc2lvblRyYW5zbWlzc2lvbik7XG59O1xuXG5jb25zdCBzdGFydFdvcmsgPSAod2l0aFJlc2V0ID0gZmFsc2UpID0+IHtcbiAgICBpZiAod2l0aFJlc2V0KSB7XG4gICAgICAgIHJlc2V0V2l0aEN1cnJlbnRWaWRlb1ZhbHVlcyh2aWRlbyk7XG4gICAgICAgIGN1cnJlbnRUaW1lID0gbmV3IERhdGUoKS5nZXRUaW1lKCk7XG4gICAgICAgIGxhc3RUaW1lID0gY3VycmVudFRpbWU7XG4gICAgfVxuICAgIGlmICghcmVxdWVzdEFuaW1hdGlvbklkKSB0aW1lcigpO1xuICAgIGVsc2UgY29uc29sZS5sb2coJ1Byb2ZpbGVyIGlzIGFscmVhZHkgcnVubmluZycpO1xuXG4gICAgc2Vzc2lvbiA9IG5ldyBTZXNzaW9uKCk7XG59O1xuXG5jb25zdCBzdG9wV29yayA9ICh3aXRoQ2xvc2VTZXNzaW9uID0gZmFsc2UpID0+IHtcbiAgICBjYW5jZWxBbmltYXRpb25GcmFtZShyZXF1ZXN0QW5pbWF0aW9uSWQpO1xuICAgIHJlcXVlc3RBbmltYXRpb25JZCA9IDA7XG4gICAgaWYgKHdpdGhDbG9zZVNlc3Npb24pIGNsb3NlU2Vzc2lvbigpO1xufTtcblxuY29uc3Qgb25WaWRlb0VuZGVkID0gKGV2ZW50KSA9PiB7XG4gICAgZW5kZWQoZXZlbnQsIHNlc3Npb24pOyAvLyB0cmFjayBpbnRvIGFuYWx5dGljc1xuICAgIHN0b3BXb3JrKHRydWUpOyAvLyBzdG9wcGluZyBzbmlmZmluZ1xuICAgIHJlc2V0QWxsKCk7IC8vIHJlc2V0IGFsbCB2YWx1ZXMgaW4gb3JkZXIgdG8gcGxheSB0aGUgbmV4dCB2aWRlb1xufTtcblxuY29uc3Qgb25UYWJWaXNpYmlsaXR5Y2hhbmdlID0gZXZlbnQgPT4ge1xuICAgIGlmIChkb2N1bWVudC52aXNpYmlsaXR5U3RhdGUgPT09ICdoaWRkZW4nKSBzdG9wV29yaygpO1xuICAgIGVsc2Ugc3RhcnRXb3JrKHRydWUpO1xufTtcblxuY29uc3Qgb25WaWRlb1BsYXlpbmcgPSBldmVudCA9PiB7XG4gICAgc3RhcnRXb3JrKCk7XG59O1xuXG5leHBvcnQgY29uc3Qgc3RvcFNuaWZmaW5nVmlkZW9NZXRyaWNzID0gKCkgPT4ge1xuICAgIGNvbnNvbGUubG9nKCdQcm9maWxlciBpcyBnb2luZyB0byBzdG9wIHdvcmsnKTtcbiAgICBkb2N1bWVudC5yZW1vdmVFdmVudExpc3RlbmVyKCd2aXNpYmlsaXR5Y2hhbmdlJywgb25UYWJWaXNpYmlsaXR5Y2hhbmdlKTtcbiAgICB2aWRlby5yZW1vdmVFdmVudExpc3RlbmVyKCdsb2Fkc3RhcnQnLCBsb2FkU3RhcnQsIGZhbHNlKTtcbiAgICB2aWRlby5yZW1vdmVFdmVudExpc3RlbmVyKCdkdXJhdGlvbmNoYW5nZScsIGR1cmF0aW9uY2hhbmdlLCBmYWxzZSk7XG4gICAgdmlkZW8ucmVtb3ZlRXZlbnRMaXN0ZW5lcignbG9hZGVkbWV0YWRhdGEnLCBsb2FkZWRtZXRhZGF0YSwgZmFsc2UpO1xuICAgIHZpZGVvLnJlbW92ZUV2ZW50TGlzdGVuZXIoJ2xvYWRlZGRhdGEnLCBsb2FkZWRkYXRhLCBmYWxzZSk7XG4gICAgdmlkZW8ucmVtb3ZlRXZlbnRMaXN0ZW5lcigncHJvZ3Jlc3MnLCBwcm9ncmVzcywgZmFsc2UpO1xuICAgIHZpZGVvLnJlbW92ZUV2ZW50TGlzdGVuZXIoJ2NhbnBsYXknLCBjYW5wbGF5LCBmYWxzZSk7XG4gICAgdmlkZW8ucmVtb3ZlRXZlbnRMaXN0ZW5lcignY2FucGxheXRocm91Z2gnLCBjYW5wbGF5dGhyb3VnaCwgZmFsc2UpO1xuICAgIHZpZGVvLnJlbW92ZUV2ZW50TGlzdGVuZXIoJ3dhaXRpbmcnLCB3YWl0aW5nLCBmYWxzZSk7XG4gICAgdmlkZW8ucmVtb3ZlRXZlbnRMaXN0ZW5lcigncGF1c2UnLCBwYXVzZSwgZmFsc2UpO1xuICAgIHZpZGVvLnJlbW92ZUV2ZW50TGlzdGVuZXIoJ2VuZGVkJywgb25WaWRlb0VuZGVkLCBmYWxzZSk7XG4gICAgdmlkZW8ucmVtb3ZlRXZlbnRMaXN0ZW5lcigncGxheWluZycsIG9uVmlkZW9QbGF5aW5nLCBmYWxzZSk7XG4gICAgc3RvcFdvcmsoKTtcbn07XG5cbmNvbnN0IGNoZWNrU3RhdHVzSW50ZXJ2YWwgPSAoYWNjZXNzVG9rZW4sIGFwaUhvc3RuYW1lKSA9PiB7XG4gICAgbGV0IGludGVydmFsID0gc2V0SW50ZXJ2YWwoKCkgPT4ge1xuICAgICAgICBjaGVja0lzRW5hYmxlZFN0YXR1cyhhY2Nlc3NUb2tlbiwgYXBpSG9zdG5hbWUpLnRoZW4oKHJlc3BvbnNlKSA9PiB7XG4gICAgICAgICAgICBpZiAoIXJlc3BvbnNlKSB7XG4gICAgICAgICAgICAgICAgc3RvcFNuaWZmaW5nVmlkZW9NZXRyaWNzKCk7XG4gICAgICAgICAgICAgICAgY2xlYXJJbnRlcnZhbChpbnRlcnZhbCk7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICBpZiAocmVzcG9uc2UgJiYgIXJlcXVlc3RBbmltYXRpb25JZCkgc3RhcnRXb3JrKCk7XG4gICAgICAgIH0pXG4gICAgICAgICAgICAuY2F0Y2goKCkgPT4ge1xuICAgICAgICAgICAgICAgIHN0b3BTbmlmZmluZ1ZpZGVvTWV0cmljcygpO1xuICAgICAgICAgICAgICAgIGNsZWFySW50ZXJ2YWwoaW50ZXJ2YWwpO1xuICAgICAgICAgICAgfSk7XG4gICAgfSwgRU5BQkxJTkdfU1RBVFVTX01JTExJU0VDT05EUyk7XG59O1xuXG5leHBvcnQgY29uc3Qgc3RhcnRTbmlmZmluZ1ZpZGVvTWV0cmljcyA9ICh1c2VyU2V0dGluZ3MsIHBsYXllclR5cGUsIHRyYW5zbWlzc2lvbiA9IFRSQU5TTUlTU0lPTl9UWVBFLkxPR1NUQVNILCBhcGlIb3N0bmFtZSA9IEFQSV9IT1NUTkFNRSkgPT4ge1xuICAgIGZpbmRIVE1MNVZpZGVvKHVzZXJTZXR0aW5ncywgYXBpSG9zdG5hbWUpXG4gICAgICAgIC50aGVuKGZvdW5kVmlkZW8gPT4ge1xuICAgICAgICAgICAgdmlkZW8gPSBmb3VuZFZpZGVvO1xuICAgICAgICAgICAgY29uc3Qgc2Vzc2lvbklkID0gdW5pcWlkKCk7XG4gICAgICAgICAgICBjb25zdCBwcm9maWxlID0gIXVzZXJTZXR0aW5ncyA/IGdldFVzZXJQYXJhbXMoKSA6IHVzZXJTZXR0aW5ncztcbiAgICAgICAgICAgIHNlc3Npb25UcmFuc21pc3Npb24gPSB0cmFuc21pc3Npb247XG4gICAgICAgICAgICBpbml0QW5hbHl0aWNzKHByb2ZpbGUudXNlcklkKTtcbiAgICAgICAgICAgIHZpZGVvLnNlc3Npb25JZCA9IHNlc3Npb25JZDtcbiAgICAgICAgICAgIHJlcG9ydC5zZXRTZXNzaW9uSWQoc2Vzc2lvbklkKTtcblxuICAgICAgICAgICAgZG9jdW1lbnQuYWRkRXZlbnRMaXN0ZW5lcigndmlzaWJpbGl0eWNoYW5nZScsIG9uVGFiVmlzaWJpbGl0eWNoYW5nZSk7XG4gICAgICAgICAgICB2aWRlby5wbGF5ZXJUeXBlID0gcGxheWVyVHlwZSB8fCBQTEFZRVJfVFlQRS5QTEFURlJPTTtcbiAgICAgICAgICAgIHZpZGVvLmFkZEV2ZW50TGlzdGVuZXIoJ2xvYWRzdGFydCcsIGxvYWRTdGFydCwgZmFsc2UpO1xuICAgICAgICAgICAgdmlkZW8uYWRkRXZlbnRMaXN0ZW5lcignZHVyYXRpb25jaGFuZ2UnLCBkdXJhdGlvbmNoYW5nZSwgZmFsc2UpO1xuICAgICAgICAgICAgdmlkZW8uYWRkRXZlbnRMaXN0ZW5lcignbG9hZGVkbWV0YWRhdGEnLCBsb2FkZWRtZXRhZGF0YSwgZmFsc2UpO1xuICAgICAgICAgICAgdmlkZW8uYWRkRXZlbnRMaXN0ZW5lcignbG9hZGVkZGF0YScsIGxvYWRlZGRhdGEsIGZhbHNlKTtcbiAgICAgICAgICAgIHZpZGVvLmFkZEV2ZW50TGlzdGVuZXIoJ3Byb2dyZXNzJywgcHJvZ3Jlc3MsIGZhbHNlKTtcbiAgICAgICAgICAgIHZpZGVvLmFkZEV2ZW50TGlzdGVuZXIoJ2NhbnBsYXknLCBjYW5wbGF5LCBmYWxzZSk7XG4gICAgICAgICAgICB2aWRlby5hZGRFdmVudExpc3RlbmVyKCdjYW5wbGF5dGhyb3VnaCcsIGNhbnBsYXl0aHJvdWdoLCBmYWxzZSk7XG4gICAgICAgICAgICB2aWRlby5hZGRFdmVudExpc3RlbmVyKCd3YWl0aW5nJywgd2FpdGluZywgZmFsc2UpO1xuICAgICAgICAgICAgdmlkZW8uYWRkRXZlbnRMaXN0ZW5lcigncGF1c2UnLCBwYXVzZSwgZmFsc2UpO1xuICAgICAgICAgICAgdmlkZW8uYWRkRXZlbnRMaXN0ZW5lcignZW5kZWQnLCBvblZpZGVvRW5kZWQsIGZhbHNlKTtcbiAgICAgICAgICAgIHZpZGVvLmFkZEV2ZW50TGlzdGVuZXIoJ3BsYXlpbmcnLCBvblZpZGVvUGxheWluZywgZmFsc2UpO1xuXG4gICAgICAgICAgICByZXBvcnQuc2V0VXNlclNldHRpbmdzKHByb2ZpbGUpO1xuXG4gICAgICAgICAgICBnZXRJcEFkZHJlc3MoKS50aGVuKGNhbGwgPT4ge1xuICAgICAgICAgICAgICAgIGlmIChjYWxsICYmIGNhbGwuZGF0YSAmJiBjYWxsLmRhdGEucmVzcG9uc2UpIHtcbiAgICAgICAgICAgICAgICAgICAgcmVwb3J0LnNldElwQWRkcmVzcyhjYWxsLmRhdGEucmVzcG9uc2UpO1xuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgIH0pO1xuXG4gICAgICAgICAgICBsYXN0VGltZSA9IG5ldyBEYXRlKCkuZ2V0VGltZSgpO1xuICAgICAgICAgICAgbGV0IG51bVBhdXNlZFNlY29uZHMgPSAwO1xuICAgICAgICAgICAgY3VycmVudFRpbWUgPSAwO1xuXG4gICAgICAgICAgICBjaGVja1N0YXR1c0ludGVydmFsKHByb2ZpbGUuYWNjZXNzVG9rZW4sIGFwaUhvc3RuYW1lKTtcblxuICAgICAgICAgICAgdGltZXIgPSAoKSA9PiB7XG4gICAgICAgICAgICAgICAgcmVxdWVzdEFuaW1hdGlvbklkID0gcmVxdWVzdEFuaW1GcmFtZSh0aW1lcik7XG4gICAgICAgICAgICAgICAgc2Vzc2lvbi5zZXRTZXNzaW9uUHJvcGVydGllcyhzZXNzaW9uSWQsIHZpZGVvLmR1cmF0aW9uLCB2aWRlby5jdXJyZW50U3JjKTtcbiAgICAgICAgICAgICAgICBjdXJyZW50VGltZSA9IG5ldyBEYXRlKCkuZ2V0VGltZSgpO1xuXG4gICAgICAgICAgICAgICAgaWYgKGN1cnJlbnRUaW1lIC0gbGFzdFRpbWUgPj0gMTAwMCkge1xuICAgICAgICAgICAgICAgICAgICAvLyDDqCBwYXNzYXRvIHVuIHNlY29uZG9cbiAgICAgICAgICAgICAgICAgICAgbGFzdFRpbWUgPSBjdXJyZW50VGltZTtcblxuICAgICAgICAgICAgICAgICAgICBpZiAocGF1c2VkKHZpZGVvKSkge1xuICAgICAgICAgICAgICAgICAgICAgICAgbnVtUGF1c2VkU2Vjb25kcysrO1xuICAgICAgICAgICAgICAgICAgICAgICAgaWYgKG51bVBhdXNlZFNlY29uZHMgPiBNQVhfUEFVU0VEX1NFQ09ORFMpIHN0b3BXb3JrKHRydWUpO1xuICAgICAgICAgICAgICAgICAgICAgICAgcmV0dXJuO1xuICAgICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgICAgIG51bVBhdXNlZFNlY29uZHMgPSAwO1xuXG4gICAgICAgICAgICAgICAgICAgIGxldCBtZXRyaWMgPSBjb21wb3NlTWV0cmljKHJlcG9ydC5zdGFydFRpbWUsIHZpZGVvKTtcblxuICAgICAgICAgICAgICAgICAgICB0b3RhbFZpZGVvQml0UmF0ZSA9IGNvbnZlcnRCeXRlc1RvQml0cyhtZXRyaWMuZGVjb2RlZEJ5dGVzKTtcbiAgICAgICAgICAgICAgICAgICAgdG90YWxBdWRpb0JpdFJhdGUgPSBjb252ZXJ0Qnl0ZXNUb0JpdHMoXG4gICAgICAgICAgICAgICAgICAgICAgICBtZXRyaWMuZGVjb2RlZEF1ZGlvQnl0ZXMsXG4gICAgICAgICAgICAgICAgICAgICk7XG4gICAgICAgICAgICAgICAgICAgIHJlcG9ydC5zZXRSZXBvcnRQcm9wZXJ0aWVzKG1ldHJpYyk7XG5cbiAgICAgICAgICAgICAgICAgICAgbGV0IHNuYXBzaG90ID0ge1xuICAgICAgICAgICAgICAgICAgICAgICAgZWZmZWN0aXZlVGltZTogbmV3IERhdGUoKSxcbiAgICAgICAgICAgICAgICAgICAgICAgIGRlY29kZWRGcmFtZXM6IHJlcG9ydC5kZWNvZGVkRnJhbWVzIC0gbGFzdERlY29kZWRGcmFtZXMsXG4gICAgICAgICAgICAgICAgICAgICAgICBkcm9wcGVkRnJhbWVzOiByZXBvcnQuZHJvcHBlZEZyYW1lcyAtIGxhc3REcm9wcGVkRnJhbWVzLFxuICAgICAgICAgICAgICAgICAgICAgICAgZGVjb2RlZEJ5dGVzOiByZXBvcnQuZGVjb2RlZEJ5dGVzIC0gbGFzdERlY29kZWRCeXRlcyxcbiAgICAgICAgICAgICAgICAgICAgICAgIGRlY29kZWRBdWRpb0J5dGVzOlxuICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJlcG9ydC5kZWNvZGVkQXVkaW9CeXRlcyAtIGxhc3REZWNvZGVkQXVkaW9CeXRlcyxcbiAgICAgICAgICAgICAgICAgICAgICAgIGRpc3BsYXlJc0Z1bGxzY3JlZW46IGRpc3BsYXlJc0Z1bGxzY3JlZW4odmlkZW8pLFxuICAgICAgICAgICAgICAgICAgICAgICAgdmlkZW9CaXRSYXRlOiB0b3RhbFZpZGVvQml0UmF0ZSAtIGxhc3RWaWRlb0JpdFJhdGUsXG4gICAgICAgICAgICAgICAgICAgICAgICBhdWRpb0JpdFJhdGU6IHRvdGFsQXVkaW9CaXRSYXRlIC0gbGFzdEF1ZGlvQml0UmF0ZSxcbiAgICAgICAgICAgICAgICAgICAgICAgIGN1cnJlbnRUaW1lOiBjdXJyZW50VmlkZW9UaW1lKHZpZGVvKS50b0ZpeGVkKDIpLFxuICAgICAgICAgICAgICAgICAgICAgICAgbmV0d29ya1N0YXRlOiBuZXR3b3JrU3RhdGUodmlkZW8pLFxuICAgICAgICAgICAgICAgICAgICAgICAgc2Vzc2lvbklkOiByZXBvcnQuc2Vzc2lvbklkLFxuICAgICAgICAgICAgICAgICAgICAgICAgdXNlclNldHRpbmdzOiBwcm9maWxlLFxuICAgICAgICAgICAgICAgICAgICB9O1xuICAgICAgICAgICAgICAgICAgICBzZXNzaW9uLmFkZFNuYXBzaG90KHNuYXBzaG90KTtcblxuICAgICAgICAgICAgICAgICAgICByZXNldFBhcmFtcyhyZXBvcnQpO1xuICAgICAgICAgICAgICAgICAgICBDYWxsZXIoc25hcHNob3QsICdzbmFwc2hvdCcsIHNlc3Npb25UcmFuc21pc3Npb24pO1xuICAgICAgICAgICAgICAgIH1cbiAgICAgICAgICAgIH07XG4gICAgICAgIH0pXG4gICAgICAgIC5jYXRjaCgoKSA9PiB7XG4gICAgICAgICAgICAvLyBjb25zb2xlLmVycm9yKGVycik7XG4gICAgICAgIH0pO1xufTtcbiIsImltcG9ydCBSZWFjdCwgeyBDb21wb25lbnQgfSBmcm9tICdyZWFjdCc7XG5pbXBvcnQge1xuICAgIHN0YXJ0U25pZmZpbmdWaWRlb01ldHJpY3MsXG4gICAgc3RvcFNuaWZmaW5nVmlkZW9NZXRyaWNzLFxufSBmcm9tICcuL21ldHJpY3NNYW5hZ2VyJztcbmltcG9ydCBQcm9wVHlwZXMgZnJvbSAncHJvcC10eXBlcyc7XG5pbXBvcnQgeyBUUkFOU01JU1NJT05fVFlQRSwgUExBWUVSX1RZUEUsIEFQSV9IT1NUTkFNRSB9IGZyb20gJy4vY29uZmlnL2NvbmZpZyc7XG5cbmV4cG9ydCBjbGFzcyBXeU1ldHJpY1Byb2ZpbGVyIGV4dGVuZHMgQ29tcG9uZW50IHtcbiAgICBjb25zdHJ1Y3RvcigpIHtcbiAgICAgICAgc3VwZXIoKTtcbiAgICAgICAgdGhpcy5zdGF0ZSA9IHtcbiAgICAgICAgICAgIHJ1bm5pbmc6IGZhbHNlLFxuICAgICAgICAgICAgc3RhcnRPbk1vdW50OiB0cnVlLFxuICAgICAgICB9O1xuICAgIH1cblxuICAgIHN0YXRpYyBwcm9wVHlwZXMgPSB7XG4gICAgICAgIHJ1bm5pbmc6IFByb3BUeXBlcy5ib29sLmlzUmVxdWlyZWQsXG4gICAgICAgIHN0YXJ0T25Nb3VudDogUHJvcFR5cGVzLmJvb2wsXG4gICAgICAgIHVzZXJTZXR0aW5nczogUHJvcFR5cGVzLnNoYXBlKHtcbiAgICAgICAgICAgIHVzZXJJZDogUHJvcFR5cGVzLm51bWJlcixcbiAgICAgICAgICAgIHVzZXJOYW1lOiBQcm9wVHlwZXMuc3RyaW5nLFxuICAgICAgICAgICAgZ3JvdXBJZDogUHJvcFR5cGVzLm51bWJlcixcbiAgICAgICAgICAgIHN1Ymdyb3VwSWQ6IFByb3BUeXBlcy5udW1iZXIsXG4gICAgICAgICAgICBhY2Nlc3NUb2tlbjogUHJvcFR5cGVzLnN0cmluZyxcbiAgICAgICAgfSkuaXNSZXF1aXJlZCxcbiAgICAgICAgdHJhbnNtaXR0ZXI6IFByb3BUeXBlcy5vbmVPZihbVFJBTlNNSVNTSU9OX1RZUEUuTE9HU1RBU0gsIFRSQU5TTUlTU0lPTl9UWVBFLlJFU1RdKSxcbiAgICAgICAgcGxheWVyVHlwZTogUHJvcFR5cGVzLm9uZU9mKFtQTEFZRVJfVFlQRS5QTEFURk9STSwgUExBWUVSX1RZUEUuQVBQU10pLFxuICAgICAgICBjaGlsZHJlbjogUHJvcFR5cGVzLm5vZGUuaXNSZXF1aXJlZCxcbiAgICAgICAgYXBpSG9zdG5hbWU6IFByb3BUeXBlcy5zdHJpbmcsXG4gICAgfTtcblxuICAgIHN0YXRpYyBkZWZhdWx0UHJvcHMgPSB7XG4gICAgICAgIHN0YXJ0T25Nb3VudDogdHJ1ZSxcbiAgICAgICAgdHJhbnNtaXR0ZXI6IFRSQU5TTUlTU0lPTl9UWVBFLkxPR1NUQVNILFxuICAgICAgICBwbGF5ZXJUeXBlOiBQTEFZRVJfVFlQRS5QTEFURk9STSxcbiAgICAgICAgYXBpSG9zdG5hbWU6IEFQSV9IT1NUTkFNRSxcbiAgICB9O1xuXG4gICAgY29tcG9uZW50RGlkTW91bnQgPSAoKSA9PiB7XG4gICAgICAgIGNvbnN0IHsgc3RhcnRPbk1vdW50LCB1c2VyU2V0dGluZ3MsIHBsYXllclR5cGUsIHRyYW5zbWl0dGVyLCBhcGlIb3N0bmFtZSB9ID0gdGhpcy5wcm9wcztcbiAgICAgICAgaWYgKHN0YXJ0T25Nb3VudCkge1xuICAgICAgICAgICAgc3RhcnRTbmlmZmluZ1ZpZGVvTWV0cmljcyh1c2VyU2V0dGluZ3MsIHBsYXllclR5cGUsIHRyYW5zbWl0dGVyLCBhcGlIb3N0bmFtZSk7XG4gICAgICAgIH1cbiAgICB9O1xuXG4gICAgc3RhdGljIGdldERlcml2ZWRTdGF0ZUZyb21Qcm9wcyhwcm9wcywgc3RhdGUpIHtcbiAgICAgICAgY29uc3QgeyB1c2VyU2V0dGluZ3MsIHBsYXllclR5cGUsIHRyYW5zbWl0dGVyLCBydW5uaW5nLCBhcGlIb3N0bmFtZSB9ID0gcHJvcHM7XG5cbiAgICAgICAgaWYgKHJ1bm5pbmcgJiYgIXN0YXRlLnJ1bm5pbmcpIHtcbiAgICAgICAgICAgIHN0YXJ0U25pZmZpbmdWaWRlb01ldHJpY3ModXNlclNldHRpbmdzLCBwbGF5ZXJUeXBlLCB0cmFuc21pdHRlciwgYXBpSG9zdG5hbWUpO1xuICAgICAgICB9IGVsc2UgaWYgKCFydW5uaW5nICYmIHN0YXRlLnJ1bm5pbmcpIHtcbiAgICAgICAgICAgIHN0b3BTbmlmZmluZ1ZpZGVvTWV0cmljcygpO1xuICAgICAgICB9XG5cbiAgICAgICAgcmV0dXJuIHtcbiAgICAgICAgICAgIHJ1bm5pbmc6IHByb3BzLnJ1bm5pbmcsXG4gICAgICAgIH07XG4gICAgfVxuXG4gICAgcmVuZGVyKCkge1xuICAgICAgICByZXR1cm4gPGRpdj57dGhpcy5wcm9wcy5jaGlsZHJlbn08L2Rpdj47XG4gICAgfVxufVxuIl0sIm5hbWVzIjpbImRlY29kZWRGcmFtZUNvdW50IiwidmlkZW8iLCJ3ZWJraXREZWNvZGVkRnJhbWVDb3VudCIsImRlY29kZWRWaWRlb0J5dGVDb3VudCIsIndlYmtpdFZpZGVvRGVjb2RlZEJ5dGVDb3VudCIsImRlY29kZWRBdWRpb0J5dGVDb3VudCIsIndlYmtpdEF1ZGlvRGVjb2RlZEJ5dGVDb3VudCIsImRpc3BsYXlJc0Z1bGxzY3JlZW4iLCJ3ZWJraXREaXNwbGF5aW5nRnVsbHNjcmVlbiIsImRpc3BsYXlTdXBwb3J0RnVsbFNjcmVlbiIsIndlYmtpdFN1cHBvcnRzRnVsbHNjcmVlbiIsImRyb3BwZWRGcmFtZUNvdW50Iiwid2Via2l0RHJvcHBlZEZyYW1lQ291bnQiLCJkdXJhdGlvbiIsInBhdXNlZCIsImN1cnJlbnRTcmMiLCJuZXR3b3JrU3RhdGUiLCJjdXJyZW50VGltZSIsImluaXRBbmFseXRpY3MiLCJ1c2VySWQiLCJyZXN0QXBpQmFzZU5hbWUiLCJlbnYiLCJwcm9jZXNzIiwiUkVBQ1RfQVBQX0VOViIsIk5PREVfRU5WIiwiQVBJX0hPU1ROQU1FIiwiQVBJX1NFUlZFUiIsIk1BWF9TRUVLSU5HX1ZJREVPX1RBRyIsIk1BWF9QQVVTRURfU0VDT05EUyIsIkVOQUJMSU5HX1NUQVRVU19NSUxMSVNFQ09ORFMiLCJUUkFOU01JU1NJT05fVFlQRSIsIlJFU1QiLCJMT0dTVEFTSCIsIk5FVFdPUktfU1RBVEUiLCJFTVBUWSIsIklETEUiLCJMT0FESU5HIiwiTk9fU09VUkNFIiwiQU5BTFlUSUNTX0FQUF9TT1VSQ0UiLCJBTkFMWVRJQ1NfREVUQUlMRURfU09VUkNFIiwiVklERU9fU1RBUlQiLCJWSURFT19DT01QTEVURUQiLCJQTEFZRVJfVFlQRSIsIlBMQVRGT1JNIiwiQVBQUyIsIldZU0NPVVRfSE9TVE5BTUVTX1NVRkZJWCIsIkRFRkFVTFQiLCJSVSIsIkNOIiwiaXNCdWZmZXIiLCJidG9hIiwicmVxdWlyZSQkMCIsImNvb2tpZXMiLCJyZXF1aXJlJCQxIiwiZGVmYXVsdHMiLCJJbnRlcmNlcHRvck1hbmFnZXIiLCJDYW5jZWwiLCJBeGlvcyIsInJlcXVpcmUkJDIiLCJyZXF1aXJlJCQzIiwidG9TdHJpbmciLCJpc0FycmF5IiwiaXNBcnJheUJ1ZmZlciIsImlzRm9ybURhdGEiLCJpc0FycmF5QnVmZmVyVmlldyIsImlzU3RyaW5nIiwiaXNOdW1iZXIiLCJpc1VuZGVmaW5lZCIsImlzT2JqZWN0IiwiaXNEYXRlIiwiaXNGaWxlIiwiaXNCbG9iIiwiaXNGdW5jdGlvbiIsImlzU3RyZWFtIiwiaXNVUkxTZWFyY2hQYXJhbXMiLCJ0cmltIiwiaXNTdGFuZGFyZEJyb3dzZXJFbnYiLCJmb3JFYWNoIiwibWVyZ2UiLCJleHRlbmQiLCJiaW5kIiwidXRpbHMiLCJlbmhhbmNlRXJyb3IiLCJjcmVhdGVFcnJvciIsImVuY29kZSIsImlnbm9yZUR1cGxpY2F0ZU9mIiwiY2hhcnMiLCJFIiwiaXNVUkxTYW1lT3JpZ2luIiwiYnVpbGRVUkwiLCJwYXJzZUhlYWRlcnMiLCJzZXR0bGUiLCJERUZBVUxUX0NPTlRFTlRfVFlQRSIsInNldENvbnRlbnRUeXBlSWZVbnNldCIsImdldERlZmF1bHRBZGFwdGVyIiwibm9ybWFsaXplSGVhZGVyTmFtZSIsInRocm93SWZDYW5jZWxsYXRpb25SZXF1ZXN0ZWQiLCJpc0Fic29sdXRlVVJMIiwiY29tYmluZVVSTHMiLCJ0cmFuc2Zvcm1EYXRhIiwiaXNDYW5jZWwiLCJkaXNwYXRjaFJlcXVlc3QiLCJDYW5jZWxUb2tlbiIsImNyZWF0ZUluc3RhbmNlIiwiYXhpb3MiLCJmb3JtYXRVc2VyU2V0dGluZ3MiLCJ1c2VyU2V0dGluZ3MiLCJzdWJncm91cElkIiwiZ3JvdXBJZCIsIkxvZ1N0YXNoIiwibW9kZWwiLCJsYWJlbCIsIlByb21pc2UiLCJyZXNvbHZlIiwicmVqZWN0IiwiZmlyc3REb21haW5MZXZlbCIsImdldEZpcnN0TGV2ZWxEb21haW4iLCJ1cmwiLCJ0YWdzIiwibGV2ZWwiLCJvcHRpb25zIiwibXV0ZUNvbnNvbGUiLCJsb2dnZXIiLCJjcmVhdGUiLCJpbmZvIiwiZXJyIiwiUmVzdEFwaSIsIm1ldGhvZCIsImlkIiwiZGF0YSIsImdldElwQWRkcmVzcyIsIkNhbGxlciIsInRyYW5zbWlzc2lvbiIsImdldEdsb2JhbFN3aXRjaFN0YXR1cyIsImFjY2Vzc1Rva2VuIiwiYXBpSG9zdG5hbWUiLCJwYXJhbXMiLCJhY2Nlc3NfdG9rZW4iLCJmb3JtYXRCdWZmZXJlZFJhbmdlcyIsImZvcm1hdHRlZFJhbmdlcyIsImkiLCJidWZmZXJlZCIsImxlbmd0aCIsInB1c2giLCJzdGFydCIsImVuZCIsImZvcm1hdFNlZWthYmxlUmFuZ2VzIiwiZm9ybWF0dGVkU2Vla2FibGVSYW5nZXMiLCJzZWVrYWJsZSIsImZvcm1hdFBsYXllZFJhbmdlcyIsImZvcm1hdHRlZFBsYXllZFJhbmdlcyIsInBsYXllZCIsImdldFVybFBhcmFtcyIsImZpbmFsVXJsIiwiaW5jbHVkZXMiLCJ1c2VyTmFtZSIsInNwbGl0IiwicmVkdWNlIiwiYWNjIiwiY3VyIiwia2V5IiwidmFsIiwiZ2V0VXNlclBhcmFtcyIsInJlc3VsdCIsIndpbmRvdyIsImxvY2F0aW9uIiwiaG9zdG5hbWUiLCJocmVmIiwiY2hlY2tJc0VuYWJsZWRTdGF0dXMiLCJwcm9taXNlIiwidGhlbiIsInJlc3BvbnNlIiwiaXNFbmFibGVkIiwiY2F0Y2giLCJFcnJvciIsImZpbmRIVE1MNVZpZGVvIiwiY291bnRlciIsInNlZWtpbmciLCJzZXRJbnRlcnZhbCIsImRvY3VtZW50IiwicXVlcnlTZWxlY3RvciIsImNsZWFySW50ZXJ2YWwiLCJjcmVhdGVBbmFseXRpY3NPYmplY3QiLCJkZXRhaWxlZEFwcFNvdXJjZSIsImFwcFNvdXJjZSIsImFjdGlvblZhbHVlIiwic2Vzc2lvbklkIiwicG9zaXRpb24iLCJ0b3RhbExlbmd0aCIsInBsYXllciIsInBsYXllclR5cGUiLCJpc011dGVkIiwibXV0ZWQiLCJmdWxsU2NyZWVuIiwiaXNQbGF5bGlzdCIsIl9pc1BsYXlsaXN0Iiwic3JjIiwidmJlZ2luIiwiTnVtYmVyIiwiaXNOYU4iLCJjYWxjdWxhdGVBdmVyYWdlQml0UmF0ZSIsIl8iLCJtZWFuQnkiLCJzbmFwc2hvdHMiLCJwIiwiZGVjb2RlZEJ5dGVzIiwiY2FsY3VsYXRlQXZlcmFnZUZyYW1lUmF0ZSIsImRlY29kZWRGcmFtZXMiLCJkYXRlU3RhcnRUaW1lc3RhbXAiLCJjYW5QbGF5VGltZVN0YW1wIiwidG90YWxXYWl0aW5nU2Vjb25kcyIsInN0YXJ0V2FpdGluZ1NlY29uZHMiLCJyZWJ1ZmZlcmluZ0V2ZW50c051bSIsImxvYWRTdGFydCIsImV2ZW50IiwiRGF0ZSIsImdldFRpbWUiLCJkdXJhdGlvbmNoYW5nZSIsImxvYWRlZG1ldGFkYXRhIiwiZW5kZWQiLCJzZXNzaW9uIiwiYW5hbHl0aWNPYmoiLCJ0YXJnZXQiLCJiaXRyYXRlIiwidG9GaXhlZCIsImZyYW1lcmF0ZSIsInRyYWNrIiwibG9hZGVkZGF0YSIsInByb2dyZXNzIiwiY2FucGxheSIsInBhdXNlIiwiY2FucGxheXRocm91Z2giLCJ3YWl0aW5nIiwiZ2V0Sm9pbmVkVGltZSIsImdldFRvdGFsUmVidWZmZXJpbmdUaW1lIiwiZ2V0VG90YWxSZWJ1ZmZlcmluZ0V2ZW50c051bSIsImNvbnZlcnRCeXRlc1RvQml0cyIsImJ5dGVzIiwiY29tcG9zZU1ldHJpYyIsInN0YXJ0VGltZSIsImRyb3BwZWRGcmFtZXMiLCJkZWNvZGVkQXVkaW9CeXRlcyIsImRpc3BsYXlTdXBwb3J0RnVsbHNjcmVlbiIsImJ1ZmZlcmVkUmFuZ2VzIiwicGxheWVkUmFuZ2VzIiwic2Vla2FibGVSYW5nZXMiLCJSZXBvcnQiLCJzZXRSZXBvcnRQcm9wZXJ0aWVzIiwicmVwb3J0Iiwic2V0U25hcHNob3RzIiwic2V0U2Vzc2lvbklkIiwic2V0VXNlclNldHRpbmdzIiwiY2xlYXJTbmFwc2hvdHMiLCJzZXRKb2luZWRUaW1lIiwiam9pbmVkVGltZSIsInNldFJlYnVmZmVyaW5nVGltZSIsInJlYnVmZmVyaW5nVGltZSIsInNldFJlYnVmZmVyaW5nRXZlbnRzIiwicmVidWZmZXJpbmdFdmVudHMiLCJzZXRJcEFkZHJlc3MiLCJpcEFkZHJlc3MiLCJzZXRFbmRUaW1lIiwiZW5kVGltZSIsInNldEF2ZXJhZ2VCaXRyYXRlIiwiYXZlcmFnZUJpdHJhdGUiLCJTZXNzaW9uIiwiYWRkU25hcHNob3QiLCJzbmFwc2hvdCIsInNldFNlc3Npb25Qcm9wZXJ0aWVzIiwibGFzdERlY29kZWRGcmFtZXMiLCJsYXN0RHJvcHBlZEZyYW1lcyIsImxhc3REZWNvZGVkQnl0ZXMiLCJsYXN0RGVjb2RlZEF1ZGlvQnl0ZXMiLCJsYXN0QXVkaW9CaXRSYXRlIiwibGFzdFZpZGVvQml0UmF0ZSIsInRvdGFsQXVkaW9CaXRSYXRlIiwidG90YWxWaWRlb0JpdFJhdGUiLCJyZXF1ZXN0QW5pbWF0aW9uSWQiLCJ0aW1lciIsInNlc3Npb25UcmFuc21pc3Npb24iLCJsYXN0VGltZSIsInJlc2V0UGFyYW1zIiwidG90YWxSZXBvcnQiLCJyZXNldFdpdGhDdXJyZW50VmlkZW9WYWx1ZXMiLCJjdXJyZW50VmlkZW8iLCJyZXNldEFsbCIsInJlcXVlc3RBbmltRnJhbWUiLCJyZXF1ZXN0QW5pbWF0aW9uRnJhbWUiLCJ3ZWJraXRSZXF1ZXN0QW5pbWF0aW9uRnJhbWUiLCJtb3pSZXF1ZXN0QW5pbWF0aW9uRnJhbWUiLCJjYWxsYmFjayIsInNldFRpbWVvdXQiLCJjYW5jZWxBbmltYXRpb25GcmFtZSIsIm1vekNhbmNlbEFuaW1hdGlvbkZyYW1lIiwiY2xvc2VTZXNzaW9uIiwic3RhcnRXb3JrIiwid2l0aFJlc2V0IiwiY29uc29sZSIsImxvZyIsInN0b3BXb3JrIiwid2l0aENsb3NlU2Vzc2lvbiIsIm9uVmlkZW9FbmRlZCIsIm9uVGFiVmlzaWJpbGl0eWNoYW5nZSIsInZpc2liaWxpdHlTdGF0ZSIsIm9uVmlkZW9QbGF5aW5nIiwic3RvcFNuaWZmaW5nVmlkZW9NZXRyaWNzIiwicmVtb3ZlRXZlbnRMaXN0ZW5lciIsImNoZWNrU3RhdHVzSW50ZXJ2YWwiLCJpbnRlcnZhbCIsInN0YXJ0U25pZmZpbmdWaWRlb01ldHJpY3MiLCJmb3VuZFZpZGVvIiwidW5pcWlkIiwicHJvZmlsZSIsImFkZEV2ZW50TGlzdGVuZXIiLCJQTEFURlJPTSIsImNhbGwiLCJudW1QYXVzZWRTZWNvbmRzIiwibWV0cmljIiwiZWZmZWN0aXZlVGltZSIsInZpZGVvQml0UmF0ZSIsImF1ZGlvQml0UmF0ZSIsImN1cnJlbnRWaWRlb1RpbWUiLCJXeU1ldHJpY1Byb2ZpbGVyIiwiY29tcG9uZW50RGlkTW91bnQiLCJwcm9wcyIsInN0YXJ0T25Nb3VudCIsInRyYW5zbWl0dGVyIiwic3RhdGUiLCJydW5uaW5nIiwiUmVhY3QiLCJjaGlsZHJlbiIsIkNvbXBvbmVudCIsInByb3BUeXBlcyIsIlByb3BUeXBlcyIsImJvb2wiLCJpc1JlcXVpcmVkIiwic2hhcGUiLCJudW1iZXIiLCJzdHJpbmciLCJvbmVPZiIsIm5vZGUiLCJkZWZhdWx0UHJvcHMiXSwibWFwcGluZ3MiOiI7Ozs7Ozs7O0lBQU8sSUFBTUEsb0JBQW9CLFNBQXBCQSxpQkFBb0I7SUFBQSxTQUFTQyxNQUFNQyx1QkFBZjtJQUFBLENBQTFCOztBQUVQLElBQU8sSUFBTUMsd0JBQXdCLFNBQXhCQSxxQkFBd0I7SUFBQSxTQUFTRixNQUFNRywyQkFBZjtJQUFBLENBQTlCOztBQUVQLElBQU8sSUFBTUMsd0JBQXdCLFNBQXhCQSxxQkFBd0I7SUFBQSxTQUFTSixNQUFNSywyQkFBZjtJQUFBLENBQTlCOztBQUVQLElBQU8sSUFBTUMsc0JBQXNCLFNBQXRCQSxtQkFBc0I7SUFBQSxTQUFTTixNQUFNTywwQkFBZjtJQUFBLENBQTVCOztBQUVQLElBQU8sSUFBTUMsMkJBQTJCLFNBQTNCQSx3QkFBMkI7SUFBQSxTQUFT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