kepler.gl
Version:
kepler.gl is a webgl based application to visualize large scale location data in the browser
201 lines (196 loc) • 28.8 kB
JavaScript
var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
Object.defineProperty(exports, "__esModule", {
value: true
});
exports.calculateExportImageSize = calculateExportImageSize;
exports.convertToPng = convertToPng;
exports.dataURItoBlob = dataURItoBlob;
exports["default"] = void 0;
exports.downloadFile = downloadFile;
exports.exportHtml = exportHtml;
exports.exportImage = exportImage;
exports.exportJson = exportJson;
exports.exportMap = exportMap;
exports.exportToJsonString = exportToJsonString;
exports.getMapJSON = getMapJSON;
exports.getScaleFromImageSize = getScaleFromImageSize;
exports.isMSEdge = isMSEdge;
var _defineProperty2 = _interopRequireDefault(require("@babel/runtime/helpers/defineProperty"));
var _window = require("global/window");
var _get = _interopRequireDefault(require("lodash/get"));
var _constants = require("@kepler.gl/constants");
var _commonUtils = require("@kepler.gl/common-utils");
var _domToImage = _interopRequireDefault(require("./dom-to-image"));
var _utils = require("./utils");
var _exportMapHtml = require("./export-map-html");
var _applicationConfig = require("./application-config");
function ownKeys(e, r) { var t = Object.keys(e); if (Object.getOwnPropertySymbols) { var o = Object.getOwnPropertySymbols(e); r && (o = o.filter(function (r) { return Object.getOwnPropertyDescriptor(e, r).enumerable; })), t.push.apply(t, o); } return t; }
function _objectSpread(e) { for (var r = 1; r < arguments.length; r++) { var t = null != arguments[r] ? arguments[r] : {}; r % 2 ? ownKeys(Object(t), !0).forEach(function (r) { (0, _defineProperty2["default"])(e, r, t[r]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(e, Object.getOwnPropertyDescriptors(t)) : ownKeys(Object(t)).forEach(function (r) { Object.defineProperty(e, r, Object.getOwnPropertyDescriptor(t, r)); }); } return e; } // SPDX-License-Identifier: MIT
// Copyright contributors to the kepler.gl project
var defaultResolution = _constants.OneXResolutionOption;
var defaultRatio = _constants.FourByThreeRatioOption;
function isMSEdge(window) {
// @ts-ignore msSaveOrOpenBlob was a proprietary addition to the Navigator object, added by Microsoft for Internet Explorer.
return Boolean(window.navigator && window.navigator.msSaveOrOpenBlob);
}
function getScaleFromImageSize() {
var imageW = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : 0;
var imageH = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : 0;
var mapW = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : 0;
var mapH = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : 0;
if ([imageW, imageH, mapW, mapH].some(function (d) {
return d <= 0;
})) {
return 1;
}
var base = imageW / imageH > 1 ? imageW : imageH;
var mapBase = imageW / imageH > 1 ? mapW : mapH;
return base / mapBase;
}
function calculateExportImageSize(_ref) {
var mapW = _ref.mapW,
mapH = _ref.mapH,
ratio = _ref.ratio,
resolution = _ref.resolution;
if (mapW <= 0 || mapH <= 0) {
return null;
}
var ratioItem = _constants.EXPORT_IMG_RATIO_OPTIONS.find(function (op) {
return op.id === ratio;
}) || defaultRatio;
var resolutionItem = _constants.EXPORT_IMG_RESOLUTION_OPTIONS.find(function (op) {
return op.id === resolution;
}) || defaultResolution;
var _resolutionItem$getSi = resolutionItem.getSize(mapW, mapH),
scaledWidth = _resolutionItem$getSi.width,
scaledHeight = _resolutionItem$getSi.height;
var _ratioItem$getSize = ratioItem.getSize(scaledWidth, scaledHeight),
imageW = _ratioItem$getSize.width,
imageH = _ratioItem$getSize.height;
var _ref2 = ratioItem.id === _constants.EXPORT_IMG_RATIOS.CUSTOM ? {
scale: undefined
} : resolutionItem,
scale = _ref2.scale;
return {
scale: scale,
imageW: imageW,
imageH: imageH
};
}
function convertToPng(sourceElem, options) {
return _domToImage["default"].toPng(sourceElem, options);
}
function dataURItoBlob(dataURI) {
var binary = (0, _window.atob)(dataURI.split(',')[1]);
// separate out the mime component
var mimeString = dataURI.split(',')[0].split(':')[1].split(';')[0];
// write the bytes of the string to an ArrayBuffer
var ab = new _window.ArrayBuffer(binary.length);
// create a view into the buffer
var ia = new _window.Uint8Array(ab);
for (var i = 0; i < binary.length; i++) {
ia[i] = binary.charCodeAt(i);
}
return new _window.Blob([ab], {
type: mimeString
});
}
function downloadFile(fileBlob, fileName) {
if (isMSEdge(window)) {
window.navigator.msSaveOrOpenBlob(fileBlob, fileName);
} else {
var url = _window.URL.createObjectURL(fileBlob);
var link = _window.document.createElement('a');
link.setAttribute('href', url);
link.setAttribute('download', fileName);
_window.document.body.appendChild(link);
// in some cases where maps are embedded, e.g. need to
// create and dispatch an event so that the browser downloads
// the file instead of navigating to the url
var evt = new MouseEvent('click', {
view: window,
bubbles: false,
cancelable: true
});
link.dispatchEvent(evt);
_window.document.body.removeChild(link);
_window.URL.revokeObjectURL(url);
}
}
/**
* Whether color is rgb
* @returns
*/
function exportImage(uiStateExportImage) {
var filename = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : (0, _applicationConfig.getApplicationConfig)().defaultImageName;
var imageDataUri = uiStateExportImage.imageDataUri;
if (imageDataUri) {
var file = dataURItoBlob(imageDataUri);
downloadFile(file, filename);
}
}
function exportToJsonString(data) {
try {
return JSON.stringify(data);
} catch (e) {
if (e instanceof TypeError) return e.message;
// Non-Standard Error Object Property
return e.description;
}
}
function getMapJSON(state) {
var options = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : (0, _applicationConfig.getApplicationConfig)().defaultExportJsonSettings;
var hasData = options.hasData;
var schema = state.visState.schema;
if (!hasData) {
return schema.getConfigToSave(state);
}
var mapToSave = schema.save(state);
// add file name if title is not provided
var title = (0, _get["default"])(mapToSave, ['info', 'title']);
if (!title || !title.length) {
mapToSave = (0, _utils.set)(['info', 'title'], "keplergl_".concat((0, _commonUtils.generateHashId)(6)), mapToSave);
}
return mapToSave;
}
function exportJson(state) {
var options = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {};
var map = getMapJSON(state, options);
map.info.source = 'kepler.gl';
var fileBlob = new _window.Blob([exportToJsonString(map)], {
type: 'application/json'
});
var fileName = state.appName ? "".concat(state.appName, ".json") : (0, _applicationConfig.getApplicationConfig)().defaultJsonName;
downloadFile(fileBlob, fileName);
}
function exportHtml(state, options) {
var userMapboxToken = options.userMapboxToken,
exportMapboxAccessToken = options.exportMapboxAccessToken,
mode = options.mode;
var data = _objectSpread(_objectSpread({}, getMapJSON(state)), {}, {
mapboxApiAccessToken: (userMapboxToken || '') !== '' ? userMapboxToken : exportMapboxAccessToken,
mode: mode
});
var fileBlob = new _window.Blob([(0, _exportMapHtml.exportMapToHTML)(data)], {
type: 'text/html'
});
downloadFile(fileBlob, state.appName ? "".concat(state.appName, ".html") : (0, _applicationConfig.getApplicationConfig)().defaultHtmlName);
}
function exportMap(state) {
var options = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : (0, _applicationConfig.getApplicationConfig)().defaultExportJsonSettings;
var imageDataUri = state.uiState.exportImage.imageDataUri;
var thumbnail = imageDataUri ? dataURItoBlob(imageDataUri) : null;
var mapToSave = getMapJSON(state, options);
return {
map: mapToSave,
thumbnail: thumbnail
};
}
var exporters = {
exportImage: exportImage,
exportJson: exportJson,
exportHtml: exportHtml
};
var _default = exports["default"] = exporters;
//# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJuYW1lcyI6WyJfd2luZG93IiwicmVxdWlyZSIsIl9nZXQiLCJfaW50ZXJvcFJlcXVpcmVEZWZhdWx0IiwiX2NvbnN0YW50cyIsIl9jb21tb25VdGlscyIsIl9kb21Ub0ltYWdlIiwiX3V0aWxzIiwiX2V4cG9ydE1hcEh0bWwiLCJfYXBwbGljYXRpb25Db25maWciLCJvd25LZXlzIiwiZSIsInIiLCJ0IiwiT2JqZWN0Iiwia2V5cyIsImdldE93blByb3BlcnR5U3ltYm9scyIsIm8iLCJmaWx0ZXIiLCJnZXRPd25Qcm9wZXJ0eURlc2NyaXB0b3IiLCJlbnVtZXJhYmxlIiwicHVzaCIsImFwcGx5IiwiX29iamVjdFNwcmVhZCIsImFyZ3VtZW50cyIsImxlbmd0aCIsImZvckVhY2giLCJfZGVmaW5lUHJvcGVydHkyIiwiZ2V0T3duUHJvcGVydHlEZXNjcmlwdG9ycyIsImRlZmluZVByb3BlcnRpZXMiLCJkZWZpbmVQcm9wZXJ0eSIsImRlZmF1bHRSZXNvbHV0aW9uIiwiT25lWFJlc29sdXRpb25PcHRpb24iLCJkZWZhdWx0UmF0aW8iLCJGb3VyQnlUaHJlZVJhdGlvT3B0aW9uIiwiaXNNU0VkZ2UiLCJ3aW5kb3ciLCJCb29sZWFuIiwibmF2aWdhdG9yIiwibXNTYXZlT3JPcGVuQmxvYiIsImdldFNjYWxlRnJvbUltYWdlU2l6ZSIsImltYWdlVyIsInVuZGVmaW5lZCIsImltYWdlSCIsIm1hcFciLCJtYXBIIiwic29tZSIsImQiLCJiYXNlIiwibWFwQmFzZSIsImNhbGN1bGF0ZUV4cG9ydEltYWdlU2l6ZSIsIl9yZWYiLCJyYXRpbyIsInJlc29sdXRpb24iLCJyYXRpb0l0ZW0iLCJFWFBPUlRfSU1HX1JBVElPX09QVElPTlMiLCJmaW5kIiwib3AiLCJpZCIsInJlc29sdXRpb25JdGVtIiwiRVhQT1JUX0lNR19SRVNPTFVUSU9OX09QVElPTlMiLCJfcmVzb2x1dGlvbkl0ZW0kZ2V0U2kiLCJnZXRTaXplIiwic2NhbGVkV2lkdGgiLCJ3aWR0aCIsInNjYWxlZEhlaWdodCIsImhlaWdodCIsIl9yYXRpb0l0ZW0kZ2V0U2l6ZSIsIl9yZWYyIiwiRVhQT1JUX0lNR19SQVRJT1MiLCJDVVNUT00iLCJzY2FsZSIsImNvbnZlcnRUb1BuZyIsInNvdXJjZUVsZW0iLCJvcHRpb25zIiwiZG9tdG9pbWFnZSIsInRvUG5nIiwiZGF0YVVSSXRvQmxvYiIsImRhdGFVUkkiLCJiaW5hcnkiLCJhdG9iIiwic3BsaXQiLCJtaW1lU3RyaW5nIiwiYWIiLCJBcnJheUJ1ZmZlciIsImlhIiwiVWludDhBcnJheSIsImkiLCJjaGFyQ29kZUF0IiwiQmxvYiIsInR5cGUiLCJkb3dubG9hZEZpbGUiLCJmaWxlQmxvYiIsImZpbGVOYW1lIiwidXJsIiwiVVJMIiwiY3JlYXRlT2JqZWN0VVJMIiwibGluayIsImRvY3VtZW50IiwiY3JlYXRlRWxlbWVudCIsInNldEF0dHJpYnV0ZSIsImJvZHkiLCJhcHBlbmRDaGlsZCIsImV2dCIsIk1vdXNlRXZlbnQiLCJ2aWV3IiwiYnViYmxlcyIsImNhbmNlbGFibGUiLCJkaXNwYXRjaEV2ZW50IiwicmVtb3ZlQ2hpbGQiLCJyZXZva2VPYmplY3RVUkwiLCJleHBvcnRJbWFnZSIsInVpU3RhdGVFeHBvcnRJbWFnZSIsImZpbGVuYW1lIiwiZ2V0QXBwbGljYXRpb25Db25maWciLCJkZWZhdWx0SW1hZ2VOYW1lIiwiaW1hZ2VEYXRhVXJpIiwiZmlsZSIsImV4cG9ydFRvSnNvblN0cmluZyIsImRhdGEiLCJKU09OIiwic3RyaW5naWZ5IiwiVHlwZUVycm9yIiwibWVzc2FnZSIsImRlc2NyaXB0aW9uIiwiZ2V0TWFwSlNPTiIsInN0YXRlIiwiZGVmYXVsdEV4cG9ydEpzb25TZXR0aW5ncyIsImhhc0RhdGEiLCJzY2hlbWEiLCJ2aXNTdGF0ZSIsImdldENvbmZpZ1RvU2F2ZSIsIm1hcFRvU2F2ZSIsInNhdmUiLCJ0aXRsZSIsImdldCIsInNldCIsImNvbmNhdCIsImdlbmVyYXRlSGFzaElkIiwiZXhwb3J0SnNvbiIsIm1hcCIsImluZm8iLCJzb3VyY2UiLCJhcHBOYW1lIiwiZGVmYXVsdEpzb25OYW1lIiwiZXhwb3J0SHRtbCIsInVzZXJNYXBib3hUb2tlbiIsImV4cG9ydE1hcGJveEFjY2Vzc1Rva2VuIiwibW9kZSIsIm1hcGJveEFwaUFjY2Vzc1Rva2VuIiwiZXhwb3J0TWFwVG9IVE1MIiwiZGVmYXVsdEh0bWxOYW1lIiwiZXhwb3J0TWFwIiwidWlTdGF0ZSIsInRodW1ibmFpbCIsImV4cG9ydGVycyIsIl9kZWZhdWx0IiwiZXhwb3J0cyJdLCJzb3VyY2VzIjpbIi4uL3NyYy9leHBvcnQtdXRpbHMudHMiXSwic291cmNlc0NvbnRlbnQiOlsiLy8gU1BEWC1MaWNlbnNlLUlkZW50aWZpZXI6IE1JVFxuLy8gQ29weXJpZ2h0IGNvbnRyaWJ1dG9ycyB0byB0aGUga2VwbGVyLmdsIHByb2plY3RcblxuaW1wb3J0IHtCbG9iLCBVUkwsIGF0b2IsIFVpbnQ4QXJyYXksIEFycmF5QnVmZmVyLCBkb2N1bWVudH0gZnJvbSAnZ2xvYmFsL3dpbmRvdyc7XG5pbXBvcnQgZ2V0IGZyb20gJ2xvZGFzaC9nZXQnO1xuXG5pbXBvcnQge1xuICBFWFBPUlRfSU1HX1JFU09MVVRJT05fT1BUSU9OUyxcbiAgRVhQT1JUX0lNR19SQVRJT19PUFRJT05TLFxuICBSRVNPTFVUSU9OUyxcbiAgRVhQT1JUX0lNR19SQVRJT1MsXG4gIEZvdXJCeVRocmVlUmF0aW9PcHRpb24sXG4gIE9uZVhSZXNvbHV0aW9uT3B0aW9uLFxuICBFeHBvcnRJbWFnZVxufSBmcm9tICdAa2VwbGVyLmdsL2NvbnN0YW50cyc7XG5pbXBvcnQge2dlbmVyYXRlSGFzaElkfSBmcm9tICdAa2VwbGVyLmdsL2NvbW1vbi11dGlscyc7XG5pbXBvcnQgZG9tdG9pbWFnZSBmcm9tICcuL2RvbS10by1pbWFnZSc7XG5pbXBvcnQge3NldH0gZnJvbSAnLi91dGlscyc7XG5pbXBvcnQge2V4cG9ydE1hcFRvSFRNTH0gZnJvbSAnLi9leHBvcnQtbWFwLWh0bWwnO1xuaW1wb3J0IHtnZXRBcHBsaWNhdGlvbkNvbmZpZ30gZnJvbSAnLi9hcHBsaWNhdGlvbi1jb25maWcnO1xuXG5jb25zdCBkZWZhdWx0UmVzb2x1dGlvbiA9IE9uZVhSZXNvbHV0aW9uT3B0aW9uO1xuXG5jb25zdCBkZWZhdWx0UmF0aW8gPSBGb3VyQnlUaHJlZVJhdGlvT3B0aW9uO1xuXG5leHBvcnQgZnVuY3Rpb24gaXNNU0VkZ2Uod2luZG93OiBXaW5kb3cpOiBib29sZWFuIHtcbiAgLy8gQHRzLWlnbm9yZSBtc1NhdmVPck9wZW5CbG9iIHdhcyBhIHByb3ByaWV0YXJ5IGFkZGl0aW9uIHRvIHRoZSBOYXZpZ2F0b3Igb2JqZWN0LCBhZGRlZCBieSBNaWNyb3NvZnQgZm9yIEludGVybmV0IEV4cGxvcmVyLlxuICByZXR1cm4gQm9vbGVhbih3aW5kb3cubmF2aWdhdG9yICYmIHdpbmRvdy5uYXZpZ2F0b3IubXNTYXZlT3JPcGVuQmxvYik7XG59XG5cbmV4cG9ydCBmdW5jdGlvbiBnZXRTY2FsZUZyb21JbWFnZVNpemUoaW1hZ2VXID0gMCwgaW1hZ2VIID0gMCwgbWFwVyA9IDAsIG1hcEggPSAwKSB7XG4gIGlmIChbaW1hZ2VXLCBpbWFnZUgsIG1hcFcsIG1hcEhdLnNvbWUoZCA9PiBkIDw9IDApKSB7XG4gICAgcmV0dXJuIDE7XG4gIH1cblxuICBjb25zdCBiYXNlID0gaW1hZ2VXIC8gaW1hZ2VIID4gMSA/IGltYWdlVyA6IGltYWdlSDtcbiAgY29uc3QgbWFwQmFzZSA9IGltYWdlVyAvIGltYWdlSCA+IDEgPyBtYXBXIDogbWFwSDtcbiAgcmV0dXJuIGJhc2UgLyBtYXBCYXNlO1xufVxuXG5leHBvcnQgZnVuY3Rpb24gY2FsY3VsYXRlRXhwb3J0SW1hZ2VTaXplKHtcbiAgbWFwVyxcbiAgbWFwSCxcbiAgcmF0aW8sXG4gIHJlc29sdXRpb25cbn06IHtcbiAgbWFwVzogbnVtYmVyO1xuICBtYXBIOiBudW1iZXI7XG4gIHJhdGlvOiBrZXlvZiB0eXBlb2YgRVhQT1JUX0lNR19SQVRJT1M7XG4gIHJlc29sdXRpb246IGtleW9mIHR5cGVvZiBSRVNPTFVUSU9OUztcbn0pIHtcbiAgaWYgKG1hcFcgPD0gMCB8fCBtYXBIIDw9IDApIHtcbiAgICByZXR1cm4gbnVsbDtcbiAgfVxuXG4gIGNvbnN0IHJhdGlvSXRlbSA9IEVYUE9SVF9JTUdfUkFUSU9fT1BUSU9OUy5maW5kKG9wID0+IG9wLmlkID09PSByYXRpbykgfHwgZGVmYXVsdFJhdGlvO1xuXG4gIGNvbnN0IHJlc29sdXRpb25JdGVtID1cbiAgICBFWFBPUlRfSU1HX1JFU09MVVRJT05fT1BUSU9OUy5maW5kKG9wID0+IG9wLmlkID09PSByZXNvbHV0aW9uKSB8fCBkZWZhdWx0UmVzb2x1dGlvbjtcblxuICBjb25zdCB7d2lkdGg6IHNjYWxlZFdpZHRoLCBoZWlnaHQ6IHNjYWxlZEhlaWdodH0gPSByZXNvbHV0aW9uSXRlbS5nZXRTaXplKG1hcFcsIG1hcEgpO1xuXG4gIGNvbnN0IHt3aWR0aDogaW1hZ2VXLCBoZWlnaHQ6IGltYWdlSH0gPSByYXRpb0l0ZW0uZ2V0U2l6ZShzY2FsZWRXaWR0aCwgc2NhbGVkSGVpZ2h0KTtcblxuICBjb25zdCB7c2NhbGV9ID0gcmF0aW9JdGVtLmlkID09PSBFWFBPUlRfSU1HX1JBVElPUy5DVVNUT00gPyB7c2NhbGU6IHVuZGVmaW5lZH0gOiByZXNvbHV0aW9uSXRlbTtcblxuICByZXR1cm4ge1xuICAgIHNjYWxlLFxuICAgIGltYWdlVyxcbiAgICBpbWFnZUhcbiAgfTtcbn1cblxuZXhwb3J0IGZ1bmN0aW9uIGNvbnZlcnRUb1BuZyhzb3VyY2VFbGVtOiBIVE1MRWxlbWVudCwgb3B0aW9ucykge1xuICByZXR1cm4gZG9tdG9pbWFnZS50b1BuZyhzb3VyY2VFbGVtLCBvcHRpb25zKTtcbn1cblxuZXhwb3J0IGZ1bmN0aW9uIGRhdGFVUkl0b0Jsb2IoZGF0YVVSSTogc3RyaW5nKTogQmxvYiB7XG4gIGNvbnN0IGJpbmFyeSA9IGF0b2IoZGF0YVVSSS5zcGxpdCgnLCcpWzFdKTtcblxuICAvLyBzZXBhcmF0ZSBvdXQgdGhlIG1pbWUgY29tcG9uZW50XG4gIGNvbnN0IG1pbWVTdHJpbmcgPSBkYXRhVVJJLnNwbGl0KCcsJylbMF0uc3BsaXQoJzonKVsxXS5zcGxpdCgnOycpWzBdO1xuXG4gIC8vIHdyaXRlIHRoZSBieXRlcyBvZiB0aGUgc3RyaW5nIHRvIGFuIEFycmF5QnVmZmVyXG4gIGNvbnN0IGFiID0gbmV3IEFycmF5QnVmZmVyKGJpbmFyeS5sZW5ndGgpO1xuXG4gIC8vIGNyZWF0ZSBhIHZpZXcgaW50byB0aGUgYnVmZmVyXG4gIGNvbnN0IGlhID0gbmV3IFVpbnQ4QXJyYXkoYWIpO1xuXG4gIGZvciAobGV0IGkgPSAwOyBpIDwgYmluYXJ5Lmxlbmd0aDsgaSsrKSB7XG4gICAgaWFbaV0gPSBiaW5hcnkuY2hhckNvZGVBdChpKTtcbiAgfVxuXG4gIHJldHVybiBuZXcgQmxvYihbYWJdLCB7dHlwZTogbWltZVN0cmluZ30pO1xufVxuXG5leHBvcnQgZnVuY3Rpb24gZG93bmxvYWRGaWxlKGZpbGVCbG9iOiBCbG9iLCBmaWxlTmFtZTogc3RyaW5nKSB7XG4gIGlmIChpc01TRWRnZSh3aW5kb3cpKSB7XG4gICAgKHdpbmRvdy5uYXZpZ2F0b3IgYXMgYW55KS5tc1NhdmVPck9wZW5CbG9iKGZpbGVCbG9iLCBmaWxlTmFtZSk7XG4gIH0gZWxzZSB7XG4gICAgY29uc3QgdXJsID0gVVJMLmNyZWF0ZU9iamVjdFVSTChmaWxlQmxvYik7XG5cbiAgICBjb25zdCBsaW5rID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnYScpO1xuICAgIGxpbmsuc2V0QXR0cmlidXRlKCdocmVmJywgdXJsKTtcbiAgICBsaW5rLnNldEF0dHJpYnV0ZSgnZG93bmxvYWQnLCBmaWxlTmFtZSk7XG5cbiAgICBkb2N1bWVudC5ib2R5LmFwcGVuZENoaWxkKGxpbmspO1xuICAgIC8vIGluIHNvbWUgY2FzZXMgd2hlcmUgbWFwcyBhcmUgZW1iZWRkZWQsIGUuZy4gbmVlZCB0b1xuICAgIC8vIGNyZWF0ZSBhbmQgZGlzcGF0Y2ggYW4gZXZlbnQgc28gdGhhdCB0aGUgYnJvd3NlciBkb3dubG9hZHNcbiAgICAvLyB0aGUgZmlsZSBpbnN0ZWFkIG9mIG5hdmlnYXRpbmcgdG8gdGhlIHVybFxuICAgIGNvbnN0IGV2dCA9IG5ldyBNb3VzZUV2ZW50KCdjbGljaycsIHtcbiAgICAgIHZpZXc6IHdpbmRvdyxcbiAgICAgIGJ1YmJsZXM6IGZhbHNlLFxuICAgICAgY2FuY2VsYWJsZTogdHJ1ZVxuICAgIH0pO1xuICAgIGxpbmsuZGlzcGF0Y2hFdmVudChldnQpO1xuICAgIGRvY3VtZW50LmJvZHkucmVtb3ZlQ2hpbGQobGluayk7XG4gICAgVVJMLnJldm9rZU9iamVjdFVSTCh1cmwpO1xuICB9XG59XG5cbi8qKlxuICogV2hldGhlciBjb2xvciBpcyByZ2JcbiAqIEByZXR1cm5zXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBleHBvcnRJbWFnZShcbiAgdWlTdGF0ZUV4cG9ydEltYWdlOiBFeHBvcnRJbWFnZSxcbiAgZmlsZW5hbWUgPSBnZXRBcHBsaWNhdGlvbkNvbmZpZygpLmRlZmF1bHRJbWFnZU5hbWVcbikge1xuICBjb25zdCB7aW1hZ2VEYXRhVXJpfSA9IHVpU3RhdGVFeHBvcnRJbWFnZTtcbiAgaWYgKGltYWdlRGF0YVVyaSkge1xuICAgIGNvbnN0IGZpbGUgPSBkYXRhVVJJdG9CbG9iKGltYWdlRGF0YVVyaSk7XG4gICAgZG93bmxvYWRGaWxlKGZpbGUsIGZpbGVuYW1lKTtcbiAgfVxufVxuXG5leHBvcnQgZnVuY3Rpb24gZXhwb3J0VG9Kc29uU3RyaW5nKGRhdGEpIHtcbiAgdHJ5IHtcbiAgICByZXR1cm4gSlNPTi5zdHJpbmdpZnkoZGF0YSk7XG4gIH0gY2F0Y2ggKGUpIHtcbiAgICBpZiAoZSBpbnN0YW5jZW9mIFR5cGVFcnJvcikgcmV0dXJuIGUubWVzc2FnZTtcbiAgICAvLyBOb24tU3RhbmRhcmQgRXJyb3IgT2JqZWN0IFByb3BlcnR5XG4gICAgcmV0dXJuIChlIGFzIGFueSkuZGVzY3JpcHRpb247XG4gIH1cbn1cblxuZXhwb3J0IGZ1bmN0aW9uIGdldE1hcEpTT04oc3RhdGUsIG9wdGlvbnMgPSBnZXRBcHBsaWNhdGlvbkNvbmZpZygpLmRlZmF1bHRFeHBvcnRKc29uU2V0dGluZ3MpIHtcbiAgY29uc3Qge2hhc0RhdGF9ID0gb3B0aW9ucztcbiAgY29uc3Qgc2NoZW1hID0gc3RhdGUudmlzU3RhdGUuc2NoZW1hO1xuXG4gIGlmICghaGFzRGF0YSkge1xuICAgIHJldHVybiBzY2hlbWEuZ2V0Q29uZmlnVG9TYXZlKHN0YXRlKTtcbiAgfVxuXG4gIGxldCBtYXBUb1NhdmUgPSBzY2hlbWEuc2F2ZShzdGF0ZSk7XG4gIC8vIGFkZCBmaWxlIG5hbWUgaWYgdGl0bGUgaXMgbm90IHByb3ZpZGVkXG4gIGNvbnN0IHRpdGxlID0gZ2V0KG1hcFRvU2F2ZSwgWydpbmZvJywgJ3RpdGxlJ10pO1xuICBpZiAoIXRpdGxlIHx8ICF0aXRsZS5sZW5ndGgpIHtcbiAgICBtYXBUb1NhdmUgPSBzZXQoWydpbmZvJywgJ3RpdGxlJ10sIGBrZXBsZXJnbF8ke2dlbmVyYXRlSGFzaElkKDYpfWAsIG1hcFRvU2F2ZSk7XG4gIH1cbiAgcmV0dXJuIG1hcFRvU2F2ZTtcbn1cblxuZXhwb3J0IGZ1bmN0aW9uIGV4cG9ydEpzb24oc3RhdGUsIG9wdGlvbnM6IGFueSA9IHt9KSB7XG4gIGNvbnN0IG1hcCA9IGdldE1hcEpTT04oc3RhdGUsIG9wdGlvbnMpO1xuICBtYXAuaW5mby5zb3VyY2UgPSAna2VwbGVyLmdsJztcbiAgY29uc3QgZmlsZUJsb2IgPSBuZXcgQmxvYihbZXhwb3J0VG9Kc29uU3RyaW5nKG1hcCldLCB7dHlwZTogJ2FwcGxpY2F0aW9uL2pzb24nfSk7XG4gIGNvbnN0IGZpbGVOYW1lID0gc3RhdGUuYXBwTmFtZSA/IGAke3N0YXRlLmFwcE5hbWV9Lmpzb25gIDogZ2V0QXBwbGljYXRpb25Db25maWcoKS5kZWZhdWx0SnNvbk5hbWU7XG4gIGRvd25sb2FkRmlsZShmaWxlQmxvYiwgZmlsZU5hbWUpO1xufVxuXG5leHBvcnQgZnVuY3Rpb24gZXhwb3J0SHRtbChzdGF0ZSwgb3B0aW9ucykge1xuICBjb25zdCB7dXNlck1hcGJveFRva2VuLCBleHBvcnRNYXBib3hBY2Nlc3NUb2tlbiwgbW9kZX0gPSBvcHRpb25zO1xuXG4gIGNvbnN0IGRhdGEgPSB7XG4gICAgLi4uZ2V0TWFwSlNPTihzdGF0ZSksXG4gICAgbWFwYm94QXBpQWNjZXNzVG9rZW46XG4gICAgICAodXNlck1hcGJveFRva2VuIHx8ICcnKSAhPT0gJycgPyB1c2VyTWFwYm94VG9rZW4gOiBleHBvcnRNYXBib3hBY2Nlc3NUb2tlbixcbiAgICBtb2RlXG4gIH07XG5cbiAgY29uc3QgZmlsZUJsb2IgPSBuZXcgQmxvYihbZXhwb3J0TWFwVG9IVE1MKGRhdGEpXSwge3R5cGU6ICd0ZXh0L2h0bWwnfSk7XG4gIGRvd25sb2FkRmlsZShcbiAgICBmaWxlQmxvYixcbiAgICBzdGF0ZS5hcHBOYW1lID8gYCR7c3RhdGUuYXBwTmFtZX0uaHRtbGAgOiBnZXRBcHBsaWNhdGlvbkNvbmZpZygpLmRlZmF1bHRIdG1sTmFtZVxuICApO1xufVxuXG5leHBvcnQgZnVuY3Rpb24gZXhwb3J0TWFwKHN0YXRlLCBvcHRpb25zID0gZ2V0QXBwbGljYXRpb25Db25maWcoKS5kZWZhdWx0RXhwb3J0SnNvblNldHRpbmdzKSB7XG4gIGNvbnN0IHtpbWFnZURhdGFVcml9ID0gc3RhdGUudWlTdGF0ZS5leHBvcnRJbWFnZTtcbiAgY29uc3QgdGh1bWJuYWlsOiBCbG9iIHwgbnVsbCA9IGltYWdlRGF0YVVyaSA/IGRhdGFVUkl0b0Jsb2IoaW1hZ2VEYXRhVXJpKSA6IG51bGw7XG4gIGNvbnN0IG1hcFRvU2F2ZSA9IGdldE1hcEpTT04oc3RhdGUsIG9wdGlvbnMpO1xuXG4gIHJldHVybiB7XG4gICAgbWFwOiBtYXBUb1NhdmUsXG4gICAgdGh1bWJuYWlsXG4gIH07XG59XG5cbmNvbnN0IGV4cG9ydGVycyA9IHtcbiAgZXhwb3J0SW1hZ2UsXG4gIGV4cG9ydEpzb24sXG4gIGV4cG9ydEh0bWxcbn07XG5cbmV4cG9ydCBkZWZhdWx0IGV4cG9ydGVycztcbiJdLCJtYXBwaW5ncyI6Ijs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7QUFHQSxJQUFBQSxPQUFBLEdBQUFDLE9BQUE7QUFDQSxJQUFBQyxJQUFBLEdBQUFDLHNCQUFBLENBQUFGLE9BQUE7QUFFQSxJQUFBRyxVQUFBLEdBQUFILE9BQUE7QUFTQSxJQUFBSSxZQUFBLEdBQUFKLE9BQUE7QUFDQSxJQUFBSyxXQUFBLEdBQUFILHNCQUFBLENBQUFGLE9BQUE7QUFDQSxJQUFBTSxNQUFBLEdBQUFOLE9BQUE7QUFDQSxJQUFBTyxjQUFBLEdBQUFQLE9BQUE7QUFDQSxJQUFBUSxrQkFBQSxHQUFBUixPQUFBO0FBQTBELFNBQUFTLFFBQUFDLENBQUEsRUFBQUMsQ0FBQSxRQUFBQyxDQUFBLEdBQUFDLE1BQUEsQ0FBQUMsSUFBQSxDQUFBSixDQUFBLE9BQUFHLE1BQUEsQ0FBQUUscUJBQUEsUUFBQUMsQ0FBQSxHQUFBSCxNQUFBLENBQUFFLHFCQUFBLENBQUFMLENBQUEsR0FBQUMsQ0FBQSxLQUFBSyxDQUFBLEdBQUFBLENBQUEsQ0FBQUMsTUFBQSxXQUFBTixDQUFBLFdBQUFFLE1BQUEsQ0FBQUssd0JBQUEsQ0FBQVIsQ0FBQSxFQUFBQyxDQUFBLEVBQUFRLFVBQUEsT0FBQVAsQ0FBQSxDQUFBUSxJQUFBLENBQUFDLEtBQUEsQ0FBQVQsQ0FBQSxFQUFBSSxDQUFBLFlBQUFKLENBQUE7QUFBQSxTQUFBVSxjQUFBWixDQUFBLGFBQUFDLENBQUEsTUFBQUEsQ0FBQSxHQUFBWSxTQUFBLENBQUFDLE1BQUEsRUFBQWIsQ0FBQSxVQUFBQyxDQUFBLFdBQUFXLFNBQUEsQ0FBQVosQ0FBQSxJQUFBWSxTQUFBLENBQUFaLENBQUEsUUFBQUEsQ0FBQSxPQUFBRixPQUFBLENBQUFJLE1BQUEsQ0FBQUQsQ0FBQSxPQUFBYSxPQUFBLFdBQUFkLENBQUEsUUFBQWUsZ0JBQUEsYUFBQWhCLENBQUEsRUFBQUMsQ0FBQSxFQUFBQyxDQUFBLENBQUFELENBQUEsU0FBQUUsTUFBQSxDQUFBYyx5QkFBQSxHQUFBZCxNQUFBLENBQUFlLGdCQUFBLENBQUFsQixDQUFBLEVBQUFHLE1BQUEsQ0FBQWMseUJBQUEsQ0FBQWYsQ0FBQSxLQUFBSCxPQUFBLENBQUFJLE1BQUEsQ0FBQUQsQ0FBQSxHQUFBYSxPQUFBLFdBQUFkLENBQUEsSUFBQUUsTUFBQSxDQUFBZ0IsY0FBQSxDQUFBbkIsQ0FBQSxFQUFBQyxDQUFBLEVBQUFFLE1BQUEsQ0FBQUssd0JBQUEsQ0FBQU4sQ0FBQSxFQUFBRCxDQUFBLGlCQUFBRCxDQUFBLElBbkIxRDtBQUNBO0FBb0JBLElBQU1vQixpQkFBaUIsR0FBR0MsK0JBQW9CO0FBRTlDLElBQU1DLFlBQVksR0FBR0MsaUNBQXNCO0FBRXBDLFNBQVNDLFFBQVFBLENBQUNDLE1BQWMsRUFBVztFQUNoRDtFQUNBLE9BQU9DLE9BQU8sQ0FBQ0QsTUFBTSxDQUFDRSxTQUFTLElBQUlGLE1BQU0sQ0FBQ0UsU0FBUyxDQUFDQyxnQkFBZ0IsQ0FBQztBQUN2RTtBQUVPLFNBQVNDLHFCQUFxQkEsQ0FBQSxFQUE2QztFQUFBLElBQTVDQyxNQUFNLEdBQUFqQixTQUFBLENBQUFDLE1BQUEsUUFBQUQsU0FBQSxRQUFBa0IsU0FBQSxHQUFBbEIsU0FBQSxNQUFHLENBQUM7RUFBQSxJQUFFbUIsTUFBTSxHQUFBbkIsU0FBQSxDQUFBQyxNQUFBLFFBQUFELFNBQUEsUUFBQWtCLFNBQUEsR0FBQWxCLFNBQUEsTUFBRyxDQUFDO0VBQUEsSUFBRW9CLElBQUksR0FBQXBCLFNBQUEsQ0FBQUMsTUFBQSxRQUFBRCxTQUFBLFFBQUFrQixTQUFBLEdBQUFsQixTQUFBLE1BQUcsQ0FBQztFQUFBLElBQUVxQixJQUFJLEdBQUFyQixTQUFBLENBQUFDLE1BQUEsUUFBQUQsU0FBQSxRQUFBa0IsU0FBQSxHQUFBbEIsU0FBQSxNQUFHLENBQUM7RUFDOUUsSUFBSSxDQUFDaUIsTUFBTSxFQUFFRSxNQUFNLEVBQUVDLElBQUksRUFBRUMsSUFBSSxDQUFDLENBQUNDLElBQUksQ0FBQyxVQUFBQyxDQUFDO0lBQUEsT0FBSUEsQ0FBQyxJQUFJLENBQUM7RUFBQSxFQUFDLEVBQUU7SUFDbEQsT0FBTyxDQUFDO0VBQ1Y7RUFFQSxJQUFNQyxJQUFJLEdBQUdQLE1BQU0sR0FBR0UsTUFBTSxHQUFHLENBQUMsR0FBR0YsTUFBTSxHQUFHRSxNQUFNO0VBQ2xELElBQU1NLE9BQU8sR0FBR1IsTUFBTSxHQUFHRSxNQUFNLEdBQUcsQ0FBQyxHQUFHQyxJQUFJLEdBQUdDLElBQUk7RUFDakQsT0FBT0csSUFBSSxHQUFHQyxPQUFPO0FBQ3ZCO0FBRU8sU0FBU0Msd0JBQXdCQSxDQUFBQyxJQUFBLEVBVXJDO0VBQUEsSUFURFAsSUFBSSxHQUFBTyxJQUFBLENBQUpQLElBQUk7SUFDSkMsSUFBSSxHQUFBTSxJQUFBLENBQUpOLElBQUk7SUFDSk8sS0FBSyxHQUFBRCxJQUFBLENBQUxDLEtBQUs7SUFDTEMsVUFBVSxHQUFBRixJQUFBLENBQVZFLFVBQVU7RUFPVixJQUFJVCxJQUFJLElBQUksQ0FBQyxJQUFJQyxJQUFJLElBQUksQ0FBQyxFQUFFO0lBQzFCLE9BQU8sSUFBSTtFQUNiO0VBRUEsSUFBTVMsU0FBUyxHQUFHQyxtQ0FBd0IsQ0FBQ0MsSUFBSSxDQUFDLFVBQUFDLEVBQUU7SUFBQSxPQUFJQSxFQUFFLENBQUNDLEVBQUUsS0FBS04sS0FBSztFQUFBLEVBQUMsSUFBSW5CLFlBQVk7RUFFdEYsSUFBTTBCLGNBQWMsR0FDbEJDLHdDQUE2QixDQUFDSixJQUFJLENBQUMsVUFBQUMsRUFBRTtJQUFBLE9BQUlBLEVBQUUsQ0FBQ0MsRUFBRSxLQUFLTCxVQUFVO0VBQUEsRUFBQyxJQUFJdEIsaUJBQWlCO0VBRXJGLElBQUE4QixxQkFBQSxHQUFtREYsY0FBYyxDQUFDRyxPQUFPLENBQUNsQixJQUFJLEVBQUVDLElBQUksQ0FBQztJQUF2RWtCLFdBQVcsR0FBQUYscUJBQUEsQ0FBbEJHLEtBQUs7SUFBdUJDLFlBQVksR0FBQUoscUJBQUEsQ0FBcEJLLE1BQU07RUFFakMsSUFBQUMsa0JBQUEsR0FBd0NiLFNBQVMsQ0FBQ1EsT0FBTyxDQUFDQyxXQUFXLEVBQUVFLFlBQVksQ0FBQztJQUF0RXhCLE1BQU0sR0FBQTBCLGtCQUFBLENBQWJILEtBQUs7SUFBa0JyQixNQUFNLEdBQUF3QixrQkFBQSxDQUFkRCxNQUFNO0VBRTVCLElBQUFFLEtBQUEsR0FBZ0JkLFNBQVMsQ0FBQ0ksRUFBRSxLQUFLVyw0QkFBaUIsQ0FBQ0MsTUFBTSxHQUFHO01BQUNDLEtBQUssRUFBRTdCO0lBQVMsQ0FBQyxHQUFHaUIsY0FBYztJQUF4RlksS0FBSyxHQUFBSCxLQUFBLENBQUxHLEtBQUs7RUFFWixPQUFPO0lBQ0xBLEtBQUssRUFBTEEsS0FBSztJQUNMOUIsTUFBTSxFQUFOQSxNQUFNO0lBQ05FLE1BQU0sRUFBTkE7RUFDRixDQUFDO0FBQ0g7QUFFTyxTQUFTNkIsWUFBWUEsQ0FBQ0MsVUFBdUIsRUFBRUMsT0FBTyxFQUFFO0VBQzdELE9BQU9DLHNCQUFVLENBQUNDLEtBQUssQ0FBQ0gsVUFBVSxFQUFFQyxPQUFPLENBQUM7QUFDOUM7QUFFTyxTQUFTRyxhQUFhQSxDQUFDQyxPQUFlLEVBQVE7RUFDbkQsSUFBTUMsTUFBTSxHQUFHLElBQUFDLFlBQUksRUFBQ0YsT0FBTyxDQUFDRyxLQUFLLENBQUMsR0FBRyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUM7O0VBRTFDO0VBQ0EsSUFBTUMsVUFBVSxHQUFHSixPQUFPLENBQUNHLEtBQUssQ0FBQyxHQUFHLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQ0EsS0FBSyxDQUFDLEdBQUcsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDQSxLQUFLLENBQUMsR0FBRyxDQUFDLENBQUMsQ0FBQyxDQUFDOztFQUVwRTtFQUNBLElBQU1FLEVBQUUsR0FBRyxJQUFJQyxtQkFBVyxDQUFDTCxNQUFNLENBQUN0RCxNQUFNLENBQUM7O0VBRXpDO0VBQ0EsSUFBTTRELEVBQUUsR0FBRyxJQUFJQyxrQkFBVSxDQUFDSCxFQUFFLENBQUM7RUFFN0IsS0FBSyxJQUFJSSxDQUFDLEdBQUcsQ0FBQyxFQUFFQSxDQUFDLEdBQUdSLE1BQU0sQ0FBQ3RELE1BQU0sRUFBRThELENBQUMsRUFBRSxFQUFFO0lBQ3RDRixFQUFFLENBQUNFLENBQUMsQ0FBQyxHQUFHUixNQUFNLENBQUNTLFVBQVUsQ0FBQ0QsQ0FBQyxDQUFDO0VBQzlCO0VBRUEsT0FBTyxJQUFJRSxZQUFJLENBQUMsQ0FBQ04sRUFBRSxDQUFDLEVBQUU7SUFBQ08sSUFBSSxFQUFFUjtFQUFVLENBQUMsQ0FBQztBQUMzQztBQUVPLFNBQVNTLFlBQVlBLENBQUNDLFFBQWMsRUFBRUMsUUFBZ0IsRUFBRTtFQUM3RCxJQUFJMUQsUUFBUSxDQUFDQyxNQUFNLENBQUMsRUFBRTtJQUNuQkEsTUFBTSxDQUFDRSxTQUFTLENBQVNDLGdCQUFnQixDQUFDcUQsUUFBUSxFQUFFQyxRQUFRLENBQUM7RUFDaEUsQ0FBQyxNQUFNO0lBQ0wsSUFBTUMsR0FBRyxHQUFHQyxXQUFHLENBQUNDLGVBQWUsQ0FBQ0osUUFBUSxDQUFDO0lBRXpDLElBQU1LLElBQUksR0FBR0MsZ0JBQVEsQ0FBQ0MsYUFBYSxDQUFDLEdBQUcsQ0FBQztJQUN4Q0YsSUFBSSxDQUFDRyxZQUFZLENBQUMsTUFBTSxFQUFFTixHQUFHLENBQUM7SUFDOUJHLElBQUksQ0FBQ0csWUFBWSxDQUFDLFVBQVUsRUFBRVAsUUFBUSxDQUFDO0lBRXZDSyxnQkFBUSxDQUFDRyxJQUFJLENBQUNDLFdBQVcsQ0FBQ0wsSUFBSSxDQUFDO0lBQy9CO0lBQ0E7SUFDQTtJQUNBLElBQU1NLEdBQUcsR0FBRyxJQUFJQyxVQUFVLENBQUMsT0FBTyxFQUFFO01BQ2xDQyxJQUFJLEVBQUVyRSxNQUFNO01BQ1pzRSxPQUFPLEVBQUUsS0FBSztNQUNkQyxVQUFVLEVBQUU7SUFDZCxDQUFDLENBQUM7SUFDRlYsSUFBSSxDQUFDVyxhQUFhLENBQUNMLEdBQUcsQ0FBQztJQUN2QkwsZ0JBQVEsQ0FBQ0csSUFBSSxDQUFDUSxXQUFXLENBQUNaLElBQUksQ0FBQztJQUMvQkYsV0FBRyxDQUFDZSxlQUFlLENBQUNoQixHQUFHLENBQUM7RUFDMUI7QUFDRjs7QUFFQTtBQUNBO0FBQ0E7QUFDQTtBQUNPLFNBQVNpQixXQUFXQSxDQUN6QkMsa0JBQStCLEVBRS9CO0VBQUEsSUFEQUMsUUFBUSxHQUFBekYsU0FBQSxDQUFBQyxNQUFBLFFBQUFELFNBQUEsUUFBQWtCLFNBQUEsR0FBQWxCLFNBQUEsTUFBRyxJQUFBMEYsdUNBQW9CLEVBQUMsQ0FBQyxDQUFDQyxnQkFBZ0I7RUFFbEQsSUFBT0MsWUFBWSxHQUFJSixrQkFBa0IsQ0FBbENJLFlBQVk7RUFDbkIsSUFBSUEsWUFBWSxFQUFFO0lBQ2hCLElBQU1DLElBQUksR0FBR3hDLGFBQWEsQ0FBQ3VDLFlBQVksQ0FBQztJQUN4Q3pCLFlBQVksQ0FBQzBCLElBQUksRUFBRUosUUFBUSxDQUFDO0VBQzlCO0FBQ0Y7QUFFTyxTQUFTSyxrQkFBa0JBLENBQUNDLElBQUksRUFBRTtFQUN2QyxJQUFJO0lBQ0YsT0FBT0MsSUFBSSxDQUFDQyxTQUFTLENBQUNGLElBQUksQ0FBQztFQUM3QixDQUFDLENBQUMsT0FBTzVHLENBQUMsRUFBRTtJQUNWLElBQUlBLENBQUMsWUFBWStHLFNBQVMsRUFBRSxPQUFPL0csQ0FBQyxDQUFDZ0gsT0FBTztJQUM1QztJQUNBLE9BQVFoSCxDQUFDLENBQVNpSCxXQUFXO0VBQy9CO0FBQ0Y7QUFFTyxTQUFTQyxVQUFVQSxDQUFDQyxLQUFLLEVBQThEO0VBQUEsSUFBNURwRCxPQUFPLEdBQUFsRCxTQUFBLENBQUFDLE1BQUEsUUFBQUQsU0FBQSxRQUFBa0IsU0FBQSxHQUFBbEIsU0FBQSxNQUFHLElBQUEwRix1Q0FBb0IsRUFBQyxDQUFDLENBQUNhLHlCQUF5QjtFQUMxRixJQUFPQyxPQUFPLEdBQUl0RCxPQUFPLENBQWxCc0QsT0FBTztFQUNkLElBQU1DLE1BQU0sR0FBR0gsS0FBSyxDQUFDSSxRQUFRLENBQUNELE1BQU07RUFFcEMsSUFBSSxDQUFDRCxPQUFPLEVBQUU7SUFDWixPQUFPQyxNQUFNLENBQUNFLGVBQWUsQ0FBQ0wsS0FBSyxDQUFDO0VBQ3RDO0VBRUEsSUFBSU0sU0FBUyxHQUFHSCxNQUFNLENBQUNJLElBQUksQ0FBQ1AsS0FBSyxDQUFDO0VBQ2xDO0VBQ0EsSUFBTVEsS0FBSyxHQUFHLElBQUFDLGVBQUcsRUFBQ0gsU0FBUyxFQUFFLENBQUMsTUFBTSxFQUFFLE9BQU8sQ0FBQyxDQUFDO0VBQy9DLElBQUksQ0FBQ0UsS0FBSyxJQUFJLENBQUNBLEtBQUssQ0FBQzdHLE1BQU0sRUFBRTtJQUMzQjJHLFNBQVMsR0FBRyxJQUFBSSxVQUFHLEVBQUMsQ0FBQyxNQUFNLEVBQUUsT0FBTyxDQUFDLGNBQUFDLE1BQUEsQ0FBYyxJQUFBQywyQkFBYyxFQUFDLENBQUMsQ0FBQyxHQUFJTixTQUFTLENBQUM7RUFDaEY7RUFDQSxPQUFPQSxTQUFTO0FBQ2xCO0FBRU8sU0FBU08sVUFBVUEsQ0FBQ2IsS0FBSyxFQUFxQjtFQUFBLElBQW5CcEQsT0FBWSxHQUFBbEQsU0FBQSxDQUFBQyxNQUFBLFFBQUFELFNBQUEsUUFBQWtCLFNBQUEsR0FBQWxCLFNBQUEsTUFBRyxDQUFDLENBQUM7RUFDakQsSUFBTW9ILEdBQUcsR0FBR2YsVUFBVSxDQUFDQyxLQUFLLEVBQUVwRCxPQUFPLENBQUM7RUFDdENrRSxHQUFHLENBQUNDLElBQUksQ0FBQ0MsTUFBTSxHQUFHLFdBQVc7RUFDN0IsSUFBTWxELFFBQVEsR0FBRyxJQUFJSCxZQUFJLENBQUMsQ0FBQzZCLGtCQUFrQixDQUFDc0IsR0FBRyxDQUFDLENBQUMsRUFBRTtJQUFDbEQsSUFBSSxFQUFFO0VBQWtCLENBQUMsQ0FBQztFQUNoRixJQUFNRyxRQUFRLEdBQUdpQyxLQUFLLENBQUNpQixPQUFPLE1BQUFOLE1BQUEsQ0FBTVgsS0FBSyxDQUFDaUIsT0FBTyxhQUFVLElBQUE3Qix1Q0FBb0IsRUFBQyxDQUFDLENBQUM4QixlQUFlO0VBQ2pHckQsWUFBWSxDQUFDQyxRQUFRLEVBQUVDLFFBQVEsQ0FBQztBQUNsQztBQUVPLFNBQVNvRCxVQUFVQSxDQUFDbkIsS0FBSyxFQUFFcEQsT0FBTyxFQUFFO0VBQ3pDLElBQU93RSxlQUFlLEdBQW1DeEUsT0FBTyxDQUF6RHdFLGVBQWU7SUFBRUMsdUJBQXVCLEdBQVV6RSxPQUFPLENBQXhDeUUsdUJBQXVCO0lBQUVDLElBQUksR0FBSTFFLE9BQU8sQ0FBZjBFLElBQUk7RUFFckQsSUFBTTdCLElBQUksR0FBQWhHLGFBQUEsQ0FBQUEsYUFBQSxLQUNMc0csVUFBVSxDQUFDQyxLQUFLLENBQUM7SUFDcEJ1QixvQkFBb0IsRUFDbEIsQ0FBQ0gsZUFBZSxJQUFJLEVBQUUsTUFBTSxFQUFFLEdBQUdBLGVBQWUsR0FBR0MsdUJBQXVCO0lBQzVFQyxJQUFJLEVBQUpBO0VBQUksRUFDTDtFQUVELElBQU14RCxRQUFRLEdBQUcsSUFBSUgsWUFBSSxDQUFDLENBQUMsSUFBQTZELDhCQUFlLEVBQUMvQixJQUFJLENBQUMsQ0FBQyxFQUFFO0lBQUM3QixJQUFJLEVBQUU7RUFBVyxDQUFDLENBQUM7RUFDdkVDLFlBQVksQ0FDVkMsUUFBUSxFQUNSa0MsS0FBSyxDQUFDaUIsT0FBTyxNQUFBTixNQUFBLENBQU1YLEtBQUssQ0FBQ2lCLE9BQU8sYUFBVSxJQUFBN0IsdUNBQW9CLEVBQUMsQ0FBQyxDQUFDcUMsZUFDbkUsQ0FBQztBQUNIO0FBRU8sU0FBU0MsU0FBU0EsQ0FBQzFCLEtBQUssRUFBOEQ7RUFBQSxJQUE1RHBELE9BQU8sR0FBQWxELFNBQUEsQ0FBQUMsTUFBQSxRQUFBRCxTQUFBLFFBQUFrQixTQUFBLEdBQUFsQixTQUFBLE1BQUcsSUFBQTBGLHVDQUFvQixFQUFDLENBQUMsQ0FBQ2EseUJBQXlCO0VBQ3pGLElBQU9YLFlBQVksR0FBSVUsS0FBSyxDQUFDMkIsT0FBTyxDQUFDMUMsV0FBVyxDQUF6Q0ssWUFBWTtFQUNuQixJQUFNc0MsU0FBc0IsR0FBR3RDLFlBQVksR0FBR3ZDLGFBQWEsQ0FBQ3VDLFlBQVksQ0FBQyxHQUFHLElBQUk7RUFDaEYsSUFBTWdCLFNBQVMsR0FBR1AsVUFBVSxDQUFDQyxLQUFLLEVBQUVwRCxPQUFPLENBQUM7RUFFNUMsT0FBTztJQUNMa0UsR0FBRyxFQUFFUixTQUFTO0lBQ2RzQixTQUFTLEVBQVRBO0VBQ0YsQ0FBQztBQUNIO0FBRUEsSUFBTUMsU0FBUyxHQUFHO0VBQ2hCNUMsV0FBVyxFQUFYQSxXQUFXO0VBQ1g0QixVQUFVLEVBQVZBLFVBQVU7RUFDVk0sVUFBVSxFQUFWQTtBQUNGLENBQUM7QUFBQyxJQUFBVyxRQUFBLEdBQUFDLE9BQUEsY0FFYUYsU0FBUyIsImlnbm9yZUxpc3QiOltdfQ==
;