1 | ;
|
2 | var _a;
|
3 | Object.defineProperty(exports, "__esModule", { value: true });
|
4 | exports.AssetStaging = void 0;
|
5 | const jsiiDeprecationWarnings = require("../.warnings.jsii.js");
|
6 | const JSII_RTTI_SYMBOL_1 = Symbol.for("jsii.rtti");
|
7 | const crypto = require("crypto");
|
8 | const os = require("os");
|
9 | const path = require("path");
|
10 | const cxapi = require("@aws-cdk/cx-api");
|
11 | const fs = require("fs-extra");
|
12 | const assets_1 = require("./assets");
|
13 | const bundling_1 = require("./bundling");
|
14 | const fs_1 = require("./fs");
|
15 | const names_1 = require("./names");
|
16 | const cache_1 = require("./private/cache");
|
17 | const stack_1 = require("./stack");
|
18 | const stage_1 = require("./stage");
|
19 | // v2 - keep this import as a separate section to reduce merge conflict when forward merging with the v2 branch.
|
20 | // eslint-disable-next-line
|
21 | const construct_compat_1 = require("./construct-compat");
|
22 | const ARCHIVE_EXTENSIONS = ['.zip', '.jar'];
|
23 | /**
|
24 | * Stages a file or directory from a location on the file system into a staging
|
25 | * directory.
|
26 | *
|
27 | * This is controlled by the context key 'aws:cdk:asset-staging' and enabled
|
28 | * by the CLI by default in order to ensure that when the CDK app exists, all
|
29 | * assets are available for deployment. Otherwise, if an app references assets
|
30 | * in temporary locations, those will not be available when it exists (see
|
31 | * https://github.com/aws/aws-cdk/issues/1716).
|
32 | *
|
33 | * The `stagedPath` property is a stringified token that represents the location
|
34 | * of the file or directory after staging. It will be resolved only during the
|
35 | * "prepare" stage and may be either the original path or the staged path
|
36 | * depending on the context setting.
|
37 | *
|
38 | * The file/directory are staged based on their content hash (fingerprint). This
|
39 | * means that only if content was changed, copy will happen.
|
40 | */
|
41 | class AssetStaging extends construct_compat_1.Construct {
|
42 | constructor(scope, id, props) {
|
43 | var _b;
|
44 | super(scope, id);
|
45 | try {
|
46 | jsiiDeprecationWarnings._aws_cdk_core_AssetStagingProps(props);
|
47 | }
|
48 | catch (error) {
|
49 | if (process.env.JSII_DEBUG !== "1" && error.name === "DeprecationError") {
|
50 | Error.captureStackTrace(error, this.constructor);
|
51 | }
|
52 | throw error;
|
53 | }
|
54 | this.sourcePath = path.resolve(props.sourcePath);
|
55 | this.fingerprintOptions = props;
|
56 | if (!fs.existsSync(this.sourcePath)) {
|
57 | throw new Error(`Cannot find asset at ${this.sourcePath}`);
|
58 | }
|
59 | this.sourceStats = fs.statSync(this.sourcePath);
|
60 | const outdir = (_b = stage_1.Stage.of(this)) === null || _b === void 0 ? void 0 : _b.assetOutdir;
|
61 | if (!outdir) {
|
62 | throw new Error('unable to determine cloud assembly asset output directory. Assets must be defined indirectly within a "Stage" or an "App" scope');
|
63 | }
|
64 | this.assetOutdir = outdir;
|
65 | // Determine the hash type based on the props as props.assetHashType is
|
66 | // optional from a caller perspective.
|
67 | this.customSourceFingerprint = props.assetHash;
|
68 | this.hashType = determineHashType(props.assetHashType, this.customSourceFingerprint);
|
69 | // Decide what we're going to do, without actually doing it yet
|
70 | let stageThisAsset;
|
71 | let skip = false;
|
72 | if (props.bundling) {
|
73 | // Check if we actually have to bundle for this stack
|
74 | skip = !stack_1.Stack.of(this).bundlingRequired;
|
75 | const bundling = props.bundling;
|
76 | stageThisAsset = () => this.stageByBundling(bundling, skip);
|
77 | }
|
78 | else {
|
79 | stageThisAsset = () => this.stageByCopying();
|
80 | }
|
81 | // Calculate a cache key from the props. This way we can check if we already
|
82 | // staged this asset and reuse the result (e.g. the same asset with the same
|
83 | // configuration is used in multiple stacks). In this case we can completely
|
84 | // skip file system and bundling operations.
|
85 | //
|
86 | // The output directory and whether this asset is skipped or not should also be
|
87 | // part of the cache key to make sure we don't accidentally return the wrong
|
88 | // staged asset from the cache.
|
89 | this.cacheKey = calculateCacheKey({
|
90 | outdir: this.assetOutdir,
|
91 | sourcePath: path.resolve(props.sourcePath),
|
92 | bundling: props.bundling,
|
93 | assetHashType: this.hashType,
|
94 | customFingerprint: this.customSourceFingerprint,
|
95 | extraHash: props.extraHash,
|
96 | exclude: props.exclude,
|
97 | ignoreMode: props.ignoreMode,
|
98 | skip,
|
99 | });
|
100 | const staged = AssetStaging.assetCache.obtain(this.cacheKey, stageThisAsset);
|
101 | this.stagedPath = staged.stagedPath;
|
102 | this.absoluteStagedPath = staged.stagedPath;
|
103 | this.assetHash = staged.assetHash;
|
104 | this.packaging = staged.packaging;
|
105 | this.isArchive = staged.isArchive;
|
106 | }
|
107 | /**
|
108 | * Clears the asset hash cache
|
109 | */
|
110 | static clearAssetHashCache() {
|
111 | this.assetCache.clear();
|
112 | }
|
113 | /**
|
114 | * A cryptographic hash of the asset.
|
115 | *
|
116 | * @deprecated see `assetHash`.
|
117 | */
|
118 | get sourceHash() {
|
119 | try {
|
120 | jsiiDeprecationWarnings.print("@aws-cdk/core.AssetStaging#sourceHash", "see `assetHash`.");
|
121 | }
|
122 | catch (error) {
|
123 | if (process.env.JSII_DEBUG !== "1" && error.name === "DeprecationError") {
|
124 | Error.captureStackTrace(error, jsiiDeprecationWarnings.getPropertyDescriptor(this, "sourceHash").get);
|
125 | }
|
126 | throw error;
|
127 | }
|
128 | return this.assetHash;
|
129 | }
|
130 | /**
|
131 | * Return the path to the staged asset, relative to the Cloud Assembly (manifest) directory of the given stack
|
132 | *
|
133 | * Only returns a relative path if the asset was staged, returns an absolute path if
|
134 | * it was not staged.
|
135 | *
|
136 | * A bundled asset might end up in the outDir and still not count as
|
137 | * "staged"; if asset staging is disabled we're technically expected to
|
138 | * reference source directories, but we don't have a source directory for the
|
139 | * bundled outputs (as the bundle output is written to a temporary
|
140 | * directory). Nevertheless, we will still return an absolute path.
|
141 | *
|
142 | * A non-obvious directory layout may look like this:
|
143 | *
|
144 | * ```
|
145 | * CLOUD ASSEMBLY ROOT
|
146 | * +-- asset.12345abcdef/
|
147 | * +-- assembly-Stage
|
148 | * +-- MyStack.template.json
|
149 | * +-- MyStack.assets.json <- will contain { "path": "../asset.12345abcdef" }
|
150 | * ```
|
151 | */
|
152 | relativeStagedPath(stack) {
|
153 | var _b;
|
154 | try {
|
155 | jsiiDeprecationWarnings._aws_cdk_core_Stack(stack);
|
156 | }
|
157 | catch (error) {
|
158 | if (process.env.JSII_DEBUG !== "1" && error.name === "DeprecationError") {
|
159 | Error.captureStackTrace(error, this.relativeStagedPath);
|
160 | }
|
161 | throw error;
|
162 | }
|
163 | const asmManifestDir = (_b = stage_1.Stage.of(stack)) === null || _b === void 0 ? void 0 : _b.outdir;
|
164 | if (!asmManifestDir) {
|
165 | return this.stagedPath;
|
166 | }
|
167 | const isOutsideAssetDir = path.relative(this.assetOutdir, this.stagedPath).startsWith('..');
|
168 | if (isOutsideAssetDir || this.stagingDisabled) {
|
169 | return this.stagedPath;
|
170 | }
|
171 | return path.relative(asmManifestDir, this.stagedPath);
|
172 | }
|
173 | /**
|
174 | * Stage the source to the target by copying
|
175 | *
|
176 | * Optionally skip if staging is disabled, in which case we pretend we did something but we don't really.
|
177 | */
|
178 | stageByCopying() {
|
179 | const assetHash = this.calculateHash(this.hashType);
|
180 | const stagedPath = this.stagingDisabled
|
181 | ? this.sourcePath
|
182 | : path.resolve(this.assetOutdir, renderAssetFilename(assetHash, path.extname(this.sourcePath)));
|
183 | if (!this.sourceStats.isDirectory() && !this.sourceStats.isFile()) {
|
184 | throw new Error(`Asset ${this.sourcePath} is expected to be either a directory or a regular file`);
|
185 | }
|
186 | this.stageAsset(this.sourcePath, stagedPath, 'copy');
|
187 | return {
|
188 | assetHash,
|
189 | stagedPath,
|
190 | packaging: this.sourceStats.isDirectory() ? assets_1.FileAssetPackaging.ZIP_DIRECTORY : assets_1.FileAssetPackaging.FILE,
|
191 | isArchive: this.sourceStats.isDirectory() || ARCHIVE_EXTENSIONS.includes(path.extname(this.sourcePath).toLowerCase()),
|
192 | };
|
193 | }
|
194 | /**
|
195 | * Stage the source to the target by bundling
|
196 | *
|
197 | * Optionally skip, in which case we pretend we did something but we don't really.
|
198 | */
|
199 | stageByBundling(bundling, skip) {
|
200 | var _b;
|
201 | if (!this.sourceStats.isDirectory()) {
|
202 | throw new Error(`Asset ${this.sourcePath} is expected to be a directory when bundling`);
|
203 | }
|
204 | if (skip) {
|
205 | // We should have bundled, but didn't to save time. Still pretend to have a hash.
|
206 | // If the asset uses OUTPUT or BUNDLE, we use a CUSTOM hash to avoid fingerprinting
|
207 | // a potentially very large source directory. Other hash types are kept the same.
|
208 | let hashType = this.hashType;
|
209 | if (hashType === assets_1.AssetHashType.OUTPUT || hashType === assets_1.AssetHashType.BUNDLE) {
|
210 | this.customSourceFingerprint = names_1.Names.uniqueId(this);
|
211 | hashType = assets_1.AssetHashType.CUSTOM;
|
212 | }
|
213 | return {
|
214 | assetHash: this.calculateHash(hashType, bundling),
|
215 | stagedPath: this.sourcePath,
|
216 | packaging: assets_1.FileAssetPackaging.ZIP_DIRECTORY,
|
217 | isArchive: true,
|
218 | };
|
219 | }
|
220 | // Try to calculate assetHash beforehand (if we can)
|
221 | let assetHash = this.hashType === assets_1.AssetHashType.SOURCE || this.hashType === assets_1.AssetHashType.CUSTOM
|
222 | ? this.calculateHash(this.hashType, bundling)
|
223 | : undefined;
|
224 | const bundleDir = this.determineBundleDir(this.assetOutdir, assetHash);
|
225 | this.bundle(bundling, bundleDir);
|
226 | // Check bundling output content and determine if we will need to archive
|
227 | const bundlingOutputType = (_b = bundling.outputType) !== null && _b !== void 0 ? _b : bundling_1.BundlingOutput.AUTO_DISCOVER;
|
228 | const bundledAsset = determineBundledAsset(bundleDir, bundlingOutputType);
|
229 | // Calculate assetHash afterwards if we still must
|
230 | assetHash = assetHash !== null && assetHash !== void 0 ? assetHash : this.calculateHash(this.hashType, bundling, bundledAsset.path);
|
231 | const stagedPath = path.resolve(this.assetOutdir, renderAssetFilename(assetHash, bundledAsset.extension));
|
232 | this.stageAsset(bundledAsset.path, stagedPath, 'move');
|
233 | // If bundling produced a single archive file we "touch" this file in the bundling
|
234 | // directory after it has been moved to the staging directory. This way if bundling
|
235 | // is skipped because the bundling directory already exists we can still determine
|
236 | // the correct packaging type.
|
237 | if (bundledAsset.packaging === assets_1.FileAssetPackaging.FILE) {
|
238 | fs.closeSync(fs.openSync(bundledAsset.path, 'w'));
|
239 | }
|
240 | return {
|
241 | assetHash,
|
242 | stagedPath,
|
243 | packaging: bundledAsset.packaging,
|
244 | isArchive: true,
|
245 | };
|
246 | }
|
247 | /**
|
248 | * Whether staging has been disabled
|
249 | */
|
250 | get stagingDisabled() {
|
251 | return !!this.node.tryGetContext(cxapi.DISABLE_ASSET_STAGING_CONTEXT);
|
252 | }
|
253 | /**
|
254 | * Copies or moves the files from sourcePath to targetPath.
|
255 | *
|
256 | * Moving implies the source directory is temporary and can be trashed.
|
257 | *
|
258 | * Will not do anything if source and target are the same.
|
259 | */
|
260 | stageAsset(sourcePath, targetPath, style) {
|
261 | // Is the work already done?
|
262 | const isAlreadyStaged = fs.existsSync(targetPath);
|
263 | if (isAlreadyStaged) {
|
264 | if (style === 'move' && sourcePath !== targetPath) {
|
265 | fs.removeSync(sourcePath);
|
266 | }
|
267 | return;
|
268 | }
|
269 | // Moving can be done quickly
|
270 | if (style == 'move') {
|
271 | fs.renameSync(sourcePath, targetPath);
|
272 | return;
|
273 | }
|
274 | // Copy file/directory to staging directory
|
275 | if (this.sourceStats.isFile()) {
|
276 | fs.copyFileSync(sourcePath, targetPath);
|
277 | }
|
278 | else if (this.sourceStats.isDirectory()) {
|
279 | fs.mkdirSync(targetPath);
|
280 | fs_1.FileSystem.copyDirectory(sourcePath, targetPath, this.fingerprintOptions);
|
281 | }
|
282 | else {
|
283 | throw new Error(`Unknown file type: ${sourcePath}`);
|
284 | }
|
285 | }
|
286 | /**
|
287 | * Determine the directory where we're going to write the bundling output
|
288 | *
|
289 | * This is the target directory where we're going to write the staged output
|
290 | * files if we can (if the hash is fully known), or a temporary directory
|
291 | * otherwise.
|
292 | */
|
293 | determineBundleDir(outdir, sourceHash) {
|
294 | if (sourceHash) {
|
295 | return path.resolve(outdir, renderAssetFilename(sourceHash));
|
296 | }
|
297 | // When the asset hash isn't known in advance, bundler outputs to an
|
298 | // intermediate directory named after the asset's cache key
|
299 | return path.resolve(outdir, `bundling-temp-${this.cacheKey}`);
|
300 | }
|
301 | /**
|
302 | * Bundles an asset to the given directory
|
303 | *
|
304 | * If the given directory already exists, assume that everything's already
|
305 | * in order and don't do anything.
|
306 | *
|
307 | * @param options Bundling options
|
308 | * @param bundleDir Where to create the bundle directory
|
309 | * @returns The fully resolved bundle output directory.
|
310 | */
|
311 | bundle(options, bundleDir) {
|
312 | var _b, _c, _d, _e;
|
313 | if (fs.existsSync(bundleDir)) {
|
314 | return;
|
315 | }
|
316 | fs.ensureDirSync(bundleDir);
|
317 | // Chmod the bundleDir to full access.
|
318 | fs.chmodSync(bundleDir, 0o777);
|
319 | // Always mount input and output dir
|
320 | const volumes = [
|
321 | {
|
322 | hostPath: this.sourcePath,
|
323 | containerPath: AssetStaging.BUNDLING_INPUT_DIR,
|
324 | },
|
325 | {
|
326 | hostPath: bundleDir,
|
327 | containerPath: AssetStaging.BUNDLING_OUTPUT_DIR,
|
328 | },
|
329 | ...(_b = options.volumes) !== null && _b !== void 0 ? _b : [],
|
330 | ];
|
331 | let localBundling;
|
332 | try {
|
333 | process.stderr.write(`Bundling asset ${this.node.path}...\n`);
|
334 | localBundling = (_c = options.local) === null || _c === void 0 ? void 0 : _c.tryBundle(bundleDir, options);
|
335 | if (!localBundling) {
|
336 | let user;
|
337 | if (options.user) {
|
338 | user = options.user;
|
339 | }
|
340 | else { // Default to current user
|
341 | const userInfo = os.userInfo();
|
342 | user = userInfo.uid !== -1 // uid is -1 on Windows
|
343 | ? `${userInfo.uid}:${userInfo.gid}`
|
344 | : '1000:1000';
|
345 | }
|
346 | options.image.run({
|
347 | command: options.command,
|
348 | user,
|
349 | volumes,
|
350 | environment: options.environment,
|
351 | workingDirectory: (_d = options.workingDirectory) !== null && _d !== void 0 ? _d : AssetStaging.BUNDLING_INPUT_DIR,
|
352 | securityOpt: (_e = options.securityOpt) !== null && _e !== void 0 ? _e : '',
|
353 | });
|
354 | }
|
355 | }
|
356 | catch (err) {
|
357 | // When bundling fails, keep the bundle output for diagnosability, but
|
358 | // rename it out of the way so that the next run doesn't assume it has a
|
359 | // valid bundleDir.
|
360 | const bundleErrorDir = bundleDir + '-error';
|
361 | if (fs.existsSync(bundleErrorDir)) {
|
362 | // Remove the last bundleErrorDir.
|
363 | fs.removeSync(bundleErrorDir);
|
364 | }
|
365 | fs.renameSync(bundleDir, bundleErrorDir);
|
366 | throw new Error(`Failed to bundle asset ${this.node.path}, bundle output is located at ${bundleErrorDir}: ${err}`);
|
367 | }
|
368 | if (fs_1.FileSystem.isEmpty(bundleDir)) {
|
369 | const outputDir = localBundling ? bundleDir : AssetStaging.BUNDLING_OUTPUT_DIR;
|
370 | throw new Error(`Bundling did not produce any output. Check that content is written to ${outputDir}.`);
|
371 | }
|
372 | }
|
373 | calculateHash(hashType, bundling, outputDir) {
|
374 | var _b;
|
375 | // When bundling a CUSTOM or SOURCE asset hash type, we want the hash to include
|
376 | // the bundling configuration. We handle CUSTOM and bundled SOURCE hash types
|
377 | // as a special case to preserve existing user asset hashes in all other cases.
|
378 | if (hashType == assets_1.AssetHashType.CUSTOM || (hashType == assets_1.AssetHashType.SOURCE && bundling)) {
|
379 | const hash = crypto.createHash('sha256');
|
380 | // if asset hash is provided by user, use it, otherwise fingerprint the source.
|
381 | hash.update((_b = this.customSourceFingerprint) !== null && _b !== void 0 ? _b : fs_1.FileSystem.fingerprint(this.sourcePath, this.fingerprintOptions));
|
382 | // If we're bundling an asset, include the bundling configuration in the hash
|
383 | if (bundling) {
|
384 | hash.update(JSON.stringify(bundling));
|
385 | }
|
386 | return hash.digest('hex');
|
387 | }
|
388 | switch (hashType) {
|
389 | case assets_1.AssetHashType.SOURCE:
|
390 | return fs_1.FileSystem.fingerprint(this.sourcePath, this.fingerprintOptions);
|
391 | case assets_1.AssetHashType.BUNDLE:
|
392 | case assets_1.AssetHashType.OUTPUT:
|
393 | if (!outputDir) {
|
394 | throw new Error(`Cannot use \`${hashType}\` hash type when \`bundling\` is not specified.`);
|
395 | }
|
396 | return fs_1.FileSystem.fingerprint(outputDir, this.fingerprintOptions);
|
397 | default:
|
398 | throw new Error('Unknown asset hash type.');
|
399 | }
|
400 | }
|
401 | }
|
402 | exports.AssetStaging = AssetStaging;
|
403 | _a = JSII_RTTI_SYMBOL_1;
|
404 | AssetStaging[_a] = { fqn: "@aws-cdk/core.AssetStaging", version: "1.156.1" };
|
405 | /**
|
406 | * The directory inside the bundling container into which the asset sources will be mounted.
|
407 | */
|
408 | AssetStaging.BUNDLING_INPUT_DIR = '/asset-input';
|
409 | /**
|
410 | * The directory inside the bundling container into which the bundled output should be written.
|
411 | */
|
412 | AssetStaging.BUNDLING_OUTPUT_DIR = '/asset-output';
|
413 | /**
|
414 | * Cache of asset hashes based on asset configuration to avoid repeated file
|
415 | * system and bundling operations.
|
416 | */
|
417 | AssetStaging.assetCache = new cache_1.Cache();
|
418 | function renderAssetFilename(assetHash, extension = '') {
|
419 | return `asset.${assetHash}${extension}`;
|
420 | }
|
421 | /**
|
422 | * Determines the hash type from user-given prop values.
|
423 | *
|
424 | * @param assetHashType Asset hash type construct prop
|
425 | * @param customSourceFingerprint Asset hash seed given in the construct props
|
426 | */
|
427 | function determineHashType(assetHashType, customSourceFingerprint) {
|
428 | const hashType = customSourceFingerprint
|
429 | ? (assetHashType !== null && assetHashType !== void 0 ? assetHashType : assets_1.AssetHashType.CUSTOM)
|
430 | : (assetHashType !== null && assetHashType !== void 0 ? assetHashType : assets_1.AssetHashType.SOURCE);
|
431 | if (customSourceFingerprint && hashType !== assets_1.AssetHashType.CUSTOM) {
|
432 | throw new Error(`Cannot specify \`${assetHashType}\` for \`assetHashType\` when \`assetHash\` is specified. Use \`CUSTOM\` or leave \`undefined\`.`);
|
433 | }
|
434 | if (hashType === assets_1.AssetHashType.CUSTOM && !customSourceFingerprint) {
|
435 | throw new Error('`assetHash` must be specified when `assetHashType` is set to `AssetHashType.CUSTOM`.');
|
436 | }
|
437 | return hashType;
|
438 | }
|
439 | /**
|
440 | * Calculates a cache key from the props. Normalize by sorting keys.
|
441 | */
|
442 | function calculateCacheKey(props) {
|
443 | return crypto.createHash('sha256')
|
444 | .update(JSON.stringify(sortObject(props)))
|
445 | .digest('hex');
|
446 | }
|
447 | /**
|
448 | * Recursively sort object keys
|
449 | */
|
450 | function sortObject(object) {
|
451 | if (typeof object !== 'object' || object instanceof Array) {
|
452 | return object;
|
453 | }
|
454 | const ret = {};
|
455 | for (const key of Object.keys(object).sort()) {
|
456 | ret[key] = sortObject(object[key]);
|
457 | }
|
458 | return ret;
|
459 | }
|
460 | /**
|
461 | * Returns the single archive file of a directory or undefined
|
462 | */
|
463 | function singleArchiveFile(directory) {
|
464 | if (!fs.existsSync(directory)) {
|
465 | throw new Error(`Directory ${directory} does not exist.`);
|
466 | }
|
467 | if (!fs.statSync(directory).isDirectory()) {
|
468 | throw new Error(`${directory} is not a directory.`);
|
469 | }
|
470 | const content = fs.readdirSync(directory);
|
471 | if (content.length === 1) {
|
472 | const file = path.join(directory, content[0]);
|
473 | const extension = path.extname(content[0]).toLowerCase();
|
474 | if (fs.statSync(file).isFile() && ARCHIVE_EXTENSIONS.includes(extension)) {
|
475 | return file;
|
476 | }
|
477 | }
|
478 | return undefined;
|
479 | }
|
480 | /**
|
481 | * Returns the bundled asset to use based on the content of the bundle directory
|
482 | * and the type of output.
|
483 | */
|
484 | function determineBundledAsset(bundleDir, outputType) {
|
485 | const archiveFile = singleArchiveFile(bundleDir);
|
486 | // auto-discover means that if there is an archive file, we take it as the
|
487 | // bundle, otherwise, we will archive here.
|
488 | if (outputType === bundling_1.BundlingOutput.AUTO_DISCOVER) {
|
489 | outputType = archiveFile ? bundling_1.BundlingOutput.ARCHIVED : bundling_1.BundlingOutput.NOT_ARCHIVED;
|
490 | }
|
491 | switch (outputType) {
|
492 | case bundling_1.BundlingOutput.NOT_ARCHIVED:
|
493 | return { path: bundleDir, packaging: assets_1.FileAssetPackaging.ZIP_DIRECTORY };
|
494 | case bundling_1.BundlingOutput.ARCHIVED:
|
495 | if (!archiveFile) {
|
496 | throw new Error('Bundling output directory is expected to include only a single .zip or .jar file when `output` is set to `ARCHIVED`');
|
497 | }
|
498 | return { path: archiveFile, packaging: assets_1.FileAssetPackaging.FILE, extension: path.extname(archiveFile) };
|
499 | }
|
500 | }
|
501 | //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiYXNzZXQtc3RhZ2luZy5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbImFzc2V0LXN0YWdpbmcudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6Ijs7Ozs7O0FBQUEsaUNBQWlDO0FBQ2pDLHlCQUF5QjtBQUN6Qiw2QkFBNkI7QUFDN0IseUNBQXlDO0FBRXpDLCtCQUErQjtBQUMvQixxQ0FBMkU7QUFDM0UseUNBQTZEO0FBQzdELDZCQUFzRDtBQUN0RCxtQ0FBZ0M7QUFDaEMsMkNBQXdDO0FBQ3hDLG1DQUFnQztBQUNoQyxtQ0FBZ0M7QUFFaEMsZ0hBQWdIO0FBQ2hILDJCQUEyQjtBQUMzQix5REFBZ0U7QUFFaEUsTUFBTSxrQkFBa0IsR0FBRyxDQUFDLE1BQU0sRUFBRSxNQUFNLENBQUMsQ0FBQztBQXFDNUM7Ozs7Ozs7Ozs7Ozs7Ozs7O0dBaUJHO0FBQ0gsTUFBYSxZQUFhLFNBQVEsNEJBQWE7SUF3RjdDLFlBQVksS0FBZ0IsRUFBRSxFQUFVLEVBQUUsS0FBd0I7O1FBQ2hFLEtBQUssQ0FBQyxLQUFLLEVBQUUsRUFBRSxDQUFDLENBQUM7Ozs7Ozs7Ozs7UUFFakIsSUFBSSxDQUFDLFVBQVUsR0FBRyxJQUFJLENBQUMsT0FBTyxDQUFDLEtBQUssQ0FBQyxVQUFVLENBQUMsQ0FBQztRQUNqRCxJQUFJLENBQUMsa0JBQWtCLEdBQUcsS0FBSyxDQUFDO1FBRWhDLElBQUksQ0FBQyxFQUFFLENBQUMsVUFBVSxDQUFDLElBQUksQ0FBQyxVQUFVLENBQUMsRUFBRTtZQUNuQyxNQUFNLElBQUksS0FBSyxDQUFDLHdCQUF3QixJQUFJLENBQUMsVUFBVSxFQUFFLENBQUMsQ0FBQztTQUM1RDtRQUVELElBQUksQ0FBQyxXQUFXLEdBQUcsRUFBRSxDQUFDLFFBQVEsQ0FBQyxJQUFJLENBQUMsVUFBVSxDQUFDLENBQUM7UUFFaEQsTUFBTSxNQUFNLFNBQUcsYUFBSyxDQUFDLEVBQUUsQ0FBQyxJQUFJLENBQUMsMENBQUUsV0FBVyxDQUFDO1FBQzNDLElBQUksQ0FBQyxN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TyxDQUFDLFdBQVcsQ0FBQyxFQUFFLENBQUM7S0FDMUc7QUFDSCxDQUFDIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0ICogYXMgY3J5cHRvIGZyb20gJ2NyeXB0byc7XG5pbXBvcnQgKiBhcyBvcyBmcm9tICdvcyc7XG5pbXBvcnQgKiBhcyBwYXRoIGZyb20gJ3BhdGgnO1xuaW1wb3J0ICogYXMgY3hhcGkgZnJvbSAnQGF3cy1jZGsvY3gtYXBpJztcbmltcG9ydCB7IENvbnN0cnVjdCB9IGZyb20gJ2NvbnN0cnVjdHMnO1xuaW1wb3J0ICogYXMgZnMgZnJvbSAnZnMtZXh0cmEnO1xuaW1wb3J0IHsgQXNzZXRIYXNoVHlwZSwgQXNzZXRPcHRpb25zLCBGaWxlQXNzZXRQYWNrYWdpbmcgfSBmcm9tICcuL2Fzc2V0cyc7XG5pbXBvcnQgeyBCdW5kbGluZ09wdGlvbnMsIEJ1bmRsaW5nT3V0cHV0IH0gZnJvbSAnLi9idW5kbGluZyc7XG5pbXBvcnQgeyBGaWxlU3lzdGVtLCBGaW5nZXJwcmludE9wdGlvbnMgfSBmcm9tICcuL2ZzJztcbmltcG9ydCB7IE5hbWVzIH0gZnJvbSAnLi9uYW1lcyc7XG5pbXBvcnQgeyBDYWNoZSB9IGZyb20gJy4vcHJpdmF0ZS9jYWNoZSc7XG5pbXBvcnQgeyBTdGFjayB9IGZyb20gJy4vc3RhY2snO1xuaW1wb3J0IHsgU3RhZ2UgfSBmcm9tICcuL3N0YWdlJztcblxuLy8gdjIgLSBrZWVwIHRoaXMgaW1wb3J0IGFzIGEgc2VwYXJhdGUgc2VjdGlvbiB0byByZWR1Y2UgbWVyZ2UgY29uZmxpY3Qgd2hlbiBmb3J3YXJkIG1lcmdpbmcgd2l0aCB0aGUgdjIgYnJhbmNoLlxuLy8gZXNsaW50LWRpc2FibGUtbmV4dC1saW5lXG5pbXBvcnQgeyBDb25zdHJ1Y3QgYXMgQ29yZUNvbnN0cnVjdCB9IGZyb20gJy4vY29uc3RydWN0LWNvbXBhdCc7XG5cbmNvbnN0IEFSQ0hJVkVfRVhURU5TSU9OUyA9IFsnLnppcCcsICcuamFyJ107XG5cbi8qKlxuICogQSBwcmV2aW91c2x5IHN0YWdlZCBhc3NldFxuICovXG5pbnRlcmZhY2UgU3RhZ2VkQXNzZXQge1xuICAvKipcbiAgICogVGhlIHBhdGggd2hlcmUgd2Ugd3JvdGUgdGhpcyBhc3NldCBwcmV2aW91c2x5XG4gICAqL1xuICByZWFkb25seSBzdGFnZWRQYXRoOiBzdHJpbmc7XG5cbiAgLyoqXG4gICAqIFRoZSBoYXNoIHdlIHVzZWQgcHJldmlvdXNseVxuICAgKi9cbiAgcmVhZG9ubHkgYXNzZXRIYXNoOiBzdHJpbmc7XG5cbiAgLyoqXG4gICAqIFRoZSBwYWNrYWdpbmcgb2YgdGhlIGFzc2V0XG4gICAqL1xuICByZWFkb25seSBwYWNrYWdpbmc6IEZpbGVBc3NldFBhY2thZ2luZyxcblxuICAvKipcbiAgICogV2hldGhlciB0aGlzIGFzc2V0IGlzIGFuIGFyY2hpdmVcbiAgICovXG4gIHJlYWRvbmx5IGlzQXJjaGl2ZTogYm9vbGVhbjtcbn1cblxuLyoqXG4gKiBJbml0aWFsaXphdGlvbiBwcm9wZXJ0aWVzIGZvciBgQXNzZXRTdGFnaW5nYC5cbiAqL1xuZXhwb3J0IGludGVyZmFjZSBBc3NldFN0YWdpbmdQcm9wcyBleHRlbmRzIEZpbmdlcnByaW50T3B0aW9ucywgQXNzZXRPcHRpb25zIHtcbiAgLyoqXG4gICAqIFRoZSBzb3VyY2UgZmlsZSBvciBkaXJlY3RvcnkgdG8gY29weSBmcm9tLlxuICAgKi9cbiAgcmVhZG9ubHkgc291cmNlUGF0aDogc3RyaW5nO1xufVxuXG4vKipcbiAqIFN0YWdlcyBhIGZpbGUgb3IgZGlyZWN0b3J5IGZyb20gYSBsb2NhdGlvbiBvbiB0aGUgZmlsZSBzeXN0ZW0gaW50byBhIHN0YWdpbmdcbiAqIGRpcmVjdG9yeS5cbiAqXG4gKiBUaGlzIGlzIGNvbnRyb2xsZWQgYnkgdGhlIGNvbnRleHQga2V5ICdhd3M6Y2RrOmFzc2V0LXN0YWdpbmcnIGFuZCBlbmFibGVkXG4gKiBieSB0aGUgQ0xJIGJ5IGRlZmF1bHQgaW4gb3JkZXIgdG8gZW5zdXJlIHRoYXQgd2hlbiB0aGUgQ0RLIGFwcCBleGlzdHMsIGFsbFxuICogYXNzZXRzIGFyZSBhdmFpbGFibGUgZm9yIGRlcGxveW1lbnQuIE90aGVyd2lzZSwgaWYgYW4gYXBwIHJlZmVyZW5jZXMgYXNzZXRzXG4gKiBpbiB0ZW1wb3JhcnkgbG9jYXRpb25zLCB0aG9zZSB3aWxsIG5vdCBiZSBhdmFpbGFibGUgd2hlbiBpdCBleGlzdHMgKHNlZVxuICogaHR0cHM6Ly9naXRodWIuY29tL2F3cy9hd3MtY2RrL2lzc3Vlcy8xNzE2KS5cbiAqXG4gKiBUaGUgYHN0YWdlZFBhdGhgIHByb3BlcnR5IGlzIGEgc3RyaW5naWZpZWQgdG9rZW4gdGhhdCByZXByZXNlbnRzIHRoZSBsb2NhdGlvblxuICogb2YgdGhlIGZpbGUgb3IgZGlyZWN0b3J5IGFmdGVyIHN0YWdpbmcuIEl0IHdpbGwgYmUgcmVzb2x2ZWQgb25seSBkdXJpbmcgdGhlXG4gKiBcInByZXBhcmVcIiBzdGFnZSBhbmQgbWF5IGJlIGVpdGhlciB0aGUgb3JpZ2luYWwgcGF0aCBvciB0aGUgc3RhZ2VkIHBhdGhcbiAqIGRlcGVuZGluZyBvbiB0aGUgY29udGV4dCBzZXR0aW5nLlxuICpcbiAqIFRoZSBmaWxlL2RpcmVjdG9yeSBhcmUgc3RhZ2VkIGJhc2VkIG9uIHRoZWlyIGNvbnRlbnQgaGFzaCAoZmluZ2VycHJpbnQpLiBUaGlzXG4gKiBtZWFucyB0aGF0IG9ubHkgaWYgY29udGVudCB3YXMgY2hhbmdlZCwgY29weSB3aWxsIGhhcHBlbi5cbiAqL1xuZXhwb3J0IGNsYXNzIEFzc2V0U3RhZ2luZyBleHRlbmRzIENvcmVDb25zdHJ1Y3Qge1xuICAvKipcbiAgICogVGhlIGRpcmVjdG9yeSBpbnNpZGUgdGhlIGJ1bmRsaW5nIGNvbnRhaW5lciBpbnRvIHdoaWNoIHRoZSBhc3NldCBzb3VyY2VzIHdpbGwgYmUgbW91bnRlZC5cbiAgICovXG4gIHB1YmxpYyBzdGF0aWMgcmVhZG9ubHkgQlVORExJTkdfSU5QVVRfRElSID0gJy9hc3NldC1pbnB1dCc7XG5cbiAgLyoqXG4gICAqIFRoZSBkaXJlY3RvcnkgaW5zaWRlIHRoZSBidW5kbGluZyBjb250YWluZXIgaW50byB3aGljaCB0aGUgYnVuZGxlZCBvdXRwdXQgc2hvdWxkIGJlIHdyaXR0ZW4uXG4gICAqL1xuICBwdWJsaWMgc3RhdGljIHJlYWRvbmx5IEJVTkRMSU5HX09VVFBVVF9ESVIgPSAnL2Fzc2V0LW91dHB1dCc7XG5cbiAgLyoqXG4gICAqIENsZWFycyB0aGUgYXNzZXQgaGFzaCBjYWNoZVxuICAgKi9cbiAgcHVibGljIHN0YXRpYyBjbGVhckFzc2V0SGFzaENhY2hlKCkge1xuICAgIHRoaXMuYXNzZXRDYWNoZS5jbGVhcigpO1xuICB9XG5cbiAgLyoqXG4gICAqIENhY2hlIG9mIGFzc2V0IGhhc2hlcyBiYXNlZCBvbiBhc3NldCBjb25maWd1cmF0aW9uIHRvIGF2b2lkIHJlcGVhdGVkIGZpbGVcbiAgICogc3lzdGVtIGFuZCBidW5kbGluZyBvcGVyYXRpb25zLlxuICAgKi9cbiAgcHJpdmF0ZSBzdGF0aWMgYXNzZXRDYWNoZSA9IG5ldyBDYWNoZTxTdGFnZWRBc3NldD4oKTtcblxuICAvKipcbiAgICogQWJzb2x1dGUgcGF0aCB0byB0aGUgYXNzZXQgZGF0YS5cbiAgICpcbiAgICogSWYgYXNzZXQgc3RhZ2luZyBpcyBkaXNhYmxlZCwgdGhpcyB3aWxsIGp1c3QgYmUgdGhlIHNvdXJjZSBwYXRoIG9yXG4gICAqIGEgdGVtcG9yYXJ5IGRpcmVjdG9yeSB1c2VkIGZvciBidW5kbGluZy5cbiAgICpcbiAgICogSWYgYXNzZXQgc3RhZ2luZyBpcyBlbmFibGVkIGl0IHdpbGwgYmUgdGhlIHN0YWdlZCBwYXRoLlxuICAgKlxuICAgKiBJTVBPUlRBTlQ6IElmIHlvdSBhcmUgZ29pbmcgdG8gY2FsbCBgYWRkRmlsZUFzc2V0KClgLCB1c2VcbiAgICogYHJlbGF0aXZlU3RhZ2VkUGF0aCgpYCBpbnN0ZWFkLlxuICAgKlxuICAgKiBAZGVwcmVjYXRlZCAtIFVzZSBgYWJzb2x1dGVTdGFnZWRQYXRoYCBpbnN0ZWFkLlxuICAgKi9cbiAgcHVibGljIHJlYWRvbmx5IHN0YWdlZFBhdGg6IHN0cmluZztcblxuICAvKipcbiAgICogQWJzb2x1dGUgcGF0aCB0byB0aGUgYXNzZXQgZGF0YS5cbiAgICpcbiAgICogSWYgYXNzZXQgc3RhZ2luZyBpcyBkaXNhYmxlZCwgdGhpcyB3aWxsIGp1c3QgYmUgdGhlIHNvdXJjZSBwYXRoIG9yXG4gICAqIGEgdGVtcG9yYXJ5IGRpcmVjdG9yeSB1c2VkIGZvciBidW5kbGluZy5cbiAgICpcbiAgICogSWYgYXNzZXQgc3RhZ2luZyBpcyBlbmFibGVkIGl0IHdpbGwgYmUgdGhlIHN0YWdlZCBwYXRoLlxuICAgKlxuICAgKiBJTVBPUlRBTlQ6IElmIHlvdSBhcmUgZ29pbmcgdG8gY2FsbCBgYWRkRmlsZUFzc2V0KClgLCB1c2VcbiAgICogYHJlbGF0aXZlU3RhZ2VkUGF0aCgpYCBpbnN0ZWFkLlxuICAgKi9cbiAgcHVibGljIHJlYWRvbmx5IGFic29sdXRlU3RhZ2VkUGF0aDogc3RyaW5nO1xuXG4gIC8qKlxuICAgKiBUaGUgYWJzb2x1dGUgcGF0aCBvZiB0aGUgYXNzZXQgYXMgaXQgd2FzIHJlZmVyZW5jZWQgYnkgdGhlIHVzZXIuXG4gICAqL1xuICBwdWJsaWMgcmVhZG9ubHkgc291cmNlUGF0aDogc3RyaW5nO1xuXG4gIC8qKlxuICAgKiBBIGNyeXB0b2dyYXBoaWMgaGFzaCBvZiB0aGUgYXNzZXQuXG4gICAqL1xuICBwdWJsaWMgcmVhZG9ubHkgYXNzZXRIYXNoOiBzdHJpbmc7XG5cbiAgLyoqXG4gICAqIEhvdyB0aGlzIGFzc2V0IHNob3VsZCBiZSBwYWNrYWdlZC5cbiAgICovXG4gIHB1YmxpYyByZWFkb25seSBwYWNrYWdpbmc6IEZpbGVBc3NldFBhY2thZ2luZztcblxuICAvKipcbiAgICogV2hldGhlciB0aGlzIGFzc2V0IGlzIGFuIGFyY2hpdmUgKHppcCBvciBqYXIpLlxuICAgKi9cbiAgcHVibGljIHJlYWRvbmx5IGlzQXJjaGl2ZTogYm9vbGVhbjtcblxuICBwcml2YXRlIHJlYWRvbmx5IGZpbmdlcnByaW50T3B0aW9uczogRmluZ2VycHJpbnRPcHRpb25zO1xuXG4gIHByaXZhdGUgcmVhZG9ubHkgaGFzaFR5cGU6IEFzc2V0SGFzaFR5cGU7XG4gIHByaXZhdGUgcmVhZG9ubHkgYXNzZXRPdXRkaXI6IHN0cmluZztcblxuICAvKipcbiAgICogQSBjdXN0b20gc291cmNlIGZpbmdlcnByaW50IGdpdmVuIGJ5IHRoZSB1c2VyXG4gICAqXG4gICAqIFdpbGwgbm90IGJlIHVzZWQgbGl0ZXJhbGx5LCBhbHdheXMgaGFzaGVkIGxhdGVyIG9uLlxuICAgKi9cbiAgcHJpdmF0ZSBjdXN0b21Tb3VyY2VGaW5nZXJwcmludD86IHN0cmluZztcblxuICBwcml2YXRlIHJlYWRvbmx5IGNhY2hlS2V5OiBzdHJpbmc7XG5cbiAgcHJpdmF0ZSByZWFkb25seSBzb3VyY2VTdGF0czogZnMuU3RhdHM7XG5cbiAgY29uc3RydWN0b3Ioc2NvcGU6IENvbnN0cnVjdCwgaWQ6IHN0cmluZywgcHJvcHM6IEFzc2V0U3RhZ2luZ1Byb3BzKSB7XG4gICAgc3VwZXIoc2NvcGUsIGlkKTtcblxuICAgIHRoaXMuc291cmNlUGF0aCA9IHBhdGgucmVzb2x2ZShwcm9wcy5zb3VyY2VQYXRoKTtcbiAgICB0aGlzLmZpbmdlcnByaW50T3B0aW9ucyA9IHByb3BzO1xuXG4gICAgaWYgKCFmcy5leGlzdHNTeW5jKHRoaXMuc291cmNlUGF0aCkpIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcihgQ2Fubm90IGZpbmQgYXNzZXQgYXQgJHt0aGlzLnNvdXJjZVBhdGh9YCk7XG4gICAgfVxuXG4gICAgdGhpcy5zb3VyY2VTdGF0cyA9IGZzLnN0YXRTeW5jKHRoaXMuc291cmNlUGF0aCk7XG5cbiAgICBjb25zdCBvdXRkaXIgPSBTdGFnZS5vZih0aGlzKT8uYXNzZXRPdXRkaXI7XG4gICAgaWYgKCFvdXRkaXIpIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcigndW5hYmxlIHRvIGRldGVybWluZSBjbG91ZCBhc3NlbWJseSBhc3NldCBvdXRwdXQgZGlyZWN0b3J5LiBBc3NldHMgbXVzdCBiZSBkZWZpbmVkIGluZGlyZWN0bHkgd2l0aGluIGEgXCJTdGFnZVwiIG9yIGFuIFwiQXBwXCIgc2NvcGUnKTtcbiAgICB9XG4gICAgdGhpcy5hc3NldE91dGRpciA9IG91dGRpcjtcblxuICAgIC8vIERldGVybWluZSB0aGUgaGFzaCB0eXBlIGJhc2VkIG9uIHRoZSBwcm9wcyBhcyBwcm9wcy5hc3NldEhhc2hUeXBlIGlzXG4gICAgLy8gb3B0aW9uYWwgZnJvbSBhIGNhbGxlciBwZXJzcGVjdGl2ZS5cbiAgICB0aGlzLmN1c3RvbVNvdXJjZUZpbmdlcnByaW50ID0gcHJvcHMuYXNzZXRIYXNoO1xuICAgIHRoaXMuaGFzaFR5cGUgPSBkZXRlcm1pbmVIYXNoVHlwZShwcm9wcy5hc3NldEhhc2hUeXBlLCB0aGlzLmN1c3RvbVNvdXJjZUZpbmdlcnByaW50KTtcblxuICAgIC8vIERlY2lkZSB3aGF0IHdlJ3JlIGdvaW5nIHRvIGRvLCB3aXRob3V0IGFjdHVhbGx5IGRvaW5nIGl0IHlldFxuICAgIGxldCBzdGFnZVRoaXNBc3NldDogKCkgPT4gU3RhZ2VkQXNzZXQ7XG4gICAgbGV0IHNraXAgPSBmYWxzZTtcbiAgICBpZiAocHJvcHMuYnVuZGxpbmcpIHtcbiAgICAgIC8vIENoZWNrIGlmIHdlIGFjdHVhbGx5IGhhdmUgdG8gYnVuZGxlIGZvciB0aGlzIHN0YWNrXG4gICAgICBza2lwID0gIVN0YWNrLm9mKHRoaXMpLmJ1bmRsaW5nUmVxdWlyZWQ7XG4gICAgICBjb25zdCBidW5kbGluZyA9IHByb3BzLmJ1bmRsaW5nO1xuICAgICAgc3RhZ2VUaGlzQXNzZXQgPSAoKSA9PiB0aGlzLnN0YWdlQnlCdW5kbGluZyhidW5kbGluZywgc2tpcCk7XG4gICAgfSBlbHNlIHtcbiAgICAgIHN0YWdlVGhpc0Fzc2V0ID0gKCkgPT4gdGhpcy5zdGFnZUJ5Q29weWluZygpO1xuICAgIH1cblxuICAgIC8vIENhbGN1bGF0ZSBhIGNhY2hlIGtleSBmcm9tIHRoZSBwcm9wcy4gVGhpcyB3YXkgd2UgY2FuIGNoZWNrIGlmIHdlIGFscmVhZHlcbiAgICAvLyBzdGFnZWQgdGhpcyBhc3NldCBhbmQgcmV1c2UgdGhlIHJlc3VsdCAoZS5nLiB0aGUgc2FtZSBhc3NldCB3aXRoIHRoZSBzYW1lXG4gICAgLy8gY29uZmlndXJhdGlvbiBpcyB1c2VkIGluIG11bHRpcGxlIHN0YWNrcykuIEluIHRoaXMgY2FzZSB3ZSBjYW4gY29tcGxldGVseVxuICAgIC8vIHNraXAgZmlsZSBzeXN0ZW0gYW5kIGJ1bmRsaW5nIG9wZXJhdGlvbnMuXG4gICAgLy9cbiAgICAvLyBUaGUgb3V0cHV0IGRpcmVjdG9yeSBhbmQgd2hldGhlciB0aGlzIGFzc2V0IGlzIHNraXBwZWQgb3Igbm90IHNob3VsZCBhbHNvIGJlXG4gICAgLy8gcGFydCBvZiB0aGUgY2FjaGUga2V5IHRvIG1ha2Ugc3VyZSB3ZSBkb24ndCBhY2NpZGVudGFsbHkgcmV0dXJuIHRoZSB3cm9uZ1xuICAgIC8vIHN0YWdlZCBhc3NldCBmcm9tIHRoZSBjYWNoZS5cbiAgICB0aGlzLmNhY2hlS2V5ID0gY2FsY3VsYXRlQ2FjaGVLZXkoe1xuICAgICAgb3V0ZGlyOiB0aGlzLmFzc2V0T3V0ZGlyLFxuICAgICAgc291cmNlUGF0aDogcGF0aC5yZXNvbHZlKHByb3BzLnNvdXJjZVBhdGgpLFxuICAgICAgYnVuZGxpbmc6IHByb3BzLmJ1bmRsaW5nLFxuICAgICAgYXNzZXRIYXNoVHlwZTogdGhpcy5oYXNoVHlwZSxcbiAgICAgIGN1c3RvbUZpbmdlcnByaW50OiB0aGlzLmN1c3RvbVNvdXJjZUZpbmdlcnByaW50LFxuICAgICAgZXh0cmFIYXNoOiBwcm9wcy5leHRyYUhhc2gsXG4gICAgICBleGNsdWRlOiBwcm9wcy5leGNsdWRlLFxuICAgICAgaWdub3JlTW9kZTogcHJvcHMuaWdub3JlTW9kZSxcbiAgICAgIHNraXAsXG4gICAgfSk7XG5cbiAgICBjb25zdCBzdGFnZWQgPSBBc3NldFN0YWdpbmcuYXNzZXRDYWNoZS5vYnRhaW4odGhpcy5jYWNoZUtleSwgc3RhZ2VUaGlzQXNzZXQpO1xuICAgIHRoaXMuc3RhZ2VkUGF0aCA9IHN0YWdlZC5zdGFnZWRQYXRoO1xuICAgIHRoaXMuYWJzb2x1dGVTdGFnZWRQYXRoID0gc3RhZ2VkLnN0YWdlZFBhdGg7XG4gICAgdGhpcy5hc3NldEhhc2ggPSBzdGFnZWQuYXNzZXRIYXNoO1xuICAgIHRoaXMucGFja2FnaW5nID0gc3RhZ2VkLnBhY2thZ2luZztcbiAgICB0aGlzLmlzQXJjaGl2ZSA9IHN0YWdlZC5pc0FyY2hpdmU7XG4gIH1cblxuICAvKipcbiAgICogQSBjcnlwdG9ncmFwaGljIGhhc2ggb2YgdGhlIGFzc2V0LlxuICAgKlxuICAgKiBAZGVwcmVjYXRlZCBzZWUgYGFzc2V0SGFzaGAuXG4gICAqL1xuICBwdWJsaWMgZ2V0IHNvdXJjZUhhc2goKTogc3RyaW5nIHtcbiAgICByZXR1cm4gdGhpcy5hc3NldEhhc2g7XG4gIH1cblxuICAvKipcbiAgICogUmV0dXJuIHRoZSBwYXRoIHRvIHRoZSBzdGFnZWQgYXNzZXQsIHJlbGF0aXZlIHRvIHRoZSBDbG91ZCBBc3NlbWJseSAobWFuaWZlc3QpIGRpcmVjdG9yeSBvZiB0aGUgZ2l2ZW4gc3RhY2tcbiAgICpcbiAgICogT25seSByZXR1cm5zIGEgcmVsYXRpdmUgcGF0aCBpZiB0aGUgYXNzZXQgd2FzIHN0YWdlZCwgcmV0dXJucyBhbiBhYnNvbHV0ZSBwYXRoIGlmXG4gICAqIGl0IHdhcyBub3Qgc3RhZ2VkLlxuICAgKlxuICAgKiBBIGJ1bmRsZWQgYXNzZXQgbWlnaHQgZW5kIHVwIGluIHRoZSBvdXREaXIgYW5kIHN0aWxsIG5vdCBjb3VudCBhc1xuICAgKiBcInN0YWdlZFwiOyBpZiBhc3NldCBzdGFnaW5nIGlzIGRpc2FibGVkIHdlJ3JlIHRlY2huaWNhbGx5IGV4cGVjdGVkIHRvXG4gICAqIHJlZmVyZW5jZSBzb3VyY2UgZGlyZWN0b3JpZXMsIGJ1dCB3ZSBkb24ndCBoYXZlIGEgc291cmNlIGRpcmVjdG9yeSBmb3IgdGhlXG4gICAqIGJ1bmRsZWQgb3V0cHV0cyAoYXMgdGhlIGJ1bmRsZSBvdXRwdXQgaXMgd3JpdHRlbiB0byBhIHRlbXBvcmFyeVxuICAgKiBkaXJlY3RvcnkpLiBOZXZlcnRoZWxlc3MsIHdlIHdpbGwgc3RpbGwgcmV0dXJuIGFuIGFic29sdXRlIHBhdGguXG4gICAqXG4gICAqIEEgbm9uLW9idmlvdXMgZGlyZWN0b3J5IGxheW91dCBtYXkgbG9vayBsaWtlIHRoaXM6XG4gICAqXG4gICAqIGBgYFxuICAgKiAgIENMT1VEIEFTU0VNQkxZIFJPT1RcbiAgICogICAgICstLSBhc3NldC4xMjM0NWFiY2RlZi9cbiAgICogICAgICstLSBhc3NlbWJseS1TdGFnZVxuICAgKiAgICAgICAgICAgKy0tIE15U3RhY2sudGVtcGxhdGUuanNvblxuICAgKiAgICAgICAgICAgKy0tIE15U3RhY2suYXNzZXRzLmpzb24gPC0gd2lsbCBjb250YWluIHsgXCJwYXRoXCI6IFwiLi4vYXNzZXQuMTIzNDVhYmNkZWZcIiB9XG4gICAqIGBgYFxuICAgKi9cbiAgcHVibGljIHJlbGF0aXZlU3RhZ2VkUGF0aChzdGFjazogU3RhY2spIHtcbiAgICBjb25zdCBhc21NYW5pZmVzdERpciA9IFN0YWdlLm9mKHN0YWNrKT8ub3V0ZGlyO1xuICAgIGlmICghYXNtTWFuaWZlc3REaXIpIHsgcmV0dXJuIHRoaXMuc3RhZ2VkUGF0aDsgfVxuXG4gICAgY29uc3QgaXNPdXRzaWRlQXNzZXREaXIgPSBwYXRoLnJlbGF0aXZlKHRoaXMuYXNzZXRPdXRkaXIsIHRoaXMuc3RhZ2VkUGF0aCkuc3RhcnRzV2l0aCgnLi4nKTtcbiAgICBpZiAoaXNPdXRzaWRlQXNzZXREaXIgfHwgdGhpcy5zdGFnaW5nRGlzYWJsZWQpIHtcbiAgICAgIHJldHVybiB0aGlzLnN0YWdlZFBhdGg7XG4gICAgfVxuXG4gICAgcmV0dXJuIHBhdGgucmVsYXRpdmUoYXNtTWFuaWZlc3REaXIsIHRoaXMuc3RhZ2VkUGF0aCk7XG4gIH1cblxuICAvKipcbiAgICogU3RhZ2UgdGhlIHNvdXJjZSB0byB0aGUgdGFyZ2V0IGJ5IGNvcHlpbmdcbiAgICpcbiAgICogT3B0aW9uYWxseSBza2lwIGlmIHN0YWdpbmcgaXMgZGlzYWJsZWQsIGluIHdoaWNoIGNhc2Ugd2UgcHJldGVuZCB3ZSBkaWQgc29tZXRoaW5nIGJ1dCB3ZSBkb24ndCByZWFsbHkuXG4gICAqL1xuICBwcml2YXRlIHN0YWdlQnlDb3B5aW5nKCk6IFN0YWdlZEFzc2V0IHtcbiAgICBjb25zdCBhc3NldEhhc2ggPSB0aGlzLmNhbGN1bGF0ZUhhc2godGhpcy5oYXNoVHlwZSk7XG4gICAgY29uc3Qgc3RhZ2VkUGF0aCA9IHRoaXMuc3RhZ2luZ0Rpc2FibGVkXG4gICAgICA/IHRoaXMuc291cmNlUGF0aFxuICAgICAgOiBwYXRoLnJlc29sdmUodGhpcy5hc3NldE91dGRpciwgcmVuZGVyQXNzZXRGaWxlbmFtZShhc3NldEhhc2gsIHBhdGguZXh0bmFtZSh0aGlzLnNvdXJjZVBhdGgpKSk7XG5cbiAgICBpZiAoIXRoaXMuc291cmNlU3RhdHMuaXNEaXJlY3RvcnkoKSAmJiAhdGhpcy5zb3VyY2VTdGF0cy5pc0ZpbGUoKSkge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKGBBc3NldCAke3RoaXMuc291cmNlUGF0aH0gaXMgZXhwZWN0ZWQgdG8gYmUgZWl0aGVyIGEgZGlyZWN0b3J5IG9yIGEgcmVndWxhciBmaWxlYCk7XG4gICAgfVxuXG4gICAgdGhpcy5zdGFnZUFzc2V0KHRoaXMuc291cmNlUGF0aCwgc3RhZ2VkUGF0aCwgJ2NvcHknKTtcblxuICAgIHJldHVybiB7XG4gICAgICBhc3NldEhhc2gsXG4gICAgICBzdGFnZWRQYXRoLFxuICAgICAgcGFja2FnaW5nOiB0aGlzLnNvdXJjZVN0YXRzLmlzRGlyZWN0b3J5KCkgPyBGaWxlQXNzZXRQYWNrYWdpbmcuWklQX0RJUkVDVE9SWSA6IEZpbGVBc3NldFBhY2thZ2luZy5GSUxFLFxuICAgICAgaXNBcmNoaXZlOiB0aGlzLnNvdXJjZVN0YXRzLmlzRGlyZWN0b3J5KCkgfHwgQVJDSElWRV9FWFRFTlNJT05TLmluY2x1ZGVzKHBhdGguZXh0bmFtZSh0aGlzLnNvdXJjZVBhdGgpLnRvTG93ZXJDYXNlKCkpLFxuICAgIH07XG4gIH1cblxuICAvKipcbiAgICogU3RhZ2UgdGhlIHNvdXJjZSB0byB0aGUgdGFyZ2V0IGJ5IGJ1bmRsaW5nXG4gICAqXG4gICAqIE9wdGlvbmFsbHkgc2tpcCwgaW4gd2hpY2ggY2FzZSB3ZSBwcmV0ZW5kIHdlIGRpZCBzb21ldGhpbmcgYnV0IHdlIGRvbid0IHJlYWxseS5cbiAgICovXG4gIHByaXZhdGUgc3RhZ2VCeUJ1bmRsaW5nKGJ1bmRsaW5nOiBCdW5kbGluZ09wdGlvbnMsIHNraXA6IGJvb2xlYW4pOiBTdGFnZWRBc3NldCB7XG4gICAgaWYgKCF0aGlzLnNvdXJjZVN0YXRzLmlzRGlyZWN0b3J5KCkpIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcihgQXNzZXQgJHt0aGlzLnNvdXJjZVBhdGh9IGlzIGV4cGVjdGVkIHRvIGJlIGEgZGlyZWN0b3J5IHdoZW4gYnVuZGxpbmdgKTtcbiAgICB9XG5cbiAgICBpZiAoc2tpcCkge1xuICAgICAgLy8gV2Ugc2hvdWxkIGhhdmUgYnVuZGxlZCwgYnV0IGRpZG4ndCB0byBzYXZlIHRpbWUuIFN0aWxsIHByZXRlbmQgdG8gaGF2ZSBhIGhhc2guXG4gICAgICAvLyBJZiB0aGUgYXNzZXQgdXNlcyBPVVRQVVQgb3IgQlVORExFLCB3ZSB1c2UgYSBDVVNUT00gaGFzaCB0byBhdm9pZCBmaW5nZXJwcmludGluZ1xuICAgICAgLy8gYSBwb3RlbnRpYWxseSB2ZXJ5IGxhcmdlIHNvdXJjZSBkaXJlY3RvcnkuIE90aGVyIGhhc2ggdHlwZXMgYXJlIGtlcHQgdGhlIHNhbWUuXG4gICAgICBsZXQgaGFzaFR5cGUgPSB0aGlzLmhhc2hUeXBlO1xuICAgICAgaWYgKGhhc2hUeXBlID09PSBBc3NldEhhc2hUeXBlLk9VVFBVVCB8fCBoYXNoVHlwZSA9PT0gQXNzZXRIYXNoVHlwZS5CVU5ETEUpIHtcbiAgICAgICAgdGhpcy5jdXN0b21Tb3VyY2VGaW5nZXJwcmludCA9IE5hbWVzLnVuaXF1ZUlkKHRoaXMpO1xuICAgICAgICBoYXNoVHlwZSA9IEFzc2V0SGFzaFR5cGUuQ1VTVE9NO1xuICAgICAgfVxuICAgICAgcmV0dXJuIHtcbiAgICAgICAgYXNzZXRIYXNoOiB0aGlzLmNhbGN1bGF0ZUhhc2goaGFzaFR5cGUsIGJ1bmRsaW5nKSxcbiAgICAgICAgc3RhZ2VkUGF0aDogdGhpcy5zb3VyY2VQYXRoLFxuICAgICAgICBwYWNrYWdpbmc6IEZpbGVBc3NldFBhY2thZ2luZy5aSVBfRElSRUNUT1JZLFxuICAgICAgICBpc0FyY2hpdmU6IHRydWUsXG4gICAgICB9O1xuICAgIH1cblxuICAgIC8vIFRyeSB0byBjYWxjdWxhdGUgYXNzZXRIYXNoIGJlZm9yZWhhbmQgKGlmIHdlIGNhbilcbiAgICBsZXQgYXNzZXRIYXNoID0gdGhpcy5oYXNoVHlwZSA9PT0gQXNzZXRIYXNoVHlwZS5TT1VSQ0UgfHwgdGhpcy5oYXNoVHlwZSA9PT0gQXNzZXRIYXNoVHlwZS5DVVNUT01cbiAgICAgID8gdGhpcy5jYWxjdWxhdGVIYXNoKHRoaXMuaGFzaFR5cGUsIGJ1bmRsaW5nKVxuICAgICAgOiB1bmRlZmluZWQ7XG5cbiAgICBjb25zdCBidW5kbGVEaXIgPSB0aGlzLmRldGVybWluZUJ1bmRsZURpcih0aGlzLmFzc2V0T3V0ZGlyLCBhc3NldEhhc2gpO1xuICAgIHRoaXMuYnVuZGxlKGJ1bmRsaW5nLCBidW5kbGVEaXIpO1xuXG4gICAgLy8gQ2hlY2sgYnVuZGxpbmcgb3V0cHV0IGNvbnRlbnQgYW5kIGRldGVybWluZSBpZiB3ZSB3aWxsIG5lZWQgdG8gYXJjaGl2ZVxuICAgIGNvbnN0IGJ1bmRsaW5nT3V0cHV0VHlwZSA9IGJ1bmRsaW5nLm91dHB1dFR5cGUgPz8gQnVuZGxpbmdPdXRwdXQuQVVUT19ESVNDT1ZFUjtcbiAgICBjb25zdCBidW5kbGVkQXNzZXQgPSBkZXRlcm1pbmVCdW5kbGVkQXNzZXQoYnVuZGxlRGlyLCBidW5kbGluZ091dHB1dFR5cGUpO1xuXG4gICAgLy8gQ2FsY3VsYXRlIGFzc2V0SGFzaCBhZnRlcndhcmRzIGlmIHdlIHN0aWxsIG11c3RcbiAgICBhc3NldEhhc2ggPSBhc3NldEhhc2ggPz8gdGhpcy5jYWxjdWxhdGVIYXNoKHRoaXMuaGFzaFR5cGUsIGJ1bmRsaW5nLCBidW5kbGVkQXNzZXQucGF0aCk7XG4gICAgY29uc3Qgc3RhZ2VkUGF0aCA9IHBhdGgucmVzb2x2ZSh0aGlzLmFzc2V0T3V0ZGlyLCByZW5kZXJBc3NldEZpbGVuYW1lKGFzc2V0SGFzaCwgYnVuZGxlZEFzc2V0LmV4dGVuc2lvbikpO1xuXG4gICAgdGhpcy5zdGFnZUFzc2V0KGJ1bmRsZWRBc3NldC5wYXRoLCBzdGFnZWRQYXRoLCAnbW92ZScpO1xuXG4gICAgLy8gSWYgYnVuZGxpbmcgcHJvZHVjZWQgYSBzaW5nbGUgYXJjaGl2ZSBmaWxlIHdlIFwidG91Y2hcIiB0aGlzIGZpbGUgaW4gdGhlIGJ1bmRsaW5nXG4gICAgLy8gZGlyZWN0b3J5IGFmdGVyIGl0IGhhcyBiZWVuIG1vdmVkIHRvIHRoZSBzdGFnaW5nIGRpcmVjdG9yeS4gVGhpcyB3YXkgaWYgYnVuZGxpbmdcbiAgICAvLyBpcyBza2lwcGVkIGJlY2F1c2UgdGhlIGJ1bmRsaW5nIGRpcmVjdG9yeSBhbHJlYWR5IGV4aXN0cyB3ZSBjYW4gc3RpbGwgZGV0ZXJtaW5lXG4gICAgLy8gdGhlIGNvcnJlY3QgcGFja2FnaW5nIHR5cGUuXG4gICAgaWYgKGJ1bmRsZWRBc3NldC5wYWNrYWdpbmcgPT09IEZpbGVBc3NldFBhY2thZ2luZy5GSUxFKSB7XG4gICAgICBmcy5jbG9zZVN5bmMoZnMub3BlblN5bmMoYnVuZGxlZEFzc2V0LnBhdGgsICd3JykpO1xuICAgIH1cblxuICAgIHJldHVybiB7XG4gICAgICBhc3NldEhhc2gsXG4gICAgICBzdGFnZWRQYXRoLFxuICAgICAgcGFja2FnaW5nOiBidW5kbGVkQXNzZXQucGFja2FnaW5nLFxuICAgICAgaXNBcmNoaXZlOiB0cnVlLCAvLyBidW5kbGluZyBhbHdheXMgcHJvZHVjZXMgYW4gYXJjaGl2ZVxuICAgIH07XG4gIH1cblxuICAvKipcbiAgICogV2hldGhlciBzdGFnaW5nIGhhcyBiZWVuIGRpc2FibGVkXG4gICAqL1xuICBwcml2YXRlIGdldCBzdGFnaW5nRGlzYWJsZWQoKSB7XG4gICAgcmV0dXJuICEhdGhpcy5ub2RlLnRyeUdldENvbnRleHQoY3hhcGkuRElTQUJMRV9BU1NFVF9TVEFHSU5HX0NPTlRFWFQpO1xuICB9XG5cbiAgLyoqXG4gICAqIENvcGllcyBvciBtb3ZlcyB0aGUgZmlsZXMgZnJvbSBzb3VyY2VQYXRoIHRvIHRhcmdldFBhdGguXG4gICAqXG4gICAqIE1vdmluZyBpbXBsaWVzIHRoZSBzb3VyY2UgZGlyZWN0b3J5IGlzIHRlbXBvcmFyeSBhbmQgY2FuIGJlIHRyYXNoZWQuXG4gICAqXG4gICAqIFdpbGwgbm90IGRvIGFueXRoaW5nIGlmIHNvdXJjZSBhbmQgdGFyZ2V0IGFyZSB0aGUgc2FtZS5cbiAgICovXG4gIHByaXZhdGUgc3RhZ2VBc3NldChzb3VyY2VQYXRoOiBzdHJpbmcsIHRhcmdldFBhdGg6IHN0cmluZywgc3R5bGU6ICdtb3ZlJyB8ICdjb3B5Jykge1xuICAgIC8vIElzIHRoZSB3b3JrIGFscmVhZHkgZG9uZT9cbiAgICBjb25zdCBpc0FscmVhZHlTdGFnZWQgPSBmcy5leGlzdHNTeW5jKHRhcmdldFBhdGgpO1xuICAgIGlmIChpc0FscmVhZHlTdGFnZWQpIHtcbiAgICAgIGlmIChzdHlsZSA9PT0gJ21vdmUnICYmIHNvdXJjZVBhdGggIT09IHRhcmdldFBhdGgpIHtcbiAgICAgICAgZnMucmVtb3ZlU3luYyhzb3VyY2VQYXRoKTtcbiAgICAgIH1cbiAgICAgIHJldHVybjtcbiAgICB9XG5cbiAgICAvLyBNb3ZpbmcgY2FuIGJlIGRvbmUgcXVpY2tseVxuICAgIGlmIChzdHlsZSA9PSAnbW92ZScpIHtcbiAgICAgIGZzLnJlbmFtZVN5bmMoc291cmNlUGF0aCwgdGFyZ2V0UGF0aCk7XG4gICAgICByZXR1cm47XG4gICAgfVxuXG4gICAgLy8gQ29weSBmaWxlL2RpcmVjdG9yeSB0byBzdGFnaW5nIGRpcmVjdG9yeVxuICAgIGlmICh0aGlzLnNvdXJjZVN0YXRzLmlzRmlsZSgpKSB7XG4gICAgICBmcy5jb3B5RmlsZVN5bmMoc291cmNlUGF0aCwgdGFyZ2V0UGF0aCk7XG4gICAgfSBlbHNlIGlmICh0aGlzLnNvdXJjZVN0YXRzLmlzRGlyZWN0b3J5KCkpIHtcbiAgICAgIGZzLm1rZGlyU3luYyh0YXJnZXRQYXRoKTtcbiAgICAgIEZpbGVTeXN0ZW0uY29weURpcmVjdG9yeShzb3VyY2VQYXRoLCB0YXJnZXRQYXRoLCB0aGlzLmZpbmdlcnByaW50T3B0aW9ucyk7XG4gICAgfSBlbHNlIHtcbiAgICAgIHRocm93IG5ldyBFcnJvcihgVW5rbm93biBmaWxlIHR5cGU6ICR7c291cmNlUGF0aH1gKTtcbiAgICB9XG4gIH1cblxuICAvKipcbiAgICogRGV0ZXJtaW5lIHRoZSBkaXJlY3Rvcnkgd2hlcmUgd2UncmUgZ29pbmcgdG8gd3JpdGUgdGhlIGJ1bmRsaW5nIG91dHB1dFxuICAgKlxuICAgKiBUaGlzIGlzIHRoZSB0YXJnZXQgZGlyZWN0b3J5IHdoZXJlIHdlJ3JlIGdvaW5nIHRvIHdyaXRlIHRoZSBzdGFnZWQgb3V0cHV0XG4gICAqIGZpbGVzIGlmIHdlIGNhbiAoaWYgdGhlIGhhc2ggaXMgZnVsbHkga25vd24pLCBvciBhIHRlbXBvcmFyeSBkaXJlY3RvcnlcbiAgICogb3RoZXJ3aXNlLlxuICAgKi9cbiAgcHJpdmF0ZSBkZXRlcm1pbmVCdW5kbGVEaXIob3V0ZGlyOiBzdHJpbmcsIHNvdXJjZUhhc2g/OiBzdHJpbmcpIHtcbiAgICBpZiAoc291cmNlSGFzaCkge1xuICAgICAgcmV0dXJuIHBhdGgucmVzb2x2ZShvdXRkaXIsIHJlbmRlckFzc2V0RmlsZW5hbWUoc291cmNlSGFzaCkpO1xuICAgIH1cblxuICAgIC8vIFdoZW4gdGhlIGFzc2V0IGhhc2ggaXNuJ3Qga25vd24gaW4gYWR2YW5jZSwgYnVuZGxlciBvdXRwdXRzIHRvIGFuXG4gICAgLy8gaW50ZXJtZWRpYXRlIGRpcmVjdG9yeSBuYW1lZCBhZnRlciB0aGUgYXNzZXQncyBjYWNoZSBrZXlcbiAgICByZXR1cm4gcGF0aC5yZXNvbHZlKG91dGRpciwgYGJ1bmRsaW5nLXRlbXAtJHt0aGlzLmNhY2hlS2V5fWApO1xuICB9XG5cbiAgLyoqXG4gICAqIEJ1bmRsZXMgYW4gYXNzZXQgdG8gdGhlIGdpdmVuIGRpcmVjdG9yeVxuICAgKlxuICAgKiBJZiB0aGUgZ2l2ZW4gZGlyZWN0b3J5IGFscmVhZHkgZXhpc3RzLCBhc3N1bWUgdGhhdCBldmVyeXRoaW5nJ3MgYWxyZWFkeVxuICAgKiBpbiBvcmRlciBhbmQgZG9uJ3QgZG8gYW55dGhpbmcuXG4gICAqXG4gICAqIEBwYXJhbSBvcHRpb25zIEJ1bmRsaW5nIG9wdGlvbnNcbiAgICogQHBhcmFtIGJ1bmRsZURpciBXaGVyZSB0byBjcmVhdGUgdGhlIGJ1bmRsZSBkaXJlY3RvcnlcbiAgICogQHJldHVybnMgVGhlIGZ1bGx5IHJlc29sdmVkIGJ1bmRsZSBvdXRwdXQgZGlyZWN0b3J5LlxuICAgKi9cbiAgcHJpdmF0ZSBidW5kbGUob3B0aW9uczogQnVuZGxpbmdPcHRpb25zLCBidW5kbGVEaXI6IHN0cmluZykge1xuICAgIGlmIChmcy5leGlzdHNTeW5jKGJ1bmRsZURpcikpIHsgcmV0dXJuOyB9XG5cbiAgICBmcy5lbnN1cmVEaXJTeW5jKGJ1bmRsZURpcik7XG4gICAgLy8gQ2htb2QgdGhlIGJ1bmRsZURpciB0byBmdWxsIGFjY2Vzcy5cbiAgICBmcy5jaG1vZFN5bmMoYnVuZGxlRGlyLCAwbzc3Nyk7XG5cbiAgICAvLyBBbHdheXMgbW91bnQgaW5wdXQgYW5kIG91dHB1dCBkaXJcbiAgICBjb25zdCB2b2x1bWVzID0gW1xuICAgICAge1xuICAgICAgICBob3N0UGF0aDogdGhpcy5zb3VyY2VQYXRoLFxuICAgICAgICBjb250YWluZXJQYXRoOiBBc3NldFN0YWdpbmcuQlVORExJTkdfSU5QVVRfRElSLFxuICAgICAgfSxcbiAgICAgIHtcbiAgICAgICAgaG9zdFBhdGg6IGJ1bmRsZURpcixcbiAgICAgICAgY29udGFpbmVyUGF0aDogQXNzZXRTdGFnaW5nLkJVTkRMSU5HX09VVFBVVF9ESVIsXG4gICAgICB9LFxuICAgICAgLi4ub3B0aW9ucy52b2x1bWVzID8/IFtdLFxuICAgIF07XG5cbiAgICBsZXQgbG9jYWxCdW5kbGluZzogYm9vbGVhbiB8IHVuZGVmaW5lZDtcbiAgICB0cnkge1xuICAgICAgcHJvY2Vzcy5zdGRlcnIud3JpdGUoYEJ1bmRsaW5nIGFzc2V0ICR7dGhpcy5ub2RlLnBhdGh9Li4uXFxuYCk7XG5cbiAgICAgIGxvY2FsQnVuZGxpbmcgPSBvcHRpb25zLmxvY2FsPy50cnlCdW5kbGUoYnVuZGxlRGlyLCBvcHRpb25zKTtcbiAgICAgIGlmICghbG9jYWxCdW5kbGluZykge1xuICAgICAgICBsZXQgdXNlcjogc3RyaW5nO1xuICAgICAgICBpZiAob3B0aW9ucy51c2VyKSB7XG4gICAgICAgICAgdXNlciA9IG9wdGlvbnMudXNlcjtcbiAgICAgICAgfSBlbHNlIHsgLy8gRGVmYXVsdCB0byBjdXJyZW50IHVzZXJcbiAgICAgICAgICBjb25zdCB1c2VySW5mbyA9IG9zLnVzZXJJbmZvKCk7XG4gICAgICAgICAgdXNlciA9IHVzZXJJbmZvLnVpZCAhPT0gLTEgLy8gdWlkIGlzIC0xIG9uIFdpbmRvd3NcbiAgICAgICAgICAgID8gYCR7dXNlckluZm8udWlkfToke3VzZXJJbmZvLmdpZH1gXG4gICAgICAgICAgICA6ICcxMDAwOjEwMDAnO1xuICAgICAgICB9XG5cbiAgICAgICAgb3B0aW9ucy5pbWFnZS5ydW4oe1xuICAgICAgICAgIGNvbW1hbmQ6IG9wdGlvbnMuY29tbWFuZCxcbiAgICAgICAgICB1c2VyLFxuICAgICAgICAgIHZvbHVtZXMsXG4gICAgICAgICAgZW52aXJvbm1lbnQ6IG9wdGlvbnMuZW52aXJvbm1lbnQsXG4gICAgICAgICAgd29ya2luZ0RpcmVjdG9yeTogb3B0aW9ucy53b3JraW5nRGlyZWN0b3J5ID8/IEFzc2V0U3RhZ2luZy5CVU5ETElOR19JTlBVVF9ESVIsXG4gICAgICAgICAgc2VjdXJpdHlPcHQ6IG9wdGlvbnMuc2VjdXJpdHlPcHQgPz8gJycsXG4gICAgICAgIH0pO1xuICAgICAgfVxuICAgIH0gY2F0Y2ggKGVycikge1xuICAgICAgLy8gV2hlbiBidW5kbGluZyBmYWlscywga2VlcCB0aGUgYnVuZGxlIG91dHB1dCBmb3IgZGlhZ25vc2FiaWxpdHksIGJ1dFxuICAgICAgLy8gcmVuYW1lIGl0IG91dCBvZiB0aGUgd2F5IHNvIHRoYXQgdGhlIG5leHQgcnVuIGRvZXNuJ3QgYXNzdW1lIGl0IGhhcyBhXG4gICAgICAvLyB2YWxpZCBidW5kbGVEaXIuXG4gICAgICBjb25zdCBidW5kbGVFcnJvckRpciA9IGJ1bmRsZURpciArICctZXJyb3InO1xuICAgICAgaWYgKGZzLmV4aXN0c1N5bmMoYnVuZGxlRXJyb3JEaXIpKSB7XG4gICAgICAgIC8vIFJlbW92ZSB0aGUgbGFzdCBidW5kbGVFcnJvckRpci5cbiAgICAgICAgZnMucmVtb3ZlU3luYyhidW5kbGVFcnJvckRpcik7XG4gICAgICB9XG5cbiAgICAgIGZzLnJlbmFtZVN5bmMoYnVuZGxlRGlyLCBidW5kbGVFcnJvckRpcik7XG4gICAgICB0aHJvdyBuZXcgRXJyb3IoYEZhaWxlZCB0byBidW5kbGUgYXNzZXQgJHt0aGlzLm5vZGUucGF0aH0sIGJ1bmRsZSBvdXRwdXQgaXMgbG9jYXRlZCBhdCAke2J1bmRsZUVycm9yRGlyfTogJHtlcnJ9YCk7XG4gICAgfVxuXG4gICAgaWYgKEZpbGVTeXN0ZW0uaXNFbXB0eShidW5kbGVEaXIpKSB7XG4gICAgICBjb25zdCBvdXRwdXREaXIgPSBsb2NhbEJ1bmRsaW5nID8gYnVuZGxlRGlyIDogQXNzZXRTdGFnaW5nLkJVTkRMSU5HX09VVFBVVF9ESVI7XG4gICAgICB0aHJvdyBuZXcgRXJyb3IoYEJ1bmRsaW5nIGRpZCBub3QgcHJvZHVjZSBhbnkgb3V0cHV0LiBDaGVjayB0aGF0IGNvbnRlbnQgaXMgd3JpdHRlbiB0byAke291dHB1dERpcn0uYCk7XG4gICAgfVxuICB9XG5cbiAgcHJpdmF0ZSBjYWxjdWxhdGVIYXNoKGhhc2hUeXBlOiBBc3NldEhhc2hUeXBlLCBidW5kbGluZz86IEJ1bmRsaW5nT3B0aW9ucywgb3V0cHV0RGlyPzogc3RyaW5nKTogc3RyaW5nIHtcbiAgICAvLyBXaGVuIGJ1bmRsaW5nIGEgQ1VTVE9NIG9yIFNPVVJDRSBhc3NldCBoYXNoIHR5cGUsIHdlIHdhbnQgdGhlIGhhc2ggdG8gaW5jbHVkZVxuICAgIC8vIHRoZSBidW5kbGluZyBjb25maWd1cmF0aW9uLiBXZSBoYW5kbGUgQ1VTVE9NIGFuZCBidW5kbGVkIFNPVVJDRSBoYXNoIHR5cGVzXG4gICAgLy8gYXMgYSBzcGVjaWFsIGNhc2UgdG8gcHJlc2VydmUgZXhpc3RpbmcgdXNlciBhc3NldCBoYXNoZXMgaW4gYWxsIG90aGVyIGNhc2VzLlxuICAgIGlmIChoYXNoVHlwZSA9PSBBc3NldEhhc2hUeXBlLkNVU1RPTSB8fCAoaGFzaFR5cGUgPT0gQXNzZXRIYXNoVHlwZS5TT1VSQ0UgJiYgYnVuZGxpbmcpKSB7XG4gICAgICBjb25zdCBoYXNoID0gY3J5cHRvLmNyZWF0ZUhhc2goJ3NoYTI1NicpO1xuXG4gICAgICAvLyBpZiBhc3NldCBoYXNoIGlzIHByb3ZpZGVkIGJ5IHVzZXIsIHVzZSBpdCwgb3RoZXJ3aXNlIGZpbmdlcnByaW50IHRoZSBzb3VyY2UuXG4gICAgICBoYXNoLnVwZGF0ZSh0aGlzLmN1c3RvbVNvdXJjZUZpbmdlcnByaW50ID8/IEZpbGVTeXN0ZW0uZmluZ2VycHJpbnQodGhpcy5zb3VyY2VQYXRoLCB0aGlzLmZpbmdlcnByaW50T3B0aW9ucykpO1xuXG4gICAgICAvLyBJZiB3ZSdyZSBidW5kbGluZyBhbiBhc3NldCwgaW5jbHVkZSB0aGUgYnVuZGxpbmcgY29uZmlndXJhdGlvbiBpbiB0aGUgaGFzaFxuICAgICAgaWYgKGJ1bmRsaW5nKSB7XG4gICAgICAgIGhhc2gudXBkYXRlKEpTT04uc3RyaW5naWZ5KGJ1bmRsaW5nKSk7XG4gICAgICB9XG5cbiAgICAgIHJldHVybiBoYXNoLmRpZ2VzdCgnaGV4Jyk7XG4gICAgfVxuXG4gICAgc3dpdGNoIChoYXNoVHlwZSkge1xuICAgICAgY2FzZSBBc3NldEhhc2hUeXBlLlNPVVJDRTpcbiAgICAgICAgcmV0dXJuIEZpbGVTeXN0ZW0uZmluZ2VycHJpbnQodGhpcy5zb3VyY2VQYXRoLCB0aGlzLmZpbmdlcnByaW50T3B0aW9ucyk7XG4gICAgICBjYXNlIEFzc2V0SGFzaFR5cGUuQlVORExFOlxuICAgICAgY2FzZSBBc3NldEhhc2hUeXBlLk9VVFBVVDpcbiAgICAgICAgaWYgKCFvdXRwdXREaXIpIHtcbiAgICAgICAgICB0aHJvdyBuZXcgRXJyb3IoYENhbm5vdCB1c2UgXFxgJHtoYXNoVHlwZX1cXGAgaGFzaCB0eXBlIHdoZW4gXFxgYnVuZGxpbmdcXGAgaXMgbm90IHNwZWNpZmllZC5gKTtcbiAgICAgICAgfVxuICAgICAgICByZXR1cm4gRmlsZVN5c3RlbS5maW5nZXJwcmludChvdXRwdXREaXIsIHRoaXMuZmluZ2VycHJpbnRPcHRpb25zKTtcbiAgICAgIGRlZmF1bHQ6XG4gICAgICAgIHRocm93IG5ldyBFcnJvcignVW5rbm93biBhc3NldCBoYXNoIHR5cGUuJyk7XG4gICAgfVxuICB9XG59XG5cbmZ1bmN0aW9uIHJlbmRlckFzc2V0RmlsZW5hbWUoYXNzZXRIYXNoOiBzdHJpbmcsIGV4dGVuc2lvbiA9ICcnKSB7XG4gIHJldHVybiBgYXNzZXQuJHthc3NldEhhc2h9JHtleHRlbnNpb259YDtcbn1cblxuLyoqXG4gKiBEZXRlcm1pbmVzIHRoZSBoYXNoIHR5cGUgZnJvbSB1c2VyLWdpdmVuIHByb3AgdmFsdWVzLlxuICpcbiAqIEBwYXJhbSBhc3NldEhhc2hUeXBlIEFzc2V0IGhhc2ggdHlwZSBjb25zdHJ1Y3QgcHJvcFxuICogQHBhcmFtIGN1c3RvbVNvdXJjZUZpbmdlcnByaW50IEFzc2V0IGhhc2ggc2VlZCBnaXZlbiBpbiB0aGUgY29uc3RydWN0IHByb3BzXG4gKi9cbmZ1bmN0aW9uIGRldGVybWluZUhhc2hUeXBlKGFzc2V0SGFzaFR5cGU/OiBBc3NldEhhc2hUeXBlLCBjdXN0b21Tb3VyY2VGaW5nZXJwcmludD86IHN0cmluZykge1xuICBjb25zdCBoYXNoVHlwZSA9IGN1c3RvbVNvdXJjZUZpbmdlcnByaW50XG4gICAgPyAoYXNzZXRIYXNoVHlwZSA/PyBBc3NldEhhc2hUeXBlLkNVU1RPTSlcbiAgICA6IChhc3NldEhhc2hUeXBlID8/IEFzc2V0SGFzaFR5cGUuU09VUkNFKTtcblxuICBpZiAoY3VzdG9tU291cmNlRmluZ2VycHJpbnQgJiYgaGFzaFR5cGUgIT09IEFzc2V0SGFzaFR5cGUuQ1VTVE9NKSB7XG4gICAgdGhyb3cgbmV3IEVycm9yKGBDYW5ub3Qgc3BlY2lmeSBcXGAke2Fzc2V0SGFzaFR5cGV9XFxgIGZvciBcXGBhc3NldEhhc2hUeXBlXFxgIHdoZW4gXFxgYXNzZXRIYXNoXFxgIGlzIHNwZWNpZmllZC4gVXNlIFxcYENVU1RPTVxcYCBvciBsZWF2ZSBcXGB1bmRlZmluZWRcXGAuYCk7XG4gIH1cbiAgaWYgKGhhc2hUeXBlID09PSBBc3NldEhhc2hUeXBlLkNVU1RPTSAmJiAhY3VzdG9tU291cmNlRmluZ2VycHJpbnQpIHtcbiAgICB0aHJvdyBuZXcgRXJyb3IoJ2Bhc3NldEhhc2hgIG11c3QgYmUgc3BlY2lmaWVkIHdoZW4gYGFzc2V0SGFzaFR5cGVgIGlzIHNldCB0byBgQXNzZXRIYXNoVHlwZS5DVVNUT01gLicpO1xuICB9XG5cbiAgcmV0dXJuIGhhc2hUeXBlO1xufVxuXG4vKipcbiAqIENhbGN1bGF0ZXMgYSBjYWNoZSBrZXkgZnJvbSB0aGUgcHJvcHMuIE5vcm1hbGl6ZSBieSBzb3J0aW5nIGtleXMuXG4gKi9cbmZ1bmN0aW9uIGNhbGN1bGF0ZUNhY2hlS2V5PEEgZXh0ZW5kcyBvYmplY3Q+KHByb3BzOiBBKTogc3RyaW5nIHtcbiAgcmV0dXJuIGNyeXB0by5jcmVhdGVIYXNoKCdzaGEyNTYnKVxuICAgIC51cGRhdGUoSlNPTi5zdHJpbmdpZnkoc29ydE9iamVjdChwcm9wcykpKVxuICAgIC5kaWdlc3QoJ2hleCcpO1xufVxuXG4vKipcbiAqIFJlY3Vyc2l2ZWx5IHNvcnQgb2JqZWN0IGtleXNcbiAqL1xuZnVuY3Rpb24gc29ydE9iamVjdChvYmplY3Q6IHsgW2tleTogc3RyaW5nXTogYW55IH0pOiB7IFtrZXk6IHN0cmluZ106IGFueSB9IHtcbiAgaWYgKHR5cGVvZiBvYmplY3QgIT09ICdvYmplY3QnIHx8IG9iamVjdCBpbnN0YW5jZW9mIEFycmF5KSB7XG4gICAgcmV0dXJuIG9iamVjdDtcbiAgfVxuICBjb25zdCByZXQ6IHsgW2tleTogc3RyaW5nXTogYW55IH0gPSB7fTtcbiAgZm9yIChjb25zdCBrZXkgb2YgT2JqZWN0LmtleXMob2JqZWN0KS5zb3J0KCkpIHtcbiAgICByZXRba2V5XSA9IHNvcnRPYmplY3Qob2JqZWN0W2tleV0pO1xuICB9XG4gIHJldHVybiByZXQ7XG59XG5cbi8qKlxuICogUmV0dXJucyB0aGUgc2luZ2xlIGFyY2hpdmUgZmlsZSBvZiBhIGRpcmVjdG9yeSBvciB1bmRlZmluZWRcbiAqL1xuZnVuY3Rpb24gc2luZ2xlQXJjaGl2ZUZpbGUoZGlyZWN0b3J5OiBzdHJpbmcpOiBzdHJpbmcgfCB1bmRlZmluZWQge1xuICBpZiAoIWZzLmV4aXN0c1N5bmMoZGlyZWN0b3J5KSkge1xuICAgIHRocm93IG5ldyBFcnJvcihgRGlyZWN0b3J5ICR7ZGlyZWN0b3J5fSBkb2VzIG5vdCBleGlzdC5gKTtcbiAgfVxuXG4gIGlmICghZnMuc3RhdFN5bmMoZGlyZWN0b3J5KS5pc0RpcmVjdG9yeSgpKSB7XG4gICAgdGhyb3cgbmV3IEVycm9yKGAke2RpcmVjdG9yeX0gaXMgbm90IGEgZGlyZWN0b3J5LmApO1xuICB9XG5cbiAgY29uc3QgY29udGVudCA9IGZzLnJlYWRkaXJTeW5jKGRpcmVjdG9yeSk7XG4gIGlmIChjb250ZW50Lmxlbmd0aCA9PT0gMSkge1xuICAgIGNvbnN0IGZpbGUgPSBwYXRoLmpvaW4oZGlyZWN0b3J5LCBjb250ZW50WzBdKTtcbiAgICBjb25zdCBleHRlbnNpb24gPSBwYXRoLmV4dG5hbWUoY29udGVudFswXSkudG9Mb3dlckNhc2UoKTtcbiAgICBpZiAoZnMuc3RhdFN5bmMoZmlsZSkuaXNGaWxlKCkgJiYgQVJDSElWRV9FWFRFTlNJT05TLmluY2x1ZGVzKGV4dGVuc2lvbikpIHtcbiAgICAgIHJldHVybiBmaWxlO1xuICAgIH1cbiAgfVxuXG4gIHJldHVybiB1bmRlZmluZWQ7XG59XG5cbmludGVyZmFjZSBCdW5kbGVkQXNzZXQge1xuICBwYXRoOiBzdHJpbmcsXG4gIHBhY2thZ2luZzogRmlsZUFzc2V0UGFja2FnaW5nLFxuICBleHRlbnNpb24/OiBzdHJpbmdcbn1cblxuLyoqXG4gKiBSZXR1cm5zIHRoZSBidW5kbGVkIGFzc2V0IHRvIHVzZSBiYXNlZCBvbiB0aGUgY29udGVudCBvZiB0aGUgYnVuZGxlIGRpcmVjdG9yeVxuICogYW5kIHRoZSB0eXBlIG9mIG91dHB1dC5cbiAqL1xuZnVuY3Rpb24gZGV0ZXJtaW5lQnVuZGxlZEFzc2V0KGJ1bmRsZURpcjogc3RyaW5nLCBvdXRwdXRUeXBlOiBCdW5kbGluZ091dHB1dCk6IEJ1bmRsZWRBc3NldCB7XG4gIGNvbnN0IGFyY2hpdmVGaWxlID0gc2luZ2xlQXJjaGl2ZUZpbGUoYnVuZGxlRGlyKTtcblxuICAvLyBhdXRvLWRpc2NvdmVyIG1lYW5zIHRoYXQgaWYgdGhlcmUgaXMgYW4gYXJjaGl2ZSBmaWxlLCB3ZSB0YWtlIGl0IGFzIHRoZVxuICAvLyBidW5kbGUsIG90aGVyd2lzZSwgd2Ugd2lsbCBhcmNoaXZlIGhlcmUuXG4gIGlmIChvdXRwdXRUeXBlID09PSBCdW5kbGluZ091dHB1dC5BVVRPX0RJU0NPVkVSKSB7XG4gICAgb3V0cHV0VHlwZSA9IGFyY2hpdmVGaWxlID8gQnVuZGxpbmdPdXRwdXQuQVJDSElWRUQgOiBCdW5kbGluZ091dHB1dC5OT1RfQVJDSElWRUQ7XG4gIH1cblxuICBzd2l0Y2ggKG91dHB1dFR5cGUpIHtcbiAgICBjYXNlIEJ1bmRsaW5nT3V0cHV0Lk5PVF9BUkNISVZFRDpcbiAgICAgIHJldHVybiB7IHBhdGg6IGJ1bmRsZURpciwgcGFja2FnaW5nOiBGaWxlQXNzZXRQYWNrYWdpbmcuWklQX0RJUkVDVE9SWSB9O1xuICAgIGNhc2UgQnVuZGxpbmdPdXRwdXQuQVJDSElWRUQ6XG4gICAgICBpZiAoIWFyY2hpdmVGaWxlKSB7XG4gICAgICAgIHRocm93IG5ldyBFcnJvcignQnVuZGxpbmcgb3V0cHV0IGRpcmVjdG9yeSBpcyBleHBlY3RlZCB0byBpbmNsdWRlIG9ubHkgYSBzaW5nbGUgLnppcCBvciAuamFyIGZpbGUgd2hlbiBgb3V0cHV0YCBpcyBzZXQgdG8gYEFSQ0hJVkVEYCcpO1xuICAgICAgfVxuICAgICAgcmV0dXJuIHsgcGF0aDogYXJjaGl2ZUZpbGUsIHBhY2thZ2luZzogRmlsZUFzc2V0UGFja2FnaW5nLkZJTEUsIGV4dGVuc2lvbjogcGF0aC5leHRuYW1lKGFyY2hpdmVGaWxlKSB9O1xuICB9XG59XG4iXX0= |
\ | No newline at end of file |