kepler.gl
Version:
kepler.gl is a webgl based application to visualize large scale location data in the browser
488 lines (409 loc) • 58.5 kB
JavaScript
"use strict";
var _interopRequireWildcard = require("@babel/runtime/helpers/interopRequireWildcard");
var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
Object.defineProperty(exports, "__esModule", {
value: true
});
exports["default"] = void 0;
var _slicedToArray2 = _interopRequireDefault(require("@babel/runtime/helpers/slicedToArray"));
var _extends2 = _interopRequireDefault(require("@babel/runtime/helpers/extends"));
var _toConsumableArray2 = _interopRequireDefault(require("@babel/runtime/helpers/toConsumableArray"));
var _typeof2 = _interopRequireDefault(require("@babel/runtime/helpers/typeof"));
var _classCallCheck2 = _interopRequireDefault(require("@babel/runtime/helpers/classCallCheck"));
var _createClass2 = _interopRequireDefault(require("@babel/runtime/helpers/createClass"));
var _possibleConstructorReturn2 = _interopRequireDefault(require("@babel/runtime/helpers/possibleConstructorReturn"));
var _getPrototypeOf3 = _interopRequireDefault(require("@babel/runtime/helpers/getPrototypeOf"));
var _assertThisInitialized2 = _interopRequireDefault(require("@babel/runtime/helpers/assertThisInitialized"));
var _inherits2 = _interopRequireDefault(require("@babel/runtime/helpers/inherits"));
var _defineProperty2 = _interopRequireDefault(require("@babel/runtime/helpers/defineProperty"));
var _taggedTemplateLiteral2 = _interopRequireDefault(require("@babel/runtime/helpers/taggedTemplateLiteral"));
var _react = _interopRequireWildcard(require("react"));
var _window = require("global/window");
var _redux = require("redux");
var _styledComponents = _interopRequireWildcard(require("styled-components"));
var _reselect = require("reselect");
var _keplerglConnect = require("../connect/keplergl-connect");
var _reactIntl = require("react-intl");
var _localization = require("../localization");
var _context = require("./context");
var VisStateActions = _interopRequireWildcard(require("../actions/vis-state-actions"));
var MapStateActions = _interopRequireWildcard(require("../actions/map-state-actions"));
var MapStyleActions = _interopRequireWildcard(require("../actions/map-style-actions"));
var UIStateActions = _interopRequireWildcard(require("../actions/ui-state-actions"));
var ProviderActions = _interopRequireWildcard(require("../actions/provider-actions"));
var _defaultSettings = require("../constants/default-settings");
var _userFeedbacks = require("../constants/user-feedbacks");
var _sidePanel = _interopRequireDefault(require("./side-panel"));
var _mapContainer = _interopRequireDefault(require("./map-container"));
var _bottomWidget = _interopRequireDefault(require("./bottom-widget"));
var _modalContainer = _interopRequireDefault(require("./modal-container"));
var _plotContainer = _interopRequireDefault(require("./plot-container"));
var _notificationPanel = _interopRequireDefault(require("./notification-panel"));
var _utils = require("../utils/utils");
var _mapboxUtils = require("../utils/mapbox-utils");
var _base = require("../styles/base");
function ownKeys(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); if (enumerableOnly) symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; }); keys.push.apply(keys, symbols); } return keys; }
function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i] != null ? arguments[i] : {}; if (i % 2) { ownKeys(Object(source), true).forEach(function (key) { (0, _defineProperty2["default"])(target, key, source[key]); }); } else if (Object.getOwnPropertyDescriptors) { Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)); } else { ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } } return target; }
function _templateObject() {
var data = (0, _taggedTemplateLiteral2["default"])(["\n font-family: ", ";\n font-weight: ", ";\n font-size: ", ";\n line-height: ", ";\n\n *,\n *:before,\n *:after {\n -webkit-box-sizing: border-box;\n -moz-box-sizing: border-box;\n box-sizing: border-box;\n }\n\n ul {\n margin: 0;\n padding: 0;\n }\n\n li {\n margin: 0;\n }\n\n a {\n text-decoration: none;\n color: ", ";\n }\n"]);
_templateObject = function _templateObject() {
return data;
};
return data;
}
// Maybe we should think about exporting this or creating a variable
// as part of the base.js theme
var GlobalStyle = _styledComponents["default"].div(_templateObject(), function (props) {
return props.theme.fontFamily;
}, function (props) {
return props.theme.fontWeight;
}, function (props) {
return props.theme.fontSize;
}, function (props) {
return props.theme.lineHeight;
}, function (props) {
return props.theme.labelColor;
});
KeplerGlFactory.deps = [_bottomWidget["default"], _mapContainer["default"], _modalContainer["default"], _sidePanel["default"], _plotContainer["default"], _notificationPanel["default"]];
function KeplerGlFactory(BottomWidget, MapContainer, ModalContainer, SidePanel, PlotContainer, NotificationPanel) {
var KeplerGL =
/*#__PURE__*/
function (_Component) {
(0, _inherits2["default"])(KeplerGL, _Component);
function KeplerGL() {
var _getPrototypeOf2;
var _this;
(0, _classCallCheck2["default"])(this, KeplerGL);
for (var _len = arguments.length, args = new Array(_len), _key = 0; _key < _len; _key++) {
args[_key] = arguments[_key];
}
_this = (0, _possibleConstructorReturn2["default"])(this, (_getPrototypeOf2 = (0, _getPrototypeOf3["default"])(KeplerGL)).call.apply(_getPrototypeOf2, [this].concat(args)));
(0, _defineProperty2["default"])((0, _assertThisInitialized2["default"])(_this), "root", (0, _react.createRef)());
(0, _defineProperty2["default"])((0, _assertThisInitialized2["default"])(_this), "themeSelector", function (props) {
return props.theme;
});
(0, _defineProperty2["default"])((0, _assertThisInitialized2["default"])(_this), "availableThemeSelector", (0, _reselect.createSelector)(_this.themeSelector, function (theme) {
return (0, _typeof2["default"])(theme) === 'object' ? _objectSpread({}, _base.theme, {}, theme) : theme === _defaultSettings.THEME.light ? _base.themeLT : theme === _defaultSettings.THEME.base ? _base.themeBS : theme;
}));
(0, _defineProperty2["default"])((0, _assertThisInitialized2["default"])(_this), "availableProviders", (0, _reselect.createSelector)(function (props) {
return props.cloudProviders;
}, function (providers) {
return Array.isArray(providers) && providers.length ? {
hasStorage: providers.some(function (p) {
return p.hasPrivateStorage();
}),
hasShare: providers.some(function (p) {
return p.hasSharingUrl();
})
} : {};
}));
(0, _defineProperty2["default"])((0, _assertThisInitialized2["default"])(_this), "_loadMapStyle", function () {
var defaultStyles = Object.values(_this.props.mapStyle.mapStyles); // add id to custom map styles if not given
var customStyles = (_this.props.mapStyles || []).map(function (ms) {
return _objectSpread({}, ms, {
id: ms.id || (0, _utils.generateHashId)()
});
});
var allStyles = [].concat((0, _toConsumableArray2["default"])(customStyles), (0, _toConsumableArray2["default"])(defaultStyles)).reduce(function (accu, style) {
var hasStyleObject = style.style && (0, _typeof2["default"])(style.style) === 'object';
accu[hasStyleObject ? 'toLoad' : 'toRequest'][style.id] = style;
return accu;
}, {
toLoad: {},
toRequest: {}
});
_this.props.mapStyleActions.loadMapStyles(allStyles.toLoad);
_this.props.mapStyleActions.requestMapStyles(allStyles.toRequest);
});
return _this;
}
(0, _createClass2["default"])(KeplerGL, [{
key: "componentDidMount",
value: function componentDidMount() {
this._validateMapboxToken();
this._loadMapStyle(this.props.mapStyles);
this._handleResize(this.props);
}
}, {
key: "componentDidUpdate",
value: function componentDidUpdate(prevProps) {
if ( // if dimension props has changed
this.props.height !== prevProps.height || this.props.width !== prevProps.width || // react-map-gl will dispatch updateViewport after this._handleResize is called
// here we check if this.props.mapState.height is sync with props.height
this.props.height !== this.props.mapState.height) {
this._handleResize(this.props);
}
}
}, {
key: "_validateMapboxToken",
/* private methods */
value: function _validateMapboxToken() {
var mapboxApiAccessToken = this.props.mapboxApiAccessToken;
if (!(0, _mapboxUtils.validateToken)(mapboxApiAccessToken)) {
_window.console.warn(_userFeedbacks.MISSING_MAPBOX_TOKEN);
}
}
}, {
key: "_handleResize",
value: function _handleResize(_ref) {
var width = _ref.width,
height = _ref.height;
if (!Number.isFinite(width) || !Number.isFinite(height)) {
_window.console.warn('width and height is required');
return;
}
this.props.mapStateActions.updateMap({
width: width / (1 + Number(this.props.mapState.isSplit)),
height: height
});
}
}, {
key: "render",
value: function render() {
var _this$props = this.props,
id = _this$props.id,
appName = _this$props.appName,
version = _this$props.version,
appWebsite = _this$props.appWebsite,
onSaveMap = _this$props.onSaveMap,
onViewStateChange = _this$props.onViewStateChange,
width = _this$props.width,
height = _this$props.height,
mapboxApiAccessToken = _this$props.mapboxApiAccessToken,
mapboxApiUrl = _this$props.mapboxApiUrl,
getMapboxRef = _this$props.getMapboxRef,
mapStyle = _this$props.mapStyle,
mapState = _this$props.mapState,
uiState = _this$props.uiState,
visState = _this$props.visState,
providerState = _this$props.providerState,
visStateActions = _this$props.visStateActions,
mapStateActions = _this$props.mapStateActions,
mapStyleActions = _this$props.mapStyleActions,
uiStateActions = _this$props.uiStateActions,
providerActions = _this$props.providerActions;
var availableProviders = this.availableProviders(this.props);
var filters = visState.filters,
layers = visState.layers,
splitMaps = visState.splitMaps,
layerOrder = visState.layerOrder,
layerBlending = visState.layerBlending,
layerClasses = visState.layerClasses,
interactionConfig = visState.interactionConfig,
datasets = visState.datasets,
layerData = visState.layerData,
hoverInfo = visState.hoverInfo,
clicked = visState.clicked,
mousePos = visState.mousePos,
animationConfig = visState.animationConfig,
mapInfo = visState.mapInfo;
var notificationPanelFields = {
removeNotification: uiStateActions.removeNotification,
notifications: uiState.notifications
};
var sideFields = {
appName: appName,
version: version,
appWebsite: appWebsite,
datasets: datasets,
filters: filters,
layers: layers,
layerOrder: layerOrder,
layerClasses: layerClasses,
interactionConfig: interactionConfig,
mapStyle: mapStyle,
mapInfo: mapInfo,
layerBlending: layerBlending,
onSaveMap: onSaveMap,
uiState: uiState,
mapStyleActions: mapStyleActions,
visStateActions: visStateActions,
uiStateActions: uiStateActions,
width: this.props.sidePanelWidth,
availableProviders: availableProviders,
mapSaved: providerState.mapSaved
};
var mapFields = {
datasets: datasets,
getMapboxRef: getMapboxRef,
mapboxApiAccessToken: mapboxApiAccessToken,
mapboxApiUrl: mapboxApiUrl,
mapState: mapState,
uiState: uiState,
editor: visState.editor,
mapStyle: mapStyle,
mapControls: uiState.mapControls,
layers: layers,
layerOrder: layerOrder,
layerData: layerData,
layerBlending: layerBlending,
filters: filters,
interactionConfig: interactionConfig,
hoverInfo: hoverInfo,
clicked: clicked,
mousePos: mousePos,
readOnly: uiState.readOnly,
onViewStateChange: onViewStateChange,
uiStateActions: uiStateActions,
visStateActions: visStateActions,
mapStateActions: mapStateActions,
animationConfig: animationConfig
};
var isSplit = splitMaps && splitMaps.length > 1;
var containerW = mapState.width * (Number(isSplit) + 1);
var mapContainers = !isSplit ? [_react["default"].createElement(MapContainer, (0, _extends2["default"])({
key: 0,
index: 0
}, mapFields, {
mapLayers: null
}))] : splitMaps.map(function (settings, index) {
return _react["default"].createElement(MapContainer, (0, _extends2["default"])({
key: index,
index: index
}, mapFields, {
mapLayers: splitMaps[index].layers
}));
});
var isExporting = uiState.currentModal === _defaultSettings.EXPORT_IMAGE_ID || uiState.currentModal === _defaultSettings.SAVE_MAP_ID || uiState.currentModal === _defaultSettings.SHARE_MAP_ID || uiState.currentModal === _defaultSettings.OVERWRITE_MAP_ID;
var theme = this.availableThemeSelector(this.props);
return _react["default"].createElement(_context.RootContext.Provider, {
value: this.root
}, _react["default"].createElement(_reactIntl.IntlProvider, {
locale: uiState.locale,
messages: _localization.messages[uiState.locale]
}, _react["default"].createElement(_styledComponents.ThemeProvider, {
theme: theme
}, _react["default"].createElement(GlobalStyle, {
width: width,
height: height,
className: "kepler-gl",
id: "kepler-gl__".concat(id),
ref: this.root
}, _react["default"].createElement(NotificationPanel, notificationPanelFields), !uiState.readOnly && _react["default"].createElement(SidePanel, sideFields), _react["default"].createElement("div", {
className: "maps",
style: {
display: 'flex'
}
}, mapContainers), isExporting && _react["default"].createElement(PlotContainer, {
width: width,
height: height,
exportImageSetting: uiState.exportImage,
mapFields: mapFields,
addNotification: uiStateActions.addNotification,
startExportingImage: uiStateActions.startExportingImage,
setExportImageDataUri: uiStateActions.setExportImageDataUri,
setExportImageError: uiStateActions.setExportImageError
}), _react["default"].createElement(BottomWidget, {
filters: filters,
datasets: datasets,
uiState: uiState,
layers: layers,
animationConfig: animationConfig,
visStateActions: visStateActions,
sidePanelWidth: uiState.readOnly ? 0 : this.props.sidePanelWidth + _defaultSettings.DIMENSIONS.sidePanel.margin.left,
containerW: containerW
}), _react["default"].createElement(ModalContainer, {
mapStyle: mapStyle,
visState: visState,
mapState: mapState,
uiState: uiState,
mapboxApiAccessToken: mapboxApiAccessToken,
mapboxApiUrl: mapboxApiUrl,
visStateActions: visStateActions,
uiStateActions: uiStateActions,
mapStyleActions: mapStyleActions,
providerActions: providerActions,
rootNode: this.root.current,
containerW: containerW,
containerH: mapState.height,
providerState: this.props.providerState // User defined cloud provider props
,
cloudProviders: this.props.cloudProviders,
onExportToCloudSuccess: this.props.onExportToCloudSuccess,
onLoadCloudMapSuccess: this.props.onLoadCloudMapSuccess,
onLoadCloudMapError: this.props.onLoadCloudMapError,
onExportToCloudError: this.props.onExportToCloudError
})))));
}
}]);
return KeplerGL;
}(_react.Component);
(0, _defineProperty2["default"])(KeplerGL, "defaultProps", {
mapStyles: [],
mapStylesReplaceDefault: false,
mapboxApiUrl: _defaultSettings.DEFAULT_MAPBOX_API_URL,
width: 800,
height: 800,
appName: _defaultSettings.KEPLER_GL_NAME,
version: _defaultSettings.KEPLER_GL_VERSION,
sidePanelWidth: _defaultSettings.DIMENSIONS.sidePanel.width,
theme: {},
cloudProviders: []
});
(0, _defineProperty2["default"])(KeplerGL, "contextType", _context.RootContext);
return (0, _keplerglConnect.connect)(mapStateToProps, makeMapDispatchToProps)((0, _styledComponents.withTheme)(KeplerGL));
}
function mapStateToProps() {
var state = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {};
var props = arguments.length > 1 ? arguments[1] : undefined;
return _objectSpread({}, props, {
visState: state.visState,
mapStyle: state.mapStyle,
mapState: state.mapState,
uiState: state.uiState,
providerState: state.providerState
});
}
var defaultUserActions = {};
var getDispatch = function getDispatch(dispatch) {
return dispatch;
};
var getUserActions = function getUserActions(dispatch, props) {
return props.actions || defaultUserActions;
};
function makeGetActionCreators() {
return (0, _reselect.createSelector)([getDispatch, getUserActions], function (dispatch, userActions) {
var _map = [VisStateActions, MapStateActions, MapStyleActions, UIStateActions, ProviderActions].map(function (actions) {
return (0, _redux.bindActionCreators)(mergeActions(actions, userActions), dispatch);
}),
_map2 = (0, _slicedToArray2["default"])(_map, 5),
visStateActions = _map2[0],
mapStateActions = _map2[1],
mapStyleActions = _map2[2],
uiStateActions = _map2[3],
providerActions = _map2[4];
return {
visStateActions: visStateActions,
mapStateActions: mapStateActions,
mapStyleActions: mapStyleActions,
uiStateActions: uiStateActions,
providerActions: providerActions,
dispatch: dispatch
};
});
}
function makeMapDispatchToProps() {
var getActionCreators = makeGetActionCreators();
var mapDispatchToProps = function mapDispatchToProps(dispatch, ownProps) {
var groupedActionCreators = getActionCreators(dispatch, ownProps);
return _objectSpread({}, groupedActionCreators, {
dispatch: dispatch
});
};
return mapDispatchToProps;
}
/**
* Override default kepler.gl actions with user defined actions using the same key
*/
function mergeActions(actions, userActions) {
var overrides = {};
for (var key in userActions) {
if (userActions.hasOwnProperty(key) && actions.hasOwnProperty(key)) {
overrides[key] = userActions[key];
}
}
return _objectSpread({}, actions, {}, overrides);
}
var _default = KeplerGlFactory;
exports["default"] = _default;
//# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi4uLy4uL3NyYy9jb21wb25lbnRzL2tlcGxlci1nbC5qcyJdLCJuYW1lcyI6WyJHbG9iYWxTdHlsZSIsInN0eWxlZCIsImRpdiIsInByb3BzIiwidGhlbWUiLCJmb250RmFtaWx5IiwiZm9udFdlaWdodCIsImZvbnRTaXplIiwibGluZUhlaWdodCIsImxhYmVsQ29sb3IiLCJLZXBsZXJHbEZhY3RvcnkiLCJkZXBzIiwiQm90dG9tV2lkZ2V0RmFjdG9yeSIsIk1hcENvbnRhaW5lckZhY3RvcnkiLCJNb2RhbENvbnRhaW5lckZhY3RvcnkiLCJTaWRlUGFuZWxGYWN0b3J5IiwiUGxvdENvbnRhaW5lckZhY3RvcnkiLCJOb3RpZmljYXRpb25QYW5lbEZhY3RvcnkiLCJCb3R0b21XaWRnZXQiLCJNYXBDb250YWluZXIiLCJNb2RhbENvbnRhaW5lciIsIlNpZGVQYW5lbCIsIlBsb3RDb250YWluZXIiLCJOb3RpZmljYXRpb25QYW5lbCIsIktlcGxlckdMIiwidGhlbWVTZWxlY3RvciIsImJhc2ljVGhlbWUiLCJUSEVNRSIsImxpZ2h0IiwidGhlbWVMVCIsImJhc2UiLCJ0aGVtZUJTIiwiY2xvdWRQcm92aWRlcnMiLCJwcm92aWRlcnMiLCJBcnJheSIsImlzQXJyYXkiLCJsZW5ndGgiLCJoYXNTdG9yYWdlIiwic29tZSIsInAiLCJoYXNQcml2YXRlU3RvcmFnZSIsImhhc1NoYXJlIiwiaGFzU2hhcmluZ1VybCIsImRlZmF1bHRTdHlsZXMiLCJPYmplY3QiLCJ2YWx1ZXMiLCJtYXBTdHlsZSIsIm1hcFN0eWxlcyIsImN1c3RvbVN0eWxlcyIsIm1hcCIsIm1zIiwiaWQiLCJhbGxTdHlsZXMiLCJyZWR1Y2UiLCJhY2N1Iiwic3R5bGUiLCJoYXNTdHlsZU9iamVjdCIsInRvTG9hZCIsInRvUmVxdWVzdCIsIm1hcFN0eWxlQWN0aW9ucyIsImxvYWRNYXBTdHlsZXMiLCJyZXF1ZXN0TWFwU3R5bGVzIiwiX3ZhbGlkYXRlTWFwYm94VG9rZW4iLCJfbG9hZE1hcFN0eWxlIiwiX2hhbmRsZVJlc2l6ZSIsInByZXZQcm9wcyIsImhlaWdodCIsIndpZHRoIiwibWFwU3RhdGUiLCJtYXBib3hBcGlBY2Nlc3NUb2tlbiIsIkNvbnNvbGUiLCJ3YXJuIiwiTUlTU0lOR19NQVBCT1hfVE9LRU4iLCJOdW1iZXIiLCJpc0Zpbml0ZSIsIm1hcFN0YXRlQWN0aW9ucyIsInVwZGF0ZU1hcCIsImlzU3BsaXQiLCJhcHBOYW1lIiwidmVyc2lvbiIsImFwcFdlYnNpdGUiLCJvblNhdmVNYXAiLCJvblZpZXdTdGF0ZUNoYW5nZSIsIm1hcGJveEFwaVVybCIsImdldE1hcGJveFJlZiIsInVpU3RhdGUiLCJ2aXNTdGF0ZSIsInByb3ZpZGVyU3RhdGUiLCJ2aXNTdGF0ZUFjdGlvbnMiLCJ1aVN0YXRlQWN0aW9ucyIsInByb3ZpZGVyQWN0aW9ucyIsImF2YWlsYWJsZVByb3ZpZGVycyIsImZpbHRlcnMiLCJsYXllcnMiLCJzcGxpdE1hcHMiLCJsYXllck9yZGVyIiwibGF5ZXJCbGVuZGluZyIsImxheWVyQ2xhc3NlcyIsImludGVyYWN0aW9uQ29uZmlnIiwiZGF0YXNldHMiLCJsYXllckRhdGEiLCJob3ZlckluZm8iLCJjbGlja2VkIiwibW91c2VQb3MiLCJhbmltYXRpb25Db25maWciLCJtYXBJbmZvIiwibm90aWZpY2F0aW9uUGFuZWxGaWVsZHMiLCJyZW1vdmVOb3RpZmljYXRpb24iLCJub3RpZmljYXRpb25zIiwic2lkZUZpZWxkcyIsInNpZGVQYW5lbFdpZHRoIiwibWFwU2F2ZWQiLCJtYXBGaWVsZHMiLCJlZGl0b3IiLCJtYXBDb250cm9scyIsInJlYWRPbmx5IiwiY29udGFpbmVyVyIsIm1hcENvbnRhaW5lcnMiLCJzZXR0aW5ncyIsImluZGV4IiwiaXNFeHBvcnRpbmciLCJjdXJyZW50TW9kYWwiLCJFWFBPUlRfSU1BR0VfSUQiLCJTQVZFX01BUF9JRCIsIlNIQVJFX01BUF9JRCIsIk9WRVJXUklURV9NQVBfSUQiLCJhdmFpbGFibGVUaGVtZVNlbGVjdG9yIiwicm9vdCIsImxvY2FsZSIsIm1lc3NhZ2VzIiwiZGlzcGxheSIsImV4cG9ydEltYWdlIiwiYWRkTm90aWZpY2F0aW9uIiwic3RhcnRFeHBvcnRpbmdJbWFnZSIsInNldEV4cG9ydEltYWdlRGF0YVVyaSIsInNldEV4cG9ydEltYWdlRXJyb3IiLCJESU1FTlNJT05TIiwic2lkZVBhbmVsIiwibWFyZ2luIiwibGVmdCIsImN1cnJlbnQiLCJvbkV4cG9ydFRvQ2xvdWRTdWNjZXNzIiwib25Mb2FkQ2xvdWRNYXBTdWNjZXNzIiwib25Mb2FkQ2xvdWRNYXBFcnJvciIsIm9uRXhwb3J0VG9DbG91ZEVycm9yIiwiQ29tcG9uZW50IiwibWFwU3R5bGVzUmVwbGFjZURlZmF1bHQiLCJERUZBVUxUX01BUEJPWF9BUElfVVJMIiwiS0VQTEVSX0dMX05BTUUiLCJLRVBMRVJfR0xfVkVSU0lPTiIsIlJvb3RDb250ZXh0IiwibWFwU3RhdGVUb1Byb3BzIiwibWFrZU1hcERpc3BhdGNoVG9Qcm9wcyIsInN0YXRlIiwiZGVmYXVsdFVzZXJBY3Rpb25zIiwiZ2V0RGlzcGF0Y2giLCJkaXNwYXRjaCIsImdldFVzZXJBY3Rpb25zIiwiYWN0aW9ucyIsIm1ha2VHZXRBY3Rpb25DcmVhdG9ycyIsInVzZXJBY3Rpb25zIiwiVmlzU3RhdGVBY3Rpb25zIiwiTWFwU3RhdGVBY3Rpb25zIiwiTWFwU3R5bGVBY3Rpb25zIiwiVUlTdGF0ZUFjdGlvbnMiLCJQcm92aWRlckFjdGlvbnMiLCJtZXJnZUFjdGlvbnMiLCJnZXRBY3Rpb25DcmVhdG9ycyIsIm1hcERpc3BhdGNoVG9Qcm9wcyIsIm93blByb3BzIiwiZ3JvdXBlZEFjdGlvbkNyZWF0b3JzIiwib3ZlcnJpZGVzIiwia2V5IiwiaGFzT3duUHJvcGVydHkiXSwibWFwcGluZ3MiOiI7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O0FBb0JBOztBQUNBOztBQUNBOztBQUNBOztBQUNBOztBQUNBOztBQUNBOztBQUNBOztBQUNBOztBQUVBOztBQUNBOztBQUNBOztBQUNBOztBQUNBOztBQUVBOztBQVdBOztBQUVBOztBQUNBOztBQUNBOztBQUNBOztBQUNBOztBQUNBOztBQUVBOztBQUNBOztBQUVBOzs7Ozs7Ozs7Ozs7Ozs7O0FBRUE7QUFDQTtBQUNBLElBQU1BLFdBQVcsR0FBR0MsNkJBQU9DLEdBQVYsb0JBQ0EsVUFBQUMsS0FBSztBQUFBLFNBQUlBLEtBQUssQ0FBQ0MsS0FBTixDQUFZQyxVQUFoQjtBQUFBLENBREwsRUFFQSxVQUFBRixLQUFLO0FBQUEsU0FBSUEsS0FBSyxDQUFDQyxLQUFOLENBQVlFLFVBQWhCO0FBQUEsQ0FGTCxFQUdGLFVBQUFILEtBQUs7QUFBQSxTQUFJQSxLQUFLLENBQUNDLEtBQU4sQ0FBWUcsUUFBaEI7QUFBQSxDQUhILEVBSUEsVUFBQUosS0FBSztBQUFBLFNBQUlBLEtBQUssQ0FBQ0MsS0FBTixDQUFZSSxVQUFoQjtBQUFBLENBSkwsRUF5QkosVUFBQUwsS0FBSztBQUFBLFNBQUlBLEtBQUssQ0FBQ0MsS0FBTixDQUFZSyxVQUFoQjtBQUFBLENBekJELENBQWpCOztBQTZCQUMsZUFBZSxDQUFDQyxJQUFoQixHQUF1QixDQUNyQkMsd0JBRHFCLEVBRXJCQyx3QkFGcUIsRUFHckJDLDBCQUhxQixFQUlyQkMscUJBSnFCLEVBS3JCQyx5QkFMcUIsRUFNckJDLDZCQU5xQixDQUF2Qjs7QUFTQSxTQUFTUCxlQUFULENBQ0VRLFlBREYsRUFFRUMsWUFGRixFQUdFQyxjQUhGLEVBSUVDLFNBSkYsRUFLRUMsYUFMRixFQU1FQyxpQkFORixFQU9FO0FBQUEsTUFDTUMsUUFETjtBQUFBO0FBQUE7QUFBQTs7QUFBQTtBQUFBOztBQUFBOztBQUFBOztBQUFBO0FBQUE7QUFBQTs7QUFBQTtBQUFBLCtGQWtDUyx1QkFsQ1Q7QUFBQSx3R0FzQ2tCLFVBQUFyQixLQUFLO0FBQUEsZUFBSUEsS0FBSyxDQUFDQyxLQUFWO0FBQUEsT0F0Q3ZCO0FBQUEsaUhBdUMyQiw4QkFBZSxNQUFLcUIsYUFBcEIsRUFBbUMsVUFBQXJCLEtBQUs7QUFBQSxlQUMvRCx5QkFBT0EsS0FBUCxNQUFpQixRQUFqQixxQkFFU3NCLFdBRlQsTUFHU3RCLEtBSFQsSUFLSUEsS0FBSyxLQUFLdUIsdUJBQU1DLEtBQWhCLEdBQ0FDLGFBREEsR0FFQXpCLEtBQUssS0FBS3VCLHVCQUFNRyxJQUFoQixHQUNBQyxhQURBLEdBRUEzQixLQVYyRDtBQUFBLE9BQXhDLENBdkMzQjtBQUFBLDZHQW9EdUIsOEJBQ25CLFVBQUFELEtBQUs7QUFBQSxlQUFJQSxLQUFLLENBQUM2QixjQUFWO0FBQUEsT0FEYyxFQUVuQixVQUFBQyxTQUFTO0FBQUEsZUFDUEMsS0FBSyxDQUFDQyxPQUFOLENBQWNGLFNBQWQsS0FBNEJBLFNBQVMsQ0FBQ0csTUFBdEMsR0FDSTtBQUNFQyxVQUFBQSxVQUFVLEVBQUVKLFNBQVMsQ0FBQ0ssSUFBVixDQUFlLFVBQUFDLENBQUM7QUFBQSxtQkFBSUEsQ0FBQyxDQUFDQyxpQkFBRixFQUFKO0FBQUEsV0FBaEIsQ0FEZDtBQUVFQyxVQUFBQSxRQUFRLEVBQUVSLFNBQVMsQ0FBQ0ssSUFBVixDQUFlLFVBQUFDLENBQUM7QUFBQSxtQkFBSUEsQ0FBQyxDQUFDRyxhQUFGLEVBQUo7QUFBQSxXQUFoQjtBQUZaLFNBREosR0FLSSxFQU5HO0FBQUEsT0FGVSxDQXBEdkI7QUFBQSx3R0FrRmtCLFlBQU07QUFDcEIsWUFBTUMsYUFBYSxHQUFHQyxNQUFNLENBQUNDLE1BQVAsQ0FBYyxNQUFLMUMsS0FBTCxDQUFXMkMsUUFBWCxDQUFvQkMsU0FBbEMsQ0FBdEIsQ0FEb0IsQ0FFcEI7O0FBQ0EsWUFBTUMsWUFBWSxHQUFHLENBQUMsTUFBSzdDLEtBQUwsQ0FBVzRDLFNBQVgsSUFBd0IsRUFBekIsRUFBNkJFLEdBQTdCLENBQWlDLFVBQUFDLEVBQUU7QUFBQSxtQ0FDbkRBLEVBRG1EO0FBRXREQyxZQUFBQSxFQUFFLEVBQUVELEVBQUUsQ0FBQ0MsRUFBSCxJQUFTO0FBRnlDO0FBQUEsU0FBbkMsQ0FBckI7QUFLQSxZQUFNQyxTQUFTLEdBQUcsOENBQUlKLFlBQUosdUNBQXFCTCxhQUFyQixHQUFvQ1UsTUFBcEMsQ0FDaEIsVUFBQ0MsSUFBRCxFQUFPQyxLQUFQLEVBQWlCO0FBQ2YsY0FBTUMsY0FBYyxHQUFHRCxLQUFLLENBQUNBLEtBQU4sSUFBZSx5QkFBT0EsS0FBSyxDQUFDQSxLQUFiLE1BQXVCLFFBQTdEO0FBQ0FELFVBQUFBLElBQUksQ0FBQ0UsY0FBYyxHQUFHLFFBQUgsR0FBYyxXQUE3QixDQUFKLENBQThDRCxLQUFLLENBQUNKLEVBQXBELElBQTBESSxLQUExRDtBQUVBLGlCQUFPRCxJQUFQO0FBQ0QsU0FOZSxFQU9oQjtBQUFDRyxVQUFBQSxNQUFNLEVBQUUsRUFBVDtBQUFhQyxVQUFBQSxTQUFTLEVBQUU7QUFBeEIsU0FQZ0IsQ0FBbEI7O0FBVUEsY0FBS3ZELEtBQUwsQ0FBV3dELGVBQVgsQ0FBMkJDLGFBQTNCLENBQXlDUixTQUFTLENBQUNLLE1BQW5EOztBQUNBLGNBQUt0RCxLQUFMLENBQVd3RCxlQUFYLENBQTJCRSxnQkFBM0IsQ0FBNENULFNBQVMsQ0FBQ00sU0FBdEQ7QUFDRCxPQXRHSDtBQUFBO0FBQUE7O0FBQUE7QUFBQTtBQUFBLDBDQWVzQjtBQUNsQixhQUFLSSxvQkFBTDs7QUFDQSxhQUFLQyxhQUFMLENBQW1CLEtBQUs1RCxLQUFMLENBQVc0QyxTQUE5Qjs7QUFDQSxhQUFLaUIsYUFBTCxDQUFtQixLQUFLN0QsS0FBeEI7QUFDRDtBQW5CSDtBQUFBO0FBQUEseUNBcUJxQjhELFNBckJyQixFQXFCZ0M7QUFDNUIsYUFDRTtBQUNBLGFBQUs5RCxLQUFMLENBQVcrRCxNQUFYLEtBQXNCRCxTQUFTLENBQUNDLE1BQWhDLElBQ0EsS0FBSy9ELEtBQUwsQ0FBV2dFLEtBQVgsS0FBcUJGLFNBQVMsQ0FBQ0UsS0FEL0IsSUFFQTtBQUNBO0FBQ0EsYUFBS2hFLEtBQUwsQ0FBVytELE1BQVgsS0FBc0IsS0FBSy9ELEtBQUwsQ0FBV2lFLFFBQVgsQ0FBb0JGLE1BTjVDLEVBT0U7QUFDQSxlQUFLRixhQUFMLENBQW1CLEtBQUs3RCxLQUF4QjtBQUNEO0FBQ0Y7QUFoQ0g7QUFBQTs7QUErREU7QUEvREYsNkNBZ0V5QjtBQUFBLFlBQ2RrRSxvQkFEYyxHQUNVLEtBQUtsRSxLQURmLENBQ2RrRSxvQkFEYzs7QUFFckIsWUFBSSxDQUFDLGdDQUFjQSxvQkFBZCxDQUFMLEVBQTBDO0FBQ3hDQywwQkFBUUMsSUFBUixDQUFhQyxtQ0FBYjtBQUNEO0FBQ0Y7QUFyRUg7QUFBQTtBQUFBLDBDQXVFaUM7QUFBQSxZQUFoQkwsS0FBZ0IsUUFBaEJBLEtBQWdCO0FBQUEsWUFBVEQsTUFBUyxRQUFUQSxNQUFTOztBQUM3QixZQUFJLENBQUNPLE1BQU0sQ0FBQ0MsUUFBUCxDQUFnQlAsS0FBaEIsQ0FBRCxJQUEyQixDQUFDTSxNQUFNLENBQUNDLFFBQVAsQ0FBZ0JSLE1BQWhCLENBQWhDLEVBQXlEO0FBQ3ZESSwwQkFBUUMsSUFBUixDQUFhLDhCQUFiOztBQUNBO0FBQ0Q7O0FBQ0QsYUFBS3BFLEtBQUwsQ0FBV3dFLGVBQVgsQ0FBMkJDLFNBQTNCLENBQXFDO0FBQ25DVCxVQUFBQSxLQUFLLEVBQUVBLEtBQUssSUFBSSxJQUFJTSxNQUFNLENBQUMsS0FBS3RFLEtBQUwsQ0FBV2lFLFFBQVgsQ0FBb0JTLE9BQXJCLENBQWQsQ0FEdUI7QUFFbkNYLFVBQUFBLE1BQU0sRUFBTkE7QUFGbUMsU0FBckM7QUFJRDtBQWhGSDtBQUFBO0FBQUEsK0JBd0dXO0FBQUEsMEJBNEJILEtBQUsvRCxLQTVCRjtBQUFBLFlBR0xnRCxFQUhLLGVBR0xBLEVBSEs7QUFBQSxZQUlMMkIsT0FKSyxlQUlMQSxPQUpLO0FBQUEsWUFLTEMsT0FMSyxlQUtMQSxPQUxLO0FBQUEsWUFNTEMsVUFOSyxlQU1MQSxVQU5LO0FBQUEsWUFPTEMsU0FQSyxlQU9MQSxTQVBLO0FBQUEsWUFRTEMsaUJBUkssZUFRTEEsaUJBUks7QUFBQSxZQVNMZixLQVRLLGVBU0xBLEtBVEs7QUFBQSxZQVVMRCxNQVZLLGVBVUxBLE1BVks7QUFBQSxZQVdMRyxvQkFYSyxlQVdMQSxvQkFYSztBQUFBLFlBWUxjLFlBWkssZUFZTEEsWUFaSztBQUFBLFlBYUxDLFlBYkssZUFhTEEsWUFiSztBQUFBLFlBZ0JMdEMsUUFoQkssZUFnQkxBLFFBaEJLO0FBQUEsWUFpQkxzQixRQWpCSyxlQWlCTEEsUUFqQks7QUFBQSxZQWtCTGlCLE9BbEJLLGVBa0JMQSxPQWxCSztBQUFBLFlBbUJMQyxRQW5CSyxlQW1CTEEsUUFuQks7QUFBQSxZQW9CTEMsYUFwQkssZUFvQkxBLGFBcEJLO0FBQUEsWUF1QkxDLGVBdkJLLGVBdUJMQSxlQXZCSztBQUFBLFlBd0JMYixlQXhCSyxlQXdCTEEsZUF4Qks7QUFBQSxZQXlCTGhCLGVBekJLLGVBeUJMQSxlQXpCSztBQUFBLFlBMEJMOEIsY0ExQkssZUEwQkxBLGNBMUJLO0FBQUEsWUEyQkxDLGVBM0JLLGVBMkJMQSxlQTNCSztBQThCUCxZQUFNQyxrQkFBa0IsR0FBRyxLQUFLQSxrQkFBTCxDQUF3QixLQUFLeEYsS0FBN0IsQ0FBM0I7QUE5Qk8sWUFpQ0x5RixPQWpDSyxHQStDSE4sUUEvQ0csQ0FpQ0xNLE9BakNLO0FBQUEsWUFrQ0xDLE1BbENLLEdBK0NIUCxRQS9DRyxDQWtDTE8sTUFsQ0s7QUFBQSxZQW1DTEMsU0FuQ0ssR0ErQ0hSLFFBL0NHLENBbUNMUSxTQW5DSztBQUFBLFlBb0NMQyxVQXBDSyxHQStDSFQsUUEvQ0csQ0FvQ0xTLFVBcENLO0FBQUEsWUFxQ0xDLGFBckNLLEdBK0NIVixRQS9DRyxDQXFDTFUsYUFyQ0s7QUFBQSxZQXNDTEMsWUF0Q0ssR0ErQ0hYLFFBL0NHLENBc0NMVyxZQXRDSztBQUFBLFlBdUNMQyxpQkF2Q0ssR0ErQ0haLFFBL0NHLENBdUNMWSxpQkF2Q0s7QUFBQSxZQXdDTEMsUUF4Q0ssR0ErQ0hiLFFBL0NHLENBd0NMYSxRQXhDSztBQUFBLFlBeUNMQyxTQXpDSyxHQStDSGQsUUEvQ0csQ0F5Q0xjLFNBekNLO0FBQUEsWUEwQ0xDLFNBMUNLLEdBK0NIZixRQS9DRyxDQTBDTGUsU0ExQ0s7QUFBQSxZQTJDTEMsT0EzQ0ssR0ErQ0hoQixRQS9DRyxDQTJDTGdCLE9BM0NLO0FBQUEsWUE0Q0xDLFFBNUNLLEdBK0NIakIsUUEvQ0csQ0E0Q0xpQixRQTVDSztBQUFBLFlBNkNMQyxlQTdDSyxHQStDSGxCLFFBL0NHLENBNkNMa0IsZUE3Q0s7QUFBQSxZQThDTEMsT0E5Q0ssR0ErQ0huQixRQS9DRyxDQThDTG1CLE9BOUNLO0FBaURQLFlBQU1DLHVCQUF1QixHQUFHO0FBQzlCQyxVQUFBQSxrQkFBa0IsRUFBRWxCLGNBQWMsQ0FBQ2tCLGtCQURMO0FBRTlCQyxVQUFBQSxhQUFhLEVBQUV2QixPQUFPLENBQUN1QjtBQUZPLFNBQWhDO0FBS0EsWUFBTUMsVUFBVSxHQUFHO0FBQ2pCL0IsVUFBQUEsT0FBTyxFQUFQQSxPQURpQjtBQUVqQkMsVUFBQUEsT0FBTyxFQUFQQSxPQUZpQjtBQUdqQkMsVUFBQUEsVUFBVSxFQUFWQSxVQUhpQjtBQUlqQm1CLFVBQUFBLFFBQVEsRUFBUkEsUUFKaUI7QUFLakJQLFVBQUFBLE9BQU8sRUFBUEEsT0FMaUI7QUFNakJDLFVBQUFBLE1BQU0sRUFBTkEsTUFOaUI7QUFPakJFLFVBQUFBLFVBQVUsRUFBVkEsVUFQaUI7QUFRakJFLFVBQUFBLFlBQVksRUFBWkEsWUFSaUI7QUFTakJDLFVBQUFBLGlCQUFpQixFQUFqQkEsaUJBVGlCO0FBVWpCcEQsVUFBQUEsUUFBUSxFQUFSQSxRQVZpQjtBQVdqQjJELFVBQUFBLE9BQU8sRUFBUEEsT0FYaUI7QUFZakJULFVBQUFBLGFBQWEsRUFBYkEsYUFaaUI7QUFhakJmLFVBQUFBLFNBQVMsRUFBVEEsU0FiaUI7QUFjakJJLFVBQUFBLE9BQU8sRUFBUEEsT0FkaUI7QUFlakIxQixVQUFBQSxlQUFlLEVBQWZBLGVBZmlCO0FBZ0JqQjZCLFVBQUFBLGVBQWUsRUFBZkEsZUFoQmlCO0FBaUJqQkMsVUFBQUEsY0FBYyxFQUFkQSxjQWpCaUI7QUFrQmpCdEIsVUFBQUEsS0FBSyxFQUFFLEtBQUtoRSxLQUFMLENBQVcyRyxjQWxCRDtBQW1CakJuQixVQUFBQSxrQkFBa0IsRUFBbEJBLGtCQW5CaUI7QUFvQmpCb0IsVUFBQUEsUUFBUSxFQUFFeEIsYUFBYSxDQUFDd0I7QUFwQlAsU0FBbkI7QUF1QkEsWUFBTUMsU0FBUyxHQUFHO0FBQ2hCYixVQUFBQSxRQUFRLEVBQVJBLFFBRGdCO0FBRWhCZixVQUFBQSxZQUFZLEVBQVpBLFlBRmdCO0FBR2hCZixVQUFBQSxvQkFBb0IsRUFBcEJBLG9CQUhnQjtBQUloQmMsVUFBQUEsWUFBWSxFQUFaQSxZQUpnQjtBQUtoQmYsVUFBQUEsUUFBUSxFQUFSQSxRQUxnQjtBQU1oQmlCLFVBQUFBLE9BQU8sRUFBUEEsT0FOZ0I7QUFPaEI0QixVQUFBQSxNQUFNLEVBQUUzQixRQUFRLENBQUMyQixNQVBEO0FBUWhCbkUsVUFBQUEsUUFBUSxFQUFSQSxRQVJnQjtBQVNoQm9FLFVBQUFBLFdBQVcsRUFBRTdCLE9BQU8sQ0FBQzZCLFdBVEw7QUFVaEJyQixVQUFBQSxNQUFNLEVBQU5BLE1BVmdCO0FBV2hCRSxVQUFBQSxVQUFVLEVBQVZBLFVBWGdCO0FBWWhCSyxVQUFBQSxTQUFTLEVBQVRBLFNBWmdCO0FBYWhCSixVQUFBQSxhQUFhLEVBQWJBLGFBYmdCO0FBY2hCSixVQUFBQSxPQUFPLEVBQVBBLE9BZGdCO0FBZWhCTSxVQUFBQSxpQkFBaUIsRUFBakJBLGlCQWZnQjtBQWdCaEJHLFVBQUFBLFNBQVMsRUFBVEEsU0FoQmdCO0FBaUJoQkMsVUFBQUEsT0FBTyxFQUFQQSxPQWpCZ0I7QUFrQmhCQyxVQUFBQSxRQUFRLEVBQVJBLFFBbEJnQjtBQW1CaEJZLFVBQUFBLFFBQVEsRUFBRTlCLE9BQU8sQ0FBQzhCLFFBbkJGO0FBb0JoQmpDLFVBQUFBLGlCQUFpQixFQUFqQkEsaUJBcEJnQjtBQXFCaEJPLFVBQUFBLGNBQWMsRUFBZEEsY0FyQmdCO0FBc0JoQkQsVUFBQUEsZUFBZSxFQUFmQSxlQXRCZ0I7QUF1QmhCYixVQUFBQSxlQUFlLEVBQWZBLGVBdkJnQjtBQXdCaEI2QixVQUFBQSxlQUFlLEVBQWZBO0FBeEJnQixTQUFsQjtBQTJCQSxZQUFNM0IsT0FBTyxHQUFHaUIsU0FBUyxJQUFJQSxTQUFTLENBQUMxRCxNQUFWLEdBQW1CLENBQWhEO0FBQ0EsWUFBTWdGLFVBQVUsR0FBR2hELFFBQVEsQ0FBQ0QsS0FBVCxJQUFrQk0sTUFBTSxDQUFDSSxPQUFELENBQU4sR0FBa0IsQ0FBcEMsQ0FBbkI7QUFFQSxZQUFNd0MsYUFBYSxHQUFHLENBQUN4QyxPQUFELEdBQ2xCLENBQUMsZ0NBQUMsWUFBRDtBQUFjLFVBQUEsR0FBRyxFQUFFLENBQW5CO0FBQXNCLFVBQUEsS0FBSyxFQUFFO0FBQTdCLFdBQW9DbUMsU0FBcEM7QUFBK0MsVUFBQSxTQUFTLEVBQUU7QUFBMUQsV0FBRCxDQURrQixHQUVsQmxCLFNBQVMsQ0FBQzdDLEdBQVYsQ0FBYyxVQUFDcUUsUUFBRCxFQUFXQyxLQUFYO0FBQUEsaUJBQ1osZ0NBQUMsWUFBRDtBQUNFLFlBQUEsR0FBRyxFQUFFQSxLQURQO0FBRUUsWUFBQSxLQUFLLEVBQUVBO0FBRlQsYUFHTVAsU0FITjtBQUlFLFlBQUEsU0FBUyxFQUFFbEIsU0FBUyxDQUFDeUIsS0FBRCxDQUFULENBQWlCMUI7QUFKOUIsYUFEWTtBQUFBLFNBQWQsQ0FGSjtBQVdBLFlBQU0yQixXQUFXLEdBQ2ZuQyxPQUFPLENBQUNvQyxZQUFSLEtBQXlCQyxnQ0FBekIsSUFDQXJDLE9BQU8sQ0FBQ29DLFlBQVIsS0FBeUJFLDRCQUR6QixJQUVBdEMsT0FBTyxDQUFDb0MsWUFBUixLQUF5QkcsNkJBRnpCLElBR0F2QyxPQUFPLENBQUNvQyxZQUFSLEtBQXlCSSxpQ0FKM0I7QUFNQSxZQUFNekgsS0FBSyxHQUFHLEtBQUswSCxzQkFBTCxDQUE0QixLQUFLM0gsS0FBakMsQ0FBZDtBQUVBLGVBQ0UsZ0NBQUMsb0JBQUQsQ0FBYSxRQUFiO0FBQXNCLFVBQUEsS0FBSyxFQUFFLEtBQUs0SDtBQUFsQyxXQUNFLGdDQUFDLHVCQUFEO0FBQWMsVUFBQSxNQUFNLEVBQUUxQyxPQUFPLENBQUMyQyxNQUE5QjtBQUFzQyxVQUFBLFFBQVEsRUFBRUMsdUJBQVM1QyxPQUFPLENBQUMyQyxNQUFqQjtBQUFoRCxXQUNFLGdDQUFDLCtCQUFEO0FBQWUsVUFBQSxLQUFLLEVBQUU1SDtBQUF0QixXQUNFLGdDQUFDLFdBQUQ7QUFDRSxVQUFBLEtBQUssRUFBRStELEtBRFQ7QUFFRSxVQUFBLE1BQU0sRUFBRUQsTUFGVjtBQUdFLFVBQUEsU0FBUyxFQUFDLFdBSFo7QUFJRSxVQUFBLEVBQUUsdUJBQWdCZixFQUFoQixDQUpKO0FBS0UsVUFBQSxHQUFHLEVBQUUsS0FBSzRFO0FBTFosV0FPRSxnQ0FBQyxpQkFBRCxFQUF1QnJCLHVCQUF2QixDQVBGLEVBUUcsQ0FBQ3JCLE9BQU8sQ0FBQzhCLFFBQVQsSUFBcUIsZ0NBQUMsU0FBRCxFQUFlTixVQUFmLENBUnhCLEVBU0U7QUFBSyxVQUFBLFNBQVMsRUFBQyxNQUFmO0FBQXNCLFVBQUEsS0FBSyxFQUFFO0FBQUNxQixZQUFBQSxPQUFPLEVBQUU7QUFBVjtBQUE3QixXQUNHYixhQURILENBVEYsRUFZR0csV0FBVyxJQUNWLGdDQUFDLGFBQUQ7QUFDRSxVQUFBLEtBQUssRUFBRXJELEtBRFQ7QUFFRSxVQUFBLE1BQU0sRUFBRUQsTUFGVjtBQUdFLFVBQUEsa0JBQWtCLEVBQUVtQixPQUFPLENBQUM4QyxXQUg5QjtBQUlFLFVBQUEsU0FBUyxFQUFFbkIsU0FKYjtBQUtFLFVBQUEsZUFBZSxFQUFFdkIsY0FBYyxDQUFDMkMsZUFMbEM7QUFNRSxVQUFBLG1CQUFtQixFQUFFM0MsY0FBYyxDQUFDNEMsbUJBTnRDO0FBT0UsVUFBQSxxQkFBcUIsRUFBRTVDLGNBQWMsQ0FBQzZDLHFCQVB4QztBQVFFLFVBQUEsbUJBQW1CLEVBQUU3QyxjQUFjLENBQUM4QztBQVJ0QyxVQWJKLEVBd0JFLGdDQUFDLFlBQUQ7QUFDRSxVQUFBLE9BQU8sRUFBRTNDLE9BRFg7QUFFRSxVQUFBLFFBQVEsRUFBRU8sUUFGWjtBQUdFLFVBQUEsT0FBTyxFQUFFZCxPQUhYO0FBSUUsVUFBQSxNQUFNLEVBQUVRLE1BSlY7QUFLRSxVQUFBLGVBQWUsRUFBRVcsZUFMbkI7QUFNRSxVQUFBLGVBQWUsRUFBRWhCLGVBTm5CO0FBT0UsVUFBQSxjQUFjLEVBQ1pILE9BQU8sQ0FBQzhCLFFBQVIsR0FDSSxDQURKLEdBRUksS0FBS2hILEtBQUwsQ0FBVzJHLGNBQVgsR0FBNEIwQiw0QkFBV0MsU0FBWCxDQUFxQkMsTUFBckIsQ0FBNEJDLElBVmhFO0FBWUUsVUFBQSxVQUFVLEVBQUV2QjtBQVpkLFVBeEJGLEVBc0NFLGdDQUFDLGNBQUQ7QUFDRSxVQUFBLFFBQVEsRUFBRXRFLFFBRFo7QUFFRSxVQUFBLFFBQVEsRUFBRXdDLFFBRlo7QUFHRSxVQUFBLFFBQVEsRUFBRWxCLFFBSFo7QUFJRSxVQUFBLE9BQU8sRUFBRWlCLE9BSlg7QUFLRSxVQUFBLG9CQUFvQixFQUFFaEIsb0JBTHhCO0FBTUUsVUFBQSxZQUFZLEVBQUVjLFlBTmhCO0FBT0UsVUFBQSxlQUFlLEVBQUVLLGVBUG5CO0FBUUUsVUFBQSxjQUFjLEVBQUVDLGNBUmxCO0FBU0UsVUFBQSxlQUFlLEVBQUU5QixlQVRuQjtBQVVFLFVBQUEsZUFBZSxFQUFFK0IsZUFWbkI7QUFXRSxVQUFBLFFBQVEsRUFBRSxLQUFLcUMsSUFBTCxDQUFVYSxPQVh0QjtBQVlFLFVBQUEsVUFBVSxFQUFFeEIsVUFaZDtBQWFFLFVBQUEsVUFBVSxFQUFFaEQsUUFBUSxDQUFDRixNQWJ2QjtBQWNFLFVBQUEsYUFBYSxFQUFFLEtBQUsvRCxLQUFMLENBQVdvRixhQWQ1QixDQWVFO0FBZkY7QUFnQkUsVUFBQSxjQUFjLEVBQUUsS0FBS3BGLEtBQUwsQ0FBVzZCLGNBaEI3QjtBQWlCRSxVQUFBLHNCQUFzQixFQUFFLEtBQUs3QixLQUFMLENBQVcwSSxzQkFqQnJDO0FBa0JFLFVBQUEscUJBQXFCLEVBQUUsS0FBSzFJLEtBQUwsQ0FBVzJJLHFCQWxCcEM7QUFtQkUsVUFBQSxtQkFBbUIsRUFBRSxLQUFLM0ksS0FBTCxDQUFXNEksbUJBbkJsQztBQW9CRSxVQUFBLG9CQUFvQixFQUFFLEtBQUs1SSxLQUFMLENBQVc2STtBQXBCbkMsVUF0Q0YsQ0FERixDQURGLENBREYsQ0FERjtBQXFFRDtBQTNTSDtBQUFBO0FBQUEsSUFDdUJDLGdCQUR2Qjs7QUFBQSxtQ0FDTXpILFFBRE4sa0JBRXdCO0FBQ3BCdUIsSUFBQUEsU0FBUyxFQUFFLEVBRFM7QUFFcEJtRyxJQUFBQSx1QkFBdUIsRUFBRSxLQUZMO0FBR3BCL0QsSUFBQUEsWUFBWSxFQUFFZ0UsdUNBSE07QUFJcEJoRixJQUFBQSxLQUFLLEVBQUUsR0FKYTtBQUtwQkQsSUFBQUEsTUFBTSxFQUFFLEdBTFk7QUFNcEJZLElBQUFBLE9BQU8sRUFBRXNFLCtCQU5XO0FBT3BCckUsSUFBQUEsT0FBTyxFQUFFc0Usa0NBUFc7QUFRcEJ2QyxJQUFBQSxjQUFjLEVBQUUwQiw0QkFBV0MsU0FBWCxDQUFxQnRFLEtBUmpCO0FBU3BCL0QsSUFBQUEsS0FBSyxFQUFFLEVBVGE7QUFVcEI0QixJQUFBQSxjQUFjLEVBQUU7QUFWSSxHQUZ4QjtBQUFBLG1DQUNNUixRQUROLGlCQW1DdUI4SCxvQkFuQ3ZCO0FBOFNBLFNBQU8sOEJBQWdCQyxlQUFoQixFQUFpQ0Msc0JBQWpDLEVBQXlELGlDQUFVaEksUUFBVixDQUF6RCxDQUFQO0FBQ0Q7O0FBRUQsU0FBUytILGVBQVQsR0FBNEM7QUFBQSxNQUFuQkUsS0FBbUIsdUVBQVgsRUFBVztBQUFBLE1BQVB0SixLQUFPO0FBQzFDLDJCQUNLQSxLQURMO0FBRUVtRixJQUFBQSxRQUFRLEVBQUVtRSxLQUFLLENBQUNuRSxRQUZsQjtBQUdFeEMsSUFBQUEsUUFBUSxFQUFFMkcsS0FBSyxDQUFDM0csUUFIbEI7QUFJRXNCLElBQUFBLFFBQVEsRUFBRXFGLEtBQUssQ0FBQ3JGLFFBSmxCO0FBS0VpQixJQUFBQSxPQUFPLEVBQUVvRSxLQUFLLENBQUNwRSxPQUxqQjtBQU1FRSxJQUFBQSxhQUFhLEVBQUVrRSxLQUFLLENBQUNsRTtBQU52QjtBQVFEOztBQUVELElBQU1tRSxrQkFBa0IsR0FBRyxFQUEzQjs7QUFDQSxJQUFNQyxXQUFXLEdBQUcsU0FBZEEsV0FBYyxDQUFBQyxRQUFRO0FBQUEsU0FBSUEsUUFBSjtBQUFBLENBQTVCOztBQUNBLElBQU1DLGNBQWMsR0FBRyxTQUFqQkEsY0FBaUIsQ0FBQ0QsUUFBRCxFQUFXekosS0FBWDtBQUFBLFNBQXFCQSxLQUFLLENBQUMySixPQUFOLElBQWlCSixrQkFBdEM7QUFBQSxDQUF2Qjs7QUFFQSxTQUFTSyxxQkFBVCxHQUFpQztBQUMvQixTQUFPLDhCQUFlLENBQUNKLFdBQUQsRUFBY0UsY0FBZCxDQUFmLEVBQThDLFVBQUNELFFBQUQsRUFBV0ksV0FBWCxFQUEyQjtBQUFBLGVBQ2UsQ0FDM0ZDLGVBRDJGLEVBRTNGQyxlQUYyRixFQUczRkMsZUFIMkYsRUFJM0ZDLGNBSjJGLEVBSzNGQyxlQUwyRixFQU0zRnBILEdBTjJGLENBTXZGLFVBQUE2RyxPQUFPO0FBQUEsYUFBSSwrQkFBbUJRLFlBQVksQ0FBQ1IsT0FBRCxFQUFVRSxXQUFWLENBQS9CLEVBQXVESixRQUF2RCxDQUFKO0FBQUEsS0FOZ0YsQ0FEZjtBQUFBO0FBQUEsUUFDdkVwRSxlQUR1RTtBQUFBLFFBQ3REYixlQURzRDtBQUFBLFFBQ3JDaEIsZUFEcUM7QUFBQSxRQUNwQjhCLGNBRG9CO0FBQUEsUUFDSkMsZUFESTs7QUFTOUUsV0FBTztBQUNMRixNQUFBQSxlQUFlLEVBQWZBLGVBREs7QUFFTGIsTUFBQUEsZUFBZSxFQUFmQSxlQUZLO0FBR0xoQixNQUFBQSxlQUFlLEVBQWZBLGVBSEs7QUFJTDhCLE1BQUFBLGNBQWMsRUFBZEEsY0FKSztBQUtMQyxNQUFBQSxlQUFlLEVBQWZBLGVBTEs7QUFNTGtFLE1BQUFBLFFBQVEsRUFBUkE7QUFOSyxLQUFQO0FBUUQsR0FqQk0sQ0FBUDtBQWtCRDs7QUFFRCxTQUFTSixzQkFBVCxHQUFrQztBQUNoQyxNQUFNZSxpQkFBaUIsR0FBR1IscUJBQXFCLEVBQS9DOztBQUNBLE1BQU1TLGtCQUFrQixHQUFHLFNBQXJCQSxrQkFBcUIsQ0FBQ1osUUFBRCxFQUFXYSxRQUFYLEVBQXdCO0FBQ2pELFFBQU1DLHFCQUFxQixHQUFHSCxpQkFBaUIsQ0FBQ1gsUUFBRCxFQUFXYSxRQUFYLENBQS9DO0FBRUEsNkJBQ0tDLHFCQURMO0FBRUVkLE1BQUFBLFFBQVEsRUFBUkE7QUFGRjtBQUlELEdBUEQ7O0FBU0EsU0FBT1ksa0JBQVA7QUFDRDtBQUVEOzs7OztBQUdBLFNBQVNGLFlBQVQsQ0FBc0JSLE9BQXRCLEVBQStCRSxXQUEvQixFQUE0QztBQUMxQyxNQUFNVyxTQUFTLEdBQUcsRUFBbEI7O0FBQ0EsT0FBSyxJQUFNQyxHQUFYLElBQWtCWixXQUFsQixFQUErQjtBQUM3QixRQUFJQSxXQUFXLENBQUNhLGNBQVosQ0FBMkJELEdBQTNCLEtBQW1DZCxPQUFPLENBQUNlLGNBQVIsQ0FBdUJELEdBQXZCLENBQXZDLEVBQW9FO0FBQ2xFRCxNQUFBQSxTQUFTLENBQUNDLEdBQUQsQ0FBVCxHQUFpQlosV0FBVyxDQUFDWSxHQUFELENBQTVCO0FBQ0Q7QUFDRjs7QUFFRCwyQkFBV2QsT0FBWCxNQUF1QmEsU0FBdkI7QUFDRDs7ZUFFY2pLLGUiLCJzb3VyY2VzQ29udGVudCI6WyIvLyBDb3B5cmlnaHQgKGMpIDIwMjAgVWJlciBUZWNobm9sb2dpZXMsIEluYy5cbi8vXG4vLyBQZXJtaXNzaW9uIGlzIGhlcmVieSBncmFudGVkLCBmcmVlIG9mIGNoYXJnZSwgdG8gYW55IHBlcnNvbiBvYnRhaW5pbmcgYSBjb3B5XG4vLyBvZiB0aGlzIHNvZnR3YXJlIGFuZCBhc3NvY2lhdGVkIGRvY3VtZW50YXRpb24gZmlsZXMgKHRoZSBcIlNvZnR3YXJlXCIpLCB0byBkZWFsXG4vLyBpbiB0aGUgU29mdHdhcmUgd2l0aG91dCByZXN0cmljdGlvbiwgaW5jbHVkaW5nIHdpdGhvdXQgbGltaXRhdGlvbiB0aGUgcmlnaHRzXG4vLyB0byB1c2UsIGNvcHksIG1vZGlmeSwgbWVyZ2UsIHB1Ymxpc2gsIGRpc3RyaWJ1dGUsIHN1YmxpY2Vuc2UsIGFuZC9vciBzZWxsXG4vLyBjb3BpZXMgb2YgdGhlIFNvZnR3YXJlLCBhbmQgdG8gcGVybWl0IHBlcnNvbnMgdG8gd2hvbSB0aGUgU29mdHdhcmUgaXNcbi8vIGZ1cm5pc2hlZCB0byBkbyBzbywgc3ViamVjdCB0byB0aGUgZm9sbG93aW5nIGNvbmRpdGlvbnM6XG4vL1xuLy8gVGhlIGFib3ZlIGNvcHlyaWdodCBub3RpY2UgYW5kIHRoaXMgcGVybWlzc2lvbiBub3RpY2Ugc2hhbGwgYmUgaW5jbHVkZWQgaW5cbi8vIGFsbCBjb3BpZXMgb3Igc3Vic3RhbnRpYWwgcG9ydGlvbnMgb2YgdGhlIFNvZnR3YXJlLlxuLy9cbi8vIFRIRSBTT0ZUV0FSRSBJUyBQUk9WSURFRCBcIkFTIElTXCIsIFdJVEhPVVQgV0FSUkFOVFkgT0YgQU5ZIEtJTkQsIEVYUFJFU1MgT1Jcbi8vIElNUExJRUQsIElOQ0xVRElORyBCVVQgTk9UIExJTUlURUQgVE8gVEhFIFdBUlJBTlRJRVMgT0YgTUVSQ0hBTlRBQklMSVRZLFxuLy8gRklUTkVTUyBGT1IgQSBQQVJUSUNVTEFSIFBVUlBPU0UgQU5EIE5PTklORlJJTkdFTUVOVC4gSU4gTk8gRVZFTlQgU0hBTEwgVEhFXG4vLyBBVVRIT1JTIE9SIENPUFlSSUdIVCBIT0xERVJTIEJFIExJQUJMRSBGT1IgQU5ZIENMQUlNLCBEQU1BR0VTIE9SIE9USEVSXG4vLyBMSUFCSUxJVFksIFdIRVRIRVIgSU4gQU4gQUNUSU9OIE9GIENPTlRSQUNULCBUT1JUIE9SIE9USEVSV0lTRSwgQVJJU0lORyBGUk9NLFxuLy8gT1VUIE9GIE9SIElOIENPTk5FQ1RJT04gV0lUSCBUSEUgU09GVFdBUkUgT1IgVEhFIFVTRSBPUiBPVEhFUiBERUFMSU5HUyBJTlxuLy8gVEhFIFNPRlRXQVJFLlxuXG5pbXBvcnQgUmVhY3QsIHtDb21wb25lbnQsIGNyZWF0ZVJlZn0gZnJvbSAncmVhY3QnO1xuaW1wb3J0IHtjb25zb2xlIGFzIENvbnNvbGV9IGZyb20gJ2dsb2JhbC93aW5kb3cnO1xuaW1wb3J0IHtiaW5kQWN0aW9uQ3JlYXRvcnN9IGZyb20gJ3JlZHV4JztcbmltcG9ydCBzdHlsZWQsIHtUaGVtZVByb3ZpZGVyLCB3aXRoVGhlbWV9IGZyb20gJ3N0eWxlZC1jb21wb25lbnRzJztcbmltcG9ydCB7Y3JlYXRlU2VsZWN0b3J9IGZyb20gJ3Jlc2VsZWN0JztcbmltcG9ydCB7Y29ubmVjdCBhcyBrZXBsZXJHbENvbm5lY3R9IGZyb20gJ2Nvbm5lY3Qva2VwbGVyZ2wtY29ubmVjdCc7XG5pbXBvcnQge0ludGxQcm92aWRlcn0gZnJvbSAncmVhY3QtaW50bCc7XG5pbXBvcnQge21lc3NhZ2VzfSBmcm9tICcuLi9sb2NhbGl6YXRpb24nO1xuaW1wb3J0IHtSb290Q29udGV4dH0gZnJvbSAnY29tcG9uZW50cy9jb250ZXh0JztcblxuaW1wb3J0ICogYXMgVmlzU3RhdGVBY3Rpb25zIGZyb20gJ2FjdGlvbnMvdmlzLXN0YXRlLWFjdGlvbnMnO1xuaW1wb3J0ICogYXMgTWFwU3RhdGVBY3Rpb25zIGZyb20gJ2FjdGlvbnMvbWFwLXN0YXRlLWFjdGlvbnMnO1xuaW1wb3J0ICogYXMgTWFwU3R5bGVBY3Rpb25zIGZyb20gJ2FjdGlvbnMvbWFwLXN0eWxlLWFjdGlvbnMnO1xuaW1wb3J0ICogYXMgVUlTdGF0ZUFjdGlvbnMgZnJvbSAnYWN0aW9ucy91aS1zdGF0ZS1hY3Rpb25zJztcbmltcG9ydCAqIGFzIFByb3ZpZGVyQWN0aW9ucyBmcm9tICdhY3Rpb25zL3Byb3ZpZGVyLWFjdGlvbnMnO1xuXG5pbXBvcnQge1xuICBFWFBPUlRfSU1BR0VfSUQsXG4gIERJTUVOU0lPTlMsXG4gIEtFUExFUl9HTF9OQU1FLFxuICBLRVBMRVJfR0xfVkVSU0lPTixcbiAgVEhFTUUsXG4gIERFRkFVTFRfTUFQQk9YX0FQSV9VUkwsXG4gIFNBVkVfTUFQX0lELFxuICBTSEFSRV9NQVBfSUQsXG4gIE9WRVJXUklURV9NQVBfSURcbn0gZnJvbSAnY29uc3RhbnRzL2RlZmF1bHQtc2V0dGluZ3MnO1xuaW1wb3J0IHtNSVNTSU5HX01BUEJPWF9UT0tFTn0gZnJvbSAnY29uc3RhbnRzL3VzZXItZmVlZGJhY2tzJztcblxuaW1wb3J0IFNpZGVQYW5lbEZhY3RvcnkgZnJvbSAnLi9zaWRlLXBhbmVsJztcbmltcG9ydCBNYXBDb250YWluZXJGYWN0b3J5IGZyb20gJy4vbWFwLWNvbnRhaW5lcic7XG5pbXBvcnQgQm90dG9tV2lkZ2V0RmFjdG9yeSBmcm9tICcuL2JvdHRvbS13aWRnZXQnO1xuaW1wb3J0IE1vZGFsQ29udGFpbmVyRmFjdG9yeSBmcm9tICcuL21vZGFsLWNvbnRhaW5lcic7XG5pbXBvcnQgUGxvdENvbnRhaW5lckZhY3RvcnkgZnJvbSAnLi9wbG90LWNvbnRhaW5lcic7XG5pbXBvcnQgTm90aWZpY2F0aW9uUGFuZWxGYWN0b3J5IGZyb20gJy4vbm90aWZpY2F0aW9uLXBhbmVsJztcblxuaW1wb3J0IHtnZW5lcmF0ZUhhc2hJZH0gZnJvbSAndXRpbHMvdXRpbHMnO1xuaW1wb3J0IHt2YWxpZGF0ZVRva2VufSBmcm9tICd1dGlscy9tYXBib3gtdXRpbHMnO1xuXG5pbXBvcnQge3RoZW1lIGFzIGJhc2ljVGhlbWUsIHRoZW1lTFQsIHRoZW1lQlN9IGZyb20gJ3N0eWxlcy9iYXNlJztcblxuLy8gTWF5YmUgd2Ugc2hvdWxkIHRoaW5rIGFib3V0IGV4cG9ydGluZyB0aGlzIG9yIGNyZWF0aW5nIGEgdmFyaWFibGVcbi8vIGFzIHBhcnQgb2YgdGhlIGJhc2UuanMgdGhlbWVcbmNvbnN0IEdsb2JhbFN0eWxlID0gc3R5bGVkLmRpdmBcbiAgZm9udC1mYW1pbHk6ICR7cHJvcHMgPT4gcHJvcHMudGhlbWUuZm9udEZhbWlseX07XG4gIGZvbnQtd2VpZ2h0OiAke3Byb3BzID0+IHByb3BzLnRoZW1lLmZvbnRXZWlnaHR9O1xuICBmb250LXNpemU6ICR7cHJvcHMgPT4gcHJvcHMudGhlbWUuZm9udFNpemV9O1xuICBsaW5lLWhlaWdodDogJHtwcm9wcyA9PiBwcm9wcy50aGVtZS5saW5lSGVpZ2h0fTtcblxuICAqLFxuICAqOmJlZm9yZSxcbiAgKjphZnRlciB7XG4gICAgLXdlYmtpdC1ib3gtc2l6aW5nOiBib3JkZXItYm94O1xuICAgIC1tb3otYm94LXNpemluZzogYm9yZGVyLWJveDtcbiAgICBib3gtc2l6aW5nOiBib3JkZXItYm94O1xuICB9XG5cbiAgdWwge1xuICAgIG1hcmdpbjogMDtcbiAgICBwYWRkaW5nOiAwO1xuICB9XG5cbiAgbGkge1xuICAgIG1hcmdpbjogMDtcbiAgfVxuXG4gIGEge1xuICAgIHRleHQtZGVjb3JhdGlvbjogbm9uZTtcbiAgICBjb2xvcjogJHtwcm9wcyA9PiBwcm9wcy50aGVtZS5sYWJlbENvbG9yfTtcbiAgfVxuYDtcblxuS2VwbGVyR2xGYWN0b3J5LmRlcHMgPSBbXG4gIEJvdHRvbVdpZGdldEZhY3RvcnksXG4gIE1hcENvbnRhaW5lckZhY3RvcnksXG4gIE1vZGFsQ29udGFpbmVyRmFjdG9yeSxcbiAgU2lkZVBhbmVsRmFjdG9yeSxcbiAgUGxvdENvbnRhaW5lckZhY3RvcnksXG4gIE5vdGlmaWNhdGlvblBhbmVsRmFjdG9yeVxuXTtcblxuZnVuY3Rpb24gS2VwbGVyR2xGYWN0b3J5KFxuICBCb3R0b21XaWRnZXQsXG4gIE1hcENvbnRhaW5lcixcbiAgTW9kYWxDb250YWluZXIsXG4gIFNpZGVQYW5lbCxcbiAgUGxvdENvbnRhaW5lcixcbiAgTm90aWZpY2F0aW9uUGFuZWxcbikge1xuICBjbGFzcyBLZXBsZXJHTCBleHRlbmRzIENvbXBvbmVudCB7XG4gICAgc3RhdGljIGRlZmF1bHRQcm9wcyA9IHtcbiAgICAgIG1hcFN0eWxlczogW10sXG4gICAgICBtYXBTdHlsZXNSZXBsYWNlRGVmYXVsdDogZmFsc2UsXG4gICAgICBtYXBib3hBcGlVcmw6IERFRkFVTFRfTUFQQk9YX0FQSV9VUkwsXG4gICAgICB3aWR0aDogODAwLFxuICAgICAgaGVpZ2h0OiA4MDAsXG4gICAgICBhcHBOYW1lOiBLRVBMRVJfR0xfTkFNRSxcbiAgICAgIHZlcnNpb246IEtFUExFUl9HTF9WRVJTSU9OLFxuICAgICAgc2lkZVBhbmVsV2lkdGg6IERJTUVOU0lPTlMuc2lkZVBhbmVsLndpZHRoLFxuICAgICAgdGhlbWU6IHt9LFxuICAgICAgY2xvdWRQcm92aWRlcnM6IFtdXG4gICAgfTtcblxuICAgIGNvbXBvbmVudERpZE1vdW50KCkge1xuICAgICAgdGhpcy5fdmFsaWRhdGVNYXBib3hUb2tlbigpO1xuICAgICAgdGhpcy5fbG9hZE1hcFN0eWxlKHRoaXMucHJvcHMubWFwU3R5bGVzKTtcbiAgICAgIHRoaXMuX2hhbmRsZVJlc2l6ZSh0aGlzLnByb3BzKTtcbiAgICB9XG5cbiAgICBjb21wb25lbnREaWRVcGRhdGUocHJldlByb3BzKSB7XG4gICAgICBpZiAoXG4gICAgICAgIC8vIGlmIGRpbWVuc2lvbiBwcm9wcyBoYXMgY2hhbmdlZFxuICAgICAgICB0aGlzLnByb3BzLmhlaWdodCAhPT0gcHJldlByb3BzLmhlaWdodCB8fFxuICAgICAgICB0aGlzLnByb3BzLndpZHRoICE9PSBwcmV2UHJvcHMud2lkdGggfHxcbiAgICAgICAgLy8gcmVhY3QtbWFwLWdsIHdpbGwgZGlzcGF0Y2ggdXBkYXRlVmlld3BvcnQgYWZ0ZXIgdGhpcy5faGFuZGxlUmVzaXplIGlzIGNhbGxlZFxuICAgICAgICAvLyBoZXJlIHdlIGNoZWNrIGlmIHRoaXMucHJvcHMubWFwU3RhdGUuaGVpZ2h0IGlzIHN5bmMgd2l0aCBwcm9wcy5oZWlnaHRcbiAgICAgICAgdGhpcy5wcm9wcy5oZWlnaHQgIT09IHRoaXMucHJvcHMubWFwU3RhdGUuaGVpZ2h0XG4gICAgICApIHtcbiAgICAgICAgdGhpcy5faGFuZGxlUmVzaXplKHRoaXMucHJvcHMpO1xuICAgICAgfVxuICAgIH1cblxuICAgIHJvb3QgPSBjcmVhdGVSZWYoKTtcbiAgICBzdGF0aWMgY29udGV4dFR5cGUgPSBSb290Q29udGV4dDtcblxuICAgIC8qIHNlbGVjdG9ycyAqL1xuICAgIHRoZW1lU2VsZWN0b3IgPSBwcm9wcyA9PiBwcm9wcy50aGVtZTtcbiAgICBhdmFpbGFibGVUaGVtZVNlbGVjdG9yID0gY3JlYXRlU2VsZWN0b3IodGhpcy50aGVtZVNlbGVjdG9yLCB0aGVtZSA9PlxuICAgICAgdHlwZW9mIHRoZW1lID09PSAnb2JqZWN0J1xuICAgICAgICA/IHtcbiAgICAgICAgICAgIC4uLmJhc2ljVGhlbWUsXG4gICAgICAgICAgICAuLi50aGVtZVxuICAgICAgICAgIH1cbiAgICAgICAgOiB0aGVtZSA9PT0gVEhFTUUubGlnaHRcbiAgICAgICAgPyB0aGVtZUxUXG4gICAgICAgIDogdGhlbWUgPT09IFRIRU1FLmJhc2VcbiAgICAgICAgPyB0aGVtZUJTXG4gICAgICAgIDogdGhlbWVcbiAgICApO1xuXG4gICAgYXZhaWxhYmxlUHJvdmlkZXJzID0gY3JlYXRlU2VsZWN0b3IoXG4gICAgICBwcm9wcyA9PiBwcm9wcy5jbG91ZFByb3ZpZGVycyxcbiAgICAgIHByb3ZpZGVycyA9PlxuICAgICAgICBBcnJheS5pc0FycmF5KHByb3ZpZGVycykgJiYgcHJvdmlkZXJzLmxlbmd0aFxuICAgICAgICAgID8ge1xuICAgICAgICAgICAgICBoYXNTdG9yYWdlOiBwcm92aWRlcnMuc29tZShwID0+IHAuaGFzUHJpdmF0ZVN0b3JhZ2UoKSksXG4gICAgICAgICAgICAgIGhhc1NoYXJlOiBwcm92aWRlcnMuc29tZShwID0+IHAuaGFzU2hhcmluZ1VybCgpKVxuICAgICAgICAgICAgfVxuICAgICAgICAgIDoge31cbiAgICApO1xuXG4gICAgLyogcHJpdmF0ZSBtZXRob2RzICovXG4gICAgX3ZhbGlkYXRlTWFwYm94VG9rZW4oKSB7XG4gICAgICBjb25zdCB7bWFwYm94QXBpQWNjZXNzVG9rZW59ID0gdGhpcy5wcm9wcztcbiAgICAgIGlmICghdmFsaWRhdGVUb2tlbihtYXBib3hBcGlBY2Nlc3NUb2tlbikpIHtcbiAgICAgICAgQ29uc29sZS53YXJuKE1JU1NJTkdfTUFQQk9YX1RPS0VOKTtcbiAgICAgIH1cbiAgICB9XG5cbiAgICBfaGFuZGxlUmVzaXplKHt3aWR0aCwgaGVpZ2h0fSkge1xuICAgICAgaWYgKCFOdW1iZXIuaXNGaW5pdGUod2lkdGgpIHx8ICFOdW1iZXIuaXNGaW5pdGUoaGVpZ2h0KSkge1xuICAgICAgICBDb25zb2xlLndhcm4oJ3dpZHRoIGFuZCBoZWlnaHQgaXMgcmVxdWlyZWQnKTtcbiAgICAgICAgcmV0dXJuO1xuICAgICAgfVxuICAgICAgdGhpcy5wcm9wcy5tYXBTdGF0ZUFjdGlvbnMudXBkYXRlTWFwKHtcbiAgICAgICAgd2lkdGg6IHdpZHRoIC8gKDEgKyBOdW1iZXIodGhpcy5wcm9wcy5tYXBTdGF0ZS5pc1NwbGl0KSksXG4gICAgICAgIGhlaWdodFxuICAgICAgfSk7XG4gICAgfVxuXG4gICAgX2xvYWRNYXBTdHlsZSA9ICgpID0+IHtcbiAgICAgIGNvbnN0IGRlZmF1bHRTdHlsZXMgPSBPYmplY3QudmFsdWVzKHRoaXMucHJvcHMubWFwU3R5bGUubWFwU3R5bGVzKTtcbiAgICAgIC8vIGFkZCBpZCB0byBjdXN0b20gbWFwIHN0eWxlcyBpZiBub3QgZ2l2ZW5cbiAgICAgIGNvbnN0IGN1c3RvbVN0eWxlcyA9ICh0aGlzLnByb3BzLm1hcFN0eWxlcyB8fCBbXSkubWFwKG1zID0+ICh7XG4gICAgICAgIC4uLm1zLFxuICAgICAgICBpZDogbXMuaWQgfHwgZ2VuZXJhdGVIYXNoSWQoKVxuICAgICAgfSkpO1xuXG4gICAgICBjb25zdCBhbGxTdHlsZXMgPSBbLi4uY3VzdG9tU3R5bGVzLCAuLi5kZWZhdWx0U3R5bGVzXS5yZWR1Y2UoXG4gICAgICAgIChhY2N1LCBzdHlsZSkgPT4ge1xuICAgICAgICAgIGNvbnN0IGhhc1N0eWxlT2JqZWN0ID0gc3R5bGUuc3R5bGUgJiYgdHlwZW9mIHN0eWxlLnN0eWxlID09PSAnb2JqZWN0JztcbiAgICAgICAgICBhY2N1W2hhc1N0eWxlT2JqZWN0ID8gJ3RvTG9hZCcgOiAndG9SZXF1ZXN0J11bc3R5bGUuaWRdID0gc3R5bGU7XG5cbiAgICAgICAgICByZXR1cm4gYWNjdTtcbiAgICAgICAgfSxcbiAgICAgICAge3RvTG9hZDoge30sIHRvUmVxdWVzdDoge319XG4gICAgICApO1xuXG4gICAgICB0aGlzLnByb3BzLm1hcFN0eWxlQWN0aW9ucy5sb2FkTWFwU3R5bGVzKGFsbFN0eWxlcy50b0xvYWQpO1xuICAgICAgdGhpcy5wcm9wcy5tYXBTdHlsZUFjdGlvbnMucmVxdWVzdE1hcFN0eWxlcyhhbGxTdHlsZXMudG9SZXF1ZXN0KTtcbiAgICB9O1xuXG4gICAgcmVuZGVyKCkge1xuICAgICAgY29uc3Qge1xuICAgICAgICAvLyBwcm9wc1xuICAgICAgICBpZCxcbiAgICAgICAgYXBwTmFtZSxcbiAgICAgICAgdmVyc2lvbixcbiAgICAgICAgYXBwV2Vic2l0ZSxcbiAgICAgICAgb25TYXZlTWFwLFxuICAgICAgICBvblZpZXdTdGF0ZUNoYW5nZSxcbiAgICAgICAgd2lkdGgsXG4gICAgICAgIGhlaWdodCxcbiAgICAgICAgbWFwYm94QXBpQWNjZXNzVG9rZW4sXG4gICAgICAgIG1hcGJveEFwaVVybCxcbiAgICAgICAgZ2V0TWFwYm94UmVmLFxuXG4gICAgICAgIC8vIHJlZHV4IHN0YXRlXG4gICAgICAgIG1hcFN0eWxlLFxuICAgICAgICBtYXBTdGF0ZSxcbiAgICAgICAgdWlTdGF0ZSxcbiAgICAgICAgdmlzU3RhdGUsXG4gICAgICAgIHByb3ZpZGVyU3RhdGUsXG5cbiAgICAgICAgLy8gYWN0aW9ucyxcbiAgICAgICAgdmlzU3RhdGVBY3Rpb25zLFxuICAgICAgICBtYXBTdGF0ZUFjdGlvbnMsXG4gICAgICAgIG1hcFN0eWxlQWN0aW9ucyxcbiAgICAgICAgdWlTdGF0ZUFjdGlvbnMsXG4gICAgICAgIHByb3ZpZGVyQWN0aW9uc1xuICAgICAgfSA9IHRoaXMucHJvcHM7XG5cbiAgICAgIGNvbnN0IGF2YWlsYWJsZVByb3ZpZGVycyA9IHRoaXMuYXZhaWxhYmxlUHJvdmlkZXJzKHRoaXMucHJvcHMpO1xuXG4gICAgICBjb25zdCB7XG4gICAgICAgIGZpbHRlcnMsXG4gICAgICAgIGxheWVycyxcbiAgICAgICAgc3BsaXRNYXBzLCAvLyB0aGlzIHdpbGwgc3RvcmUgc3VwcG9ydCBmb3Igc3BsaXQgbWFwIHZpZXcgaXMgbmVjZXNzYXJ5XG4gICAgICAgIGxheWVyT3JkZXIsXG4gICAgICAgIGxheWVyQmxlbmRpbmcsXG4gICAgICAgIGxheWVyQ2xhc3NlcyxcbiAgICAgICAgaW50ZXJhY3Rpb25Db25maWcsXG4gICAgICAgIGRhdGFzZXRzLFxuICAgICAgICBsYXllckRhdGEsXG4gICAgICAgIGhvdmVySW5mbyxcbiAgICAgICAgY2xpY2tlZCxcbiAgICAgICAgbW91c2VQb3MsXG4gICAgICAgIGFuaW1hdGlvbkNvbmZpZyxcbiAgICAgICAgbWFwSW5mb1xuICAgICAgfSA9IHZpc1N0YXRlO1xuXG4gICAgICBjb25zdCBub3RpZmljYXRpb25QYW5lbEZpZWxkcyA9IHtcbiAgICAgICAgcmVtb3ZlTm90aWZpY2F0aW9uOiB1aVN0YXRlQWN0aW9ucy5yZW1vdmVOb3RpZmljYXRpb24sXG4gICAgICAgIG5vdGlmaWNhdGlvbnM6IHVpU3RhdGUubm90aWZpY2F0aW9uc1xuICAgICAgfTtcblxuICAgICAgY29uc3Qgc2lkZUZpZWxkcyA9IHtcbiAgICAgICAgYXBwTmFtZSxcbiAgICAgICAgdmVyc2lvbixcbiAgICAgICAgYXBwV2Vic2l0ZSxcbiAgICAgICAgZGF0YXNldHMsXG4gICAgICAgIGZpbHRlcnMsXG4gICAgICAgIGxheWVycyxcbiAgICAgICAgbGF5ZXJPcmRlcixcbiAgICAgICAgbGF5ZXJDbGFzc2VzLFxuICAgICAgICBpbnRlcmFjdGlvbkNvbmZpZyxcbiAgICAgICAgbWFwU3R5bGUsXG4gICAgICAgIG1hcEluZm8sXG4gICAgICAgIGxheWVyQmxlbmRpbmcsXG4gICAgICAgIG9uU2F2ZU1hcCxcbiAgICAgICAgdWlTdGF0ZSxcbiAgICAgICAgbWFwU3R5bGVBY3Rpb25zLFxuICAgICAgICB2aXNTdGF0ZUFjdGlvbnMsXG4gICAgICAgIHVpU3RhdGVBY3Rpb25zLFxuICAgICAgICB3aWR0aDogdGhpcy5wcm9wcy5zaWRlUGFuZWxXaWR0aCxcbiAgICAgICAgYXZhaWxhYmxlUHJvdmlkZXJzLFxuICAgICAgICBtYXBTYXZlZDogcHJvdmlkZXJTdGF0ZS5