turbo-gulp
Version:
Gulp tasks to boost high-quality projects.
272 lines (270 loc) • 45.1 kB
JavaScript
/**
* This module defines the _lib_ target type used to create libraries for other projects.
*
* In the following list of tasks, `{target}` represents the name of the target as defined by the `name` property
* of the target options.
* The _lib_ target provides the following tasks:
*
* ## {target}:build
*
* Performs a full build of the library to the build directory, used for development.
* This copies the static assets and compiles the scripts.
*
* The following sub-tasks are available:
* - `{target}:build:copy`: Only copy the static assets
* - `{target}:build:script`: Only compile the scripts
*
* For distribution builds, use `{target:dist}`
*
* ## {target}:watch
*
* Watch the files and run incremental builds on change.
* This useful during development to get build errors reported immediately or accelerate the code/test cycle.
* You can combine it with _Nodemon_ to continuously restart your Node process when changing the source.
*
* ## {target}:dist
*
* Performs a full build of the library to the dist directory, used for distribution (ie. publication to _npm_).
* This build creates a fully autonomous directory with its own `package.json`, source code, license file, etc.
* This allows to use a different structure for distribution rather than structure of the repo, the main benefit is
* to provide support for deep package imports (`import * as mod from "my-lib/deep/module"`) by placing the build
* at the root of the package.
* This build also allows you to remap the `package.json`, for example to set the version dynamically.
*
* The following sub-tasks are available:
* - `{target}:dist:publish`: Publish the package to an _npm_ registry (it honors the `registry` option, to publish
* to private _npm_ registries such as _Verdaccio_). It uses the authentication token of the current user, this
* token is in `~/.npmrc`. For CI, you can use the following command to set the token the registry `npm.example.com`.
* (for the official registry, use `//registry.npmjs.org`):
* ```
* echo "//npm.example.com/:_authToken=\"${NPM_TOKEN}\"" > ~/.npmrc
* ```
* - `{target}:dist:copy-src`: Only copy the source files to the build directory.
* - `{target}:dist:package.json`: Copy (and eventually transform) the root `package.json` to the build directory.
*
* For development builds, use `{target:build}`.
*
* ## {target}:typedoc
*
* Generate _Typedoc_ documentation.
*
* ## {target}:typedoc:deploy
*
* Deploy the _Typedoc_ documentation using _git_. This can be used to easily deploy the documentation to the
* `gh-pages` branch.
*
* ## {target}:clean
*
* Remove both the build and dist directories corresponding to this target.
*
* ## {target}:tsconfig.json
*
* Emit a `tsconfig.json` file corresponding to the configuration for this target. This allows to compile it using
* the command line `tsc` program. This is also useful for IDE to auto-detect the configuration of the project.
*
* @module targets/lib
*/
import { Minimatch } from "minimatch";
import path from "path";
import { getBuildTypescriptTask } from "../target-tasks/build-typescript";
import { getTypedocTask } from "../target-tasks/typedoc";
import { branchPublish } from "../utils/branch-publish";
import { getHeadHash } from "../utils/git";
import * as matcher from "../utils/matcher";
import { npmPublish } from "../utils/npm-publish";
import { readJsonFile } from "../utils/project";
import { generateBaseTasks, getCopy, gulpBufferSrc, nameTask, resolveTargetBase, } from "./_base";
/**
* Resolve absolute paths and dependencies for the provided target.
*
* @param target Non-resolved target.
* @return Resolved target.
*/
function resolveLibTarget(target) {
const base = resolveTargetBase(target);
let typedoc = undefined;
if (target.typedoc !== undefined) {
typedoc = {
dir: path.posix.join(base.project.absRoot, target.typedoc.dir),
name: target.typedoc.name,
deploy: target.typedoc.deploy,
};
}
let dist;
if (target.dist === undefined || target.dist === false) {
dist = false;
}
else {
const defaultDistDir = path.posix.join(base.project.absDistDir, target.name);
const defaultPackageJsonMap = pkg => pkg;
const defaultCopy = (dest) => [{
files: ["./*.md"],
}];
if (target.dist === true) { // `true` literal
dist = {
distDir: defaultDistDir,
packageJsonMap: defaultPackageJsonMap,
npmPublish: {},
copySrc: true,
copy: defaultCopy(defaultDistDir),
};
}
else {
const distDir = target.dist.distDir !== undefined ? target.dist.distDir : defaultDistDir;
dist = {
distDir,
packageJsonMap: target.dist.packageJsonMap !== undefined ? target.dist.packageJsonMap : defaultPackageJsonMap,
npmPublish: target.dist.npmPublish,
copySrc: target.dist.copySrc !== undefined ? target.dist.copySrc : true,
copy: defaultCopy(distDir),
};
}
}
return Object.assign({}, base, { mainModule: target.mainModule, typedoc, dist });
}
/**
* Generates gulp tasks for the provided lib target.
*
* @param gulp Gulp instance used to generate tasks manipulating files.
* @param targetOptions Target configuration.
*/
export function generateLibTasks(gulp, targetOptions) {
const target = resolveLibTarget(targetOptions);
const result = generateBaseTasks(gulp, targetOptions);
const tsOptions = {
tscOptions: target.tscOptions,
tsconfigJson: target.tsconfigJson,
customTypingsDir: target.customTypingsDir,
packageJson: target.project.absPackageJson,
buildDir: target.buildDir,
srcDir: target.srcDir,
scripts: target.scripts,
outModules: target.outModules,
};
// typedoc
if (target.typedoc !== undefined) {
const typedocOptions = target.typedoc;
result.typedoc = nameTask(`${target.name}:typedoc`, gulp.series([result.tsconfigJson, getTypedocTask(gulp, tsOptions, typedocOptions)]));
// typedoc:deploy
if (typedocOptions.deploy !== undefined) {
const deploy = typedocOptions.deploy;
async function deployTypedocTask() {
const commitMessage = `Deploy documentation for ${await getHeadHash()}`;
return branchPublish(Object.assign({}, deploy, { dir: typedocOptions.dir, commitMessage }));
}
result.typedocDeploy = nameTask(`${target.name}:typedoc:deploy`, gulp.series(result.typedoc, deployTypedocTask));
}
}
// dist
if (target.dist !== false) {
const dist = target.dist;
const distTasks = [];
const copyTasks = [];
// Locations for compilation: default to the original sources but compile the copied files if copySrc is used
let srcDir = target.srcDir;
let customTypingsDir = target.customTypingsDir;
// dist:copy:scripts
if (target.dist.copySrc) {
srcDir = path.posix.join(dist.distDir, "_src");
copyTasks.push(nameTask(`${target.name}:dist:copy:scripts`, () => {
return gulp
.src([...target.scripts], { base: target.srcDir })
.pipe(gulp.dest(srcDir));
}));
// dist:copy:custom-typings
if (target.customTypingsDir !== null) {
const srcCustomTypingsDir = target.customTypingsDir;
const destCustomTypingsDir = path.posix.join(dist.distDir, "_custom-typings");
customTypingsDir = destCustomTypingsDir;
copyTasks.push(nameTask(`${target.name}:dist:copy:custom-typings`, () => {
return gulp
.src([path.posix.join(srcCustomTypingsDir, "**/*.d.ts")], { base: srcCustomTypingsDir })
.pipe(gulp.dest(destCustomTypingsDir));
}));
}
// dist:copy:dist
if (target.dist.copy !== undefined) {
const [copyBaseTask, copyBaseWatchTask] = getCopy(gulp, target.project.absRoot, target.dist.distDir, target.dist.copy);
copyTasks.push(nameTask(`${target.name}:dist:copy:dist`, copyBaseTask));
}
}
// dist:copy:lib
if (target.copy !== undefined) {
const [copyBaseTask, copyBaseWatchTask] = getCopy(gulp, target.srcDir, target.dist.distDir, target.copy);
copyTasks.push(nameTask(`${target.name}:dist:copy:lib`, copyBaseTask));
}
result.distCopy = nameTask(`${target.name}:dist:copy`, gulp.parallel(copyTasks));
// Resolve tsconfig for `dist`
const tsconfigJson = target.tsconfigJson !== null ?
path.posix.join(srcDir, "tsconfig.json") :
null;
let scripts = [];
if (srcDir !== target.srcDir) {
for (const script of target.scripts) {
scripts.push(matcher.asString(matcher.join(srcDir, matcher.relative(target.srcDir, new Minimatch(script)))));
}
}
else {
scripts = [...target.scripts];
}
const tsOptions = {
tscOptions: target.tscOptions,
tsconfigJson,
customTypingsDir,
packageJson: target.project.absPackageJson,
buildDir: dist.distDir,
srcDir,
scripts,
outModules: target.outModules,
};
// dist:scripts
distTasks.push(nameTask(`${target.name}:dist:scripts`, gulp.series(result.distCopy, getBuildTypescriptTask(gulp, tsOptions))));
// dist:package.json
{
async function distPackageJsonTask() {
let pkg = await readJsonFile(target.project.absPackageJson);
if (typeof target.mainModule === "string") {
pkg.main = target.mainModule;
pkg.types = `${target.mainModule}.d.ts`;
}
pkg.gitHead = await getHeadHash();
pkg = dist.packageJsonMap(pkg);
return gulpBufferSrc("package.json", Buffer.from(JSON.stringify(pkg, null, 2)))
.pipe(gulp.dest(dist.distDir));
}
result.distPackageJson = nameTask(`${target.name}:dist:package.json`, distPackageJsonTask);
distTasks.push(result.distPackageJson);
}
const distTask = result.clean !== undefined ?
gulp.series(result.clean, gulp.parallel(distTasks)) :
gulp.parallel(distTasks);
result.dist = nameTask(`${target.name}:dist`, distTask);
if (dist.npmPublish !== undefined) {
const npmPublishOptions = dist.npmPublish;
const npmPublishTask = async () => {
return npmPublish(Object.assign({}, npmPublishOptions, { directory: dist.distDir }));
};
npmPublishTask.displayName = `${target.name}:dist:publish`;
gulp.task(npmPublishTask);
result.distPublish = nameTask(`${target.name}:dist:publish`, gulp.series(distTask, npmPublishTask));
}
}
return result;
}
/**
* Generates and registers gulp tasks for the provided lib target.
*
* @param gulp Gulp instance where the tasks will be registered.
* @param targetOptions Target configuration.
*/
export function registerLibTasks(gulp, targetOptions) {
const tasks = generateLibTasks(gulp, targetOptions);
for (const key in tasks) {
const task = tasks[key];
if (task !== undefined) {
gulp.task(task);
}
}
return tasks;
}
//# sourceMappingURL=data:application/json;charset=utf8;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbIl9zcmMvdGFyZ2V0cy9saWIudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUE7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O0dBaUVHO0FBS0gsT0FBTyxFQUFFLFNBQVMsRUFBRSxNQUFNLFdBQVcsQ0FBQztBQUN0QyxPQUFPLElBQUksTUFBTSxNQUFNLENBQUM7QUFPeEIsT0FBTyxFQUFFLHNCQUFzQixFQUFFLE1BQU0sa0NBQWtDLENBQUM7QUFDMUUsT0FBTyxFQUFFLGNBQWMsRUFBRSxNQUFNLHlCQUF5QixDQUFDO0FBRXpELE9BQU8sRUFBRSxhQUFhLEVBQUUsTUFBTSx5QkFBeUIsQ0FBQztBQUN4RCxPQUFPLEVBQUUsV0FBVyxFQUFFLE1BQU0sY0FBYyxDQUFDO0FBQzNDLE9BQU8sS0FBSyxPQUFPLE1BQU0sa0JBQWtCLENBQUM7QUFDNUMsT0FBTyxFQUFFLFVBQVUsRUFBRSxNQUFNLHNCQUFzQixDQUFDO0FBQ2xELE9BQU8sRUFBZSxZQUFZLEVBQUUsTUFBTSxrQkFBa0IsQ0FBQztBQUM3RCxPQUFPLEVBRUwsaUJBQWlCLEVBQ2pCLE9BQU8sRUFDUCxhQUFhLEVBQ2IsUUFBUSxFQUdSLGlCQUFpQixHQUVsQixNQUFNLFNBQVMsQ0FBQztBQTJKakI7Ozs7O0dBS0c7QUFDSCwwQkFBMEIsTUFBaUI7SUFDekMsTUFBTSxJQUFJLEdBQXVCLGlCQUFpQixDQUFDLE1BQU0sQ0FBQyxDQUFDO0lBRTNELElBQUksT0FBTyxHQUF1QyxTQUFTLENBQUM7SUFDNUQsSUFBSSxNQUFNLENBQUMsT0FBTyxLQUFLLFNBQVMsRUFBRTtRQUNoQyxPQUFPLEdBQUc7WUFDUixHQUFHLEVBQUUsSUFBSSxDQUFDLEtBQUssQ0FBQyxJQUFJLENBQUMsSUFBSSxDQUFDLE9BQU8sQ0FBQyxPQUFPLEVBQUUsTUFBTSxDQUFDLE9BQU8sQ0FBQyxHQUFHLENBQUM7WUFDOUQsSUFBSSxFQUFFLE1BQU0sQ0FB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WUFDRixjQUFjLENBQUMsV0FBVyxHQUFHLEdBQUcsTUFBTSxDQUFDLElBQUksZUFBZSxDQUFDO1lBQzNELElBQUksQ0FBQyxJQUFJLENBQUMsY0FBYyxDQUFDLENBQUM7WUFDMUIsTUFBTSxDQUFDLFdBQVcsR0FBRyxRQUFRLENBQUMsR0FBRyxNQUFNLENBQUMsSUFBSSxlQUFlLEVBQUUsSUFBSSxDQUFDLE1BQU0sQ0FBQyxRQUFRLEVBQUUsY0FBYyxDQUFDLENBQUMsQ0FBQztTQUNyRztLQUNGO0lBRUQsT0FBTyxNQUFNLENBQUM7QUFDaEIsQ0FBQztBQUVEOzs7OztHQUtHO0FBQ0gsTUFBTSwyQkFBMkIsSUFBVSxFQUFFLGFBQXdCO0lBQ25FLE1BQU0sS0FBSyxHQUFhLGdCQUFnQixDQUFDLElBQUksRUFBRSxhQUFhLENBQUMsQ0FBQztJQUM5RCxLQUFLLE1BQU0sR0FBRyxJQUFJLEtBQUssRUFBRTtRQUN2QixNQUFNLElBQUksR0FBb0MsS0FBTSxDQUFDLEdBQUcsQ0FBQyxDQUFDO1FBQzFELElBQUksSUFBSSxLQUFLLFNBQVMsRUFBRTtZQUN0QixJQUFJLENBQUMsSUFBSSxDQUFDLElBQUksQ0FBQyxDQUFDO1NBQ2pCO0tBQ0Y7SUFDRCxPQUFPLEtBQUssQ0FBQztBQUNmLENBQUMiLCJmaWxlIjoidGFyZ2V0cy9saWIuanMiLCJzb3VyY2VzQ29udGVudCI6WyIvKipcbiAqIFRoaXMgbW9kdWxlIGRlZmluZXMgdGhlIF9saWJfIHRhcmdldCB0eXBlIHVzZWQgdG8gY3JlYXRlIGxpYnJhcmllcyBmb3Igb3RoZXIgcHJvamVjdHMuXG4gKlxuICogSW4gdGhlIGZvbGxvd2luZyBsaXN0IG9mIHRhc2tzLCBge3RhcmdldH1gIHJlcHJlc2VudHMgdGhlIG5hbWUgb2YgdGhlIHRhcmdldCBhcyBkZWZpbmVkIGJ5IHRoZSBgbmFtZWAgcHJvcGVydHlcbiAqIG9mIHRoZSB0YXJnZXQgb3B0aW9ucy5cbiAqIFRoZSBfbGliXyB0YXJnZXQgcHJvdmlkZXMgdGhlIGZvbGxvd2luZyB0YXNrczpcbiAqXG4gKiAjIyB7dGFyZ2V0fTpidWlsZFxuICpcbiAqIFBlcmZvcm1zIGEgZnVsbCBidWlsZCBvZiB0aGUgbGlicmFyeSB0byB0aGUgYnVpbGQgZGlyZWN0b3J5LCB1c2VkIGZvciBkZXZlbG9wbWVudC5cbiAqIFRoaXMgY29waWVzIHRoZSBzdGF0aWMgYXNzZXRzIGFuZCBjb21waWxlcyB0aGUgc2NyaXB0cy5cbiAqXG4gKiBUaGUgZm9sbG93aW5nIHN1Yi10YXNrcyBhcmUgYXZhaWxhYmxlOlxuICogLSBge3RhcmdldH06YnVpbGQ6Y29weWA6IE9ubHkgY29weSB0aGUgc3RhdGljIGFzc2V0c1xuICogLSBge3RhcmdldH06YnVpbGQ6c2NyaXB0YDogT25seSBjb21waWxlIHRoZSBzY3JpcHRzXG4gKlxuICogRm9yIGRpc3RyaWJ1dGlvbiBidWlsZHMsIHVzZSBge3RhcmdldDpkaXN0fWBcbiAqXG4gKiAjIyB7dGFyZ2V0fTp3YXRjaFxuICpcbiAqIFdhdGNoIHRoZSBmaWxlcyBhbmQgcnVuIGluY3JlbWVudGFsIGJ1aWxkcyBvbiBjaGFuZ2UuXG4gKiBUaGlzIHVzZWZ1bCBkdXJpbmcgZGV2ZWxvcG1lbnQgdG8gZ2V0IGJ1aWxkIGVycm9ycyByZXBvcnRlZCBpbW1lZGlhdGVseSBvciBhY2NlbGVyYXRlIHRoZSBjb2RlL3Rlc3QgY3ljbGUuXG4gKiBZb3UgY2FuIGNvbWJpbmUgaXQgd2l0aCBfTm9kZW1vbl8gdG8gY29udGludW91c2x5IHJlc3RhcnQgeW91ciBOb2RlIHByb2Nlc3Mgd2hlbiBjaGFuZ2luZyB0aGUgc291cmNlLlxuICpcbiAqICMjIHt0YXJnZXR9OmRpc3RcbiAqXG4gKiBQZXJmb3JtcyBhIGZ1bGwgYnVpbGQgb2YgdGhlIGxpYnJhcnkgdG8gdGhlIGRpc3QgZGlyZWN0b3J5LCB1c2VkIGZvciBkaXN0cmlidXRpb24gKGllLiBwdWJsaWNhdGlvbiB0byBfbnBtXykuXG4gKiBUaGlzIGJ1aWxkIGNyZWF0ZXMgYSBmdWxseSBhdXRvbm9tb3VzIGRpcmVjdG9yeSB3aXRoIGl0cyBvd24gYHBhY2thZ2UuanNvbmAsIHNvdXJjZSBjb2RlLCBsaWNlbnNlIGZpbGUsIGV0Yy5cbiAqIFRoaXMgYWxsb3dzIHRvIHVzZSBhIGRpZmZlcmVudCBzdHJ1Y3R1cmUgZm9yIGRpc3RyaWJ1dGlvbiByYXRoZXIgdGhhbiBzdHJ1Y3R1cmUgb2YgdGhlIHJlcG8sIHRoZSBtYWluIGJlbmVmaXQgaXNcbiAqIHRvIHByb3ZpZGUgc3VwcG9ydCBmb3IgZGVlcCBwYWNrYWdlIGltcG9ydHMgKGBpbXBvcnQgKiBhcyBtb2QgZnJvbSBcIm15LWxpYi9kZWVwL21vZHVsZVwiYCkgYnkgcGxhY2luZyB0aGUgYnVpbGRcbiAqIGF0IHRoZSByb290IG9mIHRoZSBwYWNrYWdlLlxuICogVGhpcyBidWlsZCBhbHNvIGFsbG93cyB5b3UgdG8gcmVtYXAgdGhlIGBwYWNrYWdlLmpzb25gLCBmb3IgZXhhbXBsZSB0byBzZXQgdGhlIHZlcnNpb24gZHluYW1pY2FsbHkuXG4gKlxuICogVGhlIGZvbGxvd2luZyBzdWItdGFza3MgYXJlIGF2YWlsYWJsZTpcbiAqIC0gYHt0YXJnZXR9OmRpc3Q6cHVibGlzaGA6IFB1Ymxpc2ggdGhlIHBhY2thZ2UgdG8gYW4gX25wbV8gcmVnaXN0cnkgKGl0IGhvbm9ycyB0aGUgYHJlZ2lzdHJ5YCBvcHRpb24sIHRvIHB1Ymxpc2hcbiAqICAgdG8gcHJpdmF0ZSBfbnBtXyByZWdpc3RyaWVzIHN1Y2ggYXMgX1ZlcmRhY2Npb18pLiBJdCB1c2VzIHRoZSBhdXRoZW50aWNhdGlvbiB0b2tlbiBvZiB0aGUgY3VycmVudCB1c2VyLCB0aGlzXG4gKiAgIHRva2VuIGlzIGluIGB+Ly5ucG1yY2AuIEZvciBDSSwgeW91IGNhbiB1c2UgdGhlIGZvbGxvd2luZyBjb21tYW5kIHRvIHNldCB0aGUgdG9rZW4gdGhlIHJlZ2lzdHJ5IGBucG0uZXhhbXBsZS5jb21gLlxuICogICAoZm9yIHRoZSBvZmZpY2lhbCByZWdpc3RyeSwgdXNlIGAvL3JlZ2lzdHJ5Lm5wbWpzLm9yZ2ApOlxuICogICBgYGBcbiAqICAgZWNobyBcIi8vbnBtLmV4YW1wbGUuY29tLzpfYXV0aFRva2VuPVxcXCIke05QTV9UT0tFTn1cXFwiXCIgPiB+Ly5ucG1yY1xuICogICBgYGBcbiAqIC0gYHt0YXJnZXR9OmRpc3Q6Y29weS1zcmNgOiBPbmx5IGNvcHkgdGhlIHNvdXJjZSBmaWxlcyB0byB0aGUgYnVpbGQgZGlyZWN0b3J5LlxuICogLSBge3RhcmdldH06ZGlzdDpwYWNrYWdlLmpzb25gOiBDb3B5IChhbmQgZXZlbnR1YWxseSB0cmFuc2Zvcm0pIHRoZSByb290IGBwYWNrYWdlLmpzb25gIHRvIHRoZSBidWlsZCBkaXJlY3RvcnkuXG4gKlxuICogRm9yIGRldmVsb3BtZW50IGJ1aWxkcywgdXNlIGB7dGFyZ2V0OmJ1aWxkfWAuXG4gKlxuICogIyMge3RhcmdldH06dHlwZWRvY1xuICpcbiAqIEdlbmVyYXRlIF9UeXBlZG9jXyBkb2N1bWVudGF0aW9uLlxuICpcbiAqICMjIHt0YXJnZXR9OnR5cGVkb2M6ZGVwbG95XG4gKlxuICogRGVwbG95IHRoZSBfVHlwZWRvY18gZG9jdW1lbnRhdGlvbiB1c2luZyBfZ2l0Xy4gVGhpcyBjYW4gYmUgdXNlZCB0byBlYXNpbHkgZGVwbG95IHRoZSBkb2N1bWVudGF0aW9uIHRvIHRoZVxuICogYGdoLXBhZ2VzYCBicmFuY2guXG4gKlxuICogIyMge3RhcmdldH06Y2xlYW5cbiAqXG4gKiBSZW1vdmUgYm90aCB0aGUgYnVpbGQgYW5kIGRpc3QgZGlyZWN0b3JpZXMgY29ycmVzcG9uZGluZyB0byB0aGlzIHRhcmdldC5cbiAqXG4gKiAjIyB7dGFyZ2V0fTp0c2NvbmZpZy5qc29uXG4gKlxuICogRW1pdCBhIGB0c2NvbmZpZy5qc29uYCBmaWxlIGNvcnJlc3BvbmRpbmcgdG8gdGhlIGNvbmZpZ3VyYXRpb24gZm9yIHRoaXMgdGFyZ2V0LiBUaGlzIGFsbG93cyB0byBjb21waWxlIGl0IHVzaW5nXG4gKiB0aGUgY29tbWFuZCBsaW5lIGB0c2NgIHByb2dyYW0uIFRoaXMgaXMgYWxzbyB1c2VmdWwgZm9yIElERSB0byBhdXRvLWRldGVjdCB0aGUgY29uZmlndXJhdGlvbiBvZiB0aGUgcHJvamVjdC5cbiAqXG4gKiBAbW9kdWxlIHRhcmdldHMvbGliXG4gKi9cblxuLyoqIChQbGFjZWhvbGRlciBjb21tZW50LCBzZWUgY2hyaXN0b3BoZXJ0aGllbGVuL3R5cGVkb2MtcGx1Z2luLWV4dGVybmFsLW1vZHVsZS1uYW1lIzYpICovXG5cbmltcG9ydCB7IEd1bHAsIFRhc2tGdW5jdGlvbiB9IGZyb20gXCJndWxwXCI7XG5pbXBvcnQgeyBNaW5pbWF0Y2ggfSBmcm9tIFwibWluaW1hdGNoXCI7XG5pbXBvcnQgcGF0aCBmcm9tIFwicGF0aFwiO1xuaW1wb3J0IHsgQ2xlYW5PcHRpb25zIH0gZnJvbSBcIi4uL29wdGlvbnMvY2xlYW5cIjtcbmltcG9ydCB7IENvcHlPcHRpb25zIH0gZnJvbSBcIi4uL29wdGlvbnMvY29weVwiO1xuaW1wb3J0IHsgQ29tcGlsZXJPcHRpb25zSnNvbiB9IGZyb20gXCIuLi9vcHRpb25zL3RzY1wiO1xuaW1wb3J0IHsgT3V0TW9kdWxlcyB9IGZyb20gXCIuLi9vcHRpb25zL3R5cGVzY3JpcHRcIjtcbmltcG9ydCB7IFJlc29sdmVkUHJvamVjdCB9IGZyb20gXCIuLi9wcm9qZWN0XCI7XG5pbXBvcnQgeyBUeXBlc2NyaXB0Q29uZmlnIH0gZnJvbSBcIi4uL3RhcmdldC10YXNrcy9fdHlwZXNjcmlwdFwiO1xuaW1wb3J0IHsgZ2V0QnVpbGRUeXBlc2NyaXB0VGFzayB9IGZyb20gXCIuLi90YXJnZXQtdGFza3MvYnVpbGQtdHlwZXNjcmlwdFwiO1xuaW1wb3J0IHsgZ2V0VHlwZWRvY1Rhc2sgfSBmcm9tIFwiLi4vdGFyZ2V0LXRhc2tzL3R5cGVkb2NcIjtcbmltcG9ydCB7IEFic1Bvc2l4UGF0aCwgUmVsUG9zaXhQYXRoIH0gZnJvbSBcIi4uL3R5cGVzXCI7XG5pbXBvcnQgeyBicmFuY2hQdWJsaXNoIH0gZnJvbSBcIi4uL3V0aWxzL2JyYW5jaC1wdWJsaXNoXCI7XG5pbXBvcnQgeyBnZXRIZWFkSGFzaCB9IGZyb20gXCIuLi91dGlscy9naXRcIjtcbmltcG9ydCAqIGFzIG1hdGNoZXIgZnJvbSBcIi4uL3V0aWxzL21hdGNoZXJcIjtcbmltcG9ydCB7IG5wbVB1Ymxpc2ggfSBmcm9tIFwiLi4vdXRpbHMvbnBtLXB1Ymxpc2hcIjtcbmltcG9ydCB7IFBhY2thZ2VKc29uLCByZWFkSnNvbkZpbGUgfSBmcm9tIFwiLi4vdXRpbHMvcHJvamVjdFwiO1xuaW1wb3J0IHtcbiAgQmFzZVRhc2tzLFxuICBnZW5lcmF0ZUJhc2VUYXNrcyxcbiAgZ2V0Q29weSxcbiAgZ3VscEJ1ZmZlclNyYyxcbiAgbmFtZVRhc2ssXG4gIFJlc29sdmVkQmFzZURlcGVuZGVuY2llcyxcbiAgUmVzb2x2ZWRUYXJnZXRCYXNlLFxuICByZXNvbHZlVGFyZ2V0QmFzZSxcbiAgVGFyZ2V0QmFzZSxcbn0gZnJvbSBcIi4vX2Jhc2VcIjtcblxuLyoqXG4gKiBSZXByZXNlbnRzIGEgVHlwZXNjcmlwdCBsaWJyYXJ5LlxuICogVGhpcyBpcyBjb21wYXRpYmxlIHdpdGggYm90aCBicm93c2VycyBhbmQgTm9kZS5cbiAqL1xuZXhwb3J0IGludGVyZmFjZSBMaWJUYXJnZXQgZXh0ZW5kcyBUYXJnZXRCYXNlIHtcbiAgLyoqXG4gICAqIFJlbGF0aXZlIHBhdGggZm9yIHRoZSBtYWluIG1vZHVsZSAoZW50cnkgcG9pbnQgb2YgdGhlIGxpYikgV0lUSE9VVCBFWFRFTlNJT04sIHJlbGF0aXZlIHRvIGBwcm9qZWN0LnNyY0RpcmAuXG4gICAqIERlZmF1bHQ6IGBcImluZGV4XCJgLlxuICAgKi9cbiAgbWFpbk1vZHVsZTogUmVsUG9zaXhQYXRoO1xuXG4gIC8qKlxuICAgKiBQYXRoIHRvIHRoZSBgdHlwZWRvY2AgZGlyZWN0b3J5LCByZWxhdGl2ZSB0byBgcHJvamVjdC5yb290RGlyYC5cbiAgICogVXNlIGBudWxsYCB0byBub3QgZ2VuZXJhdGUgYSBgdHlwZWRvY2AgdGFzay5cbiAgICogRGVmYXVsdDogYGpvaW4ocHJvamVjdC5yb290RGlyLCBcInR5cGVkb2NcIilgLlxuICAgKi9cbiAgdHlwZWRvYz86IFR5cGVkb2NPcHRpb25zO1xuXG4gIC8qKlxuICAgKiBPcHRpb25zIGZvciBkaXN0cmlidXRpb24gYnVpbGRzLlxuICAgKiBgZmFsc2VgOiBObyBkaXN0cmlidXRpb24gYnVpbGRcbiAgICogYHRydWVgOiBEaXN0cmlidXRpb24gYnVpbGQgd2l0aCBkZWZhdWx0c1xuICAgKiBgRGlzdE9wdGlvbnNgOiBQcm92aWRlIGN1c3RvbSBvcHRpb25zXG4gICAqIERlZmF1bHQ6IGBmYWxzZWAsIG5vIGRpc3RyaWJ1dGlvbiBidWlsZC5cbiAgICovXG4gIGRpc3Q/OiB0cnVlIHwgZmFsc2UgfCBEaXN0T3B0aW9ucztcbn1cblxuLyoqXG4gKiBMaWJyYXJ5IHdpdGggZnVsbHkgcmVzb2x2ZWQgcGF0aHMgYW5kIGRlcGVuZGVuY2llcy5cbiAqL1xuaW50ZXJmYWNlIFJlc29sdmVkTGliVGFyZ2V0IGV4dGVuZHMgTGliVGFyZ2V0LCBSZXNvbHZlZFRhcmdldEJhc2Uge1xuICByZWFkb25seSBwcm9qZWN0OiBSZXNvbHZlZFByb2plY3Q7XG5cbiAgcmVhZG9ubHkgc3JjRGlyOiBBYnNQb3NpeFBhdGg7XG5cbiAgcmVhZG9ubHkgYnVpbGREaXI6IEFic1Bvc2l4UGF0aDtcblxuICByZWFkb25seSBzY3JpcHRzOiBJdGVyYWJsZTxzdHJpbmc+O1xuXG4gIHJlYWRvbmx5IGN1c3RvbVR5cGluZ3NEaXI6IEFic1Bvc2l4UGF0aCB8IG51bGw7XG5cbiAgcmVhZG9ubHkgdHNjT3B0aW9uczogQ29tcGlsZXJPcHRpb25zSnNvbjtcblxuICAvKipcbiAgICogVE9ET1xuICAgKi9cbiAgcmVhZG9ubHkgb3V0TW9kdWxlczogT3V0TW9kdWxlcztcblxuICByZWFkb25seSB0c2NvbmZpZ0pzb246IEFic1Bvc2l4UGF0aCB8IG51bGw7XG5cbiAgcmVhZG9ubHkgdHlwZWRvYz86IFJlc29sdmVkVHlwZWRvY09wdGlvbnM7XG5cbiAgcmVhZG9ubHkgZGVwZW5kZW5jaWVzOiBSZXNvbHZlZEJhc2VEZXBlbmRlbmNpZXM7XG5cbiAgcmVhZG9ubHkgY29weT86IENvcHlPcHRpb25zW107XG5cbiAgcmVhZG9ubHkgY2xlYW4/OiBDbGVhbk9wdGlvbnM7XG5cbiAgcmVhZG9ubHkgZGlzdDogZmFsc2UgfCBSZXNvbHZlZERpc3RPcHRpb25zO1xufVxuXG5leHBvcnQgaW50ZXJmYWNlIERpc3RPcHRpb25zIHtcbiAgLyoqXG4gICAqIERpcmVjdG9yeSB1c2VkIHdoZXJlIHRoZSBkaXN0cmlidXRpb24gYnVpbGRzIHdpbGwgYmUgd3JpdHRlbi5cbiAgICogRGVmYXVsdDogYHByb2plY3QuZGlzdERpcmBcbiAgICovXG4gIHJlYWRvbmx5IGRpc3REaXI/OiBSZWxQb3NpeFBhdGg7XG5cbiAgLyoqXG4gICAqIENvcHkgdGhlIHNvdXJjZXMgZnJvbSBgdGFyZ2V0LnNyY0RpcmAgdG8gYHRhcmdldC5kaXN0LmRpc3REaXJgLiBEZWZhdWx0OiBgdHJ1ZWAuXG4gICAqL1xuICByZWFkb25seSBjb3B5U3JjPzogYm9vbGVhbjtcblxuICAvKipcbiAgICogQ29weSBvcGVyYXRpb25zIHRvIHBlcmZvcm0gd2hlbiBkaXN0cmlidXRpbmcgdGhlIHBhY2thZ2UuXG4gICAqIFRoZSBkZWZhdWx0IGNvcGllcyB0aGUgTWFya2Rvd24gZmlsZXMgYXQgdGhlIHByb2plY3Qgcm9vdCAoc28geW91IGdldCBgUkVBRE1FLm1kYCwgYExJQ0VOU0UubWRgLCAuLi4pLlxuICAgKlxuICAgKiBUaGUgYmFzZSB2YWx1ZXMgYXJlOlxuICAgKiAtIGBzcmNgOiBgcHJvamVjdC5yb290YFxuICAgKiAtIGBkZXN0YDogYGRpc3QuZGlzdERpcmBcbiAgICovXG4gIHJlYWRvbmx5IGNvcHk/OiBDb3B5T3B0aW9uc1tdO1xuXG4gIHJlYWRvbmx5IG5wbVB1Ymxpc2g/OiBOcG1QdWJsaXNoT3B0aW9ucztcblxuICAvKipcbiAgICogT3B0aW9uYWwgZnVuY3Rpb24gdG8gYXBwbHkgd2hlbiBjb3B5aW5nIHRoZSBgcGFja2FnZS5qc29uYCBmaWxlIHRvIHRoZSBkaXN0IGRpcmVjdG9yeS5cbiAgICovXG4gIHBhY2thZ2VKc29uTWFwPyhvbGQ6IFBhY2thZ2VKc29uKTogUGFja2FnZUpzb247XG59XG5cbmV4cG9ydCBpbnRlcmZhY2UgUmVzb2x2ZWREaXN0T3B0aW9ucyBleHRlbmRzIERpc3RPcHRpb25zIHtcbiAgLyoqXG4gICAqIERpcmVjdG9yeSB1c2VkIGZvciBkaXN0cmlidXRpb24gYnVpbGRzLlxuICAgKi9cbiAgcmVhZG9ubHkgZGlzdERpcjogQWJzUG9zaXhQYXRoO1xuXG4gIC8qKlxuICAgKiBEZXBlbmRpbmcgb24gdGhlIHZhbHVlOlxuICAgKiAtIGBmYWxzZWA6IERvIG5vdCBjb3B5IHRoZSBzb3VyY2UgYC50c2AgZmlsZXNcbiAgICogLSBgdHJ1ZWA6IENvcHkgdGhlIHNvdXJjZSBgLnRzYCBmaWxlIGZyb20gYHRhcmdldC5zcmNEaXJgIHRvIGAke3RhcmdldC5kaXN0LmRpc3REaXJ9L19zcmNgLiBUaGUgY3VzdG9tIHR5cGluZ3MgYXJlXG4gICAqICAgY29waWVkIHRvIGBfY3VzdG9tLXR5cGluZ3NgLlxuICAgKlxuICAgKiBEZWZhdWx0OiBgdHJ1ZWAuXG4gICAqL1xuICByZWFkb25seSBjb3B5U3JjOiBib29sZWFuO1xuXG4gIC8qKlxuICAgKiBPcHRpb25hbCBmdW5jdGlvbiB0byBhcHBseSB3aGVuIGNvcHlpbmcgdGhlIGBwYWNrYWdlLmpzb25gIGZpbGUgdG8gdGhlIGRpc3QgZGlyZWN0b3J5LlxuICAgKi9cbiAgcGFja2FnZUpzb25NYXAob2xkOiBQYWNrYWdlSnNvbik6IFBhY2thZ2VKc29uO1xufVxuXG5leHBvcnQgaW50ZXJmYWNlIFR5cGVkb2NPcHRpb25zIHtcbiAgLyoqXG4gICAqIFBhdGggdG8gdGhlIGB0eXBlZG9jYCBkaXJlY3RvcnksIHJlbGF0aXZlIHRvIGBwcm9qZWN0LnJvb3REaXJgLlxuICAgKiBVc2UgYG51bGxgIHRvIG5vdCBnZW5lcmF0ZSBhIGB0eXBlZG9jYCB0YXNrLlxuICAgKiBEZWZhdWx0OiBgam9pbihwcm9qZWN0LnJvb3REaXIsIFwidHlwZWRvY1wiKWAuXG4gICAqL1xuICByZWFkb25seSBkaXI6IFJlbFBvc2l4UGF0aDtcblxuICByZWFkb25seSBuYW1lOiBzdHJpbmc7XG5cbiAgcmVhZG9ubHkgZGVwbG95PzogR2l0RGVwbG95T3B0aW9ucztcbn1cblxuZXhwb3J0IGludGVyZmFjZSBSZXNvbHZlZFR5cGVkb2NPcHRpb25zIGV4dGVuZHMgVHlwZWRvY09wdGlvbnMge1xuICByZWFkb25seSBkaXI6IEFic1Bvc2l4UGF0aDtcbn1cblxuZXhwb3J0IGludGVyZmFjZSBOcG1QdWJsaXNoT3B0aW9ucyB7XG4gIC8qKlxuICAgKiBUYWcgdG8gdXNlIGZvciB0aGlzIHB1YmxpY2F0aW9uLlxuICAgKlxuICAgKiBEZWZhdWx0OiBgXCJsYXRlc3RcImAuXG4gICAqL1xuICByZWFkb25seSB0YWc/OiBzdHJpbmc7XG5cbiAgLyoqXG4gICAqIFBhdGggdG8gdGhlIG5wbSBjb21tYW5kLWxpbmUgcHJvZ3JhbS5cbiAgICpcbiAgICogRGVmYXVsdDogYFwibnBtXCJgIChhc3N1bWVzIHRoYXQgYG5wbWAgaXMgaW4gdGhlIGAkUEFUSGApXG4gICAqL1xuICByZWFkb25seSBjb21tYW5kPzogc3RyaW5nO1xufVxuXG5leHBvcnQgaW50ZXJmYWNlIEdpdERlcGxveU9wdGlvbnMge1xuICByZWFkb25seSByZXBvc2l0b3J5OiBzdHJpbmc7XG4gIHJlYWRvbmx5IGJyYW5jaDogc3RyaW5nO1xuICByZWFkb25seSBjb21taXRBdXRob3I/OiBzdHJpbmc7XG59XG5cbi8qKlxuICogUmVzb2x2ZSBhYnNvbHV0ZSBwYXRocyBhbmQgZGVwZW5kZW5jaWVzIGZvciB0aGUgcHJvdmlkZWQgdGFyZ2V0LlxuICpcbiAqIEBwYXJhbSB0YXJnZXQgTm9uLXJlc29sdmVkIHRhcmdldC5cbiAqIEByZXR1cm4gUmVzb2x2ZWQgdGFyZ2V0LlxuICovXG5mdW5jdGlvbiByZXNvbHZlTGliVGFyZ2V0KHRhcmdldDogTGliVGFyZ2V0KTogUmVzb2x2ZWRMaWJUYXJnZXQge1xuICBjb25zdCBiYXNlOiBSZXNvbHZlZFRhcmdldEJhc2UgPSByZXNvbHZlVGFyZ2V0QmFzZSh0YXJnZXQpO1xuXG4gIGxldCB0eXBlZG9jOiBSZXNvbHZlZFR5cGVkb2NPcHRpb25zIHwgdW5kZWZpbmVkID0gdW5kZWZpbmVkO1xuICBpZiAodGFyZ2V0LnR5cGVkb2MgIT09IHVuZGVmaW5lZCkge1xuICAgIHR5cGVkb2MgPSB7XG4gICAgICBkaXI6IHBhdGgucG9zaXguam9pbihiYXNlLnByb2plY3QuYWJzUm9vdCwgdGFyZ2V0LnR5cGVkb2MuZGlyKSxcbiAgICAgIG5hbWU6IHRhcmdldC50eXBlZG9jLm5hbWUsXG4gICAgICBkZXBsb3k6IHRhcmdldC50eXBlZG9jLmRlcGxveSxcbiAgICB9O1xuICB9XG5cbiAgbGV0IGRpc3Q6IFJlc29sdmVkRGlzdE9wdGlvbnMgfCBmYWxzZTtcbiAgaWYgKHRhcmdldC5kaXN0ID09PSB1bmRlZmluZWQgfHwgdGFyZ2V0LmRpc3QgPT09IGZhbHNlKSB7XG4gICAgZGlzdCA9IGZhbHNlO1xuICB9IGVsc2Uge1xuICAgIGNvbnN0IGRlZmF1bHREaXN0RGlyOiBBYnNQb3NpeFBhdGggPSBwYXRoLnBvc2l4LmpvaW4oYmFzZS5wcm9qZWN0LmFic0Rpc3REaXIsIHRhcmdldC5uYW1lKTtcbiAgICBjb25zdCBkZWZhdWx0UGFja2FnZUpzb25NYXA6IChwa2c6IFBhY2thZ2VKc29uKSA9PiBQYWNrYWdlSnNvbiA9IHBrZyA9PiBwa2c7XG4gICAgY29uc3QgZGVmYXVsdENvcHk6IChkZXN0OiBBYnNQb3NpeFBhdGgpID0+IENvcHlPcHRpb25zW10gPSAoZGVzdDogQWJzUG9zaXhQYXRoKSA9PiBbe1xuICAgICAgZmlsZXM6IFtcIi4vKi5tZFwiXSxcbiAgICB9XTtcblxuICAgIGlmICh0YXJnZXQuZGlzdCA9PT0gdHJ1ZSkgeyAvLyBgdHJ1ZWAgbGl0ZXJhbFxuICAgICAgZGlzdCA9IHtcbiAgICAgICAgZGlzdERpcjogZGVmYXVsdERpc3REaXIsXG4gICAgICAgIHBhY2thZ2VKc29uTWFwOiBkZWZhdWx0UGFja2FnZUpzb25NYXAsXG4gICAgICAgIG5wbVB1Ymxpc2g6IHt9LFxuICAgICAgICBjb3B5U3JjOiB0cnVlLFxuICAgICAgICBjb3B5OiBkZWZhdWx0Q29weShkZWZhdWx0RGlzdERpciksXG4gICAgICB9O1xuICAgIH0gZWxzZSB7XG4gICAgICBjb25zdCBkaXN0RGlyOiBBYnNQb3NpeFBhdGggPSB0YXJnZXQuZGlzdC5kaXN0RGlyICE9PSB1bmRlZmluZWQgPyB0YXJnZXQuZGlzdC5kaXN0RGlyIDogZGVmYXVsdERpc3REaXI7XG4gICAgICBkaXN0ID0ge1xuICAgICAgICBkaXN0RGlyLFxuICAgICAgICBwYWNrYWdlSnNvbk1hcDogdGFyZ2V0LmRpc3QucGFja2FnZUpzb25NYXAgIT09IHVuZGVmaW5lZCA/IHRhcmdldC5kaXN0LnBhY2thZ2VKc29uTWFwIDogZGVmYXVsdFBhY2thZ2VKc29uTWFwLFxuICAgICAgICBucG1QdWJsaXNoOiB0YXJnZXQuZGlzdC5ucG1QdWJsaXNoLFxuICAgICAgICBjb3B5U3JjOiB0YXJnZXQuZGlzdC5jb3B5U3JjICE9PSB1bmRlZmluZWQgPyB0YXJnZXQuZGlzdC5jb3B5U3JjIDogdHJ1ZSxcbiAgICAgICAgY29weTogZGVmYXVsdENvcHkoZGlzdERpciksXG4gICAgICB9O1xuICAgIH1cbiAgfVxuXG4gIHJldHVybiB7Li4uYmFzZSwgbWFpbk1vZHVsZTogdGFyZ2V0Lm1haW5Nb2R1bGUsIHR5cGVkb2MsIGRpc3R9O1xufVxuXG5leHBvcnQgaW50ZXJmYWNlIExpYlRhc2tzIGV4dGVuZHMgQmFzZVRhc2tzIHtcbiAgdHlwZWRvYz86IFRhc2tGdW5jdGlvbjtcbiAgdHlwZWRvY0RlcGxveT86IFRhc2tGdW5jdGlvbjtcbiAgZGlzdD86IFRhc2tGdW5jdGlvbjtcbiAgZGlzdENvcHk/OiBUYXNrRnVuY3Rpb247XG4gIGRpc3RQdWJsaXNoPzogVGFza0Z1bmN0aW9uO1xuICBkaXN0UGFja2FnZUpzb24/OiBUYXNrRnVuY3Rpb247XG59XG5cbi8qKlxuICogR2VuZXJhdGVzIGd1bHAgdGFza3MgZm9yIHRoZSBwcm92aWRlZCBsaWIgdGFyZ2V0LlxuICpcbiAqIEBwYXJhbSBndWxwIEd1bHAgaW5zdGFuY2UgdXNlZCB0byBnZW5lcmF0ZSB0YXNrcyBtYW5pcHVsYXRpbmcgZmlsZXMuXG4gKiBAcGFyYW0gdGFyZ2V0T3B0aW9ucyBUYXJnZXQgY29uZmlndXJhdGlvbi5cbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIGdlbmVyYXRlTGliVGFza3MoZ3VscDogR3VscCwgdGFyZ2V0T3B0aW9uczogTGliVGFyZ2V0KTogTGliVGFza3Mge1xuICBjb25zdCB0YXJnZXQ6IFJlc29sdmVkTGliVGFyZ2V0ID0gcmVzb2x2ZUxpYlRhcmdldCh0YXJnZXRPcHRpb25zKTtcbiAgY29uc3QgcmVzdWx0OiBMaWJUYXNrcyA9IDxMaWJUYXNrcz4gZ2VuZXJhdGVCYXNlVGFza3MoZ3VscCwgdGFyZ2V0T3B0aW9ucyk7XG5cbiAgY29uc3QgdHNPcHRpb25zOiBUeXBlc2NyaXB0Q29uZmlnID0ge1xuICAgIHRzY09wdGlvbnM6IHRhcmdldC50c2NPcHRpb25zLFxuICAgIHRzY29uZmlnSnNvbjogdGFyZ2V0LnRzY29uZmlnSnNvbixcbiAgICBjdXN0b21UeXBpbmdzRGlyOiB0YXJnZXQuY3VzdG9tVHlwaW5nc0RpcixcbiAgICBwYWNrYWdlSnNvbjogdGFyZ2V0LnByb2plY3QuYWJzUGFja2FnZUpzb24sXG4gICAgYnVpbGREaXI6IHRhcmdldC5idWlsZERpcixcbiAgICBzcmNEaXI6IHRhcmdldC5zcmNEaXIsXG4gICAgc2NyaXB0czogdGFyZ2V0LnNjcmlwdHMsXG4gICAgb3V0TW9kdWxlczogdGFyZ2V0Lm91dE1vZHVsZXMsXG4gIH07XG5cbiAgLy8gdHlwZWRvY1xuICBpZiAodGFyZ2V0LnR5cGVkb2MgIT09IHVuZGVmaW5lZCkge1xuICAgIGNvbnN0IHR5cGVkb2NPcHRpb25zOiBUeXBlZG9jT3B0aW9ucyA9IHRhcmdldC50eXBlZG9jO1xuICAgIHJlc3VsdC50eXBlZG9jID0gbmFtZVRhc2soXG4gICAgICBgJHt0YXJnZXQubmFtZX06dHlwZWRvY2AsXG4gICAgICBndWxwLnNlcmllcyhbcmVzdWx0LnRzY29uZmlnSnNvbiwgZ2V0VHlwZWRvY1Rhc2soZ3VscCwgdHNPcHRpb25zLCB0eXBlZG9jT3B0aW9ucyldKSxcbiAgICApO1xuXG4gICAgLy8gdHlwZWRvYzpkZXBsb3lcbiAgICBpZiAodHlwZWRvY09wdGlvbnMuZGVwbG95ICE9PSB1bmRlZmluZWQpIHtcbiAgICAgIGNvbnN0IGRlcGxveTogR2l0RGVwbG95T3B0aW9ucyA9IHR5cGVkb2NPcHRpb25zLmRlcGxveTtcblxuICAgICAgYXN5bmMgZnVuY3Rpb24gZGVwbG95VHlwZWRvY1Rhc2soKTogUHJvbWlzZTx2b2lkPiB7XG4gICAgICAgIGNvbnN0IGNvbW1pdE1lc3NhZ2U6IHN0cmluZyA9IGBEZXBsb3kgZG9jdW1lbnRhdGlvbiBmb3IgJHthd2FpdCBnZXRIZWFkSGFzaCgpfWA7XG4gICAgICAgIHJldHVybiBicmFuY2hQdWJsaXNoKHsuLi5kZXBsb3ksIGRpcjogdHlwZWRvY09wdGlvbnMuZGlyLCBjb21taXRNZXNzYWdlfSk7XG4gICAgICB9XG5cbiAgICAgIHJlc3VsdC50eXBlZG9jRGVwbG95ID0gbmFtZVRhc2soYCR7dGFyZ2V0Lm5hbWV9OnR5cGVkb2M6ZGVwbG95YCwgZ3VscC5zZXJpZXMocmVzdWx0LnR5cGVkb2MhLCBkZXBsb3lUeXBlZG9jVGFzaykpO1xuICAgIH1cbiAgfVxuXG4gIC8vIGRpc3RcbiAgaWYgKHRhcmdldC5kaXN0ICE9PSBmYWxzZSkge1xuICAgIGNvbnN0IGRpc3Q6IFJlc29sdmVkRGlzdE9wdGlvbnMgPSB0YXJnZXQuZGlzdDtcbiAgICBjb25zdCBkaXN0VGFza3M6IFRhc2tGdW5jdGlvbltdID0gW107XG4gICAgY29uc3QgY29weVRhc2tzOiBUYXNrRnVuY3Rpb25bXSA9IFtdO1xuXG4gICAgLy8gTG9jYXRpb25zIGZvciBjb21waWxhdGlvbjogZGVmYXVsdCB0byB0aGUgb3JpZ2luYWwgc291cmNlcyBidXQgY29tcGlsZSB0aGUgY29waWVkIGZpbGVzIGlmIGNvcHlTcmMgaXMgdXNlZFxuICAgIGxldCBzcmNEaXI6IEFic1Bvc2l4UGF0aCA9IHRhcmdldC5zcmNEaXI7XG4gICAgbGV0IGN1c3RvbVR5cGluZ3NEaXI6IEFic1Bvc2l4UGF0aCB8IG51bGwgPSB0YXJnZXQuY3VzdG9tVHlwaW5nc0RpcjtcbiAgICAvLyBkaXN0OmNvcHk6c2NyaXB0c1xuICAgIGlmICh0YXJnZXQuZGlzdC5jb3B5U3JjKSB7XG4gICAgICBzcmNEaXIgPSBwYXRoLnBvc2l4LmpvaW4oZGlzdC5kaXN0RGlyLCBcIl9zcmNcIik7XG4gICAgICBjb3B5VGFza3MucHVzaChuYW1lVGFzayhcbiAgICAgICAgYCR7dGFyZ2V0Lm5hbWV9OmRpc3Q6Y29weTpzY3JpcHRzYCxcbiAgICAgICAgKCk6IE5vZGVKUy5SZWFkYWJsZVN0cmVhbSA9PiB7XG4gICAgICAgICAgcmV0dXJuIGd1bHBcbiAgICAgICAgICAgIC5zcmMoWy4uLnRhcmdldC5zY3JpcHRzXSwge2Jhc2U6IHRhcmdldC5zcmNEaXJ9KVxuICAgICAgICAgICAgLnBpcGUoZ3VscC5kZXN0KHNyY0RpcikpO1xuICAgICAgICB9LFxuICAgICAgKSk7XG4gICAgICAvLyBkaXN0OmNvcHk6Y3VzdG9tLXR5cGluZ3NcbiAgICAgIGlmICh0YXJnZXQuY3VzdG9tVHlwaW5nc0RpciAhPT0gbnVsbCkge1xuICAgICAgICBjb25zdCBzcmNDdXN0b21UeXBpbmdzRGlyOiBBYnNQb3NpeFBhdGggPSB0YXJnZXQuY3VzdG9tVHlwaW5nc0RpcjtcbiAgICAgICAgY29uc3QgZGVzdEN1c3RvbVR5cGluZ3NEaXI6IEFic1Bvc2l4UGF0aCA9IHBhdGgucG9zaXguam9pbihkaXN0LmRpc3REaXIsIFwiX2N1c3RvbS10eXBpbmdzXCIpO1xuICAgICAgICBjdXN0b21UeXBpbmdzRGlyID0gZGVzdEN1c3RvbVR5cGluZ3NEaXI7XG4gICAgICAgIGNvcHlUYXNrcy5wdXNoKG5hbWVUYXNrKFxuICAgICAgICAgIGAke3RhcmdldC5uYW1lfTpkaXN0OmNvcHk6Y3VzdG9tLXR5cGluZ3NgLFxuICAgICAgICAgICgpOiBOb2RlSlMuUmVhZGFibGVTdHJlYW0gPT4ge1xuICAgICAgICAgICAgcmV0dXJuIGd1bHBcbiAgICAgICAgICAgICAgLnNyYyhbcGF0aC5wb3NpeC5qb2luKHNyY0N1c3RvbVR5cGluZ3NEaXIsIFwiKiovKi5kLnRzXCIpXSwge2Jhc2U6IHNyY0N1c3RvbVR5cGluZ3NEaXJ9KVxuICAgICAgICAgICAgICAucGlwZShndWxwLmRlc3QoZGVzdEN1c3RvbVR5cGluZ3NEaXIhKSk7XG4gICAgICAgICAgfSxcbiAgICAgICAgKSk7XG4gICAgICB9XG5cbiAgICAgIC8vIGRpc3Q6Y29weTpkaXN0XG4gICAgICBpZiAodGFyZ2V0LmRpc3QuY29weSAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICAgIGNvbnN0IFtjb3B5QmFzZVRhc2ssIGNvcHlCYXNlV2F0Y2hUYXNrXTogW1Rhc2tGdW5jdGlvbiwgVGFza0Z1bmN0aW9uXSA9IGdldENvcHkoXG4gICAgICAgICAgZ3VscCxcbiAgICAgICAgICB0YXJnZXQucHJvamVjdC5hYnNSb290LFxuICAgICAgICAgIHRhcmdldC5kaXN0LmRpc3REaXIsXG4gICAgICAgICAgdGFyZ2V0LmRpc3QuY29weSxcbiAgICAgICAgKTtcbiAgICAgICAgY29weVRhc2tzLnB1c2gobmFtZVRhc2soYCR7dGFyZ2V0Lm5hbWV9OmRpc3Q6Y29weTpkaXN0YCwgY29weUJhc2VUYXNrKSk7XG4gICAgICB9XG4gICAgfVxuXG4gICAgLy8gZGlzdDpjb3B5OmxpYlxuICAgIGlmICh0YXJnZXQuY29weSAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICBjb25zdCBbY29weUJhc2VUYXNrLCBjb3B5QmFzZVdhdGNoVGFza106IFtUYXNrRnVuY3Rpb24sIFRhc2tGdW5jdGlvbl0gPSBnZXRDb3B5KFxuICAgICAgICBndWxwLFxuICAgICAgICB0YXJnZXQuc3JjRGlyLFxuICAgICAgICB0YXJnZXQuZGlzdC5kaXN0RGlyLFxuICAgICAgICB0YXJnZXQuY29weSxcbiAgICAgICk7XG4gICAgICBjb3B5VGFza3MucHVzaChuYW1lVGFzayhgJHt0YXJnZXQubmFtZX06ZGlzdDpjb3B5OmxpYmAsIGNvcHlCYXNlVGFzaykpO1xuICAgIH1cblxuICAgIHJlc3VsdC5kaXN0Q29weSA9IG5hbWVUYXNrKGAke3RhcmdldC5uYW1lfTpkaXN0OmNvcHlgLCBndWxwLnBhcmFsbGVsKGNvcHlUYXNrcykpO1xuXG4gICAgLy8gUmVzb2x2ZSB0c2NvbmZpZyBmb3IgYGRpc3RgXG4gICAgY29uc3QgdHNjb25maWdKc29uOiBBYnNQb3NpeFBhdGggfCBudWxsID0gdGFyZ2V0LnRzY29uZmlnSnNvbiAhPT0gbnVsbCA/XG4gICAgICBwYXRoLnBvc2l4LmpvaW4oc3JjRGlyLCBcInRzY29uZmlnLmpzb25cIikgOlxuICAgICAgbnVsbDtcbiAgICBsZXQgc2NyaXB0czogc3RyaW5nW10gPSBbXTtcbiAgICBpZiAoc3JjRGlyICE9PSB0YXJnZXQuc3JjRGlyKSB7XG4gICAgICBmb3IgKGNvbnN0IHNjcmlwdCBvZiB0YXJnZXQuc2NyaXB0cykge1xuICAgICAgICBzY3JpcHRzLnB1c2goXG4gICAgICAgICAgbWF0Y2hlci5hc1N0cmluZyhtYXRjaGVyLmpvaW4oc3JjRGlyLCBtYXRjaGVyLnJlbGF0aXZlKHRhcmdldC5zcmNEaXIsIG5ldyBNaW5pbWF0Y2goc2NyaXB0KSkpKSxcbiAgICAgICAgKTtcbiAgICAgIH1cbiAgICB9IGVsc2Uge1xuICAgICAgc2NyaXB0cyA9IFsuLi50YXJnZXQuc2NyaXB0c107XG4gICAgfVxuXG4gICAgY29uc3QgdHNPcHRpb25zOiBUeXBlc2NyaXB0Q29uZmlnID0ge1xuICAgICAgdHNjT3B0aW9uczogdGFyZ2V0LnRzY09wdGlvbnMsXG4gICAgICB0c2NvbmZpZ0pzb24sXG4gICAgICBjdXN0b21UeXBpbmdzRGlyLFxuICAgICAgcGFja2FnZUpzb246IHRhcmdldC5wcm9qZWN0LmFic1BhY2thZ2VKc29uLFxuICAgICAgYnVpbGREaXI6IGRpc3QuZGlzdERpcixcbiAgICAgIHNyY0RpcixcbiAgICAgIHNjcmlwdHMsXG4gICAgICBvdXRNb2R1bGVzOiB0YXJnZXQub3V0TW9kdWxlcyxcbiAgICB9O1xuXG4gICAgLy8gZGlzdDpzY3JpcHRzXG4gICAgZGlzdFRhc2tzLnB1c2gobmFtZVRhc2soXG4gICAgICBgJHt0YXJnZXQubmFtZX06ZGlzdDpzY3JpcHRzYCxcbiAgICAgIGd1bHAuc2VyaWVzKHJlc3VsdC5kaXN0Q29weSwgZ2V0QnVpbGRUeXBlc2NyaXB0VGFzayhndWxwLCB0c09wdGlvbnMpKSxcbiAgICApKTtcblxuICAgIC8vIGRpc3Q6cGFja2FnZS5qc29uXG4gICAge1xuICAgICAgYXN5bmMgZnVuY3Rpb24gZGlzdFBhY2thZ2VKc29uVGFzaygpOiBQcm9taXNlPE5vZGVKUy5SZWFkYWJsZVN0cmVhbT4ge1xuICAgICAgICBsZXQgcGtnOiBQYWNrYWdlSnNvbiA9IGF3YWl0IHJlYWRKc29uRmlsZSh0YXJnZXQucHJvamVjdC5hYnNQYWNrYWdlSnNvbik7XG4gICAgICAgIGlmICh0eXBlb2YgdGFyZ2V0Lm1haW5Nb2R1bGUgPT09IFwic3RyaW5nXCIpIHtcbiAgICAgICAgICBwa2cubWFpbiA9IHRhcmdldC5tYWluTW9kdWxlO1xuICAgICAgICAgIHBrZy50eXBlcyA9IGAke3RhcmdldC5tYWluTW9kdWxlfS5kLnRzYDtcbiAgICAgICAgfVxuICAgICAgICBwa2cuZ2l0SGVhZCA9IGF3YWl0IGdldEhlYWRIYXNoKCk7XG4gICAgICAgIHBrZyA9IGRpc3QucGFja2FnZUpzb25NYXAocGtnKTtcblxuICAgICAgICByZXR1cm4gZ3VscEJ1ZmZlclNyYyhcInBhY2thZ2UuanNvblwiLCBCdWZmZXIuZnJvbShKU09OLnN0cmluZ2lmeShwa2csIG51bGwsIDIpKSlcbiAgICAgICAgICAucGlwZShndWxwLmRlc3QoZGlzdC5kaXN0RGlyKSk7XG4gICAgICB9XG5cbiAgICAgIHJlc3VsdC5kaXN0UGFja2FnZUpzb24gPSBuYW1lVGFzayhgJHt0YXJnZXQubmFtZX06ZGlzdDpwYWNrYWdlLmpzb25gLCBkaXN0UGFja2FnZUpzb25UYXNrKTtcbiAgICAgIGRpc3RUYXNrcy5wdXNoKHJlc3VsdC5kaXN0UGFja2FnZUpzb24pO1xuICAgIH1cblxuICAgIGNvbnN0IGRpc3RUYXNrOiBUYXNrRnVuY3Rpb24gPSByZXN1bHQuY2xlYW4gIT09IHVuZGVmaW5lZCA/XG4gICAgICBndWxwLnNlcmllcyhyZXN1bHQuY2xlYW4sIGd1bHAucGFyYWxsZWwoZGlzdFRhc2tzKSkgOlxuICAgICAgZ3VscC5wYXJhbGxlbChkaXN0VGFza3MpO1xuICAgIHJlc3VsdC5kaXN0ID0gbmFtZVRhc2soYCR7dGFyZ2V0Lm5hbWV9OmRpc3RgLCBkaXN0VGFzayk7XG5cbiAgICBpZiAoZGlzdC5ucG1QdWJsaXNoICE9PSB1bmRlZmluZWQpIHtcbiAgICAgIGNvbnN0IG5wbVB1Ymxpc2hPcHRpb25zOiBOcG1QdWJsaXNoT3B0aW9ucyA9IGRpc3QubnBtUHVibGlzaDtcbiAgICAgIGNvbnN0IG5wbVB1Ymxpc2hUYXNrOiBUYXNrRnVuY3Rpb24gPSBhc3luYyAoKTogUHJvbWlzZTx2b2lkPiA9PiB7XG4gICAgICAgIHJldHVybiBucG1QdWJsaXNoKHtcbiAgICAgICAgICAuLi5ucG1QdWJsaXNoT3B0aW9ucyxcbiAgICAgICAgICBkaXJlY3Rvcnk6IGRpc3QuZGlzdERpcixcbiAgICAgICAgfSk7XG4gICAgICB9O1xuICAgICAgbnBtUHVibGlzaFRhc2suZGlzcGxheU5hbWUgPSBgJHt0YXJnZXQubmFtZX06ZGlzdDpwdWJsaXNoYDtcbiAgICAgIGd1bHAudGFzayhucG1QdWJsaXNoVGFzayk7XG4gICAgICByZXN1bHQuZGlzdFB1Ymxpc2ggPSBuYW1lVGFzayhgJHt0YXJnZXQubmFtZX06ZGlzdDpwdWJsaXNoYCwgZ3VscC5zZXJpZXMoZGlzdFRhc2ssIG5wbVB1Ymxpc2hUYXNrKSk7XG4gICAgfVxuICB9XG5cbiAgcmV0dXJuIHJlc3VsdDtcbn1cblxuLyoqXG4gKiBHZW5lcmF0ZXMgYW5kIHJlZ2lzdGVycyBndWxwIHRhc2tzIGZvciB0aGUgcHJvdmlkZWQgbGliIHRhcmdldC5cbiAqXG4gKiBAcGFyYW0gZ3VscCBHdWxwIGluc3RhbmNlIHdoZXJlIHRoZSB0YXNrcyB3aWxsIGJlIHJlZ2lzdGVyZWQuXG4gKiBAcGFyYW0gdGFyZ2V0T3B0aW9ucyBUYXJnZXQgY29uZmlndXJhdGlvbi5cbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIHJlZ2lzdGVyTGliVGFza3MoZ3VscDogR3VscCwgdGFyZ2V0T3B0aW9uczogTGliVGFyZ2V0KTogTGliVGFza3Mge1xuICBjb25zdCB0YXNrczogTGliVGFza3MgPSBnZW5lcmF0ZUxpYlRhc2tzKGd1bHAsIHRhcmdldE9wdGlvbnMpO1xuICBmb3IgKGNvbnN0IGtleSBpbiB0YXNrcykge1xuICAgIGNvbnN0IHRhc2s6IFRhc2tGdW5jdGlvbiB8IHVuZGVmaW5lZCA9ICg8YW55PiB0YXNrcylba2V5XTtcbiAgICBpZiAodGFzayAhPT0gdW5kZWZpbmVkKSB7XG4gICAgICBndWxwLnRhc2sodGFzayk7XG4gICAgfVxuICB9XG4gIHJldHVybiB0YXNrcztcbn1cbiJdLCJzb3VyY2VSb290IjoiLi4ifQ==