filestack-js
Version:
Official JavaScript library for Filestack
264 lines (262 loc) • 32.1 kB
JavaScript
/*
* Copyright (c) 2018 by Filestack.
* Some rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
import { removeEmpty } from '../utils';
import { FilestackError } from './../../filestack_error';
import { FsRequest, FsCancelToken } from '../request';
import { Store, STORE_TYPE } from './../utils/store';
/**
* @private
*/
export var PICKER_KEY = '__fs_picker_token';
/**
* key for picker callback url (specifies which tab will be opened after opening picker)
* @private
*/
export var CALLBACK_URL_KEY = 'fs-tab';
/**
* @private
*/
var CloudClient = /** @class */ (function () {
function CloudClient(session, options) {
/**
* Returns flag if token should be cached in local storage
*
* @private
* @type {boolean}
* @memberof CloudClient
*/
this.cache = false;
this.session = session;
this.storeAdapter = new Store();
this.cloudApiUrl = session.urls.cloudApiUrl;
if (options && options.sessionCache) {
this.cache = options.sessionCache;
}
}
Object.defineProperty(CloudClient.prototype, "token", {
get: function () {
if (this.cache) {
var token = this.storeAdapter.getItem(PICKER_KEY, STORE_TYPE.LOCAL);
if (token)
return token;
}
if (this.isInAppBrowser) {
return this.storeAdapter.getItem(PICKER_KEY, STORE_TYPE.SESSION);
}
return this._token;
},
set: function (key) {
if (this.cache) {
this.storeAdapter.setItem(PICKER_KEY, key, STORE_TYPE.LOCAL);
}
if (this.isInAppBrowser) {
this.storeAdapter.setItem(PICKER_KEY, key, STORE_TYPE.SESSION);
}
this._token = key;
},
enumerable: false,
configurable: true
});
Object.defineProperty(CloudClient.prototype, "isInAppBrowser", {
/**
* Return information is inappbrowser flag is set
*
* @readonly
* @memberof CloudClient
*/
get: function () {
if (this.session
&& this.session.prefetch
&& this.session.prefetch.settings
&& this.session.prefetch.settings.inapp_browser) {
return this.session.prefetch.settings.inapp_browser;
}
return false;
},
enumerable: false,
configurable: true
});
CloudClient.prototype.list = function (clouds, cancelTokenInput, accept) {
var _this = this;
var payload = {
apikey: this.session.apikey,
clouds: clouds,
flow: 'web',
token: this.token,
};
if (accept) {
if (!Array.isArray(accept)) {
accept = [accept];
}
// FS-11013.
// google-drive storing uncommon file-types in incorrect format, eg .srt (subrip) file is stored in bin (octet-stream) format
// so if user wants to accept subrip files, we should search google drive for octet-steam file.
if (accept.includes('application/x-subrip') && !accept.includes('application/octet-stream')) {
accept.push('application/octet-stream');
}
// filtering mimetypes in clouds
payload.accept = accept;
}
if (this.isInAppBrowser) {
payload.appurl = this.currentAppUrl();
}
if (this.session.policy && this.session.signature) {
payload.policy = this.session.policy;
payload.signature = this.session.signature;
}
var options = {};
if (cancelTokenInput) {
var cancelToken = new FsCancelToken();
cancelTokenInput.cancel = cancelToken.cancel.bind(cancelToken);
options.cancelToken = cancelToken;
}
return FsRequest.post("".concat(this.cloudApiUrl, "/folder/list"), payload, options).then(function (res) {
if (res.data && res.data.token) {
_this.token = res.data.token;
}
return res.data;
});
};
CloudClient.prototype.store = function (name, path, options, customSource, cancelTokenInput, uploadTags) {
var _a;
var _this = this;
if (options === void 0) { options = {}; }
if (customSource === void 0) { customSource = {}; }
if (uploadTags === void 0) { uploadTags = null; }
// Default to S3
if (options.location === undefined) {
options.location = 's3';
}
var payload = {
apikey: this.session.apikey,
token: this.token,
flow: 'web',
upload_tags: uploadTags ? uploadTags : undefined,
clouds: (_a = {},
_a[name] = {
path: path,
store: removeEmpty(options),
},
_a),
};
if (name === 'customsource' && customSource.customSourcePath) {
payload.clouds.customsource.customSourcePath = customSource.customSourcePath;
}
if (name === 'customsource' && customSource.customSourceContainer) {
payload.clouds.customsource.customSourceContainer = customSource.customSourceContainer;
}
if (this.session.policy && this.session.signature) {
payload.policy = this.session.policy;
payload.signature = this.session.signature;
}
var requestOptions = {};
if (cancelTokenInput) {
var cancelToken = new FsCancelToken();
cancelTokenInput.cancel = cancelToken.cancel.bind(cancelToken);
requestOptions.cancelToken = cancelToken;
}
return FsRequest.post("".concat(this.cloudApiUrl, "/store/"), payload, requestOptions).then(function (res) {
if (res.data && res.data.token) {
_this.token = res.data.token;
}
if (res.data && res.data[name]) {
return res.data[name];
}
return res.data;
});
};
CloudClient.prototype.logout = function (name) {
var _a;
var payload = {
apikey: this.session.apikey,
flow: 'web',
token: this.token,
};
if (name) {
payload.clouds = (_a = {}, _a[name] = {}, _a);
}
else {
if (this.cache) {
// No name means logout of ALL clouds. Clear local session.
this.storeAdapter.removeItem(PICKER_KEY, STORE_TYPE.LOCAL);
}
if (this.isInAppBrowser) {
this.storeAdapter.removeItem(PICKER_KEY, STORE_TYPE.SESSION);
}
}
return FsRequest.post("".concat(this.cloudApiUrl, "/auth/logout"), payload).then(function (res) {
if (res.data && res.data[name]) {
return res.data[name];
}
return res.data;
});
};
CloudClient.prototype.metadata = function (url, headers) {
var payload = {
apikey: this.session.apikey,
url: url,
headers: headers,
};
if (this.session.policy && this.session.signature) {
payload.policy = this.session.policy;
payload.signature = this.session.signature;
}
return FsRequest.post("".concat(this.cloudApiUrl, "/metadata"), payload).then(function (res) { return res.data; });
};
// OpenTok API Endpoints
CloudClient.prototype.tokInit = function (type) {
if (type !== 'video' && type !== 'audio') {
throw new FilestackError('Type must be one of video or audio.');
}
return FsRequest.post("".concat(this.cloudApiUrl, "/recording/").concat(type, "/init")).then(function (res) { return res.data; });
};
CloudClient.prototype.tokStart = function (type, key, sessionId) {
if (type !== 'video' && type !== 'audio') {
throw new FilestackError('Type must be one of video or audio.');
}
var payload = {
apikey: key,
session_id: sessionId,
};
return FsRequest.post("".concat(this.cloudApiUrl, "/recording/").concat(type, "/start"), payload).then(function (res) { return res.data; });
};
CloudClient.prototype.tokStop = function (type, key, sessionId, archiveId) {
if (type !== 'video' && type !== 'audio') {
throw new FilestackError('Type must be one of video or audio.');
}
var payload = {
apikey: key,
session_id: sessionId,
archive_id: archiveId,
};
return FsRequest.post("".concat(this.cloudApiUrl, "/recording/").concat(type, "/stop"), payload).then(function (res) { return res.data; });
};
CloudClient.prototype.currentAppUrl = function () {
if (!window.URLSearchParams) {
return undefined;
}
// set init string for clouds backend,
// After this cloud service can make redirect back to current page url with selected tab for given cloud
// if param exists and its value is init, backend will fill it with cloud name
var searchParams = new URLSearchParams(window.location.search);
searchParams.set(CALLBACK_URL_KEY, 'init');
return "".concat(window.location.protocol, "//").concat(window.location.host).concat(window.location.pathname, "?").concat(searchParams.toString());
};
return CloudClient;
}());
export { CloudClient };
//# sourceMappingURL=data:application/json;charset=utf8;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIi4uLy4uL3NyYy9saWIvYXBpL2Nsb3VkLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBOzs7Ozs7Ozs7Ozs7Ozs7R0FlRztBQUVILE9BQU8sRUFBRSxXQUFXLEVBQUUsTUFBTSxVQUFVLENBQUM7QUFHdkMsT0FBTyxFQUFFLGNBQWMsRUFBRSxNQUFNLHlCQUF5QixDQUFDO0FBRXpELE9BQU8sRUFBRSxTQUFTLEVBQUUsYUFBYSxFQUFFLE1BQU0sWUFBWSxDQUFDO0FBQ3RELE9BQU8sRUFBRSxLQUFLLEVBQUUsVUFBVSxFQUFFLE1BQU0sa0JBQWtCLENBQUM7QUFFckQ7O0dBRUc7QUFDSCxNQUFNLENBQUMsSUFBTSxVQUFVLEdBQUcsbUJBQW1CLENBQUM7QUFFOUM7OztHQUdHO0FBQ0gsTUFBTSxDQUFDLElBQU0sZ0JBQWdCLEdBQUcsUUFBUSxDQUFDO0FBRXpDOztHQUVHO0FBQ0g7SUErQkUscUJBQVksT0FBZ0IsRUFBRSxPQUF1QjtRQTNCckQ7Ozs7OztXQU1HO1FBQ0ssVUFBSyxHQUFZLEtBQUssQ0FBQztRQXFCN0IsSUFBSSxDQUFDLE9BQU8sR0FBRyxPQUFPLENBQUM7UUFDdkIsSUFBSSxDQUFDLFlBQVksR0FBRyxJQUFJLEtBQUssRUFBRSxDQUFDO1FBRWhDLElBQUksQ0FBQyxXQUFXLEdBQUcsT0FBTyxDQUFDLElBQUksQ0FBQyxXQUFXLENBQUM7UUFFNUMsSUFBSSxPQUFPLElBQUksT0FBTyxDQUFDLFlBQVksRUFBRTtZQUNuQyxJQUFJLENBQUMsS0FBSyxHQUFHLE9BQU8sQ0FBQyxZQUFZLENBQUM7U0FDbkM7SUFDSCxDQUFDO0lBRUQsc0JBQUksOEJBQUs7YUFBVDtZQUNFLElBQUksSUFBSSxDQUFDLEtBQUssRUFBRTtnQkFDZCxJQUFNLEtBQUssR0FBRyxJQUFJLENBQUMsWUFBWSxDQUFDLE9BQU8sQ0FBQyxVQUFVLEVBQUUsVUFBVSxDQUFDLEtBQUssQ0FBQyxDQUFDO2dCQUN0RSxJQUFJLEtBQUs7b0JBQUUsT0FBTyxLQUFLLENBQUM7YUFDekI7WUFFRCxJQUFJLElBQUksQ0FBQyxjQUFjLEVBQUU7Z0JBQ3ZCLE9BQU8sSUFBSSxDQUFDLFlBQVksQ0FBQyxPQUFPLENBQUMsVUFBVSxFQUFFLFVBQVUsQ0FBQyxPQUFPLENBQUMsQ0FBQzthQUNsRTtZQUVELE9BQU8sSUFBSSxDQUFDLE1BQU0sQ0FBQztRQUNyQixDQUFDO2FBRUQsVUFBVSxHQUFHO1lBQ1gsSUFBSSxJQUFJLENBQUMsS0FBSyxFQUFFO2dCQUNkLElBQUksQ0FBQyxZQUFZLENBQUMsT0FBTyxDQUFDLFVBQVUsRUFBRSxHQUFHLEVBQUUsVUFBVSxDQUFDLEtBQUssQ0FBQyxDQUFDO2FBQzlEO1lBRUQsSUFBSSxJQUFJLENBQUMsY0FBYyxFQUFFO2dCQUN2QixJQUFJLENBQUMsWUFBWSxDQUFDLE9BQU8sQ0FBQyxVQUFVLEVBQUUsR0FBRyxFQUFFLFVBQVUsQ0FBQyxPQUFPLENBQUMsQ0FBQzthQUNoRTtZQUVELElBQUksQ0FBQyxNQUFNLEdBQUcsR0FBRyxDQUFDO1FBQ3BCLENBQUM7OztPQVpBO0lBb0JELHNCQUFZLHVDQUFjO1FBTjFCOzs7OztXQUtHO2FBQ0g7WUFDRSxJQUFJLElBQUksQ0FBQyxPQUFPO21CQUNYLElBQUksQ0FBQyxPQUFPLENBQUMsUUFBUTttQkFDckIsSUFBSSxDQUFDLE9BQU8sQ0FBQyxRQUFRLENBQUMsUUFBUTttQkFDOUIsSUFBSSxDQUFDLE9BQU8sQ0FBQyxRQUFRLENBQUMsUUFBUSxDQUFDLGFBQWEsRUFBRTtnQkFDakQsT0FBTyxJQUFJLENBQUMsT0FBTyxDQUFDLFFBQVEsQ0FBQyxRQUFRLENBQUMsYUFBYSxDQUFDO2FBQ3JEO1lBRUQsT0FBTyxLQUFLLENBQUM7UUFDZixDQUFDOzs7T0FBQTtJQUVELDBCQUFJLEdBQUosVUFBSyxNQUFXLEVBQUUsZ0JBQXNCLEVBQUUsTUFBMEI7UUFBcEUsaUJBOENDO1FBN0NDLElBQU0sT0FBTyxHQUFRO1lBQ25CLE1BQU0sRUFBRSxJQUFJLENBQUMsT0FBTyxDQUFDLE1BQU07WUFDM0IsTUFBTSxRQUFBO1lBQ04sSUFBSSxFQUFFLEtBQUs7WUFDWCxLQUFLLEVBQUUsSUFBSSxDQUFDLEtBQUs7U0FDbEIsQ0FBQztRQUVGLElBQUksTUFBTSxFQUFFO1lBQ1YsSUFBSSxDQUFDLEtBQUssQ0FBQyxPQUFPLENBQUMsTUFBTSxDQUFDLEVBQUU7Z0JBQzFCLE1BQU0sR0FBRyxDQUFDLE1BQU0sQ0FBQyxDQUFDO2FBQ25CO1lBQ0QsWUFBWTtZQUNaLDZIQUE2SDtZQUM3SCwrRkFBK0Y7WUFDL0YsSUFBSSxNQUFNLENBQUMsUUFBUSxDQUFDLHNCQUFzQixDQUFDLElBQUksQ0FBQyxNQUFNLENBQUMsUUFBUSxDQUFDLDBCQUEwQixDQUFDLEVBQUU7Z0JBQzNGLE1BQU0sQ0FBQyxJQUFJLENBQUMsMEJBQTBCLENBQUMsQ0FBQzthQUN6QztZQUNELGdDQUFnQztZQUNoQyxPQUFPLENBQUMsTUFBTSxHQUFHLE1BQU0sQ0FBQztTQUN6QjtRQUVELElBQUksSUFBSSxDQUFDLGNBQWMsRUFBRTtZQUN2QixPQUFPLENBQUMsTUFBTSxHQUFHLElBQUksQ0FBQyxhQUFhLEVBQUUsQ0FBQztTQUN2QztRQUVELElBQUksSUFBSSxDQUFDLE9BQU8sQ0FBQyxNQUFNLElBQUksSUFBSSxDQUFDLE9BQU8sQ0FBQyxTQUFTLEVBQUU7WUFDakQsT0FBTyxDQUFDLE1BQU0sR0FBRyxJQUFJLENBQUMsT0FBTyxDQUFDLE1BQU0sQ0FBQztZQUNyQyxPQUFPLENBQUMsU0FBUyxHQUFHLElBQUksQ0FBQyxPQUFPLENBQUMsU0FBUyxDQUFDO1NBQzVDO1FBRUQsSUFBSSxPQUFPLEdBQVEsRUFBRSxDQUFDO1FBRXRCLElBQUksZ0JBQWdCLEVBQUU7WUFDcEIsSUFBTSxXQUFXLEdBQUcsSUFBSSxhQUFhLEVBQUUsQ0FBQztZQUN4QyxnQkFBZ0IsQ0FBQyxNQUFNLEdBQUcsV0FBVyxDQUFDLE1BQU0sQ0FBQyxJQUFJLENBQUMsV0FBVyxDQUFDLENBQUM7WUFDL0QsT0FBTyxDQUFDLFdBQVcsR0FBRyxXQUFXLENBQUM7U0FDbkM7UUFFRCxPQUFPLFNBQVMsQ0FBQyxJQUFJLENBQUMsVUFBRyxJQUFJLENBQUMsV0FBVyxpQkFBYyxFQUFFLE9BQU8sRUFBRSxPQUFPLENBQUMsQ0FBQyxJQUFJLENBQUMsVUFBQSxHQUFHO1lBQ2pGLElBQUksR0FBRyxDQUFDLElBQUksSUFBSSxHQUFHLENBQUMsSUFBSSxDQUFDLEtBQUssRUFBRTtnQkFDOUIsS0FBSSxDQUFDLEtBQUssR0FBRyxHQUFHLENBQUMsSUFBSSxDQUFDLEtBQUssQ0FBQzthQUM3QjtZQUVELE9BQU8sR0FBRyxDQUFDLElBQUksQ0FBQztRQUNsQixDQUFDLENBQUMsQ0FBQztJQUNMLENBQUM7SUFFRCwyQkFBSyxHQUFMLFVBQU0sSUFBWSxFQUFFLElBQVksRUFBRSxPQUF5QixFQUFFLFlBQXNCLEVBQUUsZ0JBQXNCLEVBQUUsVUFBNkI7O1FBQTFJLGlCQW1EQztRQW5EaUMsd0JBQUEsRUFBQSxZQUF5QjtRQUFFLDZCQUFBLEVBQUEsaUJBQXNCO1FBQTBCLDJCQUFBLEVBQUEsaUJBQTZCO1FBQ3hJLGdCQUFnQjtRQUNoQixJQUFJLE9BQU8sQ0FBQyxRQUFRLEtBQUssU0FBUyxFQUFFO1lBQ2xDLE9BQU8sQ0FBQyxRQUFRLEdBQUcsSUFBSSxDQUFDO1NBQ3pCO1FBRUQsSUFBTSxPQUFPLEdBQVE7WUFDbkIsTUFBTSxFQUFFLElBQUksQ0FBQyxPQUFPLENBQUMsTUFBTTtZQUMzQixLQUFLLEVBQUUsSUFBSSxDQUFDLEtBQUs7WUFDakIsSUFBSSxFQUFFLEtBQUs7WUFDWCxXQUFXLEVBQUUsVUFBVSxDQUFDLENBQUMsQ0FBQyxVQUFVLENBQUMsQ0FBQyxDQUFDLFNBQVM7WUFDaEQsTUFBTTtnQkFDSixHQUFDLElBQUksSUFBRztvQkFDTixJQUFJLE1BQUE7b0JBQ0osS0FBSyxFQUFFLFdBQVcsQ0FBQyxPQUFPLENBQUM7aUJBQzVCO21CQUNGO1NBQ0YsQ0FBQztRQUVGLElBQUksSUFBSSxLQUFLLGNBQWMsSUFBSSxZQUFZLENBQUMsZ0JBQWdCLEVBQUU7WUFDNUQsT0FBTyxDQUFDLE1BQU0sQ0FBQyxZQUFZLENBQUMsZ0JBQWdCLEdBQUcsWUFBWSxDQUFDLGdCQUFnQixDQUFDO1NBQzlFO1FBRUQsSUFBSSxJQUFJLEtBQUssY0FBYyxJQUFJLFlBQVksQ0FBQyxxQkFBcUIsRUFBRTtZQUNqRSxPQUFPLENBQUMsTUFBTSxDQUFDLFlBQVksQ0FBQyxxQkFBcUIsR0FBRyxZQUFZLENBQUMscUJBQXFCLENBQUM7U0FDeEY7UUFFRCxJQUFJLElBQUksQ0FBQyxPQUFPLENBQUMsTUFBTSxJQUFJLElBQUksQ0FBQyxPQUFPLENBQUMsU0FBUyxFQUFFO1lBQ2pELE9BQU8sQ0FBQyxNQUFNLEdBQUcsSUFBSSxDQUFDLE9BQU8sQ0FBQyxNQUFNLENBQUM7WUFDckMsT0FBTyxDQUFDLFNBQVMsR0FBRyxJQUFJLENBQUMsT0FBTyxDQUFDLFNBQVMsQ0FBQztTQUM1QztRQUVELElBQUksY0FBYyxHQUFRLEVBQUUsQ0FBQztRQUU3QixJQUFJLGdCQUFnQixFQUFFO1lBQ3BCLElBQU0sV0FBVyxHQUFHLElBQUksYUFBYSxFQUFFLENBQUM7WUFDeEMsZ0JBQWdCLENBQUMsTUFBTSxHQUFHLFdBQVcsQ0FBQyxNQUFNLENBQUMsSUFBSSxDQUFDLFdBQVcsQ0FBQyxDQUFDO1lBQy9ELGNBQWMsQ0FBQyxXQUFXLEdBQUcsV0FBVyxDQUFDO1NBQzFDO1FBRUQsT0FBTyxTQUFTLENBQUMsSUFBSSxDQUFDLFVBQUcsSUFBSSxDQUFDLFdBQVcsWUFBUyxFQUFFLE9BQU8sRUFBRSxjQUFjLENBQUMsQ0FBQyxJQUFJLENBQUMsVUFBQSxHQUFHO1lBQ25GLElBQUksR0FBRyxDQUFDLElBQUksSUFBSSxHQUFHLENBQUMsSUFBSSxDQUFDLEtBQUssRUFBRTtnQkFDOUIsS0FBSSxDQUFDLEtBQUssR0FBRyxHQUFHLENBQUMsSUFBSSxDQUFDLEtBQUssQ0FBQzthQUM3QjtZQUVELElBQUksR0FBRyxDQUFDLElBQUksSUFBSSxHQUFHLENBQUMsSUFBSSxDQUFDLElBQUksQ0FBQyxFQUFFO2dCQUM5QixPQUFPLEdBQUcsQ0FBQyxJQUFJLENBQUMsSUFBSSxDQUFDLENBQUM7YUFDdkI7WUFFRCxPQUFPLEdBQUcsQ0FBQyxJQUFJLENBQUM7UUFDbEIsQ0FBQyxDQUFDLENBQUM7SUFDTCxDQUFDO0lBRUQsNEJBQU0sR0FBTixVQUFPLElBQWE7O1FBQ2xCLElBQU0sT0FBTyxHQUFRO1lBQ25CLE1BQU0sRUFBRSxJQUFJLENBQUMsT0FBTyxDQUFDLE1BQU07WUFDM0IsSUFBSSxFQUFFLEtBQUs7WUFDWCxLQUFLLEVBQUUsSUFBSSxDQUFDLEtBQUs7U0FDbEIsQ0FBQztRQUVGLElBQUksSUFBSSxFQUFFO1lBQ1IsT0FBTyxDQUFDLE1BQU0sYUFBSyxHQUFDLElBQUksSUFBRyxFQUFFLEtBQUUsQ0FBQztTQUNqQzthQUFNO1lBQ0wsSUFBSSxJQUFJLENBQUMsS0FBSyxFQUFFO2dCQUNkLDJEQUEyRDtnQkFDM0QsSUFBSSxDQUFDLFlBQVksQ0FBQyxVQUFVLENBQUMsVUFBVSxFQUFFLFVBQVUsQ0FBQyxLQUFLLENBQUMsQ0FBQzthQUM1RDtZQUVELElBQUksSUFBSSxDQUFDLGNBQWMsRUFBRTtnQkFDdkIsSUFBSSxDQUFDLFlBQVksQ0FBQyxVQUFVLENBQUMsVUFBVSxFQUFFLFVBQVUsQ0FBQyxPQUFPLENBQUMsQ0FBQzthQUM5RDtTQUNGO1FBRUQsT0FBTyxTQUFTLENBQUMsSUFBSSxDQUFDLFVBQUcsSUFBSSxDQUFDLFdBQVcsaUJBQWMsRUFBRSxPQUFPLENBQUMsQ0FBQyxJQUFJLENBQUMsVUFBQSxHQUFHO1lBQ3hFLElBQUksR0FBRyxDQUFDLElBQUksSUFBSSxHQUFHLENBQUMsSUFBSSxDQUFDLElBQUksQ0FBQyxFQUFFO2dCQUM5QixPQUFPLEdBQUcsQ0FBQyxJQUFJLENBQUMsSUFBSSxDQUFDLENBQUM7YUFDdkI7WUFDRCxPQUFPLEdBQUcsQ0FBQyxJQUFJLENBQUM7UUFDbEIsQ0FBQyxDQUFDLENBQUM7SUFDTCxDQUFDO0lBRUQsOEJBQVEsR0FBUixVQUFTLEdBQVcsRUFBRSxPQUFpQztRQUNyRCxJQUFNLE9BQU8sR0FBUTtZQUNuQixNQUFNLEVBQUUsSUFBSSxDQUFDLE9BQU8sQ0FBQyxNQUFNO1lBQzNCLEdBQUcsS0FBQTtZQUNILE9BQU8sU0FBQTtTQUNSLENBQUM7UUFFRixJQUFJLElBQUksQ0FBQyxPQUFPLENBQUMsTUFBTSxJQUFJLElBQUksQ0FBQyxPQUFPLENBQUMsU0FBUyxFQUFFO1lBQ2pELE9BQU8sQ0FBQyxNQUFNLEdBQUcsSUFBSSxDQUFDLE9BQU8sQ0FBQyxNQUFNLENBQUM7WUFDckMsT0FBTyxDQUFDLFNBQVMsR0FBRyxJQUFJLENBQUMsT0FBTyxDQUFDLFNBQVMsQ0FBQztTQUM1QztRQUVELE9BQU8sU0FBUyxDQUFDLElBQUksQ0FBQyxVQUFHLElBQUksQ0FBQyxXQUFXLGNBQVcsRUFBRSxPQUFPLENBQUMsQ0FBQyxJQUFJLENBQUMsVUFBQSxHQUFHLElBQUksT0FBQSxHQUFHLENBQUMsSUFBSSxFQUFSLENBQVEsQ0FBQyxDQUFDO0lBQ3ZGLENBQUM7SUFFRCx3QkFBd0I7SUFDeEIsNkJBQU8sR0FBUCxVQUFRLElBQVk7UUFDbEIsSUFBSSxJQUFJLEtBQUssT0FBTyxJQUFJLElBQUksS0FBSyxPQUFPLEVBQUU7WUFDeEMsTUFBTSxJQUFJLGNBQWMsQ0FBQyxxQ0FBcUMsQ0FBQyxDQUFDO1NBQ2pFO1FBQ0QsT0FBTyxTQUFTLENBQUMsSUFBSSxDQUFDLFVBQUcsSUFBSSxDQUFDLFdBQVcsd0JBQWMsSUFBSSxVQUFPLENBQUMsQ0FBQyxJQUFJLENBQUMsVUFBQSxHQUFHLElBQUksT0FBQSxHQUFHLENBQUMsSUFBSSxFQUFSLENBQVEsQ0FBQyxDQUFDO0lBQzVGLENBQUM7SUFFRCw4QkFBUSxHQUFSLFVBQVMsSUFBWSxFQUFFLEdBQVcsRUFBRSxTQUFpQjtRQUNuRCxJQUFJLElBQUksS0FBSyxPQUFPLElBQUksSUFBSSxLQUFLLE9BQU8sRUFBRTtZQUN4QyxNQUFNLElBQUksY0FBYyxDQUFDLHFDQUFxQyxDQUFDLENBQUM7U0FDakU7UUFDRCxJQUFNLE9BQU8sR0FBRztZQUNkLE1BQU0sRUFBRSxHQUFHO1lBQ1gsVUFBVSxFQUFFLFNBQVM7U0FDdEIsQ0FBQztRQUVGLE9BQU8sU0FBUyxDQUFDLElBQUksQ0FBQyxVQUFHLElBQUksQ0FBQyxXQUFXLHdCQUFjLElBQUksV0FBUSxFQUFFLE9BQU8sQ0FBQyxDQUFDLElBQUksQ0FBQyxVQUFBLEdBQUcsSUFBSSxPQUFBLEdBQUcsQ0FBQyxJQUFJLEVBQVIsQ0FBUSxDQUFDLENBQUM7SUFDdEcsQ0FBQztJQUVELDZCQUFPLEdBQVAsVUFBUSxJQUFZLEVBQUUsR0FBVyxFQUFFLFNBQWlCLEVBQUUsU0FBaUI7UUFDckUsSUFBSSxJQUFJLEtBQUssT0FBTyxJQUFJLElBQUksS0FBSyxPQUFPLEVBQUU7WUFDeEMsTUFBTSxJQUFJLGNBQWMsQ0FBQyxxQ0FBcUMsQ0FBQyxDQUFDO1NBQ2pFO1FBRUQsSUFBTSxPQUFPLEdBQUc7WUFDZCxNQUFNLEVBQUUsR0FBRztZQUNYLFVBQVUsRUFBRSxTQUFTO1lBQ3JCLFVBQVUsRUFBRSxTQUFTO1NBQ3RCLENBQUM7UUFFRixPQUFPLFNBQVMsQ0FBQyxJQUFJLENBQUMsVUFBRyxJQUFJLENBQUMsV0FBVyx3QkFBYyxJQUFJLFVBQU8sRUFBRSxPQUFPLENBQUMsQ0FBQyxJQUFJLENBQUMsVUFBQSxHQUFHLElBQUksT0FBQSxHQUFHLENBQUMsSUFBSSxFQUFSLENBQVEsQ0FBQyxDQUFDO0lBQ3JHLENBQUM7SUFFTyxtQ0FBYSxHQUFyQjtRQUNFLElBQUksQ0FBQyxNQUFNLENBQUMsZUFBZSxFQUFFO1lBQzNCLE9BQU8sU0FBUyxDQUFDO1NBQ2xCO1FBRUQsc0NBQXNDO1FBQ3RDLHdHQUF3RztRQUN4Ryw4RUFBOEU7UUFDOUUsSUFBTSxZQUFZLEdBQUcsSUFBSSxlQUFlLENBQUMsTUFBTSxDQUFDLFFBQVEsQ0FBQyxNQUFNLENBQUMsQ0FBQztRQUNqRSxZQUFZLENBQUMsR0FBRyxDQUFDLGdCQUFnQixFQUFFLE1BQU0sQ0FBQyxDQUFDO1FBRTNDLE9BQU8sVUFBRyxNQUFNLENBQUMsUUFBUSxDQUFDLFFBQVEsZUFBSyxNQUFNLENBQUMsUUFBUSxDQUFDLElBQUksU0FBRyxNQUFNLENBQUMsUUFBUSxDQUFDLFFBQVEsY0FBSSxZQUFZLENBQUMsUUFBUSxFQUFFLENBQUUsQ0FBQztJQUN0SCxDQUFDO0lBQ0gsa0JBQUM7QUFBRCxDQW5SQSxBQW1SQyxJQUFBIiwiZmlsZSI6ImxpYi9hcGkvY2xvdWQuanMiLCJzb3VyY2VzQ29udGVudCI6WyIvKlxuICogQ29weXJpZ2h0IChjKSAyMDE4IGJ5IEZpbGVzdGFjay5cbiAqIFNvbWUgcmlnaHRzIHJlc2VydmVkLlxuICpcbiAqIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSBcIkxpY2Vuc2VcIik7XG4gKiB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuXG4gKiBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXRcbiAqXG4gKiAgICAgaHR0cDovL3d3dy5hcGFjaGUub3JnL2xpY2Vuc2VzL0xJQ0VOU0UtMi4wXG4gKlxuICogVW5sZXNzIHJlcXVpcmVkIGJ5IGFwcGxpY2FibGUgbGF3IG9yIGFncmVlZCB0byBpbiB3cml0aW5nLCBzb2Z0d2FyZVxuICogZGlzdHJpYnV0ZWQgdW5kZXIgdGhlIExpY2Vuc2UgaXMgZGlzdHJpYnV0ZWQgb24gYW4gXCJBUyBJU1wiIEJBU0lTLFxuICogV0lUSE9VVCBXQVJSQU5USUVTIE9SIENPTkRJVElPTlMgT0YgQU5ZIEtJTkQsIGVpdGhlciBleHByZXNzIG9yIGltcGxpZWQuXG4gKiBTZWUgdGhlIExpY2Vuc2UgZm9yIHRoZSBzcGVjaWZpYyBsYW5ndWFnZSBnb3Zlcm5pbmcgcGVybWlzc2lvbnMgYW5kXG4gKiBsaW1pdGF0aW9ucyB1bmRlciB0aGUgTGljZW5zZS5cbiAqL1xuXG5pbXBvcnQgeyByZW1vdmVFbXB0eSB9IGZyb20gJy4uL3V0aWxzJztcbmltcG9ydCB7IFN0b3JlUGFyYW1zIH0gZnJvbSAnLi4vZmlsZWxpbmsnO1xuaW1wb3J0IHsgQ2xpZW50T3B0aW9ucywgU2Vzc2lvbiB9IGZyb20gJy4uL2NsaWVudCc7XG5pbXBvcnQgeyBGaWxlc3RhY2tFcnJvciB9IGZyb20gJy4vLi4vLi4vZmlsZXN0YWNrX2Vycm9yJztcbmltcG9ydCB7IFVwbG9hZFRhZ3MgfSBmcm9tICcuL3VwbG9hZC9maWxlJztcbmltcG9ydCB7IEZzUmVxdWVzdCwgRnNDYW5jZWxUb2tlbiB9IGZyb20gJy4uL3JlcXVlc3QnO1xuaW1wb3J0IHsgU3RvcmUsIFNUT1JFX1RZUEUgfSBmcm9tICcuLy4uL3V0aWxzL3N0b3JlJztcblxuLyoqXG4gKiBAcHJpdmF0ZVxuICovXG5leHBvcnQgY29uc3QgUElDS0VSX0tFWSA9ICdfX2ZzX3BpY2tlcl90b2tlbic7XG5cbi8qKlxuICoga2V5IGZvciBwaWNrZXIgY2FsbGJhY2sgdXJsIChzcGVjaWZpZXMgd2hpY2ggdGFiIHdpbGwgYmUgb3BlbmVkIGFmdGVyIG9wZW5pbmcgcGlja2VyKVxuICogQHByaXZhdGVcbiAqL1xuZXhwb3J0IGNvbnN0IENBTExCQUNLX1VSTF9LRVkgPSAnZnMtdGFiJztcblxuLyoqXG4gKiBAcHJpdmF0ZVxuICovXG5leHBvcnQgY2xhc3MgQ2xvdWRDbGllbnQge1xuICBzZXNzaW9uOiBTZXNzaW9uO1xuICBjbG91ZEFwaVVybDogc3RyaW5nO1xuXG4gIC8qKlxuICAgKiBSZXR1cm5zIGZsYWcgaWYgdG9rZW4gc2hvdWxkIGJlIGNhY2hlZCBpbiBsb2NhbCBzdG9yYWdlXG4gICAqXG4gICAqIEBwcml2YXRlXG4gICAqIEB0eXBlIHtib29sZWFufVxuICAgKiBAbWVtYmVyb2YgQ2xvdWRDbGllbnRcbiAgICovXG4gIHByaXZhdGUgY2FjaGU6IGJvb2xlYW4gPSBmYWxzZTtcblxuICAvKipcbiAgICogVG9rZW4gcmV0dXJuZWQgZnJvbSBhcGkgZm9yIGFjY2Vzc2luZyBjbG91ZHNcbiAgICpcbiAgICogQHByaXZhdGVcbiAgICogQHR5cGUge3N0cmluZ31cbiAgICogQG1lbWJlcm9mIENsb3VkQ2xpZW50XG4gICAqL1xuICBwcml2YXRlIF90b2tlbjogc3RyaW5nO1xuXG4gIC8qKlxuICAgKiBTdG9yZSBhZGFwdGVyIGluc3RhbmNlXG4gICAqXG4gICAqIEBwcml2YXRlXG4gICAqIEB0eXBlIHtTdG9yZX1cbiAgICogQG1lbWJlcm9mIENsb3VkQ2xpZW50XG4gICAqL1xuICBwcml2YXRlIHN0b3JlQWRhcHRlcjogU3RvcmU7XG5cbiAgY29uc3RydWN0b3Ioc2Vzc2lvbjogU2Vzc2lvbiwgb3B0aW9ucz86IENsaWVudE9wdGlvbnMpIHtcbiAgICB0aGlzLnNlc3Npb24gPSBzZXNzaW9uO1xuICAgIHRoaXMuc3RvcmVBZGFwdGVyID0gbmV3IFN0b3JlKCk7XG5cbiAgICB0aGlzLmNsb3VkQXBpVXJsID0gc2Vzc2lvbi51cmxzLmNsb3VkQXBpVXJsO1xuXG4gICAgaWYgKG9wdGlvbnMgJiYgb3B0aW9ucy5zZXNzaW9uQ2FjaGUpIHtcbiAgICAgIHRoaXMuY2FjaGUgPSBvcHRpb25zLnNlc3Npb25DYWNoZTtcbiAgICB9XG4gIH1cblxuICBnZXQgdG9rZW4oKSB7XG4gICAgaWYgKHRoaXMuY2FjaGUpIHtcbiAgICAgIGNvbnN0IHRva2VuID0gdGhpcy5zdG9yZUFkYXB0ZXIuZ2V0SXRlbShQSUNLRVJfS0VZLCBTVE9SRV9UWVBFLkxPQ0FMKTtcbiAgICAgIGlmICh0b2tlbikgcmV0dXJuIHRva2VuO1xuICAgIH1cblxuICAgIGlmICh0aGlzLmlzSW5BcHBCcm93c2VyKSB7XG4gICAgICByZXR1cm4gdGhpcy5zdG9yZUFkYXB0ZXIuZ2V0SXRlbShQSUNLRVJfS0VZLCBTVE9SRV9UWVBFLlNFU1NJT04pO1xuICAgIH1cblxuICAgIHJldHVybiB0aGlzLl90b2tlbjtcbiAgfVxuXG4gIHNldCB0b2tlbihrZXkpIHtcbiAgICBpZiAodGhpcy5jYWNoZSkge1xuICAgICAgdGhpcy5zdG9yZUFkYXB0ZXIuc2V0SXRlbShQSUNLRVJfS0VZLCBrZXksIFNUT1JFX1RZUEUuTE9DQUwpO1xuICAgIH1cblxuICAgIGlmICh0aGlzLmlzSW5BcHBCcm93c2VyKSB7XG4gICAgICB0aGlzLnN0b3JlQWRhcHRlci5zZXRJdGVtKFBJQ0tFUl9LRVksIGtleSwgU1RPUkVfVFlQRS5TRVNTSU9OKTtcbiAgICB9XG5cbiAgICB0aGlzLl90b2tlbiA9IGtleTtcbiAgfVxuXG4gIC8qKlxuICAgKiBSZXR1cm4gaW5mb3JtYXRpb24gaXMgaW5hcHBicm93c2VyIGZsYWcgaXMgc2V0XG4gICAqXG4gICAqIEByZWFkb25seVxuICAgKiBAbWVtYmVyb2YgQ2xvdWRDbGllbnRcbiAgICovXG4gIHByaXZhdGUgZ2V0IGlzSW5BcHBCcm93c2VyKCkge1xuICAgIGlmICh0aGlzLnNlc3Npb25cbiAgICAgICYmIHRoaXMuc2Vzc2lvbi5wcmVmZXRjaFxuICAgICAgJiYgdGhpcy5zZXNzaW9uLnByZWZldGNoLnNldHRpbmdzXG4gICAgICAmJiB0aGlzLnNlc3Npb24ucHJlZmV0Y2guc2V0dGluZ3MuaW5hcHBfYnJvd3Nlcikge1xuICAgICAgcmV0dXJuIHRoaXMuc2Vzc2lvbi5wcmVmZXRjaC5zZXR0aW5ncy5pbmFwcF9icm93c2VyO1xuICAgIH1cblxuICAgIHJldHVybiBmYWxzZTtcbiAgfVxuXG4gIGxpc3QoY2xvdWRzOiBhbnksIGNhbmNlbFRva2VuSW5wdXQ/OiBhbnksIGFjY2VwdD86IHN0cmluZ1tdIHwgc3RyaW5nKSB7XG4gICAgY29uc3QgcGF5bG9hZDogYW55ID0ge1xuICAgICAgYXBpa2V5OiB0aGlzLnNlc3Npb24uYXBpa2V5LFxuICAgICAgY2xvdWRzLFxuICAgICAgZmxvdzogJ3dlYicsXG4gICAgICB0b2tlbjogdGhpcy50b2tlbixcbiAgICB9O1xuXG4gICAgaWYgKGFjY2VwdCkge1xuICAgICAgaWYgKCFBcnJheS5pc0FycmF5KGFjY2VwdCkpIHtcbiAgICAgICAgYWNjZXB0ID0gW2FjY2VwdF07XG4gICAgICB9XG4gICAgICAvLyBGUy0xMTAxMy5cbiAgICAgIC8vIGdvb2dsZS1kcml2ZSBzdG9yaW5nIHVuY29tbW9uIGZpbGUtdHlwZXMgaW4gaW5jb3JyZWN0IGZvcm1hdCwgZWcgLnNydCAoc3VicmlwKSBmaWxlIGlzIHN0b3JlZCBpbiBiaW4gKG9jdGV0LXN0cmVhbSkgZm9ybWF0XG4gICAgICAvLyBzbyBpZiB1c2VyIHdhbnRzIHRvIGFjY2VwdCBzdWJyaXAgZmlsZXMsIHdlIHNob3VsZCBzZWFyY2ggZ29vZ2xlIGRyaXZlIGZvciBvY3RldC1zdGVhbSBmaWxlLlxuICAgICAgaWYgKGFjY2VwdC5pbmNsdWRlcygnYXBwbGljYXRpb24veC1zdWJyaXAnKSAmJiAhYWNjZXB0LmluY2x1ZGVzKCdhcHBsaWNhdGlvbi9vY3RldC1zdHJlYW0nKSkge1xuICAgICAgICBhY2NlcHQucHVzaCgnYXBwbGljYXRpb24vb2N0ZXQtc3RyZWFtJyk7XG4gICAgICB9XG4gICAgICAvLyBmaWx0ZXJpbmcgbWltZXR5cGVzIGluIGNsb3Vkc1xuICAgICAgcGF5bG9hZC5hY2NlcHQgPSBhY2NlcHQ7XG4gICAgfVxuXG4gICAgaWYgKHRoaXMuaXNJbkFwcEJyb3dzZXIpIHtcbiAgICAgIHBheWxvYWQuYXBwdXJsID0gdGhpcy5jdXJyZW50QXBwVXJsKCk7XG4gICAgfVxuXG4gICAgaWYgKHRoaXMuc2Vzc2lvbi5wb2xpY3kgJiYgdGhpcy5zZXNzaW9uLnNpZ25hdHVyZSkge1xuICAgICAgcGF5bG9hZC5wb2xpY3kgPSB0aGlzLnNlc3Npb24ucG9saWN5O1xuICAgICAgcGF5bG9hZC5zaWduYXR1cmUgPSB0aGlzLnNlc3Npb24uc2lnbmF0dXJlO1xuICAgIH1cblxuICAgIGxldCBvcHRpb25zOiBhbnkgPSB7fTtcblxuICAgIGlmIChjYW5jZWxUb2tlbklucHV0KSB7XG4gICAgICBjb25zdCBjYW5jZWxUb2tlbiA9IG5ldyBGc0NhbmNlbFRva2VuKCk7XG4gICAgICBjYW5jZWxUb2tlbklucHV0LmNhbmNlbCA9IGNhbmNlbFRva2VuLmNhbmNlbC5iaW5kKGNhbmNlbFRva2VuKTtcbiAgICAgIG9wdGlvbnMuY2FuY2VsVG9rZW4gPSBjYW5jZWxUb2tlbjtcbiAgICB9XG5cbiAgICByZXR1cm4gRnNSZXF1ZXN0LnBvc3QoYCR7dGhpcy5jbG91ZEFwaVVybH0vZm9sZGVyL2xpc3RgLCBwYXlsb2FkLCBvcHRpb25zKS50aGVuKHJlcyA9PiB7XG4gICAgICBpZiAocmVzLmRhdGEgJiYgcmVzLmRhdGEudG9rZW4pIHtcbiAgICAgICAgdGhpcy50b2tlbiA9IHJlcy5kYXRhLnRva2VuO1xuICAgICAgfVxuXG4gICAgICByZXR1cm4gcmVzLmRhdGE7XG4gICAgfSk7XG4gIH1cblxuICBzdG9yZShuYW1lOiBzdHJpbmcsIHBhdGg6IHN0cmluZywgb3B0aW9uczogU3RvcmVQYXJhbXMgPSB7fSwgY3VzdG9tU291cmNlOiBhbnkgPSB7fSwgY2FuY2VsVG9rZW5JbnB1dD86IGFueSwgdXBsb2FkVGFnczogVXBsb2FkVGFncyA9IG51bGwpIHtcbiAgICAvLyBEZWZhdWx0IHRvIFMzXG4gICAgaWYgKG9wdGlvbnMubG9jYXRpb24gPT09IHVuZGVmaW5lZCkge1xuICAgICAgb3B0aW9ucy5sb2NhdGlvbiA9ICdzMyc7XG4gICAgfVxuXG4gICAgY29uc3QgcGF5bG9hZDogYW55ID0ge1xuICAgICAgYXBpa2V5OiB0aGlzLnNlc3Npb24uYXBpa2V5LFxuICAgICAgdG9rZW46IHRoaXMudG9rZW4sXG4gICAgICBmbG93OiAnd2ViJyxcbiAgICAgIHVwbG9hZF90YWdzOiB1cGxvYWRUYWdzID8gdXBsb2FkVGFncyA6IHVuZGVmaW5lZCxcbiAgICAgIGNsb3Vkczoge1xuICAgICAgICBbbmFtZV06IHtcbiAgICAgICAgICBwYXRoLFxuICAgICAgICAgIHN0b3JlOiByZW1vdmVFbXB0eShvcHRpb25zKSxcbiAgICAgICAgfSxcbiAgICAgIH0sXG4gICAgfTtcblxuICAgIGlmIChuYW1lID09PSAnY3VzdG9tc291cmNlJyAmJiBjdXN0b21Tb3VyY2UuY3VzdG9tU291cmNlUGF0aCkge1xuICAgICAgcGF5bG9hZC5jbG91ZHMuY3VzdG9tc291cmNlLmN1c3RvbVNvdXJjZVBhdGggPSBjdXN0b21Tb3VyY2UuY3VzdG9tU291cmNlUGF0aDtcbiAgICB9XG5cbiAgICBpZiAobmFtZSA9PT0gJ2N1c3RvbXNvdXJjZScgJiYgY3VzdG9tU291cmNlLmN1c3RvbVNvdXJjZUNvbnRhaW5lcikge1xuICAgICAgcGF5bG9hZC5jbG91ZHMuY3VzdG9tc291cmNlLmN1c3RvbVNvdXJjZUNvbnRhaW5lciA9IGN1c3RvbVNvdXJjZS5jdXN0b21Tb3VyY2VDb250YWluZXI7XG4gICAgfVxuXG4gICAgaWYgKHRoaXMuc2Vzc2lvbi5wb2xpY3kgJiYgdGhpcy5zZXNzaW9uLnNpZ25hdHVyZSkge1xuICAgICAgcGF5bG9hZC5wb2xpY3kgPSB0aGlzLnNlc3Npb24ucG9saWN5O1xuICAgICAgcGF5bG9hZC5zaWduYXR1cmUgPSB0aGlzLnNlc3Npb24uc2lnbmF0dXJlO1xuICAgIH1cblxuICAgIGxldCByZXF1ZXN0T3B0aW9uczogYW55ID0ge307XG5cbiAgICBpZiAoY2FuY2VsVG9rZW5JbnB1dCkge1xuICAgICAgY29uc3QgY2FuY2VsVG9rZW4gPSBuZXcgRnNDYW5jZWxUb2tlbigpO1xuICAgICAgY2FuY2VsVG9rZW5JbnB1dC5jYW5jZWwgPSBjYW5jZWxUb2tlbi5jYW5jZWwuYmluZChjYW5jZWxUb2tlbik7XG4gICAgICByZXF1ZXN0T3B0aW9ucy5jYW5jZWxUb2tlbiA9IGNhbmNlbFRva2VuO1xuICAgIH1cblxuICAgIHJldHVybiBGc1JlcXVlc3QucG9zdChgJHt0aGlzLmNsb3VkQXBpVXJsfS9zdG9yZS9gLCBwYXlsb2FkLCByZXF1ZXN0T3B0aW9ucykudGhlbihyZXMgPT4ge1xuICAgICAgaWYgKHJlcy5kYXRhICYmIHJlcy5kYXRhLnRva2VuKSB7XG4gICAgICAgIHRoaXMudG9rZW4gPSByZXMuZGF0YS50b2tlbjtcbiAgICAgIH1cblxuICAgICAgaWYgKHJlcy5kYXRhICYmIHJlcy5kYXRhW25hbWVdKSB7XG4gICAgICAgIHJldHVybiByZXMuZGF0YVtuYW1lXTtcbiAgICAgIH1cblxuICAgICAgcmV0dXJuIHJlcy5kYXRhO1xuICAgIH0pO1xuICB9XG5cbiAgbG9nb3V0KG5hbWU/OiBzdHJpbmcpIHtcbiAgICBjb25zdCBwYXlsb2FkOiBhbnkgPSB7XG4gICAgICBhcGlrZXk6IHRoaXMuc2Vzc2lvbi5hcGlrZXksXG4gICAgICBmbG93OiAnd2ViJyxcbiAgICAgIHRva2VuOiB0aGlzLnRva2VuLFxuICAgIH07XG5cbiAgICBpZiAobmFtZSkge1xuICAgICAgcGF5bG9hZC5jbG91ZHMgPSB7IFtuYW1lXToge30gfTtcbiAgICB9IGVsc2Uge1xuICAgICAgaWYgKHRoaXMuY2FjaGUpIHtcbiAgICAgICAgLy8gTm8gbmFtZSBtZWFucyBsb2dvdXQgb2YgQUxMIGNsb3Vkcy4gQ2xlYXIgbG9jYWwgc2Vzc2lvbi5cbiAgICAgICAgdGhpcy5zdG9yZUFkYXB0ZXIucmVtb3ZlSXRlbShQSUNLRVJfS0VZLCBTVE9SRV9UWVBFLkxPQ0FMKTtcbiAgICAgIH1cblxuICAgICAgaWYgKHRoaXMuaXNJbkFwcEJyb3dzZXIpIHtcbiAgICAgICAgdGhpcy5zdG9yZUFkYXB0ZXIucmVtb3ZlSXRlbShQSUNLRVJfS0VZLCBTVE9SRV9UWVBFLlNFU1NJT04pO1xuICAgICAgfVxuICAgIH1cblxuICAgIHJldHVybiBGc1JlcXVlc3QucG9zdChgJHt0aGlzLmNsb3VkQXBpVXJsfS9hdXRoL2xvZ291dGAsIHBheWxvYWQpLnRoZW4ocmVzID0+IHtcbiAgICAgIGlmIChyZXMuZGF0YSAmJiByZXMuZGF0YVtuYW1lXSkge1xuICAgICAgICByZXR1cm4gcmVzLmRhdGFbbmFtZV07XG4gICAgICB9XG4gICAgICByZXR1cm4gcmVzLmRhdGE7XG4gICAgfSk7XG4gIH1cblxuICBtZXRhZGF0YSh1cmw6IHN0cmluZywgaGVhZGVycz86IHtba2V5OiBzdHJpbmddOiBzdHJpbmd9KSB7XG4gICAgY29uc3QgcGF5bG9hZDogYW55ID0ge1xuICAgICAgYXBpa2V5OiB0aGlzLnNlc3Npb24uYXBpa2V5LFxuICAgICAgdXJsLFxuICAgICAgaGVhZGVycyxcbiAgICB9O1xuXG4gICAgaWYgKHRoaXMuc2Vzc2lvbi5wb2xpY3kgJiYgdGhpcy5zZXNzaW9uLnNpZ25hdHVyZSkge1xuICAgICAgcGF5bG9hZC5wb2xpY3kgPSB0aGlzLnNlc3Npb24ucG9saWN5O1xuICAgICAgcGF5bG9hZC5zaWduYXR1cmUgPSB0aGlzLnNlc3Npb24uc2lnbmF0dXJlO1xuICAgIH1cblxuICAgIHJldHVybiBGc1JlcXVlc3QucG9zdChgJHt0aGlzLmNsb3VkQXBpVXJsfS9tZXRhZGF0YWAsIHBheWxvYWQpLnRoZW4ocmVzID0+IHJlcy5kYXRhKTtcbiAgfVxuXG4gIC8vIE9wZW5Ub2sgQVBJIEVuZHBvaW50c1xuICB0b2tJbml0KHR5cGU6IHN0cmluZykge1xuICAgIGlmICh0eXBlICE9PSAndmlkZW8nICYmIHR5cGUgIT09ICdhdWRpbycpIHtcbiAgICAgIHRocm93IG5ldyBGaWxlc3RhY2tFcnJvcignVHlwZSBtdXN0IGJlIG9uZSBvZiB2aWRlbyBvciBhdWRpby4nKTtcbiAgICB9XG4gICAgcmV0dXJuIEZzUmVxdWVzdC5wb3N0KGAke3RoaXMuY2xvdWRBcGlVcmx9L3JlY29yZGluZy8ke3R5cGV9L2luaXRgKS50aGVuKHJlcyA9PiByZXMuZGF0YSk7XG4gIH1cblxuICB0b2tTdGFydCh0eXBlOiBzdHJpbmcsIGtleTogc3RyaW5nLCBzZXNzaW9uSWQ6IHN0cmluZykge1xuICAgIGlmICh0eXBlICE9PSAndmlkZW8nICYmIHR5cGUgIT09ICdhdWRpbycpIHtcbiAgICAgIHRocm93IG5ldyBGaWxlc3RhY2tFcnJvcignVHlwZSBtdXN0IGJlIG9uZSBvZiB2aWRlbyBvciBhdWRpby4nKTtcbiAgICB9XG4gICAgY29uc3QgcGF5bG9hZCA9IHtcbiAgICAgIGFwaWtleToga2V5LFxuICAgICAgc2Vzc2lvbl9pZDogc2Vzc2lvbklkLFxuICAgIH07XG5cbiAgICByZXR1cm4gRnNSZXF1ZXN0LnBvc3QoYCR7dGhpcy5jbG91ZEFwaVVybH0vcmVjb3JkaW5nLyR7dHlwZX0vc3RhcnRgLCBwYXlsb2FkKS50aGVuKHJlcyA9PiByZXMuZGF0YSk7XG4gIH1cblxuICB0b2tTdG9wKHR5cGU6IHN0cmluZywga2V5OiBzdHJpbmcsIHNlc3Npb25JZDogc3RyaW5nLCBhcmNoaXZlSWQ6IHN0cmluZykge1xuICAgIGlmICh0eXBlICE9PSAndmlkZW8nICYmIHR5cGUgIT09ICdhdWRpbycpIHtcbiAgICAgIHRocm93IG5ldyBGaWxlc3RhY2tFcnJvcignVHlwZSBtdXN0IGJlIG9uZSBvZiB2aWRlbyBvciBhdWRpby4nKTtcbiAgICB9XG5cbiAgICBjb25zdCBwYXlsb2FkID0ge1xuICAgICAgYXBpa2V5OiBrZXksXG4gICAgICBzZXNzaW9uX2lkOiBzZXNzaW9uSWQsXG4gICAgICBhcmNoaXZlX2lkOiBhcmNoaXZlSWQsXG4gICAgfTtcblxuICAgIHJldHVybiBGc1JlcXVlc3QucG9zdChgJHt0aGlzLmNsb3VkQXBpVXJsfS9yZWNvcmRpbmcvJHt0eXBlfS9zdG9wYCwgcGF5bG9hZCkudGhlbihyZXMgPT4gcmVzLmRhdGEpO1xuICB9XG5cbiAgcHJpdmF0ZSBjdXJyZW50QXBwVXJsKCkge1xuICAgIGlmICghd2luZG93LlVSTFNlYXJjaFBhcmFtcykge1xuICAgICAgcmV0dXJuIHVuZGVmaW5lZDtcbiAgICB9XG5cbiAgICAvLyBzZXQgaW5pdCBzdHJpbmcgZm9yIGNsb3VkcyBiYWNrZW5kLFxuICAgIC8vIEFmdGVyIHRoaXMgY2xvdWQgc2VydmljZSBjYW4gbWFrZSByZWRpcmVjdCBiYWNrIHRvIGN1cnJlbnQgcGFnZSB1cmwgd2l0aCBzZWxlY3RlZCB0YWIgZm9yIGdpdmVuIGNsb3VkXG4gICAgLy8gaWYgcGFyYW0gZXhpc3RzIGFuZCBpdHMgdmFsdWUgaXMgaW5pdCwgYmFja2VuZCB3aWxsIGZpbGwgaXQgd2l0aCBjbG91ZCBuYW1lXG4gICAgY29uc3Qgc2VhcmNoUGFyYW1zID0gbmV3IFVSTFNlYXJjaFBhcmFtcyh3aW5kb3cubG9jYXRpb24uc2VhcmNoKTtcbiAgICBzZWFyY2hQYXJhbXMuc2V0KENBTExCQUNLX1VSTF9LRVksICdpbml0Jyk7XG5cbiAgICByZXR1cm4gYCR7d2luZG93LmxvY2F0aW9uLnByb3RvY29sfS8vJHt3aW5kb3cubG9jYXRpb24uaG9zdH0ke3dpbmRvdy5sb2NhdGlvbi5wYXRobmFtZX0/JHtzZWFyY2hQYXJhbXMudG9TdHJpbmcoKX1gO1xuICB9XG59XG4iXX0=