@naandalist/patch-package
Version:
Fix broken node modules with no fuss
146 lines • 21.3 kB
JavaScript
;
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.getPackageResolution = void 0;
const path_1 = require("./path");
const PackageDetails_1 = require("./PackageDetails");
const detectPackageManager_1 = require("./detectPackageManager");
const fs_extra_1 = require("fs-extra");
const lockfile_1 = require("@yarnpkg/lockfile");
const yaml_1 = __importDefault(require("yaml"));
const find_workspaces_1 = require("find-workspaces");
const getPackageVersion_1 = require("./getPackageVersion");
const coerceSemVer_1 = require("./coerceSemVer");
function getPackageResolution({ packageDetails, packageManager, appPath, }) {
const isYarn = packageManager === "yarn";
const lockfileName = isYarn
? "yarn.lock"
: packageManager === "npm-shrinkwrap"
? "npm-shrinkwrap.json"
: "package-lock.json";
let lockfilePath = lockfileName;
if (!(0, fs_extra_1.existsSync)(lockfilePath)) {
const workspaceRoot = (0, find_workspaces_1.findWorkspacesRoot)(appPath);
if (!workspaceRoot) {
throw new Error(`Can't find ${lockfileName} file`);
}
lockfilePath = (0, path_1.join)(workspaceRoot.location, lockfileName);
}
if (!(0, fs_extra_1.existsSync)(lockfilePath)) {
throw new Error(`Can't find ${lockfileName} file`);
}
const lockfileString = (0, fs_extra_1.readFileSync)(lockfilePath, "utf8");
if (isYarn) {
let appLockFile;
if (lockfileString.includes("yarn lockfile v1")) {
const parsedYarnLockFile = (0, lockfile_1.parse)(lockfileString);
if (parsedYarnLockFile.type !== "success") {
throw new Error("Could not parse yarn v1 lock file");
}
else {
appLockFile = parsedYarnLockFile.object;
}
}
else {
try {
appLockFile = yaml_1.default.parse(lockfileString);
}
catch (e) {
console.log(e);
throw new Error("Could not parse yarn v2 lock file");
}
}
const installedVersion = (0, getPackageVersion_1.getPackageVersion)((0, path_1.join)((0, path_1.resolve)(appPath, packageDetails.path), "package.json"));
const entries = Object.entries(appLockFile).filter(([k, v]) => k.startsWith(packageDetails.name + "@") &&
// @ts-ignore
(0, coerceSemVer_1.coerceSemVer)(v.version) === (0, coerceSemVer_1.coerceSemVer)(installedVersion));
const resolutions = entries.map(([_, v]) => {
return v.resolved;
});
if (resolutions.length === 0) {
throw new Error(`\`${packageDetails.pathSpecifier}\`'s installed version is ${installedVersion} but a lockfile entry for it couldn't be found. Your lockfile is likely to be corrupt or you forgot to reinstall your packages.`);
}
if (new Set(resolutions).size !== 1) {
console.log(`Ambiguous lockfile entries for ${packageDetails.pathSpecifier}. Using version ${installedVersion}`);
return installedVersion;
}
if (resolutions[0]) {
return resolutions[0];
}
const packageName = packageDetails.name;
const resolutionVersion = entries[0][1].version;
// `@backstage/integration@npm:^1.5.0, @backstage/integration@npm:^1.7.0, @backstage/integration@npm:^1.7.2`
// ->
// `^1.5.0 ^1.7.0 ^1.7.2`
const resolution = entries[0][0]
.replace(new RegExp(packageName + "@", "g"), "")
.replace(/npm:/g, "")
.replace(/,/g, "");
// resolve relative file path
if (resolution.startsWith("file:.")) {
return `file:${(0, path_1.resolve)(appPath, resolution.slice("file:".length))}`;
}
// add `resolutionVersion` to ensure correct version, `^1.0.0` could resolve latest `v1.3.0`, but `^1.0.0 1.2.1` won't
return resolutionVersion ? resolution + " " + resolutionVersion : resolution;
}
else {
const lockfile = JSON.parse(lockfileString);
const lockfileStack = [lockfile];
for (const name of packageDetails.packageNames.slice(0, -1)) {
const { dependencies } = lockfileStack[0];
if (dependencies && name in dependencies) {
lockfileStack.push(dependencies[name]);
}
}
// Handle Workspaces
const rootPackageName = `node_modules/${packageDetails.packageNames[0]}`;
const { packages } = lockfile;
if (packages && rootPackageName in packages) {
if (packages[rootPackageName].link) {
// It's a workspace
const { resolved } = packages[rootPackageName];
if (resolved) {
packageDetails.workspacePath = packageDetails.path.replace(rootPackageName, resolved);
}
}
}
lockfileStack.reverse();
const relevantStackEntry = lockfileStack.find((entry) => {
if (entry.dependencies) {
return entry.dependencies && packageDetails.name in entry.dependencies;
}
else if (entry.packages) {
return (entry.packages &&
(packageDetails.path in entry.packages ||
packageDetails.workspacePath in entry.packages));
}
});
if (relevantStackEntry === undefined) {
throw new Error("Cannot find dependencies or packages in lockfile");
}
const pkg = relevantStackEntry.dependencies
? relevantStackEntry.dependencies[packageDetails.name]
: relevantStackEntry.packages[packageDetails.path] ||
relevantStackEntry.packages[packageDetails.workspacePath];
return pkg.resolved || pkg.version || pkg.from;
}
}
exports.getPackageResolution = getPackageResolution;
if (require.main === module) {
const packageDetails = (0, PackageDetails_1.getPatchDetailsFromCliString)(process.argv[2]);
if (packageDetails) {
const cwd = process.cwd();
console.log(getPackageResolution({
appPath: cwd,
packageDetails,
packageManager: (0, detectPackageManager_1.detectPackageManager)(cwd, null),
}));
}
else {
console.log(`Can't find package ${process.argv[2]}`);
process.exitCode = 1;
}
}
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZ2V0UGFja2FnZVJlc29sdXRpb24uanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi9zcmMvZ2V0UGFja2FnZVJlc29sdXRpb24udHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6Ijs7Ozs7O0FBQUEsaUNBQXNDO0FBQ3RDLHFEQUErRTtBQUMvRSxpRUFBNkU7QUFDN0UsdUNBQW1EO0FBQ25ELGdEQUE4RDtBQUM5RCxnREFBdUI7QUFDdkIscURBQW9EO0FBQ3BELDJEQUF1RDtBQUN2RCxpREFBNkM7QUFFN0MsU0FBZ0Isb0JBQW9CLENBQUMsRUFDbkMsY0FBYyxFQUNkLGNBQWMsRUFDZCxPQUFPLEdBS1I7SUFDQyxNQUFNLE1BQU0sR0FBRyxjQUFjLEtBQUssTUFBTSxDQUFBO0lBQ3hDLE1BQU0sWUFBWSxHQUFHLE1BQU07UUFDekIsQ0FBQyxDQUFDLFdBQVc7UUFDYixDQUFDLENBQUMsY0FBYyxLQUFLLGdCQUFnQjtZQUNyQyxDQUFDLENBQUMscUJBQXFCO1lBQ3ZCLENBQUMsQ0FBQyxtQkFBbUIsQ0FBQTtJQUN2QixJQUFJLFlBQVksR0FBRyxZQUFZLENBQUE7SUFDL0IsSUFBSSxDQUFDLElBQUEscUJBQVUsRUFBQyxZQUFZLENBQUMsRUFBRTtRQUM3QixNQUFNLGFBQWEsR0FBRyxJQUFBLG9DQUFrQixFQUFDLE9BQU8sQ0FBQyxDQUFBO1FBQ2pELElBQUksQ0FBQyxhQUFhLEVBQUU7WUFDbEIsTUFBTSxJQUFJLEtBQUssQ0FBQyxjQUFjLFlBQVksT0FBTyxDQUFDLENBQUE7U0FDbkQ7UUFDRCxZQUFZLEdBQUcsSUFBQSxXQUFJLEVBQUMsYUFBYSxDQUFDLFFBQVEsRUFBRSxZQUFZLENBQUMsQ0FBQTtLQUMxRDtJQUNELElBQUksQ0FBQyxJQUFBLHFCQUFVLEVBQUMsWUFBWSxDQUFDLEVBQUU7UUFDN0IsTUFBTSxJQUFJLEtBQUssQ0FBQyxjQUFjLFlBQVksT0FBTyxDQUFDLENBQUE7S0FDbkQ7SUFDRCxNQUFNLGNBQWMsR0FBRyxJQUFBLHVCQUFZ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LEdBQUcsSUFBQSw2Q0FBNEIsRUFBQyxPQUFPLENBQUMsSUFBSSxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUE7SUFDcEUsSUFBSSxjQUFjLEVBQUU7UUFDbEIsTUFBTSxHQUFHLEdBQUcsT0FBTyxDQUFDLEdBQUcsRUFBRSxDQUFBO1FBQ3pCLE9BQU8sQ0FBQyxHQUFHLENBQ1Qsb0JBQW9CLENBQUM7WUFDbkIsT0FBTyxFQUFFLEdBQUc7WUFDWixjQUFjO1lBQ2QsY0FBYyxFQUFFLElBQUEsMkNBQW9CLEVBQUMsR0FBRyxFQUFFLElBQUksQ0FBQztTQUNoRCxDQUFDLENBQ0gsQ0FBQTtLQUNGO1NBQU07UUFDTCxPQUFPLENBQUMsR0FBRyxDQUFDLHNCQUFzQixPQUFPLENBQUMsSUFBSSxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsQ0FBQTtRQUNwRCxPQUFPLENBQUMsUUFBUSxHQUFHLENBQUMsQ0FBQTtLQUNyQjtDQUNGIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgam9pbiwgcmVzb2x2ZSB9IGZyb20gXCIuL3BhdGhcIlxuaW1wb3J0IHsgUGFja2FnZURldGFpbHMsIGdldFBhdGNoRGV0YWlsc0Zyb21DbGlTdHJpbmcgfSBmcm9tIFwiLi9QYWNrYWdlRGV0YWlsc1wiXG5pbXBvcnQgeyBQYWNrYWdlTWFuYWdlciwgZGV0ZWN0UGFja2FnZU1hbmFnZXIgfSBmcm9tIFwiLi9kZXRlY3RQYWNrYWdlTWFuYWdlclwiXG5pbXBvcnQgeyByZWFkRmlsZVN5bmMsIGV4aXN0c1N5bmMgfSBmcm9tIFwiZnMtZXh0cmFcIlxuaW1wb3J0IHsgcGFyc2UgYXMgcGFyc2VZYXJuTG9ja0ZpbGUgfSBmcm9tIFwiQHlhcm5wa2cvbG9ja2ZpbGVcIlxuaW1wb3J0IHlhbWwgZnJvbSBcInlhbWxcIlxuaW1wb3J0IHsgZmluZFdvcmtzcGFjZXNSb290IH0gZnJvbSBcImZpbmQtd29ya3NwYWNlc1wiXG5pbXBvcnQgeyBnZXRQYWNrYWdlVmVyc2lvbiB9IGZyb20gXCIuL2dldFBhY2thZ2VWZXJzaW9uXCJcbmltcG9ydCB7IGNvZXJjZVNlbVZlciB9IGZyb20gXCIuL2NvZXJjZVNlbVZlclwiXG5cbmV4cG9ydCBmdW5jdGlvbiBnZXRQYWNrYWdlUmVzb2x1dGlvbih7XG4gIHBhY2thZ2VEZXRhaWxzLFxuICBwYWNrYWdlTWFuYWdlcixcbiAgYXBwUGF0aCxcbn06IHtcbiAgcGFja2FnZURldGFpbHM6IFBhY2thZ2VEZXRhaWxzXG4gIHBhY2thZ2VNYW5hZ2VyOiBQYWNrYWdlTWFuYWdlclxuICBhcHBQYXRoOiBzdHJpbmdcbn0pIHtcbiAgY29uc3QgaXNZYXJuID0gcGFja2FnZU1hbmFnZXIgPT09IFwieWFyblwiXG4gIGNvbnN0IGxvY2tmaWxlTmFtZSA9IGlzWWFyblxuICAgID8gXCJ5YXJuLmxvY2tcIlxuICAgIDogcGFja2FnZU1hbmFnZXIgPT09IFwibnBtLXNocmlua3dyYXBcIlxuICAgID8gXCJucG0tc2hyaW5rd3JhcC5qc29uXCJcbiAgICA6IFwicGFja2FnZS1sb2NrLmpzb25cIlxuICBsZXQgbG9ja2ZpbGVQYXRoID0gbG9ja2ZpbGVOYW1lXG4gIGlmICghZXhpc3RzU3luYyhsb2NrZmlsZVBhdGgpKSB7XG4gICAgY29uc3Qgd29ya3NwYWNlUm9vdCA9IGZpbmRXb3Jrc3BhY2VzUm9vdChhcHBQYXRoKVxuICAgIGlmICghd29ya3NwYWNlUm9vdCkge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKGBDYW4ndCBmaW5kICR7bG9ja2ZpbGVOYW1lfSBmaWxlYClcbiAgICB9XG4gICAgbG9ja2ZpbGVQYXRoID0gam9pbih3b3Jrc3BhY2VSb290LmxvY2F0aW9uLCBsb2NrZmlsZU5hbWUpXG4gIH1cbiAgaWYgKCFleGlzdHNTeW5jKGxvY2tmaWxlUGF0aCkpIHtcbiAgICB0aHJvdyBuZXcgRXJyb3IoYENhbid0IGZpbmQgJHtsb2NrZmlsZU5hbWV9IGZpbGVgKVxuICB9XG4gIGNvbnN0IGxvY2tmaWxlU3RyaW5nID0gcmVhZEZpbGVTeW5jKGxvY2tmaWxlUGF0aCwgXCJ1dGY4XCIpXG5cbiAgaWYgKGlzWWFybikge1xuICAgIGxldCBhcHBMb2NrRmlsZTogUmVjb3JkPFxuICAgICAgc3RyaW5nLFxuICAgICAge1xuICAgICAgICB2ZXJzaW9uOiBzdHJpbmdcbiAgICAgICAgcmVzb2x1dGlvbj86IHN0cmluZ1xuICAgICAgICByZXNvbHZlZD86IHN0cmluZ1xuICAgICAgfVxuICAgID5cbiAgICBpZiAobG9ja2ZpbGVTdHJpbmcuaW5jbHVkZXMoXCJ5YXJuIGxvY2tmaWxlIHYxXCIpKSB7XG4gICAgICBjb25zdCBwYXJzZWRZYXJuTG9ja0ZpbGUgPSBwYXJzZVlhcm5Mb2NrRmlsZShsb2NrZmlsZVN0cmluZylcbiAgICAgIGlmIChwYXJzZWRZYXJuTG9ja0ZpbGUudHlwZSAhPT0gXCJzdWNjZXNzXCIpIHtcbiAgICAgICAgdGhyb3cgbmV3IEVycm9yKFwiQ291bGQgbm90IHBhcnNlIHlhcm4gdjEgbG9jayBmaWxlXCIpXG4gICAgICB9IGVsc2Uge1xuICAgICAgICBhcHBMb2NrRmlsZSA9IHBhcnNlZFlhcm5Mb2NrRmlsZS5vYmplY3RcbiAgICAgIH1cbiAgICB9IGVsc2Uge1xuICAgICAgdHJ5IHtcbiAgICAgICAgYXBwTG9ja0ZpbGUgPSB5YW1sLnBhcnNlKGxvY2tmaWxlU3RyaW5nKVxuICAgICAgfSBjYXRjaCAoZSkge1xuICAgICAgICBjb25zb2xlLmxvZyhlKVxuICAgICAgICB0aHJvdyBuZXcgRXJyb3IoXCJDb3VsZCBub3QgcGFyc2UgeWFybiB2MiBsb2NrIGZpbGVcIilcbiAgICAgIH1cbiAgICB9XG5cbiAgICBjb25zdCBpbnN0YWxsZWRWZXJzaW9uID0gZ2V0UGFja2FnZVZlcnNpb24oXG4gICAgICBqb2luKHJlc29sdmUoYXBwUGF0aCwgcGFja2FnZURldGFpbHMucGF0aCksIFwicGFja2FnZS5qc29uXCIpLFxuICAgIClcblxuICAgIGNvbnN0IGVudHJpZXMgPSBPYmplY3QuZW50cmllcyhhcHBMb2NrRmlsZSkuZmlsdGVyKFxuICAgICAgKFtrLCB2XSkgPT5cbiAgICAgICAgay5zdGFydHNXaXRoKHBhY2thZ2VEZXRhaWxzLm5hbWUgKyBcIkBcIikgJiZcbiAgICAgICAgLy8gQHRzLWlnbm9yZVxuICAgICAgICBjb2VyY2VTZW1WZXIodi52ZXJzaW9uKSA9PT0gY29lcmNlU2VtVmVyKGluc3RhbGxlZFZlcnNpb24pLFxuICAgIClcblxuICAgIGNvbnN0IHJlc29sdXRpb25zID0gZW50cmllcy5tYXAoKFtfLCB2XSkgPT4ge1xuICAgICAgcmV0dXJuIHYucmVzb2x2ZWRcbiAgICB9KVxuXG4gICAgaWYgKHJlc29sdXRpb25zLmxlbmd0aCA9PT0gMCkge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKFxuICAgICAgICBgXFxgJHtwYWNrYWdlRGV0YWlscy5wYXRoU3BlY2lmaWVyfVxcYCdzIGluc3RhbGxlZCB2ZXJzaW9uIGlzICR7aW5zdGFsbGVkVmVyc2lvbn0gYnV0IGEgbG9ja2ZpbGUgZW50cnkgZm9yIGl0IGNvdWxkbid0IGJlIGZvdW5kLiBZb3VyIGxvY2tmaWxlIGlzIGxpa2VseSB0byBiZSBjb3JydXB0IG9yIHlvdSBmb3Jnb3QgdG8gcmVpbnN0YWxsIHlvdXIgcGFja2FnZXMuYCxcbiAgICAgIClcbiAgICB9XG5cbiAgICBpZiAobmV3IFNldChyZXNvbHV0aW9ucykuc2l6ZSAhPT0gMSkge1xuICAgICAgY29uc29sZS5sb2coXG4gICAgICAgIGBBbWJpZ3VvdXMgbG9ja2ZpbGUgZW50cmllcyBmb3IgJHtwYWNrYWdlRGV0YWlscy5wYXRoU3BlY2lmaWVyfS4gVXNpbmcgdmVyc2lvbiAke2luc3RhbGxlZFZlcnNpb259YCxcbiAgICAgIClcbiAgICAgIHJldHVybiBpbnN0YWxsZWRWZXJzaW9uXG4gICAgfVxuXG4gICAgaWYgKHJlc29sdXRpb25zWzBdKSB7XG4gICAgICByZXR1cm4gcmVzb2x1dGlvbnNbMF1cbiAgICB9XG5cbiAgICBjb25zdCBwYWNrYWdlTmFtZSA9IHBhY2thZ2VEZXRhaWxzLm5hbWVcblxuICAgIGNvbnN0IHJlc29sdXRpb25WZXJzaW9uID0gZW50cmllc1swXVsxXS52ZXJzaW9uXG5cbiAgICAvLyBgQGJhY2tzdGFnZS9pbnRlZ3JhdGlvbkBucG06XjEuNS4wLCBAYmFja3N0YWdlL2ludGVncmF0aW9uQG5wbTpeMS43LjAsIEBiYWNrc3RhZ2UvaW50ZWdyYXRpb25AbnBtOl4xLjcuMmBcbiAgICAvLyAtPlxuICAgIC8vIGBeMS41LjAgXjEuNy4wIF4xLjcuMmBcbiAgICBjb25zdCByZXNvbHV0aW9uID0gZW50cmllc1swXVswXVxuICAgICAgLnJlcGxhY2UobmV3IFJlZ0V4cChwYWNrYWdlTmFtZSArIFwiQFwiLCBcImdcIiksIFwiXCIpXG4gICAgICAucmVwbGFjZSgvbnBtOi9nLCBcIlwiKVxuICAgICAgLnJlcGxhY2UoLywvZywgXCJcIilcblxuICAgIC8vIHJlc29sdmUgcmVsYXRpdmUgZmlsZSBwYXRoXG4gICAgaWYgKHJlc29sdXRpb24uc3RhcnRzV2l0aChcImZpbGU6LlwiKSkge1xuICAgICAgcmV0dXJuIGBmaWxlOiR7cmVzb2x2ZShhcHBQYXRoLCByZXNvbHV0aW9uLnNsaWNlKFwiZmlsZTpcIi5sZW5ndGgpKX1gXG4gICAgfVxuXG4gICAgLy8gYWRkIGByZXNvbHV0aW9uVmVyc2lvbmAgdG8gZW5zdXJlIGNvcnJlY3QgdmVyc2lvbiwgYF4xLjAuMGAgY291bGQgcmVzb2x2ZSBsYXRlc3QgYHYxLjMuMGAsIGJ1dCBgXjEuMC4wIDEuMi4xYCB3b24ndFxuICAgIHJldHVybiByZXNvbHV0aW9uVmVyc2lvbiA/IHJlc29sdXRpb24gKyBcIiBcIiArIHJlc29sdXRpb25WZXJzaW9uIDogcmVzb2x1dGlvblxuICB9IGVsc2Uge1xuICAgIGNvbnN0IGxvY2tmaWxlID0gSlNPTi5wYXJzZShsb2NrZmlsZVN0cmluZylcbiAgICBjb25zdCBsb2NrZmlsZVN0YWNrID0gW2xvY2tmaWxlXVxuICAgIGZvciAoY29uc3QgbmFtZSBvZiBwYWNrYWdlRGV0YWlscy5wYWNrYWdlTmFtZXMuc2xpY2UoMCwgLTEpKSB7XG4gICAgICBjb25zdCB7IGRlcGVuZGVuY2llcyB9ID0gbG9ja2ZpbGVTdGFja1swXVxuICAgICAgaWYgKGRlcGVuZGVuY2llcyAmJiBuYW1lIGluIGRlcGVuZGVuY2llcykge1xuICAgICAgICBsb2NrZmlsZVN0YWNrLnB1c2goZGVwZW5kZW5jaWVzW25hbWVdKVxuICAgICAgfVxuICAgIH1cblxuICAgIC8vIEhhbmRsZSBXb3Jrc3BhY2VzXG4gICAgY29uc3Qgcm9vdFBhY2thZ2VOYW1lID0gYG5vZGVfbW9kdWxlcy8ke3BhY2thZ2VEZXRhaWxzLnBhY2thZ2VOYW1lc1swXX1gXG4gICAgY29uc3QgeyBwYWNrYWdlcyB9ID0gbG9ja2ZpbGVcbiAgICBpZiAocGFja2FnZXMgJiYgcm9vdFBhY2thZ2VOYW1lIGluIHBhY2thZ2VzKSB7XG4gICAgICBpZiAocGFja2FnZXNbcm9vdFBhY2thZ2VOYW1lXS5saW5rKSB7XG4gICAgICAgIC8vIEl0J3MgYSB3b3Jrc3BhY2VcbiAgICAgICAgY29uc3QgeyByZXNvbHZlZCB9ID0gcGFja2FnZXNbcm9vdFBhY2thZ2VOYW1lXVxuICAgICAgICBpZiAocmVzb2x2ZWQpIHtcbiAgICAgICAgICBwYWNrYWdlRGV0YWlscy53b3Jrc3BhY2VQYXRoID0gcGFja2FnZURldGFpbHMucGF0aC5yZXBsYWNlKFxuICAgICAgICAgICAgcm9vdFBhY2thZ2VOYW1lLFxuICAgICAgICAgICAgcmVzb2x2ZWQsXG4gICAgICAgICAgKVxuICAgICAgICB9XG4gICAgICB9XG4gICAgfVxuXG4gICAgbG9ja2ZpbGVTdGFjay5yZXZlcnNlKClcbiAgICBjb25zdCByZWxldmFudFN0YWNrRW50cnkgPSBsb2NrZmlsZVN0YWNrLmZpbmQoKGVudHJ5KSA9PiB7XG4gICAgICBpZiAoZW50cnkuZGVwZW5kZW5jaWVzKSB7XG4gICAgICAgIHJldHVybiBlbnRyeS5kZXBlbmRlbmNpZXMgJiYgcGFja2FnZURldGFpbHMubmFtZSBpbiBlbnRyeS5kZXBlbmRlbmNpZXNcbiAgICAgIH0gZWxzZSBpZiAoZW50cnkucGFja2FnZXMpIHtcbiAgICAgICAgcmV0dXJuIChcbiAgICAgICAgICBlbnRyeS5wYWNrYWdlcyAmJlxuICAgICAgICAgIChwYWNrYWdlRGV0YWlscy5wYXRoIGluIGVudHJ5LnBhY2thZ2VzIHx8XG4gICAgICAgICAgICBwYWNrYWdlRGV0YWlscy53b3Jrc3BhY2VQYXRoIGluIGVudHJ5LnBhY2thZ2VzKVxuICAgICAgICApXG4gICAgICB9XG4gICAgfSlcblxuICAgIGlmIChyZWxldmFudFN0YWNrRW50cnkgPT09IHVuZGVmaW5lZCkge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKFwiQ2Fubm90IGZpbmQgZGVwZW5kZW5jaWVzIG9yIHBhY2thZ2VzIGluIGxvY2tmaWxlXCIpXG4gICAgfVxuICAgIGNvbnN0IHBrZyA9IHJlbGV2YW50U3RhY2tFbnRyeS5kZXBlbmRlbmNpZXNcbiAgICAgID8gcmVsZXZhbnRTdGFja0VudHJ5LmRlcGVuZGVuY2llc1twYWNrYWdlRGV0YWlscy5uYW1lXVxuICAgICAgOiByZWxldmFudFN0YWNrRW50cnkucGFja2FnZXNbcGFja2FnZURldGFpbHMucGF0aF0gfHxcbiAgICAgICAgcmVsZXZhbnRTdGFja0VudHJ5LnBhY2thZ2VzW3BhY2thZ2VEZXRhaWxzLndvcmtzcGFjZVBhdGhdXG5cbiAgICByZXR1cm4gcGtnLnJlc29sdmVkIHx8IHBrZy52ZXJzaW9uIHx8IHBrZy5mcm9tXG4gIH1cbn1cblxuaWYgKHJlcXVpcmUubWFpbiA9PT0gbW9kdWxlKSB7XG4gIGNvbnN0IHBhY2thZ2VEZXRhaWxzID0gZ2V0UGF0Y2hEZXRhaWxzRnJvbUNsaVN0cmluZyhwcm9jZXNzLmFyZ3ZbMl0pXG4gIGlmIChwYWNrYWdlRGV0YWlscykge1xuICAgIGNvbnN0IGN3ZCA9IHByb2Nlc3MuY3dkKClcbiAgICBjb25zb2xlLmxvZyhcbiAgICAgIGdldFBhY2thZ2VSZXNvbHV0aW9uKHtcbiAgICAgICAgYXBwUGF0aDogY3dkLFxuICAgICAgICBwYWNrYWdlRGV0YWlscyxcbiAgICAgICAgcGFja2FnZU1hbmFnZXI6IGRldGVjdFBhY2thZ2VNYW5hZ2VyKGN3ZCwgbnVsbCksXG4gICAgICB9KSxcbiAgICApXG4gIH0gZWxzZSB7XG4gICAgY29uc29sZS5sb2coYENhbid0IGZpbmQgcGFja2FnZSAke3Byb2Nlc3MuYXJndlsyXX1gKVxuICAgIHByb2Nlc3MuZXhpdENvZGUgPSAxXG4gIH1cbn1cbiJdfQ==