UNPKG

vite-plugin-react-server

Version:
274 lines (271 loc) 37 kB
/** * vite-plugin-react-server * Copyright (c) Nico Brinkkemper * MIT License */ import { join, resolve } from 'node:path'; import { pathToFileURL } from 'node:url'; import { getModuleRef } from '../helpers/moduleRefs.js'; import { toError } from '../error/toError.js'; import { handleError } from '../error/handleError.js'; import { createSharedLoader } from '../helpers/createSharedLoader.js'; import { resolveVirtualAndNodeModules } from '../helpers/resolveVirtualAndNodeModules.js'; import { createLogger } from 'vite'; const createBuildLoader = function _createBuildLoader({ userOptions, serverManifest, staticManifest }, bundle, temporaryReferences, logger = createLogger()) { const manifestKeys = Object.keys(serverManifest); if (!manifestKeys.length) { throw new Error("Server manifest is empty"); } return async function buildLoader(id) { if (userOptions.verbose) { logger.info(`[buildLoader] id: ${id}`); logger.info(`[buildLoader] Starting lookup for: ${id}`); } const [withoutQuery, query] = id.split("?", 2); const [moduleId, exportName] = withoutQuery.split("#", 2); const [normalizedKey, normalizedValue] = userOptions.normalizer(moduleId); const virtualOrNodeModule = await resolveVirtualAndNodeModules( moduleId, exportName, userOptions.verbose, logger ); if (virtualOrNodeModule !== null) { return virtualOrNodeModule; } const moduleRef = getModuleRef(id); if (temporaryReferences?.has(moduleRef)) { const mod = temporaryReferences.get(moduleRef); if (typeof mod === "object" && mod !== null && "error" in mod) ; else { return mod; } } try { if (query === "inline") { const manifestKey = normalizedValue; if (userOptions.verbose) { logger.info( `[buildLoader] Looking for inline module: ${normalizedValue}` ); } let resolvedValue = normalizedValue; if (normalizedValue.startsWith("assets/") && normalizedValue.endsWith(".css")) { const basePath = normalizedValue.replace( /-[a-zA-Z0-9]+\.css$/, ".css" ); if (userOptions.verbose) { logger.info( `[buildLoader] CSS file detected, trying to resolve ${normalizedValue} to ${basePath}` ); } if (bundle[basePath]) { resolvedValue = basePath; if (userOptions.verbose) { logger.info( `[buildLoader] Resolved CSS file to: ${resolvedValue}` ); } } } if (userOptions.verbose) { logger.info( `[buildLoader] Trying bundle[moduleId]: bundle["${moduleId}"] = ${!!bundle[moduleId]}` ); logger.info( `[buildLoader] Trying bundle[normalizedValue]: bundle["${normalizedValue}"] = ${!!bundle[normalizedValue]}` ); logger.info( `[buildLoader] Trying bundle[resolvedValue]: bundle["${resolvedValue}"] = ${!!bundle[resolvedValue]}` ); } const serverChunk = bundle[moduleId] ?? bundle[normalizedValue] ?? bundle[resolvedValue] ?? bundle[serverManifest[manifestKey]?.file] ?? bundle[staticManifest[manifestKey]?.file] ?? bundle[serverManifest[normalizedKey]?.file] ?? bundle[staticManifest[normalizedKey]?.file] ?? Object.entries(bundle).find( ([, value]) => value.name === normalizedValue )?.[1]; if (userOptions.verbose && serverChunk) { logger.info(`[buildLoader] Found serverChunk: ${serverChunk.type}`); } if (serverChunk) { if (serverChunk.type === "asset") { if (userOptions.autoDiscover.jsonPattern.test(normalizedValue)) { const jsonContent = serverChunk.source; if (typeof jsonContent === "string") { if (userOptions.verbose) { logger.info( `[buildLoader] Returning JSON content for: ${normalizedValue}` ); } return { default: JSON.parse(jsonContent) }; } } else if (userOptions.autoDiscover.cssPattern.test(normalizedValue)) { const cssContent = serverChunk.source; if (typeof cssContent === "string") { if (userOptions.verbose) { logger.info( `[buildLoader] Returning CSS content for: ${normalizedValue}, length: ${cssContent.length}` ); } return { default: cssContent }; } else { if (userOptions.verbose) { logger.info( `[buildLoader] CSS source is not string: ${typeof cssContent}` ); } } } if (userOptions.verbose) { logger.info( `[buildLoader] Returning default asset source for: ${normalizedValue}` ); } return { default: serverChunk.source }; } else if ("code" in serverChunk) { if (userOptions.verbose) { logger.info( `[buildLoader] Returning code for: ${normalizedValue}` ); } return { default: serverChunk.code }; } } const panicError = handleError({ error: new Error( `Could not find inline module for: ${normalizedValue}` ), logger, log: true, panicThreshold: userOptions.panicThreshold, context: "Build Loader Error (inline)" }); if (panicError != null) { throw panicError; } return null; } const bundleEntry = bundle[withoutQuery]; if (bundleEntry) { try { const filePath = join( userOptions.projectRoot, userOptions.build.outDir, userOptions.build.server, withoutQuery ); const fileUrl = pathToFileURL(filePath).href; const module = await import(fileUrl); temporaryReferences?.set(moduleRef, module); return module; } catch (error) { const panicError = handleError({ error, logger, panicThreshold: userOptions.panicThreshold, context: "Build Loader Error (bundle)" }); temporaryReferences?.delete(moduleRef); if (panicError != null) { throw panicError; } } } const staticEntry = staticManifest[normalizedValue]; if (staticEntry) { try { const filePath = join( userOptions.projectRoot, userOptions.build.outDir, userOptions.build.static, staticEntry.file ); const fileUrl = pathToFileURL(filePath).href; const module = await import(fileUrl); temporaryReferences?.set(moduleRef, module); if (exportName && !(exportName in module)) { throw new Error( `Export ${exportName} not found in module ${normalizedValue}` ); } return module; } catch (error) { const panicError = handleError({ error, logger, panicThreshold: userOptions.panicThreshold, context: "Build Loader Error (static)" }); temporaryReferences?.delete(moduleRef); if (panicError != null) { throw panicError; } } } try { const module = await createSharedLoader({ moduleId, exportName, verbose: userOptions.verbose, logger, resolveVirtual: true, manifest: serverManifest, normalizer: userOptions.normalizer, moduleBase: userOptions.moduleBase, preserveModulesRoot: userOptions.build.preserveModulesRoot, projectRoot: userOptions.projectRoot, buildOutDir: userOptions.build.outDir, buildServerDir: userOptions.build.server, isBuildMode: true, isServeMode: false, effectiveProjectRoot: userOptions.projectRoot, build: { outDir: userOptions.build.outDir, server: userOptions.build.server, client: userOptions.build.client, static: userOptions.build.static } }); temporaryReferences?.set(moduleRef, module); return module; } catch (error) { const err = toError(error); const panicError = handleError({ error: err, logger, panicThreshold: userOptions.panicThreshold, context: "Build Loader Error (shared)" }); temporaryReferences?.delete(moduleRef); if (panicError != null) { throw panicError; } } } catch (error) { let enhancedError = error instanceof Error ? error : new Error(String(error)); if (enhancedError.message.includes("React Server Writer cannot be used outside a react-server environment")) { const filePath = resolve( userOptions.projectRoot, userOptions.build.outDir, userOptions.build.server, moduleId ); enhancedError = new Error( `${enhancedError.message} → Imported from: ${moduleId} → Export: ${exportName} → File path: ${filePath} → NODE_OPTIONS: ${process.env.NODE_OPTIONS || "not set"} → execArgv: ${process.execArgv.join(" ") || "not set"}` ); throw enhancedError; } const emptyExports = { error: enhancedError, id }; temporaryReferences?.delete(moduleRef); return emptyExports; } }; }; export { createBuildLoader }; //# sourceMappingURL=data:application/json;charset=utf-8;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiY3JlYXRlQnVpbGRMb2FkZXIuc2VydmVyLmpzIiwic291cmNlcyI6WyIuLi8uLi8uLi9wbHVnaW4vcmVhY3Qtc3RhdGljL2NyZWF0ZUJ1aWxkTG9hZGVyLnNlcnZlci50cyJdLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQgeyBqb2luLCByZXNvbHZlIH0gZnJvbSBcIm5vZGU6cGF0aFwiO1xuaW1wb3J0IHsgcGF0aFRvRmlsZVVSTCB9IGZyb20gXCJub2RlOnVybFwiO1xuaW1wb3J0IHsgZ2V0TW9kdWxlUmVmIH0gZnJvbSBcIi4uL2hlbHBlcnMvbW9kdWxlUmVmcy5qc1wiO1xuaW1wb3J0IHsgdG9FcnJvciB9IGZyb20gXCIuLi9lcnJvci90b0Vycm9yLmpzXCI7XG5pbXBvcnQgeyBoYW5kbGVFcnJvciB9IGZyb20gXCIuLi9lcnJvci9oYW5kbGVFcnJvci5qc1wiO1xuaW1wb3J0IHsgY3JlYXRlU2hhcmVkTG9hZGVyIH0gZnJvbSBcIi4uL2hlbHBlcnMvY3JlYXRlU2hhcmVkTG9hZGVyLmpzXCI7XG5pbXBvcnQgeyByZXNvbHZlVmlydHVhbEFuZE5vZGVNb2R1bGVzIH0gZnJvbSBcIi4uL2hlbHBlcnMvcmVzb2x2ZVZpcnR1YWxBbmROb2RlTW9kdWxlcy5qc1wiO1xuXG5pbXBvcnQgdHlwZSB7IENyZWF0ZUJ1aWxkTG9hZGVyRm4gfSBmcm9tIFwiLi90eXBlcy5qc1wiO1xuaW1wb3J0IHsgY3JlYXRlTG9nZ2VyIH0gZnJvbSBcInZpdGVcIjtcblxuLyoqXG4gKiBDcmVhdGVzIGEgbG9hZGVyIGZ1bmN0aW9uIGZvciBoYW5kbGluZyBtb2R1bGUgcmVzb2x1dGlvbiBkdXJpbmcgYnVpbGQuXG4gKlxuICogVGhlIGxvYWRlciBoYW5kbGVzIHRoZSBmb2xsb3dpbmcgc3RyYXRlZ3k6XG4gKiAgLSBGb3IgaW5saW5lIG1vZHVsZXM6IEhhbmRsZSB0aGVtIHVzaW5nIGJ1bmRsZVxuICovXG5leHBvcnQgY29uc3QgY3JlYXRlQnVpbGRMb2FkZXI6IENyZWF0ZUJ1aWxkTG9hZGVyRm4gPVxuICBmdW5jdGlvbiBfY3JlYXRlQnVpbGRMb2FkZXIoXG4gICAgeyB1c2VyT3B0aW9ucywgc2VydmVyTWFuaWZlc3QsIHN0YXRpY01hbmlmZXN0IH0sXG4gICAgYnVuZGxlLFxuICAgIHRlbXBvcmFyeVJlZmVyZW5jZXMsXG4gICAgbG9nZ2VyID0gY3JlYXRlTG9nZ2VyKClcbiAgKSB7XG4gICAgY29uc3QgbWFuaWZlc3RLZXlzID0gT2JqZWN0LmtleXMoc2VydmVyTWFuaWZlc3QpO1xuICAgIGlmICghbWFuaWZlc3RLZXlzLmxlbmd0aCkge1xuICAgICAgdGhyb3cgbmV3IEVycm9yKFwiU2VydmVyIG1hbmlmZXN0IGlzIGVtcHR5XCIpO1xuICAgIH1cblxuICAgIHJldHVybiBhc3luYyBmdW5jdGlvbiBidWlsZExvYWRlcihpZCkge1xuICAgICAgaWYgKHVzZXJPcHRpb25zLnZlcmJvc2UpIHtcbiAgICAgICAgbG9nZ2VyLmluZm8oYFtidWlsZExvYWRlcl0gaWQ6ICR7aWR9YCk7XG4gICAgICAgIGxvZ2dlci5pbmZvKGBbYnVpbGRMb2FkZXJdIFN0YXJ0aW5nIGxvb2t1cCBmb3I6ICR7aWR9YCk7XG4gICAgICB9XG4gICAgICBjb25zdCBbd2l0aG91dFF1ZXJ5LCBxdWVyeV0gPSBpZC5zcGxpdChcIj9cIiwgMik7XG4gICAgICBjb25zdCBbbW9kdWxlSWQsIGV4cG9ydE5hbWVdID0gd2l0aG91dFF1ZXJ5LnNwbGl0KFwiI1wiLCAyKTtcbiAgICAgIFxuICAgICAgLy8gTm9ybWFsaXplIHRoZSBtb2R1bGVJZCBlYXJseSAodXNlZCB0aHJvdWdob3V0IHRoZSBmdW5jdGlvbilcbiAgICAgIGNvbnN0IFtub3JtYWxpemVkS2V5LCBub3JtYWxpemVkVmFsdWVdID0gdXNlck9wdGlvbnMubm9ybWFsaXplcihtb2R1bGVJZCk7XG4gICAgICBcbiAgICAgIC8vIEZvciB2aXJ0dWFsIG1vZHVsZXMgYW5kIG5vZGVfbW9kdWxlcywgdXNlIHNoYXJlZCB1dGlsaXR5IChzYW1lIGFzIFJTQyB3b3JrZXIgbG9hZGVyKVxuICAgICAgLy8gVGhpcyBoYW5kbGVzIF92aXJ0dWFsL2R5bmFtaWMtaW1wb3J0LWhlbHBlci5qcyBhbmQgcHJvdmlkZXMgc2hpbXMgaWYgbmVlZGVkXG4gICAgICAvLyBDaGVjayB0aGlzIGVhcmx5LCBiZWZvcmUgYnVpbGQtc3BlY2lmaWMgaGFuZGxpbmdcbiAgICAgIGNvbnN0IHZpcnR1YWxPck5vZGVNb2R1bGUgPSBhd2FpdCByZXNvbHZlVmlydHVhbEFuZE5vZGVNb2R1bGVzKFxuICAgICAgICBtb2R1bGVJZCxcbiAgICAgICAgZXhwb3J0TmFtZSxcbiAgICAgICAgdXNlck9wdGlvbnMudmVyYm9zZSxcbiAgICAgICAgbG9nZ2VyXG4gICAgICApO1xuICAgICAgaWYgKHZpcnR1YWxPck5vZGVNb2R1bGUgIT09IG51bGwpIHtcbiAgICAgICAgcmV0dXJuIHZpcnR1YWxPck5vZGVNb2R1bGU7XG4gICAgICB9XG4gICAgICBcbiAgICAgIGNvbnN0IG1vZHVsZVJlZiA9IGdldE1vZHVsZVJlZihpZCk7XG5cbiAgICAgIC8vIENoZWNrIGlmIHdlIGhhdmUgYSB0ZW1wb3JhcnkgcmVmZXJlbmNlIChjYWNoZWQgbW9kdWxlKVxuICAgICAgaWYgKHRlbXBvcmFyeVJlZmVyZW5jZXM/Lmhhcyhtb2R1bGVSZWYpKSB7XG4gICAgICAgIGNvbnN0IG1vZCA9IHRlbXBvcmFyeVJlZmVyZW5jZXMuZ2V0KG1vZHVsZVJlZik7XG4gICAgICAgIGlmICh0eXBlb2YgbW9kID09PSBcIm9iamVjdFwiICYmIG1vZCAhPT0gbnVsbCAmJiBcImVycm9yXCIgaW4gbW9kKSB7XG4gICAgICAgICAgLy8gaWdub3JlIGl0XG4gICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgcmV0dXJuIG1vZDtcbiAgICAgICAgfVxuICAgICAgfVxuXG4gICAgICB0cnkge1xuICAgICAgICAvLyBGb3IgaW5saW5lIG1vZHVsZXMsIGhhbmRsZSB0aGVtIGRpcmVjdGx5XG4gICAgICAgIGlmIChxdWVyeSA9PT0gXCJpbmxpbmVcIikge1xuICAgICAgICAgIGNvbnN0IG1hbmlmZXN0S2V5ID0gbm9ybWFsaXplZFZhbHVlO1xuICAgICAgICAgIGlmICh1c2VyT3B0aW9ucy52ZXJib3NlKSB7XG4gICAgICAgICAgICBsb2dnZXIuaW5mbyhcbiAgICAgICAgICAgICAgYFtidWlsZExvYWRlcl0gTG9va2luZyBmb3IgaW5saW5lIG1vZHVsZTogJHtub3JtYWxpemVkVmFsdWV9YFxuICAgICAgICAgICAgKTtcbiAgICAgICAgICB9XG5cbiAgICAgICAgICAvLyBGb3IgQ1NTIGZpbGVzLCB0cnkgdG8gcmVzb2x2ZSB0aGUgaGFzaGVkIGZpbGVuYW1lIHRvIHRoZSBhY3R1YWwgYnVuZGxlIGZpbGVuYW1lXG4gICAgICAgICAgbGV0IHJlc29sdmVkVmFsdWUgPSBub3JtYWxpemVkVmFsdWU7XG4gICAgICAgICAgaWYgKFxuICAgICAgICAgICAgbm9ybWFsaXplZFZhbHVlLnN0YXJ0c1dpdGgoXCJhc3NldHMvXCIpICYmXG4gICAgICAgICAgICBub3JtYWxpemVkVmFsdWUuZW5kc1dpdGgoXCIuY3NzXCIpXG4gICAgICAgICAgKSB7XG4gICAgICAgICAgICAvLyBFeHRyYWN0IHRoZSBiYXNlIHBhdGggd2l0aG91dCBoYXNoXG4gICAgICAgICAgICBjb25zdCBiYXNlUGF0aCA9IG5vcm1hbGl6ZWRWYWx1ZS5yZXBsYWNlKFxuICAgICAgICAgICAgICAvLVthLXpBLVowLTldK1xcLmNzcyQvLFxuICAgICAgICAgICAgICBcIi5jc3NcIlxuICAgICAgICAgICAgKTtcbiAgICAgICAgICAgIGlmICh1c2VyT3B0aW9ucy52ZXJib3NlKSB7XG4gICAgICAgICAgICAgIGxvZ2dlci5pbmZvKFxuICAgICAgICAgICAgICAgIGBbYnVpbGRMb2FkZXJdIENTUyBmaWxlIGRldGVjdGVkLCB0cnlpbmcgdG8gcmVzb2x2ZSAke25vcm1hbGl6ZWRWYWx1ZX0gdG8gJHtiYXNlUGF0aH1gXG4gICAgICAgICAgICAgICk7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICAvLyBUcnkgdGhlIGJhc2UgcGF0aCBmaXJzdFxuICAgICAgICAgICAgaWYgKGJ1bmRsZVtiYXNlUGF0aF0pIHtcbiAgICAgICAgICAgICAgcmVzb2x2ZWRWYWx1ZSA9IGJhc2VQYXRoO1xuICAgICAgICAgICAgICBpZiAodXNlck9wdGlvbnMudmVyYm9zZSkge1xuICAgICAgICAgICAgICAgIGxvZ2dlci5pbmZvKFxuICAgICAgICAgICAgICAgICAgYFtidWlsZExvYWRlcl0gUmVzb2x2ZWQgQ1NTIGZpbGUgdG86ICR7cmVzb2x2ZWRWYWx1ZX1gXG4gICAgICAgICAgICAgICAgKTtcbiAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgfVxuICAgICAgICAgIH1cblxuICAgICAgICAgIC8vIEZpcnN0IHRyeSB0byBmaW5kIHRoZSBtb2R1bGUgd2l0aG91dCB0aGUgZXhwb3J0IG5hbWVcbiAgICAgICAgICBpZiAodXNlck9wdGlvbnMudmVyYm9zZSkge1xuICAgICAgICAgICAgbG9nZ2VyLmluZm8oXG4gICAgICAgICAgICAgIGBbYnVpbGRMb2FkZXJdIFRyeWluZyBidW5kbGVbbW9kdWxlSWRdOiBidW5kbGVbXCIke21vZHVsZUlkfVwiXSA9ICR7ISFidW5kbGVbXG4gICAgICAgICAgICAgICAgbW9kdWxlSWRcbiAgICAgICAgICAgICAgXX1gXG4gICAgICAgICAgICApO1xuICAgICAgICAgICAgbG9nZ2VyLmluZm8oXG4gICAgICAgICAgICAgIGBbYnVpbGRMb2FkZXJdIFRyeWluZyBidW5kbGVbbm9ybWFsaXplZFZhbHVlXTogYnVuZGxlW1wiJHtub3JtYWxpemVkVmFsdWV9XCJdID0gJHshIWJ1bmRsZVtcbiAgICAgICAgICAgICAgICBub3JtYWxpemVkVmFsdWVcbiAgICAgICAgICAgICAgXX1gXG4gICAgICAgICAgICApO1xuICAgICAgICAgICAgbG9nZ2VyLmluZm8oXG4gICAgICAgICAgICAgIGBbYnVpbGRMb2FkZXJdIFRyeWluZyBidW5kbGVbcmVzb2x2ZWRWYWx1ZV06IGJ1bmRsZVtcIiR7cmVzb2x2ZWRWYWx1ZX1cIl0gPSAkeyEhYnVuZGxlW1xuICAgICAgICAgICAgICAgIHJlc29sdmVkVmFsdWVcbiAgICAgICAgICAgICAgXX1gXG4gICAgICAgICAgICApO1xuICAgICAgICAgIH1cbiAgICAgICAgICBjb25zdCBzZXJ2ZXJDaHVuayA9XG4gICAgICAgICAgICBidW5kbGVbbW9kdWxlSWRdID8/XG4gICAgICAgICAgICBidW5kbGVbbm9ybWFsaXplZFZhbHVlXSA/P1xuICAgICAgICAgICAgYnVuZGxlW3Jlc29sdmVkVmFsdWVdID8/XG4gICAgICAgICAgICBidW5kbGVbc2VydmVyTWFuaWZlc3RbbWFuaWZlc3RLZXldPy5maWxlXSA/P1xuICAgICAgICAgICAgYnVuZGxlW3N0YXRpY01hbmlmZXN0W21hbmlmZXN0S2V5XT8uZmlsZV0gPz9cbiAgICAgICAgICAgIGJ1bmRsZVtzZXJ2ZXJNYW5pZmVzdFtub3JtYWxpemVkS2V5XT8uZmlsZV0gPz9cbiAgICAgICAgICAgIGJ1bmRsZVtzdGF0aWNNYW5pZmVzdFtub3JtYWxpemVkS2V5XT8uZmlsZV0gPz9cbiAgICAgICAgICAgIE9iamVjdC5lbnRyaWVzKGJ1bmRsZSkuZmluZChcbiAgICAgICAgICAgICAgKFssIHZhbHVlXSkgPT4gdmFsdWUubmFtZSA9PT0gbm9ybWFsaXplZFZhbHVlXG4gICAgICAgICAgICApPy5bMV07XG5cbiAgICAgICAgICBpZiAodXNlck9wdGlvbnMudmVyYm9zZSAmJiBzZXJ2ZXJDaHVuaykge1xuICAgICAgICAgICAgbG9nZ2VyLmluZm8oYFtidWlsZExvYWRlcl0gRm91bmQgc2VydmVyQ2h1bms6ICR7c2VydmVyQ2h1bmsudHlwZX1gKTtcbiAgICAgICAgICB9XG5cbiAgICAgICAgICBpZiAoc2VydmVyQ2h1bmspIHtcbiAgICAgICAgICAgIGlmIChzZXJ2ZXJDaHVuay50eXBlID09PSBcImFzc2V0XCIpIHtcbiAgICAgICAgICAgICAgLy8gRm9yIENTUyBmaWxlcywgZW5zdXJlIHdlJ3JlIGluIHRoZSBSZWFjdCBTZXJ2ZXIgZW52aXJvbm1lbnRcbiAgICAgICAgICAgICAgaWYgKHVzZXJPcHRpb25zLmF1dG9EaXNjb3Zlci5qc29uUGF0dGVybi50ZXN0KG5vcm1hbGl6ZWRWYWx1ZSkpIHtcbiAgICAgICAgICAgICAgICBjb25zdCBqc29uQ29udGVudCA9IHNlcnZlckNodW5rLnNvdXJjZTtcbiAgICAgICAgICAgICAgICBpZiAodHlwZW9mIGpzb25Db250ZW50ID09PSBcInN0cmluZ1wiKSB7XG4gICAgICAgICAgICAgICAgICBpZiAodXNlck9wdGlvbnMudmVyYm9zZSkge1xuICAgICAgICAgICAgICAgICAgICBsb2dnZXIuaW5mbyhcbiAgICAgICAgICAgICAgICAgICAgICBgW2J1aWxkTG9hZGVyXSBSZXR1cm5pbmcgSlNPTiBjb250ZW50IGZvcjogJHtub3JtYWxpemVkVmFsdWV9YFxuICAgICAgICAgICAgICAgICAgICApO1xuICAgICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICAgICAgcmV0dXJuIHsgZGVmYXVsdDogSlNPTi5wYXJzZShqc29uQ29udGVudCkgfTtcbiAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgIH0gZWxzZSBpZiAoXG4gICAgICAgICAgICAgICAgdXNlck9wdGlvbnMuYXV0b0Rpc2NvdmVyLmNzc1BhdHRlcm4udGVzdChub3JtYWxpemVkVmFsdWUpXG4gICAgICAgICAgICAgICkge1xuICAgICAgICAgICAgICAgIGNvbnN0IGNzc0NvbnRlbnQgPSBzZXJ2ZXJDaHVuay5zb3VyY2U7XG4gICAgICAgICAgICAgICAgaWYgKHR5cGVvZiBjc3NDb250ZW50ID09PSBcInN0cmluZ1wiKSB7XG4gICAgICAgICAgICAgICAgICBpZiAodXNlck9wdGlvbnMudmVyYm9zZSkge1xuICAgICAgICAgICAgICAgICAgICBsb2dnZXIuaW5mbyhcbiAgICAgICAgICAgICAgICAgICAgICBgW2J1aWxkTG9hZGVyXSBSZXR1cm5pbmcgQ1NTIGNvbnRlbnQgZm9yOiAke25vcm1hbGl6ZWRWYWx1ZX0sIGxlbmd0aDogJHtjc3NDb250ZW50Lmxlbmd0aH1gXG4gICAgICAgICAgICAgICAgICAgICk7XG4gICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgICByZXR1cm4geyBkZWZhdWx0OiBjc3NDb250ZW50IH07XG4gICAgICAgICAgICAgICAgfSBlbHNlIHtcbiAgICAgICAgICAgICAgICAgIGlmICh1c2VyT3B0aW9ucy52ZXJib3NlKSB7XG4gICAgICAgICAgICAgICAgICAgIGxvZ2dlci5pbmZvKFxuICAgICAgICAgICAgICAgICAgICAgIGBbYnVpbGRMb2FkZXJdIENTUyBzb3VyY2UgaXMgbm90IHN0cmluZzogJHt0eXBlb2YgY3NzQ29udGVudH1gXG4gICAgICAgICAgICAgICAgICAgICk7XG4gICAgICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICB9XG4gICAgICAgICAgICAgIGlmICh1c2VyT3B0aW9ucy52ZXJib3NlKSB7XG4gICAgICAgICAgICAgICAgbG9nZ2VyLmluZm8oXG4gICAgICAgICAgICAgICAgICBgW2J1aWxkTG9hZGVyXSBSZXR1cm5pbmcgZGVmYXVsdCBhc3NldCBzb3VyY2UgZm9yOiAke25vcm1hbGl6ZWRWYWx1ZX1gXG4gICAgICAgICAgICAgICAgKTtcbiAgICAgICAgICAgICAgfVxuICAgICAgICAgICAgICByZXR1cm4geyBkZWZhdWx0OiBzZXJ2ZXJDaHVuay5zb3VyY2UgfTtcbiAgICAgICAgICAgIH0gZWxzZSBpZiAoXCJjb2RlXCIgaW4gc2VydmVyQ2h1bmspIHtcbiAgICAgICAgICAgICAgaWYgKHVzZXJPcHRpb25zLnZlcmJvc2UpIHtcbiAgICAgICAgICAgICAgICBsb2dnZXIuaW5mbyhcbiAgICAgICAgICAgICAgICAgIGBbYnVpbGRMb2FkZXJdIFJldHVybmluZyBjb2RlIGZvcjogJHtub3JtYWxpemVkVmFsdWV9YFxuICAgICAgICAgICAgICAgICk7XG4gICAgICAgICAgICAgIH1cbiAgICAgICAgICAgICAgcmV0dXJuIHsgZGVmYXVsdDogc2VydmVyQ2h1bmsuY29kZSB9O1xuICAgICAgICAgICAgfVxuICAgICAgICAgIH1cbiAgICAgICAgICBjb25zdCBwYW5pY0Vycm9yID0gaGFuZGxlRXJyb3Ioe1xuICAgICAgICAgICAgZXJyb3I6IG5ldyBFcnJvcihcbiAgICAgICAgICAgICAgYENvdWxkIG5vdCBmaW5kIGlubGluZSBtb2R1bGUgZm9yOiAke25vcm1hbGl6ZWRWYWx1ZX1gXG4gICAgICAgICAgICApLFxuICAgICAgICAgICAgbG9nZ2VyLFxuICAgICAgICAgICAgbG9nOiB0cnVlLFxuICAgICAgICAgICAgcGFuaWNUaHJlc2hvbGQ6IHVzZXJPcHRpb25zLnBhbmljVGhyZXNob2xkLFxuICAgICAgICAgICAgY29udGV4dDogXCJCdWlsZCBMb2FkZXIgRXJyb3IgKGlubGluZSlcIixcbiAgICAgICAgICB9KTtcbiAgICAgICAgICBpZiAocGFuaWNFcnJvciAhPSBudWxsKSB7XG4gICAgICAgICAgICB0aHJvdyBwYW5pY0Vycm9yO1xuICAgICAgICAgIH1cbiAgICAgICAgICByZXR1cm4gbnVsbDtcbiAgICAgICAgfVxuXG4gICAgICAgIC8vIGNoZWNrIHRoZSBidW5kbGUgbWFuaWZlc3QgZm9yIGEgZGlyZWN0IG1hdGNoXG4gICAgICAgIGNvbnN0IGJ1bmRsZUVudHJ5ID0gYnVuZGxlW3dpdGhvdXRRdWVyeV07XG4gICAgICAgIGlmIChidW5kbGVFbnRyeSkge1xuICAgICAgICAgIHRyeSB7XG4gICAgICAgICAgICBjb25zdCBmaWxlUGF0aCA9IGpvaW4oXG4gICAgICAgICAgICAgIHVzZXJPcHRpb25zLnByb2plY3RSb290LFxuICAgICAgICAgICAgICB1c2VyT3B0aW9ucy5idWlsZC5vdXREaXIsXG4gICAgICAgICAgICAgIHVzZXJPcHRpb25zLmJ1aWxkLnNlcnZlcixcbiAgICAgICAgICAgICAgd2l0aG91dFF1ZXJ5XG4gICAgICAgICAgICApO1xuICAgICAgICAgICAgY29uc3QgZmlsZVVybCA9IHBhdGhUb0ZpbGVVUkwoZmlsZVBhdGgpLmhyZWY7XG4gICAgICAgICAgICBjb25zdCBtb2R1bGUgPSBhd2FpdCBpbXBvcnQoZmlsZVVybCk7XG4gICAgICAgICAgICB0ZW1wb3JhcnlSZWZlcmVuY2VzPy5zZXQobW9kdWxlUmVmLCBtb2R1bGUpO1xuICAgICAgICAgICAgcmV0dXJuIG1vZHVsZTtcbiAgICAgICAgICB9IGNhdGNoIChlcnJvcikge1xuICAgICAgICAgICAgY29uc3QgcGFuaWNFcnJvciA9IGhhbmRsZUVycm9yKHtcbiAgICAgICAgICAgICAgZXJyb3I6IGVycm9yLFxuICAgICAgICAgICAgICBsb2dnZXIsXG4gICAgICAgICAgICAgIHBhbmljVGhyZXNob2xkOiB1c2VyT3B0aW9ucy5wYW5pY1RocmVzaG9sZCxcbiAgICAgICAgICAgICAgY29udGV4dDogXCJCdWlsZCBMb2FkZXIgRXJyb3IgKGJ1bmRsZSlcIixcbiAgICAgICAgICAgIH0pO1xuICAgICAgICAgICAgdGVtcG9yYXJ5UmVmZXJlbmNlcz8uZGVsZXRlKG1vZHVsZVJlZik7XG4gICAgICAgICAgICBpZiAocGFuaWNFcnJvciAhPSBudWxsKSB7XG4gICAgICAgICAgICAgIHRocm93IHBhbmljRXJyb3I7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgfVxuICAgICAgICB9XG5cbiAgICAgICAgLy8gRm9yIHN0YXRpYyBhc3NldHMsIHVzZSBzdGF0aWMgbWFuaWZlc3RcbiAgICAgICAgY29uc3Qgc3RhdGljRW50cnkgPSBzdGF0aWNNYW5pZmVzdFtub3JtYWxpemVkVmFsdWVdO1xuICAgICAgICBpZiAoc3RhdGljRW50cnkpIHtcbiAgICAgICAgICB0cnkge1xuICAgICAgICAgICAgY29uc3QgZmlsZVBhdGggPSBqb2luKFxuICAgICAgICAgICAgICB1c2VyT3B0aW9ucy5wcm9qZWN0Um9vdCxcbiAgICAgICAgICAgICAgdXNlck9wdGlvbnMuYnVpbGQub3V0RGlyLFxuICAgICAgICAgICAgICB1c2VyT3B0aW9ucy5idWlsZC5zdGF0aWMsXG4gICAgICAgICAgICAgIHN0YXRpY0VudHJ5LmZpbGVcbiAgICAgICAgICAgICk7XG4gICAgICAgICAgICBjb25zdCBmaWxlVXJsID0gcGF0aFRvRmlsZVVSTChmaWxlUGF0aCkuaHJlZjtcbiAgICAgICAgICAgIGNvbnN0IG1vZHVsZSA9IGF3YWl0IGltcG9ydChmaWxlVXJsKTtcbiAgICAgICAgICAgIHRlbXBvcmFyeVJlZmVyZW5jZXM/LnNldChtb2R1bGVSZWYsIG1vZHVsZSk7XG4gICAgICAgICAgICAvLyBJZiB3ZSBoYXZlIGFuIGV4cG9ydCBuYW1lLCBtYWtlIHN1cmUgaXQncyBhIGtleVxuICAgICAgICAgICAgaWYgKGV4cG9ydE5hbWUgJiYgIShleHBvcnROYW1lIGluIG1vZHVsZSkpIHtcbiAgICAgICAgICAgICAgdGhyb3cgbmV3IEVycm9yKFxuICAgICAgICAgICAgICAgIGBFeHBvcnQgJHtleHBvcnROYW1lfSBub3QgZm91bmQgaW4gbW9kdWxlICR7bm9ybWFsaXplZFZhbHVlfWBcbiAgICAgICAgICAgICAgKTtcbiAgICAgICAgICAgIH1cbiAgICAgICAgICAgIHJldHVybiBtb2R1bGU7XG4gICAgICAgICAgfSBjYXRjaCAoZXJyb3IpIHtcbiAgICAgICAgICAgIGNvbnN0IHBhbmljRXJyb3IgPSBoYW5kbGVFcnJvcih7XG4gICAgICAgICAgICAgIGVycm9yOiBlcnJvcixcbiAgICAgICAgICAgICAgbG9nZ2VyLFxuICAgICAgICAgICAgICBwYW5pY1RocmVzaG9sZDogdXNlck9wdGlvbnMucGFuaWNUaHJlc2hvbGQsXG4gICAgICAgICAgICAgIGNvbnRleHQ6IFwiQnVpbGQgTG9hZGVyIEVycm9yIChzdGF0aWMpXCIsXG4gICAgICAgICAgICB9KTtcbiAgICAgICAgICAgIHRlbXBvcmFyeVJlZmVyZW5jZXM/LmRlbGV0ZShtb2R1bGVSZWYpO1xuICAgICAgICAgICAgaWYgKHBhbmljRXJyb3IgIT0gbnVsbCkge1xuICAgICAgICAgICAgICB0aHJvdyBwYW5pY0Vycm9yO1xuICAgICAgICAgICAgfVxuICAgICAgICAgIH1cbiAgICAgICAgfVxuXG4gICAgICAgIC8vIFVzZSBzaGFyZWQgbG9hZGVyIHV0aWxpdHkgZm9yIGNvbW1vbiBjYXNlcyAodmlydHVhbCBtb2R1bGVzLCBtYW5pZmVzdCByZXNvbHV0aW9uLCBpbXBvcnRzKVxuICAgICAgICAvLyBUaGlzIGhhbmRsZXMgdGhlIHNhbWUgbG9naWMgYXMgUlNDIHdvcmtlciBsb2FkZXJcbiAgICAgICAgdHJ5IHtcbiAgICAgICAgICBjb25zdCBtb2R1bGUgPSBhd2FpdCBjcmVhdGVTaGFyZWRMb2FkZXIoe1xuICAgICAgICAgICAgbW9kdWxlSWQsXG4gICAgICAgICAgICBleHBvcnROYW1lLFxuICAgICAgICAgICAgdmVyYm9zZTogdXNlck9wdGlvbnMudmVyYm9zZSxcbiAgICAgICAgICAgIGxvZ2dlcixcbiAgICAgICAgICAgIHJlc29sdmVWaXJ0dWFsOiB0cnVlLFxuICAgICAgICAgICAgbWFuaWZlc3Q6IHNlcnZlck1hbmlmZXN0LFxuICAgICAgICAgICAgbm9ybWFsaXplcjogdXNlck9wdGlvbnMubm9ybWFsaXplcixcbiAgICAgICAgICAgIG1vZHVsZUJhc2U6IHVzZXJPcHRpb25zLm1vZHVsZUJhc2UsXG4gICAgICAgICAgICBwcmVzZXJ2ZU1vZHVsZXNSb290OiB1c2VyT3B0aW9ucy5idWlsZC5wcmVzZXJ2ZU1vZHVsZXNSb290LFxuICAgICAgICAgICAgcHJvamVjdFJvb3Q6IHVzZXJPcHRpb25zLnByb2plY3RSb290LFxuICAgICAgICAgICAgYnVpbGRPdXREaXI6IHVzZXJPcHRpb25zLmJ1aWxkLm91dERpcixcbiAgICAgICAgICAgIGJ1aWxkU2VydmVyRGlyOiB1c2VyT3B0aW9ucy5idWlsZC5zZXJ2ZXIsXG4gICAgICAgICAgICBpc0J1aWxkTW9kZTogdHJ1ZSxcbiAgICAgICAgICAgIGlzU2VydmVNb2RlOiBmYWxzZSxcbiAgICAgICAgICAgIGVmZmVjdGl2ZVByb2plY3RSb290OiB1c2VyT3B0aW9ucy5wcm9qZWN0Um9vdCxcbiAgICAgICAgICAgIGJ1aWxkOiB7XG4gICAgICAgICAgICAgIG91dERpcjogdXNlck9wdGlvbnMuYnVpbGQub3V0RGlyLFxuICAgICAgICAgICAgICBzZXJ2ZXI6IHVzZXJPcHRpb25zLmJ1aWxkLnNlcnZlcixcbiAgICAgICAgICAgICAgY2xpZW50OiB1c2VyT3B0aW9ucy5idWlsZC5jbGllbnQsXG4gICAgICAgICAgICAgIHN0YXRpYzogdXNlck9wdGlvbnMuYnVpbGQuc3RhdGljLFxuICAgICAgICAgICAgfSxcbiAgICAgICAgICB9KTtcbiAgICAgICAgICBcbiAgICAgICAgICAvLyBTdG9yZSBpbiB0ZW1wb3JhcnkgcmVmZXJlbmNlcyBmb3IgY2FjaGluZ1xuICAgICAgICAgIHRlbXBvcmFyeVJlZmVyZW5jZXM/LnNldChtb2R1bGVSZWYsIG1vZHVsZSk7XG4gICAgICAgICAgcmV0dXJuIG1vZHVsZTtcbiAgICAgICAgfSBjYXRjaCAoZXJyb3IpIHtcbiAgICAgICAgICBjb25zdCBlcnIgPSB0b0Vycm9yKGVycm9yKTtcbiAgICAgICAgICBjb25zdCBwYW5pY0Vycm9yID0gaGFuZGxlRXJyb3Ioe1xuICAgICAgICAgICAgZXJyb3I6IGVycixcbiAgICAgICAgICAgIGxvZ2dlcixcbiAgICAgICAgICAgIHBhbmljVGhyZXNob2xkOiB1c2VyT3B0aW9ucy5wYW5pY1RocmVzaG9sZCxcbiAgICAgICAgICAgIGNvbnRleHQ6IFwiQnVpbGQgTG9hZGVyIEVycm9yIChzaGFyZWQpXCIsXG4gICAgICAgICAgfSk7XG4gICAgICAgICAgdGVtcG9yYXJ5UmVmZXJlbmNlcz8uZGVsZXRlKG1vZHVsZVJlZik7XG4gICAgICAgICAgaWYgKHBhbmljRXJyb3IgIT0gbnVsbCkge1xuICAgICAgICAgICAgdGhyb3cgcGFuaWNFcnJvcjtcbiAgICAgICAgICB9XG4gICAgICAgIH1cbiAgICAgIH0gY2F0Y2ggKGVycm9yKSB7XG4gICAgICAgIC8vIEVuaGFuY2UgUmVhY3QgU2VydmVyIERPTSBlcnJvcnMgd2l0aCBpbXBvcnQgY29udGV4dFxuICAgICAgICBsZXQgZW5oYW5jZWRFcnJvciA9IGVycm9yIGluc3RhbmNlb2YgRXJyb3IgPyBlcnJvciA6IG5ldyBFcnJvcihTdHJpbmcoZXJyb3IpKTtcbiAgICAgICAgaWYgKGVuaGFuY2VkRXJyb3IubWVzc2FnZS5pbmNsdWRlcygnUmVhY3QgU2VydmVyIFdyaXRlciBjYW5ub3QgYmUgdXNlZCBvdXRzaWRlIGEgcmVhY3Qtc2VydmVyIGVudmlyb25tZW50JykpIHtcbiAgICAgICAgICBjb25zdCBmaWxlUGF0aCA9IHJlc29sdmUoXG4gICAgICAgICAgICB1c2VyT3B0aW9ucy5wcm9qZWN0Um9vdCxcbiAgICAgICAgICAgIHVzZXJPcHRpb25zLmJ1aWxkLm91dERpcixcbiAgICAgICAgICAgIHVzZXJPcHRpb25zLmJ1aWxkLnNlcnZlcixcbiAgICAgICAgICAgIG1vZHVsZUlkXG4gICAgICAgICAgKTtcbiAgICAgICAgICBlbmhhbmNlZEVycm9yID0gbmV3IEVycm9yKFxuICAgICAgICAgICAgYCR7ZW5oYW5jZWRFcnJvci5tZXNzYWdlfVxcbmAgK1xuICAgICAgICAgICAgYCAg4oaSIEltcG9ydGVkIGZyb206ICR7bW9kdWxlSWR9XFxuYCArXG4gICAgICAgICAgICBgICDihpIgRXhwb3J0OiAke2V4cG9ydE5hbWV9XFxuYCArXG4gICAgICAgICAgICBgICDihpIgRmlsZSBwYXRoOiAke2ZpbGVQYXRofVxcbmAgK1xuICAgICAgICAgICAgYCAg4oaSIE5PREVfT1BUSU9OUzogJHtwcm9jZXNzLmVudi5OT0RFX09QVElPTlMgfHwgJ25vdCBzZXQnfVxcbmAgK1xuICAgICAgICAgICAgYCAg4oaSIGV4ZWNBcmd2OiAke3Byb2Nlc3MuZXhlY0FyZ3Yuam9pbignICcpIHx8ICdub3Qgc2V0J31gXG4gICAgICAgICAgKTtcbiAgICAgICAgICB0aHJvdyBlbmhhbmNlZEVycm9yO1xuICAgICAgICB9XG4gICAgICAgIFxuICAgICAgICBjb25zdCBlbXB0eUV4cG9ydHMgPSB7XG4gICAgICAgICAgZXJyb3I6IGVuaGFuY2VkRXJyb3IsXG4gICAgICAgICAgaWQ6IGlkLFxuICAgICAgICB9O1xuICAgICAgICB0ZW1wb3JhcnlSZWZlcmVuY2VzPy5kZWxldGUobW9kdWxlUmVmKTtcbiAgICAgICAgcmV0dXJuIGVtcHR5RXhwb3J0cztcbiAgICAgIH1cbiAgICB9O1xuICB9O1xuIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7Ozs7Ozs7Ozs7Ozs7O0FBaUJPLE1BQU0saUJBQ1gsR0FBQSxTQUFTLGtCQUNQLENBQUEsRUFBRSxXQUFhLEVBQUEsY0FBQSxFQUFnQixjQUFlLEVBQUEsRUFDOUMsTUFDQSxFQUFBLG1CQUFBLEVBQ0EsTUFBUyxHQUFBLFlBQUEsRUFDVCxFQUFBO0FBQ0EsRUFBTSxNQUFBLFlBQUEsR0FBZSxNQUFPLENBQUEsSUFBQSxDQUFLLGNBQWMsQ0FBQTtBQUMvQyxFQUFJLElBQUEsQ0FBQyxhQUFhLE1BQVEsRUFBQTtBQUN4QixJQUFNLE1BQUEsSUFBSSxNQUFNLDBCQUEwQixDQUFBO0FBQUE7QUFHNUMsRUFBTyxPQUFBLGVBQWUsWUFBWSxFQUFJLEVBQUE7QUFDcEMsSUFBQSxJQUFJLFlBQVksT0FBUyxFQUFBO0FBQ3ZCLE1BQU8sTUFBQSxDQUFBLElBQUEsQ0FBSyxDQUFxQixrQkFBQSxFQUFBLEVBQUUsQ0FBRSxDQUFBLENBQUE7QUFDckMsTUFBTyxNQUFBLENBQUEsSUFBQSxDQUFLLENBQXNDLG1DQUFBLEVBQUEsRUFBRSxDQUFFLENBQUEsQ0FBQTtBQUFBO0FBRXhELElBQUEsTUFBTSxDQUFDLFlBQWMsRUFBQSxLQUFLLElBQUksRUFBRyxDQUFBLEtBQUEsQ0FBTSxLQUFLLENBQUMsQ0FBQTtBQUM3QyxJQUFBLE1BQU0sQ0FBQyxRQUFVLEVBQUEsVUFBVSxJQUFJLFlBQWEsQ0FBQSxLQUFBLENBQU0sS0FBSyxDQUFDLENBQUE7QUFHeEQsSUFBQSxNQUFNLENBQUMsYUFBZSxFQUFBLGVB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