@hamedb89/localghost 0.3.0 → 0.4.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/cli.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/cli.ts","../src/activity.ts","../src/config.ts","../src/parse.ts","../src/brand.ts","../src/caddy.ts","../src/fs.ts","../src/command.ts","../src/context.ts","../src/port.ts","../src/registry.ts","../src/tunnel.ts","../src/doctor.ts","../src/env.ts","../src/ghost-file.ts","../src/ghost-agent.ts","../src/relay.ts","../src/ghost-tunnel-store.ts","../src/hosts-file.ts","../src/init.ts","../src/guide.ts","../src/prompt.ts","../src/routes.ts","../src/state.ts","../src/update-check.ts","../src/process.ts"],"sourcesContent":["#!/usr/bin/env node\n\nimport { existsSync, readFileSync, unlinkSync } from \"node:fs\";\nimport { Command, InvalidArgumentError } from \"commander\";\nimport {\n getLocalghostActivityPath,\n listLocalghostSetups,\n listLocalghostRuns,\n registerLocalghostRun,\n registerLocalghostSetup,\n unregisterLocalghostSetup,\n unregisterLocalghostRun,\n type LocalghostRunRecord,\n type LocalghostSetupRecord\n} from \"./activity.js\";\nimport { getProjectName, readDevHosts, resolveDevHostsPath, sanitizeProjectName, type ReadDevHostsOptions } from \"./config.js\";\nimport { renderLocalghostBanner } from \"./brand.js\";\nimport { getCaddyfilePath, renderCaddyfile, stopCaddyProcesses, validateCaddyfile, writeCaddyfile, startCaddy, trustCaddy } from \"./caddy.js\";\nimport {\n detectDevCommand,\n detectDevServices,\n formatDetectedDevCommand,\n formatDetectedDevServices,\n type DetectedDevService\n} from \"./command.js\";\nimport { readLocalghostProjectConfig, resolveLocalghostContext } from \"./context.js\";\nimport { checkCaddy, runDoctor } from \"./doctor.js\";\nimport { assertLocalDevelopment } from \"./env.js\";\nimport { listGhostTunnelEntries } from \"./ghost-file.js\";\nimport { startGhostTunnelAgent } from \"./ghost-agent.js\";\nimport { createRedisGhostTunnelStoreFromEnv } from \"./ghost-tunnel-store.js\";\nimport { getSystemHostsPath, removeSystemHosts, renderHostsBlock, updateSystemHosts } from \"./hosts-file.js\";\nimport { initLocalghost, type PackageManager } from \"./init.js\";\nimport { formatLocalghostAgentGuide } from \"./guide.js\";\nimport { findLocalMdnsHosts, type DevHostEntry } from \"./parse.js\";\nimport { isPortAvailable } from \"./port.js\";\nimport { createLocalghostRegistry } from \"./registry.js\";\nimport { canPrompt, confirm } from \"./prompt.js\";\nimport { formatDomainRoutes, formatGhostTunnel } from \"./routes.js\";\nimport { getLocalghostStatePath, patchLocalghostState, readLocalghostState, writeLocalghostState } from \"./state.js\";\nimport { checkForUpdate, formatUpdateMessage, LOCALGHOST_VERSION, maybeNotifyAboutUpdate } from \"./update-check.js\";\nimport type { GhostTunnelConfig } from \"./tunnel.js\";\nimport { execa } from \"execa\";\nimport { signalManagedProcess, signalManagedProcessPid } from \"./process.js\";\n\nfunction warnAboutLocalMdns(entries: ReturnType<typeof readDevHosts>) {\n const localHosts = findLocalMdnsHosts(entries);\n\n if (localHosts.length > 0) {\n console.warn(\n `Warning: .local can collide with mDNS/Bonjour. Prefer .localhost for dev hosts: ${localHosts.join(\", \")}`\n );\n }\n}\n\nfunction shouldColor() {\n return process.stdout.isTTY && !process.env.NO_COLOR;\n}\n\nfunction printLocalghostBanner() {\n console.log(renderLocalghostBanner());\n console.log(\"\");\n}\n\nfunction logDomainRoutes(\n entries: ReturnType<typeof readDevHosts>,\n options: { https?: boolean; ghostTunnel?: GhostTunnelConfig; verbose?: boolean } = {}\n) {\n console.log(formatDomainRoutes(entries, options));\n if (options.ghostTunnel?.enabled) {\n console.log(formatGhostTunnel(options.ghostTunnel, {\n color: shouldColor(),\n label: \"expected\",\n verbose: options.verbose === true\n }));\n }\n}\n\nfunction parsePort(value: string) {\n const port = Number.parseInt(value, 10);\n if (!Number.isInteger(port) || port < 1 || port > 65535) {\n throw new InvalidArgumentError(\"Port must be a number between 1 and 65535.\");\n }\n\n return port;\n}\n\nfunction parsePackageManager(value: string): PackageManager {\n if (value === \"npm\" || value === \"yarn\" || value === \"pnpm\" || value === \"bun\") return value;\n throw new InvalidArgumentError(\"Package manager must be npm, pnpm, yarn, or bun.\");\n}\n\ntype ReleaseBump = \"patch\" | \"minor\" | \"major\";\n\nfunction parseReleaseBump(value: string): ReleaseBump {\n if (value === \"patch\" || value === \"minor\" || value === \"major\") return value;\n throw new InvalidArgumentError(\"Release bump must be patch, minor, or major.\");\n}\n\nfunction collect(value: string, previous: string[] = []) {\n return [...previous, value];\n}\n\nfunction parseBooleanLike(value: string | boolean) {\n if (value === true) return true;\n if (value === false) return false;\n const normalized = value.toLowerCase();\n if ([\"1\", \"true\", \"yes\", \"y\", \"on\"].includes(normalized)) return true;\n if ([\"0\", \"false\", \"no\", \"n\", \"off\"].includes(normalized)) return false;\n throw new InvalidArgumentError(\"Value must be yes or no.\");\n}\n\ntype ConfigCliOptions = {\n cwd: string;\n config?: string[];\n configPattern?: string;\n};\n\ntype ProxyModeCliOptions = {\n https?: boolean;\n ssl?: boolean;\n};\n\ntype TrustCliOptions = {\n trust?: boolean;\n};\n\ntype AutoRepairCliOptions = {\n autoRepair?: boolean;\n};\n\ntype CleanCaddyCliOptions = {\n cleanCaddy?: boolean;\n};\n\nfunction contextOptionsFromCli(options: ConfigCliOptions & { project?: string } & ProxyModeCliOptions & AutoRepairCliOptions) {\n return {\n cwd: options.cwd,\n ...(options.project ? { project: options.project } : {}),\n ...(options.config && options.config.length > 0 ? { configFiles: options.config } : {}),\n ...(options.configPattern ? { configPattern: options.configPattern } : {}),\n ...(useHttps(options) ? { https: true } : {}),\n ...(typeof options.autoRepair === \"boolean\" ? { autoRepair: options.autoRepair } : {})\n };\n}\n\nfunction readOptionsFromCli(options: ConfigCliOptions): ReadDevHostsOptions {\n return {\n cwd: options.cwd,\n ...(options.config && options.config.length > 0 ? { configFiles: options.config } : {}),\n ...(options.configPattern ? { configPattern: options.configPattern } : {})\n };\n}\n\nasync function assertCaddyReady() {\n const caddy = await checkCaddy();\n if (caddy.found) return;\n\n throw new Error([\n \"Caddy was not found.\",\n `Install it with: ${caddy.installHint}`,\n \"Localghost will not install it for you. No surprise spells.\"\n ].join(\"\\n\"));\n}\n\nfunction cleanManagedCaddyProcesses() {\n const runs = listLocalghostRuns();\n const legacyPids = runs.flatMap((run) => run.caddyPid && !run.caddyPgid ? [run.caddyPid] : []);\n const managedPgid = runs.flatMap((run) => run.caddyPgid ? [run.caddyPgid] : []);\n const legacyResult = stopCaddyProcesses(legacyPids);\n const managedResult = stopCaddyProcesses(managedPgid, signalManagedProcessPid);\n const result = {\n stopped: [...legacyResult.stopped, ...managedResult.stopped],\n alreadyExited: [...legacyResult.alreadyExited, ...managedResult.alreadyExited],\n failed: [...legacyResult.failed, ...managedResult.failed]\n };\n\n for (const run of runs) {\n const caddyIdentity = run.caddyPgid ?? run.caddyPid;\n if (caddyIdentity && (result.stopped.includes(caddyIdentity) || result.alreadyExited.includes(caddyIdentity))) {\n unregisterLocalghostRun(run.id);\n }\n }\n\n if (result.stopped.length > 0) {\n console.log(`Stopped ${result.stopped.length} Localghost-managed Caddy process${result.stopped.length === 1 ? \"\" : \"es\"}.`);\n }\n if (result.alreadyExited.length > 0) {\n console.log(`Removed ${result.alreadyExited.length} stale Localghost Caddy record${result.alreadyExited.length === 1 ? \"\" : \"s\"}.`);\n }\n if (result.failed.length > 0) {\n throw new Error(`Could not stop Localghost-managed Caddy PID(s): ${result.failed.map(({ pid }) => pid).join(\", \")}.`);\n }\n}\n\nfunction existingTrustMarkers(cwd: string) {\n const state = readLocalghostState(cwd);\n return {\n ...(state?.caddyTrustedAt ? { caddyTrustedAt: state.caddyTrustedAt } : {}),\n ...(state?.caddyTrustPromptedAt ? { caddyTrustPromptedAt: state.caddyTrustPromptedAt } : {})\n };\n}\n\nfunction explainHostsPassword() {\n console.log(\"Localghost may ask for your password to update its managed block in /etc/hosts.\");\n console.log(\"It will only touch the lines between # localghost:start and # localghost:end.\");\n}\n\nfunction explainTrustPassword() {\n console.log(\"Localghost can trust Caddy's local HTTPS CA so browsers stop showing local certificate warnings.\");\n console.log(\"macOS may ask for your password to add that local CA to Keychain.\");\n console.log(\"This only affects Caddy's local development certificates on this machine.\");\n}\n\nfunction useHttps(options: ProxyModeCliOptions) {\n return options.https === true || options.ssl === true;\n}\n\nfunction getSetupCommand(options: { https?: boolean; config?: string[]; configPattern?: string }) {\n const configFlags = [\n ...(options.config ?? []).map((config) => ` --config ${config}`),\n ...(options.configPattern ? [` --config-pattern ${options.configPattern}`] : [])\n ].join(\"\");\n return `localghost setup${configFlags}${options.https ? \" --https\" : \"\"}`;\n}\n\nfunction getSetupReadiness(options: ConfigCliOptions & {\n project?: string;\n https?: boolean;\n ignoreCaddyfile?: boolean;\n entries?: DevHostEntry[];\n configPath?: string;\n projectName?: string;\n}) {\n const projectName = sanitizeProjectName(options.projectName ?? options.project ?? getProjectName(options.cwd));\n const readOptions = readOptionsFromCli(options);\n const entries = options.entries ?? readDevHosts(readOptions);\n const configPath = options.configPath ?? resolveDevHostsPath(readOptions).path;\n const caddyfilePath = getCaddyfilePath(options.cwd);\n const statePath = getLocalghostStatePath(options.cwd);\n const state = readLocalghostState(options.cwd);\n const https = options.https === true;\n const reasons: string[] = [];\n\n if (!state) {\n reasons.push(`No Localghost setup state found at ${statePath}.`);\n } else {\n if (state.action !== \"setup\") reasons.push(`Last Localghost action is ${state.action}, not setup.`);\n if (state.projectName !== projectName) reasons.push(`Setup state is for project ${state.projectName}, not ${projectName}.`);\n if (state.configPath !== configPath) reasons.push(`Setup state points at ${state.configPath ?? \"no config\"}, not ${configPath}.`);\n }\n\n const hostsPath = getSystemHostsPath();\n try {\n const hosts = readFileSync(hostsPath, \"utf8\");\n const expectedHostsBlock = renderHostsBlock(projectName, entries).trimEnd();\n if (!hosts.includes(expectedHostsBlock)) {\n reasons.push(`The Localghost hosts block in ${hostsPath} is missing or stale.`);\n }\n } catch (error) {\n const message = error instanceof Error ? error.message : String(error);\n reasons.push(`Could not read ${hostsPath}: ${message}`);\n }\n\n if (!options.ignoreCaddyfile) {\n if (!existsSync(caddyfilePath)) {\n reasons.push(`Missing Caddyfile at ${caddyfilePath}.`);\n } else {\n const expectedCaddyfile = renderCaddyfile(entries, { https });\n const currentCaddyfile = readFileSync(caddyfilePath, \"utf8\");\n if (currentCaddyfile !== expectedCaddyfile) {\n reasons.push(`Caddyfile at ${caddyfilePath} is stale for ${https ? \"HTTPS\" : \"HTTP\"} mode.`);\n }\n }\n }\n\n return {\n ready: reasons.length === 0,\n reasons,\n entries,\n projectName,\n configPath,\n caddyfilePath,\n statePath,\n setupCommand: getSetupCommand(options)\n };\n}\n\nasync function runSetupFromReadiness(\n cwd: string,\n https: boolean,\n readiness: ReturnType<typeof getSetupReadiness>\n) {\n explainHostsPassword();\n const hostsResult = await updateSystemHosts(readiness.projectName, readiness.entries);\n const caddyfilePath = await writeCaddyfile(readiness.entries, cwd, { https });\n await validateCaddyfile(caddyfilePath);\n writeLocalghostState(cwd, {\n action: \"setup\",\n projectName: readiness.projectName,\n cwd,\n configPath: readiness.configPath,\n hostsPath: hostsResult.hostsPath,\n hostsChanged: hostsResult.changed,\n ...(hostsResult.tempPath ? { hostsTempPath: hostsResult.tempPath } : {}),\n caddyfilePath,\n caddyHttps: https,\n ...existingTrustMarkers(cwd),\n entries: readiness.entries\n });\n registerLocalghostSetup({\n cwd,\n projectName: readiness.projectName,\n configPath: readiness.configPath,\n caddyfilePath,\n https,\n entries: readiness.entries\n });\n}\n\nfunction wait(ms: number) {\n return new Promise((resolve) => setTimeout(resolve, ms));\n}\n\nasync function runTrust(cwd: string, caddyfilePath: string) {\n await wait(350);\n try {\n await trustCaddy(caddyfilePath);\n } catch {\n await wait(750);\n await trustCaddy(caddyfilePath);\n }\n\n patchLocalghostState(cwd, { caddyTrustedAt: new Date().toISOString() });\n console.log(\"Local HTTPS trust is ready.\");\n}\n\nasync function maybeTrustCaddy(\n options: {\n cwd: string;\n https: boolean;\n caddyfilePath: string;\n trust?: boolean;\n }\n) {\n if (!options.https) return;\n\n const state = readLocalghostState(options.cwd);\n if (!options.trust && state?.caddyTrustedAt) return;\n\n let shouldTrust = options.trust === true;\n\n if (!shouldTrust) {\n if (state?.caddyTrustPromptedAt || !canPrompt()) return;\n\n explainTrustPassword();\n shouldTrust = await confirm(\"Trust local HTTPS certificates now?\", true);\n }\n\n if (!shouldTrust) {\n patchLocalghostState(options.cwd, { caddyTrustPromptedAt: new Date().toISOString() });\n console.log(\"Okay. Localghost will still run HTTPS, but the browser may show a certificate warning.\");\n console.log(\"Run localghost trust when you want to trust Caddy's local CA.\");\n return;\n }\n\n await runTrust(options.cwd, options.caddyfilePath);\n}\n\ntype LocalghostRouteView = {\n host: string;\n port: number;\n target: string;\n listening: boolean;\n};\n\ntype LocalghostInstanceView = {\n id: string;\n cwd: string;\n projectName: string;\n running: boolean;\n mode: LocalghostRunRecord[\"mode\"] | \"setup\";\n updatedAt?: string;\n startedAt?: string;\n pid?: number;\n caddyPid?: number;\n childPid?: number;\n childCommand?: string[];\n configPath?: string;\n caddyfilePath?: string;\n https?: boolean;\n routes: LocalghostRouteView[];\n};\n\nfunction maybePid(pid: number | undefined) {\n return typeof pid === \"number\" && Number.isInteger(pid) && pid > 0 ? pid : undefined;\n}\n\nfunction registerCleanup(id: string) {\n let cleaned = false;\n const cleanup = () => {\n if (cleaned) return;\n cleaned = true;\n unregisterLocalghostRun(id);\n };\n\n process.once(\"exit\", cleanup);\n\n return () => {\n cleanup();\n process.off(\"exit\", cleanup);\n };\n}\n\nasync function resolveServiceRuntimeEntries(\n services: DetectedDevService[],\n dynamicPort: boolean,\n projectCwd: string\n) {\n const usedPorts = new Set<number>();\n const resolved: Array<DetectedDevService & { port: number; entry: DevHostEntry }> = [];\n const registry = dynamicPort ? createLocalghostRegistry({ cwd: projectCwd, ownerToken: `${process.pid}:services:${projectCwd}` }) : undefined;\n\n for (const service of services) {\n let port = service.requestedPort;\n if (dynamicPort) {\n const lease = await registry!.acquirePort({\n instanceKey: `service:${service.name}`,\n startPort: service.requestedPort,\n reservedPorts: usedPorts\n });\n port = lease.port;\n } else if (usedPorts.has(port)) {\n throw new Error(`Services cannot start separate commands on the same fixed port: ${port}.`);\n }\n\n usedPorts.add(port);\n resolved.push({\n ...service,\n port,\n entry: {\n host: service.host,\n port,\n target: `127.0.0.1:${port}`\n } satisfies DevHostEntry\n });\n }\n\n return {\n services: resolved,\n release: async () => {\n if (!registry) return;\n await Promise.all(resolved.map((service) => registry.releasePort({ instanceKey: `service:${service.name}` })));\n }\n };\n}\n\nasync function waitForServicePorts(entries: DevHostEntry[], timeoutMs = 10_000) {\n const deadline = Date.now() + timeoutMs;\n const ports = [...new Set(entries.map((entry) => entry.port))];\n\n while (Date.now() < deadline) {\n const availability = await Promise.all(ports.map((port) => isPortAvailable(port)));\n if (availability.every((available) => !available)) return true;\n await wait(50);\n }\n\n return false;\n}\n\nasync function waitForPortsToBeAvailable(entries: DevHostEntry[], timeoutMs = 10_000) {\n const deadline = Date.now() + timeoutMs;\n const ports = [...new Set(entries.map((entry) => entry.port))];\n\n while (Date.now() < deadline) {\n const availability = await Promise.all(ports.map((port) => isPortAvailable(port)));\n if (availability.every(Boolean)) return true;\n await wait(50);\n }\n\n return false;\n}\n\nasync function runDetectedServices(options: {\n cwd: string;\n services: DetectedDevService[];\n configPath: string;\n projectName: string;\n https: boolean;\n dynamicPort: boolean;\n autoRepair: boolean;\n}) {\n assertLocalDevelopment(\"run\");\n await assertCaddyReady();\n\n const runtime = await resolveServiceRuntimeEntries(options.services, options.dynamicPort, options.cwd);\n try {\n const runtimeServices = runtime.services;\n const entries = runtimeServices.map((service) => service.entry);\n const readiness = getSetupReadiness({\n cwd: options.cwd,\n https: options.https,\n ignoreCaddyfile: true,\n entries,\n configPath: options.configPath,\n projectName: options.projectName\n });\n\n if (!readiness.ready) {\n if (!options.autoRepair) {\n throw new Error([\n \"Localghost setup is missing or stale.\",\n ...readiness.reasons.map((reason) => `- ${reason}`),\n \"Automatic repair is disabled. Enable autoRepair or run localghost repair.\"\n ].join(\"\\n\"));\n }\n console.log(\"Localghost setup is stale; repairing it now.\");\n await runSetupFromReadiness(options.cwd, options.https, readiness);\n }\n\n for (const service of runtimeServices) {\n if (service.port !== service.requestedPort) {\n console.log(`${service.name}: port ${service.requestedPort} is busy; using ${service.port}.`);\n }\n }\n\n const caddyfile = await writeCaddyfile(entries, options.cwd, { https: options.https });\n await validateCaddyfile(caddyfile);\n const caddy = startCaddy(caddyfile);\n const caddyExit = caddy.catch((error: unknown) => {\n if (!caddy.killed) throw error;\n });\n const children = runtimeServices.map((service) => execa(service.command[0]!, service.command.slice(1), {\n cwd: service.cwd,\n stdio: \"inherit\",\n detached: process.platform !== \"win32\",\n env: {\n ...process.env,\n LOCALGHOST_PORT: String(service.port),\n LOCALGHOST_DYNAMIC_PORT: options.dynamicPort ? \"1\" : \"0\",\n LOCALGHOST_SERVICE: service.name,\n VITE_PORT: String(service.port)\n }\n }));\n const caddyPid = maybePid(caddy.pid);\n const runRecord = registerLocalghostRun({\n mode: \"run\",\n cwd: options.cwd,\n projectName: options.projectName,\n configPath: options.configPath,\n caddyfilePath: caddyfile,\n ...(caddyPid ? { caddyPid } : {}),\n ...(caddyPid ? { caddyPgid: caddyPid } : {}),\n childCommand: [\"services\", ...runtimeServices.map((service) => service.name)],\n https: options.https,\n dynamicPort: options.dynamicPort,\n entries\n });\n const cleanupRun = registerCleanup(runRecord.id);\n const processExit = Promise.race([caddyExit, ...children]);\n\n try {\n const ready = await Promise.race([\n waitForServicePorts(entries),\n processExit.then(() => false)\n ]);\n if (ready) {\n console.log(\"\");\n logDomainRoutes(entries, { https: options.https });\n }\n await processExit;\n } finally {\n for (const child of children) {\n signalManagedProcess(child, \"SIGINT\");\n }\n signalManagedProcess(caddy, \"SIGINT\");\n await Promise.allSettled([caddyExit, ...children]);\n if (!(await waitForPortsToBeAvailable(entries))) {\n console.warn(\"Localghost: timed out waiting for service ports to be released.\");\n }\n cleanupRun();\n }\n } finally {\n await runtime.release();\n }\n}\n\nasync function getRouteViews(entries: DevHostEntry[]): Promise<LocalghostRouteView[]> {\n const portStatus = new Map<number, boolean>();\n\n for (const entry of entries) {\n if (!portStatus.has(entry.port)) {\n portStatus.set(entry.port, !(await isPortAvailable(entry.port)));\n }\n }\n\n return entries.map((entry) => ({\n host: entry.host,\n port: entry.port,\n target: `127.0.0.1:${entry.port}`,\n listening: portStatus.get(entry.port) ?? false\n }));\n}\n\nfunction setupKey(input: Pick<LocalghostSetupRecord, \"cwd\" | \"projectName\" | \"configPath\">) {\n return `${input.projectName}:${input.cwd}:${input.configPath ?? \"\"}`;\n}\n\nfunction runKey(input: Pick<LocalghostRunRecord, \"cwd\" | \"projectName\" | \"configPath\">) {\n return `${input.projectName}:${input.cwd}:${input.configPath ?? \"\"}`;\n}\n\nasync function getInstanceViews(setups: LocalghostSetupRecord[], runs: LocalghostRunRecord[]): Promise<LocalghostInstanceView[]> {\n const runBySetup = new Map(runs.map((run) => [runKey(run), run]));\n const instances: LocalghostInstanceView[] = [];\n\n for (const setup of setups) {\n const run = runBySetup.get(setupKey(setup));\n if (run) {\n instances.push(await getRunInstanceView(run, setup));\n runBySetup.delete(setupKey(setup));\n continue;\n }\n\n instances.push({\n id: setup.id,\n cwd: setup.cwd,\n projectName: setup.projectName,\n running: false,\n mode: \"setup\",\n updatedAt: setup.updatedAt,\n ...(setup.configPath ? { configPath: setup.configPath } : {}),\n ...(setup.caddyfilePath ? { caddyfilePath: setup.caddyfilePath } : {}),\n ...(typeof setup.https === \"boolean\" ? { https: setup.https } : {}),\n routes: await getRouteViews(setup.entries)\n });\n }\n\n for (const run of runBySetup.values()) {\n instances.push(await getRunInstanceView(run));\n }\n\n return instances.sort((left, right) => {\n if (left.running !== right.running) return left.running ? -1 : 1;\n return left.projectName.localeCompare(right.projectName);\n });\n}\n\nasync function getRunInstanceView(run: LocalghostRunRecord, setup?: LocalghostSetupRecord): Promise<LocalghostInstanceView> {\n return {\n id: setup?.id ?? run.id,\n cwd: run.cwd,\n projectName: run.projectName,\n running: true,\n mode: run.mode,\n updatedAt: setup?.updatedAt ?? run.updatedAt,\n startedAt: run.startedAt,\n pid: run.pid,\n ...(run.caddyPid ? { caddyPid: run.caddyPid } : {}),\n ...(run.childPid ? { childPid: run.childPid } : {}),\n ...(run.childCommand ? { childCommand: run.childCommand } : {}),\n ...(run.configPath ? { configPath: run.configPath } : {}),\n ...(run.caddyfilePath ? { caddyfilePath: run.caddyfilePath } : {}),\n ...(typeof run.https === \"boolean\" ? { https: run.https } : {}),\n routes: await getRouteViews(run.entries)\n };\n}\n\nfunction formatInstanceViews(instances: LocalghostInstanceView[]) {\n if (instances.length === 0) return \"No Localghost setups found.\";\n\n const lines = [\"localghost ps\"];\n for (const instance of instances) {\n const command = instance.childCommand?.length ? ` ${instance.childCommand.join(\" \")}` : \"\";\n const mode = command ? `${instance.mode}:${command}` : instance.mode === \"setup\" ? \"\" : instance.mode;\n lines.push(\"\");\n lines.push(`${instance.projectName} ${instance.running ? \"running\" : \"setup\"}${mode ? ` ${mode}` : \"\"}`);\n lines.push(` cwd: ${instance.cwd}`);\n if (instance.pid) {\n lines.push(` pid: ${instance.pid}${instance.caddyPid ? `, caddy: ${instance.caddyPid}` : \"\"}${instance.childPid ? `, child: ${instance.childPid}` : \"\"}`);\n }\n if (instance.startedAt) lines.push(` started: ${instance.startedAt}`);\n if (!instance.startedAt && instance.updatedAt) lines.push(` setup: ${instance.updatedAt}`);\n for (const route of instance.routes) {\n lines.push(` ${route.host} -> ${route.target} (${route.listening ? \"listening\" : \"not listening\"})`);\n }\n }\n\n return lines.join(\"\\n\");\n}\n\nconst program = new Command();\n\nprogram\n .name(\"localghost\")\n .description(\"Buh. Friendly local hostnames for app repos.\")\n .version(LOCALGHOST_VERSION)\n .option(\"--no-update-check\", \"Skip the npm update check for this run\");\n\nprogram.hook(\"postAction\", async (_thisCommand, actionCommand) => {\n if (actionCommand.name() === \"update\" || actionCommand.name() === \"release\") return;\n\n const options = program.opts<{ updateCheck?: boolean }>();\n await maybeNotifyAboutUpdate({ disabled: options.updateCheck === false });\n});\n\nprogram\n .command(\"init\")\n .description(\"Create a .localghost config for this project\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .option(\"--config <file>\", \"Config file to create\", \".localghost\")\n .option(\"--host <host>\", \"Primary local hostname\")\n .option(\"--port <number>\", \"Primary app port\", parsePort)\n .option(\"--api-host <host>\", \"API local hostname\")\n .option(\"--api-port <number>\", \"API port\", parsePort)\n .option(\"--package-manager <npm|pnpm|yarn|bun>\", \"Package manager for suggested commands\", parsePackageManager)\n .option(\"--write-scripts\", \"Add localghost scripts to package.json\")\n .option(\"--force\", \"Overwrite an existing config file\")\n .action((options: {\n cwd: string;\n config: string;\n host?: string;\n port?: number;\n apiHost?: string;\n apiPort?: number;\n packageManager?: PackageManager;\n writeScripts?: boolean;\n force?: boolean;\n }) => {\n const result = initLocalghost({ ...options, configFile: options.config });\n\n if (result.configCreated) {\n console.log(`Buh. Created ${result.configPath}`);\n } else {\n console.log(`${result.configPath} already exists. Use --force to rewrite it.`);\n }\n\n if (options.writeScripts) {\n if (result.packageJsonChanged) {\n console.log(`Updated ${result.packageJsonPath}`);\n } else if (result.packageJsonPath) {\n console.log(`${result.packageJsonPath} already has localghost scripts.`);\n } else {\n console.log(\"No package.json found; skipped script setup.\");\n }\n }\n\n console.log(\"Next:\");\n for (const step of result.nextSteps) {\n console.log(` ${step}`);\n }\n });\n\nprogram\n .command(\"guide\")\n .description(\"Explain the recommended Localghost workflow to humans or agents\")\n .option(\"--agent\", \"Print the agent-oriented workflow guide\")\n .option(\"--json\", \"Print the guide as JSON\")\n .action((options: { agent?: boolean; json?: boolean }) => {\n console.log(formatLocalghostAgentGuide(options.json ? \"json\" : \"text\"));\n });\n\nprogram\n .command(\"doctor\")\n .description(\"Check machine prerequisites, ports, and Localghost registry state\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .option(\"--config <file>\", \"Config file to inspect. Can be repeated.\", collect, [])\n .option(\"--config-pattern <regex>\", \"Regex for config filenames in the project root\")\n .option(\"--json\", \"Print raw JSON\")\n .action(async (options: ConfigCliOptions & { json?: boolean }) => {\n const result = await runDoctor({\n cwd: options.cwd,\n ...(options.config && options.config.length > 0 ? { configFiles: options.config } : {}),\n ...(options.configPattern ? { configPattern: options.configPattern } : {})\n });\n\n if (options.json) {\n console.log(JSON.stringify(result, null, 2));\n if (!result.ok) process.exitCode = 1;\n return;\n }\n\n if (result.caddy.found) {\n console.log(`Caddy: ${result.caddy.version ?? \"found\"}`);\n } else {\n console.log(\"Caddy: missing\");\n console.log(`Run: ${result.caddy.installHint}`);\n console.log(\"Localghost will not install it for you. No surprise spells.\");\n }\n\n if (result.ports.configured === undefined) {\n console.log(\"Port: could not resolve project configuration.\");\n } else {\n console.log(`Port ${result.ports.configured}: ${result.ports.available ? \"available\" : \"occupied\"}`);\n }\n if (result.ports.staleLeases.length > 0) {\n console.log(`Registry: ${result.ports.staleLeases.length} stale lease(s); run localghost repair --prune-registry.`);\n }\n for (const duplicate of result.ports.duplicateAllocations) {\n console.log(`Registry: port ${duplicate.port} is allocated to ${duplicate.projects.join(\", \")}.`);\n }\n\n if (!result.ok) {\n process.exitCode = 1;\n }\n });\n\nprogram\n .command(\"update\")\n .description(\"Check npm for a newer localghost release\")\n .option(\"--json\", \"Print raw JSON\")\n .action(async (options: { json?: boolean }) => {\n const result = await checkForUpdate({ force: true, timeoutMs: 5000 });\n\n if (options.json) {\n console.log(JSON.stringify(result, null, 2));\n return;\n }\n\n const message = formatUpdateMessage(result);\n if (message) {\n console.log(message);\n return;\n }\n\n if (result.source === \"error\") {\n console.log(`Could not check npm for updates: ${result.error ?? \"unknown error\"}`);\n process.exitCode = 1;\n return;\n }\n\n console.log(`localghost is up to date. Current: ${result.currentVersion}`);\n });\n\nprogram\n .command(\"release\")\n .description(\"Dispatch an automated Localghost CLI release\")\n .argument(\"<bump>\", \"Semantic version increment: patch, minor, or major\", parseReleaseBump)\n .action(async (bump: ReleaseBump) => {\n const repository = \"hamedb89/localghost\";\n\n try {\n await execa(\"gh\", [\n \"workflow\",\n \"run\",\n \"release.yml\",\n \"--repo\",\n repository,\n \"--ref\",\n \"main\",\n \"-f\",\n `bump=${bump}`\n ]);\n } catch (error) {\n const detail = error instanceof Error ? error.message : String(error);\n throw new Error(\n `Could not dispatch the Localghost release workflow. Install and authenticate GitHub CLI with \\`gh auth login\\`, then retry.\\n${detail}`\n );\n }\n\n console.log(`Dispatched a ${bump} Localghost release from main.`);\n console.log(`Track it at https://github.com/${repository}/actions/workflows/release.yml`);\n });\n\nprogram\n .command(\"setup\")\n .description(\"Update /etc/hosts and generate/validate Caddyfile\")\n .option(\"--project <name>\", \"Managed /etc/hosts block name\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .option(\"--config <file>\", \"Config file to look for. Can be repeated.\", collect, [])\n .option(\"--config-pattern <regex>\", \"Regex for config filenames in the project root\")\n .option(\"--https\", \"Generate a local HTTPS Caddy proxy with Caddy local certificates\")\n .option(\"--ssl\", \"Alias for --https\")\n .action(async (options: ConfigCliOptions & { project?: string } & ProxyModeCliOptions) => {\n assertLocalDevelopment(\"setup\");\n printLocalghostBanner();\n await assertCaddyReady();\n\n const context = await resolveLocalghostContext({ ...contextOptionsFromCli(options), dynamicPort: false });\n const https = context.https;\n const projectName = context.projectName;\n const configPath = context.configPath;\n const entries = context.entries;\n\n warnAboutLocalMdns(entries);\n logDomainRoutes(entries, { https, ghostTunnel: context.ghostTunnel });\n\n explainHostsPassword();\n const hostsResult = await updateSystemHosts(projectName, entries);\n\n if (hostsResult.changed) {\n console.log(`Updated ${hostsResult.hostsPath}`);\n } else {\n console.log(`${hostsResult.hostsPath} already up to date`);\n }\n\n const caddyfile = await writeCaddyfile(entries, options.cwd, { https });\n await validateCaddyfile(caddyfile);\n\n const statePath = writeLocalghostState(options.cwd, {\n action: \"setup\",\n projectName,\n cwd: options.cwd,\n configPath,\n hostsPath: hostsResult.hostsPath,\n hostsChanged: hostsResult.changed,\n ...(hostsResult.tempPath ? { hostsTempPath: hostsResult.tempPath } : {}),\n caddyfilePath: caddyfile,\n caddyHttps: https,\n ...existingTrustMarkers(options.cwd),\n entries\n });\n registerLocalghostSetup({\n cwd: options.cwd,\n projectName,\n configPath,\n caddyfilePath: caddyfile,\n https,\n entries\n });\n\n console.log(`Generated ${caddyfile}`);\n console.log(`Mode ${https ? \"HTTPS\" : \"HTTP\"}`);\n console.log(`State ${statePath}`);\n console.log(\"Setup complete.\");\n });\n\nprogram\n .command(\"trust\")\n .description(\"Trust Caddy's local HTTPS CA for this project's HTTPS proxy\")\n .option(\"--project <name>\", \"Managed /etc/hosts block name\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .option(\"--config <file>\", \"Config file to look for. Can be repeated.\", collect, [])\n .option(\"--config-pattern <regex>\", \"Regex for config filenames in the project root\")\n .option(\"--https\", \"Use HTTPS mode for the Caddyfile\")\n .option(\"--ssl\", \"Alias for --https\")\n .action(async (options: ConfigCliOptions & { project?: string } & ProxyModeCliOptions) => {\n assertLocalDevelopment(\"trust\");\n await assertCaddyReady();\n\n const context = await resolveLocalghostContext({ ...contextOptionsFromCli(options), dynamicPort: false });\n if (!context.https) {\n throw new Error(\"Localghost HTTPS is not enabled for this context. Set https: true in localghost.config.mjs or pass --https.\");\n }\n\n warnAboutLocalMdns(context.entries);\n logDomainRoutes(context.entries, { https: true, ghostTunnel: context.ghostTunnel });\n explainTrustPassword();\n\n const caddyfile = await writeCaddyfile(context.entries, options.cwd, { https: true });\n await validateCaddyfile(caddyfile);\n await runTrust(options.cwd, caddyfile);\n });\n\nprogram\n .command(\"repair\")\n .description(\"Reconcile stale setup, ports, registry state, and optional HTTPS trust\")\n .option(\"--project <name>\", \"Managed /etc/hosts block name\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .option(\"--config <file>\", \"Config file to look for. Can be repeated.\", collect, [])\n .option(\"--config-pattern <regex>\", \"Regex for config filenames in the project root\")\n .option(\"--https\", \"Repair an HTTPS Caddy setup\")\n .option(\"--ssl\", \"Alias for --https\")\n .option(\"--trust\", \"Re-run Caddy's local HTTPS trust step\")\n .option(\"--reallocate-port\", \"Persist a stable replacement for an occupied port\")\n .option(\"--prune-registry\", \"Remove expired or dead registry leases\")\n .action(async (\n options: ConfigCliOptions & { project?: string; reallocatePort?: boolean; pruneRegistry?: boolean } & ProxyModeCliOptions & TrustCliOptions\n ) => {\n assertLocalDevelopment(\"repair\");\n printLocalghostBanner();\n await assertCaddyReady();\n\n const registry = createLocalghostRegistry({ cwd: options.cwd });\n if (options.pruneRegistry) {\n const result = await registry.prune();\n console.log(`Pruned ${result.removedLeases} stale registry lease${result.removedLeases === 1 ? \"\" : \"s\"}.`);\n }\n const context = await resolveLocalghostContext({\n ...contextOptionsFromCli(options),\n dynamicPort: options.reallocatePort ? true : false,\n ...(options.reallocatePort ? { reservePort: true, instanceKey: \"run\" } : {})\n });\n const readiness = getSetupReadiness({\n ...options,\n https: context.https,\n entries: context.entries,\n configPath: context.configPath,\n projectName: context.projectName\n });\n\n if (options.trust && !context.https) {\n throw new Error(\"Cannot repair HTTPS trust unless HTTPS is enabled. Pass --https or configure https: true.\");\n }\n\n warnAboutLocalMdns(context.entries);\n logDomainRoutes(context.entries, { https: context.https, ghostTunnel: context.ghostTunnel });\n try {\n await runSetupFromReadiness(options.cwd, context.https, readiness);\n\n if (options.trust) {\n await runTrust(options.cwd, readiness.caddyfilePath);\n }\n\n if (context.port !== context.requestedPort) {\n console.log(`Reallocated port ${context.requestedPort} -> ${context.port}.`);\n }\n console.log(`Repaired hosts: ${getSystemHostsPath()}`);\n console.log(`Repaired Caddyfile: ${readiness.caddyfilePath}`);\n console.log(`Repaired state: ${readiness.statePath}`);\n console.log(\"Repair complete.\");\n } finally {\n await context.releasePort?.();\n }\n });\n\nprogram\n .command(\"reset\")\n .description(\"Remove Localghost setup state without deleting .localghost\")\n .option(\"--project <name>\", \"Managed /etc/hosts block name\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .action(async (options: { project?: string; cwd: string }) => {\n assertLocalDevelopment(\"reset\");\n\n const projectName = sanitizeProjectName(options.project ?? getProjectName(options.cwd));\n const caddyfilePath = getCaddyfilePath(options.cwd);\n const statePath = getLocalghostStatePath(options.cwd);\n\n explainHostsPassword();\n const hostsResult = await removeSystemHosts(projectName);\n\n if (existsSync(caddyfilePath)) {\n unlinkSync(caddyfilePath);\n console.log(`Removed ${caddyfilePath}`);\n } else {\n console.log(`${caddyfilePath} was not present`);\n }\n\n if (existsSync(statePath)) {\n unlinkSync(statePath);\n console.log(`Removed ${statePath}`);\n } else {\n console.log(`${statePath} was not present`);\n }\n\n if (hostsResult.removed) {\n console.log(`Removed Localghost hosts block from ${hostsResult.hostsPath}`);\n } else {\n console.log(`No Localghost hosts block found in ${hostsResult.hostsPath}`);\n }\n\n unregisterLocalghostSetup({ cwd: options.cwd, projectName });\n console.log(\".localghost was left in place. Run localghost setup when you are ready.\");\n });\n\nprogram\n .command(\"teardown\")\n .description(\"Remove Localghost's managed /etc/hosts block\")\n .option(\"--project <name>\", \"Managed /etc/hosts block name\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .option(\"--remove-caddyfile\", \"Also remove ops/local/Caddyfile\")\n .action(async (options: { project?: string; cwd: string; removeCaddyfile?: boolean }) => {\n assertLocalDevelopment(\"teardown\");\n const projectName = sanitizeProjectName(options.project ?? getProjectName(options.cwd));\n explainHostsPassword();\n const hostsResult = await removeSystemHosts(projectName);\n const caddyfilePath = getCaddyfilePath(options.cwd);\n let caddyfileRemoved = false;\n\n if (options.removeCaddyfile && existsSync(caddyfilePath)) {\n unlinkSync(caddyfilePath);\n caddyfileRemoved = true;\n }\n\n const statePath = writeLocalghostState(options.cwd, {\n action: \"teardown\",\n projectName,\n cwd: options.cwd,\n hostsPath: hostsResult.hostsPath,\n hostsChanged: hostsResult.changed,\n ...(hostsResult.tempPath ? { hostsTempPath: hostsResult.tempPath } : {}),\n caddyfilePath,\n caddyfileRemoved\n });\n\n if (hostsResult.removed) {\n console.log(`Removed Localghost hosts block from ${hostsResult.hostsPath}`);\n } else {\n console.log(`No Localghost hosts block found in ${hostsResult.hostsPath}`);\n }\n\n if (options.removeCaddyfile) {\n console.log(caddyfileRemoved ? `Removed ${caddyfilePath}` : `${caddyfilePath} was not present`);\n }\n\n unregisterLocalghostSetup({ cwd: options.cwd, projectName });\n console.log(`State ${statePath}`);\n });\n\nprogram\n .command(\"status\")\n .description(\"Print Localghost's project-local state file\")\n .option(\"--project <name>\", \"Managed /etc/hosts block name\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .option(\"--config <file>\", \"Config file to look for. Can be repeated.\", collect, [])\n .option(\"--config-pattern <regex>\", \"Regex for config filenames in the project root\")\n .option(\"--ready\", \"Exit non-zero when setup is missing or stale\")\n .option(\"--https\", \"Check setup readiness for HTTPS mode\")\n .option(\"--ssl\", \"Alias for --https\")\n .option(\"--json\", \"Print raw JSON\")\n .action(async (options: ConfigCliOptions & { project?: string; ready?: boolean; json?: boolean } & ProxyModeCliOptions) => {\n const state = readLocalghostState(options.cwd);\n const statePath = getLocalghostStatePath(options.cwd);\n const context = await resolveLocalghostContext({ ...contextOptionsFromCli(options), dynamicPort: false });\n const readiness = getSetupReadiness({\n ...options,\n https: context.https,\n entries: context.entries,\n configPath: context.configPath,\n projectName: context.projectName\n });\n\n if (options.json) {\n console.log(JSON.stringify({ state, setup: readiness }, null, 2));\n return;\n }\n\n if (!state) {\n console.log(`No Localghost state found at ${statePath}`);\n } else {\n console.log(`State: ${statePath}`);\n console.log(`Last action: ${state.action}`);\n console.log(`Updated: ${state.updatedAt}`);\n console.log(`Project: ${state.projectName}`);\n if (state.configPath) console.log(`Config: ${state.configPath}`);\n if (state.hostsPath) console.log(`Hosts: ${state.hostsPath}`);\n if (state.caddyfilePath) console.log(`Caddyfile: ${state.caddyfilePath}`);\n if (typeof state.caddyHttps === \"boolean\") console.log(`Mode: ${state.caddyHttps ? \"HTTPS\" : \"HTTP\"}`);\n if (state.caddyTrustedAt) console.log(`HTTPS trust: yes (${state.caddyTrustedAt})`);\n if (!state.caddyTrustedAt && state.caddyTrustPromptedAt) console.log(`HTTPS trust: not enabled (asked ${state.caddyTrustPromptedAt})`);\n if (typeof state.caddyfileRemoved === \"boolean\") console.log(`Caddyfile removed: ${state.caddyfileRemoved}`);\n }\n\n if (readiness.ready) {\n console.log(\"Setup ready: yes\");\n return;\n }\n\n console.log(\"Setup ready: no\");\n for (const reason of readiness.reasons) {\n console.log(` - ${reason}`);\n }\n console.log(`Run: ${readiness.setupCommand}`);\n\n if (options.ready) {\n process.exitCode = 1;\n }\n });\n\nprogram\n .command(\"routes\")\n .description(\"Print domain to upstream routes\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .option(\"--config <file>\", \"Config file to look for. Can be repeated.\", collect, [])\n .option(\"--config-pattern <regex>\", \"Regex for config filenames in the project root\")\n .option(\"--http\", \"Print domain URLs with http instead of https\")\n .option(\"--https\", \"Print domain URLs with https\")\n .option(\"--ssl\", \"Alias for --https\")\n .option(\"--verbose\", \"Print Ghost Tunnel mode, domains, and guardrails\")\n .action(async (options: ConfigCliOptions & { http?: boolean; verbose?: boolean } & ProxyModeCliOptions) => {\n const context = await resolveLocalghostContext({ ...contextOptionsFromCli(options), dynamicPort: false });\n warnAboutLocalMdns(context.entries);\n console.log(formatDomainRoutes(context.entries, { https: options.http ? false : context.https }));\n if (context.ghostTunnel.enabled) {\n console.log(formatGhostTunnel(context.ghostTunnel, {\n color: shouldColor(),\n label: \"expected\",\n verbose: options.verbose === true\n }));\n }\n });\n\nprogram\n .command(\"dev\")\n .description(\"Run the Localghost Caddy proxy, repairing stale setup when needed\")\n .option(\"--project <name>\", \"Managed /etc/hosts block name\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .option(\"--config <file>\", \"Config file to look for. Can be repeated.\", collect, [])\n .option(\"--config-pattern <regex>\", \"Regex for config filenames in the project root\")\n .option(\"--https\", \"Run a local HTTPS proxy with Caddy local certificates\")\n .option(\"--ssl\", \"Alias for --https\")\n .option(\"--setup\", \"Alias for automatic repair when setup is missing or stale\")\n .option(\"--auto-repair [yes|no]\", \"Repair stale setup before starting (default: yes)\", parseBooleanLike)\n .option(\"--clean-caddy\", \"Stop Localghost-managed Caddy processes before starting\")\n .option(\"--trust\", \"Trust Caddy's local HTTPS CA before starting the proxy\")\n .action(async (\n options: ConfigCliOptions & { project?: string; setup?: boolean } & ProxyModeCliOptions & TrustCliOptions & AutoRepairCliOptions & CleanCaddyCliOptions\n ) => {\n assertLocalDevelopment(\"dev\");\n await assertCaddyReady();\n\n if (options.cleanCaddy) cleanManagedCaddyProcesses();\n\n const context = await resolveLocalghostContext({ ...contextOptionsFromCli(options), dynamicPort: false });\n const https = context.https;\n const readiness = getSetupReadiness({\n ...options,\n https,\n entries: context.entries,\n configPath: context.configPath,\n projectName: context.projectName\n });\n\n if (!readiness.ready) {\n if (!options.setup && !context.autoRepair) {\n throw new Error(\n [\n \"Localghost setup is missing or stale.\",\n ...readiness.reasons.map((reason) => `- ${reason}`),\n `Run: ${readiness.setupCommand}`,\n \"Automatic repair is disabled. Rerun without --auto-repair=no or run localghost repair.\"\n ].join(\"\\n\")\n );\n }\n\n console.log(\"Localghost setup is stale; repairing it now.\");\n await runSetupFromReadiness(options.cwd, https, readiness);\n }\n\n warnAboutLocalMdns(readiness.entries);\n logDomainRoutes(readiness.entries, { https, ghostTunnel: context.ghostTunnel });\n\n const caddyfile = await writeCaddyfile(readiness.entries, options.cwd, { https });\n await validateCaddyfile(caddyfile);\n const caddy = startCaddy(caddyfile);\n try {\n await maybeTrustCaddy({\n cwd: options.cwd,\n https,\n caddyfilePath: caddyfile,\n ...(typeof options.trust === \"boolean\" ? { trust: options.trust } : {})\n });\n } catch (error) {\n signalManagedProcess(caddy, \"SIGINT\");\n throw error;\n }\n const caddyPid = maybePid(caddy.pid);\n const runRecord = registerLocalghostRun({\n mode: \"dev\",\n cwd: options.cwd,\n projectName: readiness.projectName,\n configPath: readiness.configPath,\n caddyfilePath: caddyfile,\n ...(caddyPid ? { caddyPid } : {}),\n ...(caddyPid ? { caddyPgid: caddyPid } : {}),\n https,\n entries: readiness.entries\n });\n const cleanupRun = registerCleanup(runRecord.id);\n\n try {\n await caddy;\n } finally {\n cleanupRun();\n }\n });\n\nprogram\n .command(\"run\")\n .description(\"Run Caddy and a dev command from the same Localghost context\")\n .option(\"--project <name>\", \"Managed /etc/hosts block name\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .option(\"--config <file>\", \"Config file to look for. Can be repeated.\", collect, [])\n .option(\"--config-pattern <regex>\", \"Regex for config filenames in the project root\")\n .option(\"--port <number>\", \"Initial app port\", parsePort)\n .option(\"--https\", \"Run a local HTTPS proxy with Caddy local certificates\")\n .option(\"--ssl\", \"Alias for --https\")\n .option(\"--setup\", \"Alias for automatic repair when setup is missing or stale\")\n .option(\"--auto-repair [yes|no]\", \"Repair stale setup before starting (default: yes)\", parseBooleanLike)\n .option(\"--clean-caddy\", \"Stop Localghost-managed Caddy processes before starting\")\n .option(\"--trust\", \"Trust Caddy's local HTTPS CA before starting the child command\")\n .option(\"--dynamic-port [yes|no]\", \"Use the requested port if free, otherwise continue upward\", parseBooleanLike)\n .argument(\"<command...>\", \"Command to run after --, for example: localghost run -- vite\")\n .action(async (\n command: string[],\n options: ConfigCliOptions & { project?: string; port?: number; setup?: boolean; dynamicPort?: boolean } & ProxyModeCliOptions & TrustCliOptions & AutoRepairCliOptions & CleanCaddyCliOptions\n ) => {\n assertLocalDevelopment(\"run\");\n await assertCaddyReady();\n\n if (options.cleanCaddy) cleanManagedCaddyProcesses();\n\n const context = await resolveLocalghostContext({\n cwd: options.cwd,\n ...(options.project ? { project: options.project } : {}),\n ...(options.config && options.config.length > 0 ? { configFiles: options.config } : {}),\n ...(options.configPattern ? { configPattern: options.configPattern } : {}),\n ...(options.port ? { port: options.port } : {}),\n reservePort: true,\n instanceKey: \"run\",\n ...(useHttps(options) ? { https: true } : {}),\n ...(typeof options.dynamicPort === \"boolean\" ? { dynamicPort: options.dynamicPort } : {}),\n ...(typeof options.autoRepair === \"boolean\" ? { autoRepair: options.autoRepair } : {})\n });\n const https = context.https;\n const readiness = getSetupReadiness({\n ...options,\n https,\n ignoreCaddyfile: true,\n entries: context.entries,\n configPath: context.configPath,\n projectName: context.projectName\n });\n\n if (!readiness.ready) {\n if (!options.setup && !context.autoRepair) {\n throw new Error(\n [\n \"Localghost setup is missing or stale.\",\n ...readiness.reasons.map((reason) => `- ${reason}`),\n `Run: ${readiness.setupCommand}`,\n \"Automatic repair is disabled. Rerun without --auto-repair=no or run localghost repair.\"\n ].join(\"\\n\")\n );\n }\n\n console.log(\"Localghost setup is stale; repairing it now.\");\n await runSetupFromReadiness(options.cwd, https, readiness);\n console.log(`Repair complete. Setup state: ${getLocalghostStatePath(options.cwd)}`);\n }\n\n if (context.dynamicPort && context.port !== context.requestedPort) {\n console.log(`Port ${context.requestedPort} is busy; using ${context.port}.`);\n }\n\n warnAboutLocalMdns(context.entries);\n logDomainRoutes(context.entries, { https, ghostTunnel: context.ghostTunnel });\n\n const caddyfile = await writeCaddyfile(context.entries, options.cwd, { https });\n await validateCaddyfile(caddyfile);\n const caddy = startCaddy(caddyfile);\n const caddyExit = caddy.catch((error: unknown) => {\n if (!caddy.killed) throw error;\n });\n try {\n await maybeTrustCaddy({\n cwd: options.cwd,\n https,\n caddyfilePath: caddyfile,\n ...(typeof options.trust === \"boolean\" ? { trust: options.trust } : {})\n });\n } catch (error) {\n signalManagedProcess(caddy, \"SIGINT\");\n throw error;\n }\n const [binary, ...args] = command;\n if (!binary) {\n throw new Error(\"Missing command. Use: localghost run -- vite\");\n }\n\n const child = execa(binary, args, {\n cwd: options.cwd,\n stdio: \"inherit\",\n detached: process.platform !== \"win32\",\n env: {\n ...process.env,\n LOCALGHOST_PORT: String(context.port),\n LOCALGHOST_DYNAMIC_PORT: context.dynamicPort ? \"1\" : \"0\",\n VITE_PORT: String(context.port)\n }\n });\n const caddyPid = maybePid(caddy.pid);\n const childPid = maybePid(child.pid);\n const runRecord = registerLocalghostRun({\n mode: \"run\",\n cwd: context.cwd,\n projectName: context.projectName,\n configPath: context.configPath,\n caddyfilePath: caddyfile,\n ...(caddyPid ? { caddyPid } : {}),\n ...(caddyPid ? { caddyPgid: caddyPid } : {}),\n ...(childPid ? { childPid } : {}),\n childCommand: command,\n https,\n requestedPort: context.requestedPort,\n port: context.port,\n dynamicPort: context.dynamicPort,\n entries: context.entries\n });\n const cleanupRun = registerCleanup(runRecord.id);\n\n const stopCaddy = () => {\n signalManagedProcess(caddy, \"SIGINT\");\n };\n const stopChild = () => {\n signalManagedProcess(child, \"SIGINT\");\n };\n\n try {\n await Promise.race([child, caddyExit]);\n } finally {\n stopChild();\n stopCaddy();\n await Promise.allSettled([child, caddyExit]);\n if (!(await waitForPortsToBeAvailable(context.entries))) {\n console.warn(\"Localghost: timed out waiting for service ports to be released.\");\n }\n cleanupRun();\n await context.releasePort?.();\n }\n });\n\nprogram\n .command(\"tunnel\")\n .description(\"Run the experimental local Ghost Tunnel agent\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .option(\"--config <file>\", \"Config file to look for. Can be repeated.\", collect, [])\n .option(\"--config-pattern <regex>\", \"Regex for config filenames in the project root\")\n .option(\"--ghost-config <file>\", \"Exact Ghost Tunnel route file\", \".ghosttunnel\")\n .option(\"--target-host <host>\", \"Local target host for .ghosttunnel ports\", \"127.0.0.1\")\n .action(async (options: ConfigCliOptions & { ghostConfig: string; targetHost: string }) => {\n assertLocalDevelopment(\"tunnel\");\n\n const context = await resolveLocalghostContext({\n cwd: options.cwd,\n ...(options.config && options.config.length > 0 ? { configFiles: options.config } : {}),\n ...(options.configPattern ? { configPattern: options.configPattern } : {}),\n dynamicPort: false\n });\n if (!context.ghostTunnel.enabled) {\n throw new Error(\"Ghost Tunnel is not enabled in localghost.config.mjs.\");\n }\n if (context.ghostTunnel.transport.kind !== \"tunnel\") {\n throw new Error(`Ghost Tunnel transport must be tunnel for localghost tunnel. Current: ${context.ghostTunnel.transport.kind}`);\n }\n\n const entries = listGhostTunnelEntries({\n cwd: options.cwd,\n fileName: options.ghostConfig\n });\n if (entries.length === 0) {\n throw new Error(`No exact Ghost Tunnel routes found in ${options.ghostConfig}.`);\n }\n\n const transport = context.ghostTunnel.transport;\n const store = createRedisGhostTunnelStoreFromEnv({\n namespace: transport.store.namespace\n });\n const controller = new AbortController();\n const stop = () => controller.abort();\n process.once(\"SIGINT\", stop);\n process.once(\"SIGTERM\", stop);\n\n const agent = startGhostTunnelAgent({\n entries,\n store,\n targetHost: options.targetHost,\n routeTtlSeconds: transport.routeTtlSeconds,\n requestTtlSeconds: transport.requestTtlSeconds,\n pollIntervalMs: transport.pollIntervalMs,\n maxResponseBodyBytes: transport.maxResponseBodyBytes,\n signal: controller.signal,\n log: (message) => console.log(message)\n });\n\n try {\n await agent.done;\n } finally {\n process.off(\"SIGINT\", stop);\n process.off(\"SIGTERM\", stop);\n }\n });\n\nprogram\n .command(\"ps\")\n .description(\"Show Localghost setups and currently running sessions\")\n .option(\"--json\", \"Print raw JSON\")\n .action(async (options: { json?: boolean }) => {\n const setups = listLocalghostSetups();\n const runs = listLocalghostRuns();\n const instances = await getInstanceViews(setups, runs);\n\n if (options.json) {\n console.log(JSON.stringify({ activityPath: getLocalghostActivityPath(), setups, runs, instances }, null, 2));\n return;\n }\n\n console.log(formatInstanceViews(instances));\n });\n\nprogram\n .command(\"print\")\n .description(\"Print parsed host config\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .option(\"--config <file>\", \"Config file to look for. Can be repeated.\", collect, [])\n .option(\"--config-pattern <regex>\", \"Regex for config filenames in the project root\")\n .action((options: ConfigCliOptions) => {\n const entries = readDevHosts(readOptionsFromCli(options));\n warnAboutLocalMdns(entries);\n console.log(JSON.stringify(entries, null, 2));\n });\n\nfunction readImplicitInvocation(args: string[]) {\n if (args.some((arg) => arg === \"--help\" || arg === \"-h\" || arg === \"--version\" || arg === \"-V\")) return null;\n\n let cwd = process.cwd();\n let dryRun = false;\n let updateCheck = true;\n const forwardedArgs: string[] = [];\n\n for (let index = 0; index < args.length; index += 1) {\n const arg = args[index];\n if (!arg) continue;\n if (arg === \"--dry-run\") {\n dryRun = true;\n continue;\n }\n if (arg === \"--no-update-check\") {\n updateCheck = false;\n continue;\n }\n if ([\"--clean-caddy\", \"--https\", \"--ssl\", \"--setup\", \"--trust\"].includes(arg)) {\n forwardedArgs.push(arg);\n continue;\n }\n if (arg === \"--auto-repair\" || arg === \"--dynamic-port\") {\n const value = args[index + 1];\n forwardedArgs.push(arg);\n if (value && !value.startsWith(\"--\")) {\n forwardedArgs.push(value);\n index += 1;\n }\n continue;\n }\n if (arg === \"--port\" || arg === \"--project\" || arg === \"--config\" || arg === \"--config-pattern\") {\n const value = args[index + 1];\n if (!value) throw new Error(`${arg} requires a value.`);\n forwardedArgs.push(arg, value);\n index += 1;\n continue;\n }\n if ([\"--auto-repair=\", \"--dynamic-port=\", \"--port=\", \"--project=\", \"--config=\", \"--config-pattern=\"].some((prefix) => arg.startsWith(prefix))) {\n forwardedArgs.push(arg);\n continue;\n }\n if (arg === \"--cwd\") {\n const value = args[index + 1];\n if (!value) throw new Error(\"--cwd requires a path.\");\n cwd = value;\n index += 1;\n continue;\n }\n if (arg.startsWith(\"--cwd=\")) {\n cwd = arg.slice(\"--cwd=\".length);\n continue;\n }\n return null;\n }\n\n return { cwd, dryRun, updateCheck, forwardedArgs };\n}\n\nfunction hasForwardedFlag(args: string[], ...flags: string[]) {\n return args.some((arg) => flags.includes(arg));\n}\n\nfunction forwardedBoolean(args: string[], name: string) {\n const inline = args.find((arg) => arg.startsWith(`${name}=`));\n if (inline) return parseBooleanLike(inline.slice(name.length + 1));\n return args.includes(name) ? true : undefined;\n}\n\nasync function main() {\n const implicit = readImplicitInvocation(process.argv.slice(2));\n if (!implicit) {\n await program.parseAsync();\n return;\n }\n\n const projectConfig = await readLocalghostProjectConfig({ cwd: implicit.cwd });\n printLocalghostBanner();\n if (projectConfig.config.services) {\n if (!projectConfig.path) throw new Error(\"Multi-service configuration must come from localghost.config.mjs.\");\n const services = detectDevServices({\n cwd: implicit.cwd,\n services: projectConfig.config.services\n });\n console.log(formatDetectedDevServices(services));\n if (implicit.dryRun) return;\n\n if (hasForwardedFlag(implicit.forwardedArgs, \"--clean-caddy\")) cleanManagedCaddyProcesses();\n\n await runDetectedServices({\n cwd: implicit.cwd,\n services,\n configPath: projectConfig.path,\n projectName: sanitizeProjectName(projectConfig.config.project ?? getProjectName(implicit.cwd)),\n https: hasForwardedFlag(implicit.forwardedArgs, \"--https\", \"--ssl\") || (projectConfig.config.https ?? false),\n dynamicPort: forwardedBoolean(implicit.forwardedArgs, \"--dynamic-port\") ?? projectConfig.config.dynamicPort ?? true,\n autoRepair: forwardedBoolean(implicit.forwardedArgs, \"--auto-repair\") ?? projectConfig.config.autoRepair ?? true\n });\n await maybeNotifyAboutUpdate({ disabled: !implicit.updateCheck });\n return;\n }\n\n const detected = detectDevCommand({\n cwd: implicit.cwd,\n ...(projectConfig.config.command ? { command: projectConfig.config.command } : {})\n });\n console.log(`Localghost detected: ${formatDetectedDevCommand(detected)}`);\n\n if (implicit.dryRun) return;\n\n await program.parseAsync([\n process.argv[0] ?? process.execPath,\n process.argv[1] ?? \"localghost\",\n ...(implicit.updateCheck ? [] : [\"--no-update-check\"]),\n \"run\",\n ...implicit.forwardedArgs,\n \"--cwd\",\n implicit.cwd,\n \"--\",\n ...detected.command\n ]);\n}\n\nmain().catch((error: unknown) => {\n const message = error instanceof Error ? error.message : String(error);\n console.error(message);\n process.exitCode = 1;\n});\n","import { existsSync, mkdirSync, readFileSync, writeFileSync } from \"node:fs\";\nimport { homedir } from \"node:os\";\nimport { dirname, join } from \"node:path\";\nimport type { DevHostEntry } from \"./parse.js\";\n\nexport const LOCALGHOST_ACTIVITY_VERSION = 1;\n\nexport type LocalghostRunMode = \"dev\" | \"run\" | \"vite\";\n\nexport type LocalghostRunRecord = {\n id: string;\n mode: LocalghostRunMode;\n pid: number;\n cwd: string;\n projectName: string;\n startedAt: string;\n updatedAt: string;\n configPath?: string;\n caddyfilePath?: string;\n caddyPid?: number;\n caddyPgid?: number;\n childPid?: number;\n childCommand?: string[];\n https?: boolean;\n requestedPort?: number;\n port?: number;\n dynamicPort?: boolean;\n entries: DevHostEntry[];\n};\n\nexport type LocalghostSetupRecord = {\n id: string;\n cwd: string;\n projectName: string;\n updatedAt: string;\n configPath?: string;\n caddyfilePath?: string;\n https?: boolean;\n entries: DevHostEntry[];\n};\n\nexport type LocalghostActivity = {\n version: typeof LOCALGHOST_ACTIVITY_VERSION;\n runs: LocalghostRunRecord[];\n setups: LocalghostSetupRecord[];\n};\n\nexport type RegisterLocalghostRunInput = Omit<LocalghostRunRecord, \"id\" | \"pid\" | \"startedAt\" | \"updatedAt\"> & {\n id?: string;\n pid?: number;\n startedAt?: string;\n};\n\nexport type RegisterLocalghostSetupInput = Omit<LocalghostSetupRecord, \"id\" | \"updatedAt\"> & {\n id?: string;\n};\n\nexport function getLocalghostActivityPath(env: NodeJS.ProcessEnv = process.env) {\n if (env.LOCALGHOST_ACTIVITY_PATH) return env.LOCALGHOST_ACTIVITY_PATH;\n\n const stateRoot = env.XDG_STATE_HOME || join(homedir(), \".local/state\");\n return join(stateRoot, \"localghost\", \"activity.json\");\n}\n\nexport function isProcessRunning(pid: number) {\n if (!Number.isInteger(pid) || pid < 1) return false;\n\n try {\n process.kill(pid, 0);\n return true;\n } catch (error) {\n const code = typeof error === \"object\" && error !== null && \"code\" in error ? error.code : undefined;\n return code === \"EPERM\";\n }\n}\n\nfunction emptyActivity(): LocalghostActivity {\n return { version: LOCALGHOST_ACTIVITY_VERSION, runs: [], setups: [] };\n}\n\nexport function readLocalghostActivity(path = getLocalghostActivityPath()): LocalghostActivity {\n if (!existsSync(path)) return emptyActivity();\n\n try {\n const parsed = JSON.parse(readFileSync(path, \"utf8\")) as Partial<LocalghostActivity>;\n return {\n version: LOCALGHOST_ACTIVITY_VERSION,\n runs: Array.isArray(parsed.runs) ? parsed.runs : [],\n setups: Array.isArray(parsed.setups) ? parsed.setups : []\n };\n } catch {\n return emptyActivity();\n }\n}\n\nexport function writeLocalghostActivity(activity: LocalghostActivity, path = getLocalghostActivityPath()) {\n mkdirSync(dirname(path), { recursive: true });\n writeFileSync(path, `${JSON.stringify(activity, null, 2)}\\n`, \"utf8\");\n return path;\n}\n\nfunction createRunId(input: Pick<RegisterLocalghostRunInput, \"mode\" | \"cwd\" | \"projectName\">, pid: number) {\n return `${input.projectName}:${input.mode}:${pid}:${Date.now()}`;\n}\n\nfunction createSetupId(input: Pick<RegisterLocalghostSetupInput, \"cwd\" | \"projectName\" | \"configPath\">) {\n return `${input.projectName}:${input.cwd}:${input.configPath ?? \"\"}`;\n}\n\nexport function pruneLocalghostActivity(path = getLocalghostActivityPath()) {\n const activity = readLocalghostActivity(path);\n const activeRuns = activity.runs.filter((run) => isProcessRunning(run.pid));\n const pruned = activeRuns.length !== activity.runs.length;\n\n if (pruned) {\n writeLocalghostActivity({ ...activity, version: LOCALGHOST_ACTIVITY_VERSION, runs: activeRuns }, path);\n }\n\n return {\n path,\n pruned,\n runs: activeRuns,\n setups: activity.setups\n };\n}\n\nexport function listLocalghostRuns(path = getLocalghostActivityPath()) {\n return pruneLocalghostActivity(path).runs;\n}\n\nexport function listLocalghostSetups(path = getLocalghostActivityPath()) {\n return pruneLocalghostActivity(path).setups;\n}\n\nexport function registerLocalghostRun(input: RegisterLocalghostRunInput, path = getLocalghostActivityPath()) {\n const now = new Date().toISOString();\n const pid = input.pid ?? process.pid;\n const record: LocalghostRunRecord = {\n id: input.id ?? createRunId(input, pid),\n mode: input.mode,\n pid,\n cwd: input.cwd,\n projectName: input.projectName,\n startedAt: input.startedAt ?? now,\n updatedAt: now,\n ...(input.configPath ? { configPath: input.configPath } : {}),\n ...(input.caddyfilePath ? { caddyfilePath: input.caddyfilePath } : {}),\n ...(input.caddyPid ? { caddyPid: input.caddyPid } : {}),\n ...(input.caddyPgid ? { caddyPgid: input.caddyPgid } : {}),\n ...(input.childPid ? { childPid: input.childPid } : {}),\n ...(input.childCommand ? { childCommand: input.childCommand } : {}),\n ...(typeof input.https === \"boolean\" ? { https: input.https } : {}),\n ...(input.requestedPort ? { requestedPort: input.requestedPort } : {}),\n ...(input.port ? { port: input.port } : {}),\n ...(typeof input.dynamicPort === \"boolean\" ? { dynamicPort: input.dynamicPort } : {}),\n entries: input.entries\n };\n const current = pruneLocalghostActivity(path).runs.filter((run) => run.id !== record.id);\n const activity = readLocalghostActivity(path);\n writeLocalghostActivity({ version: LOCALGHOST_ACTIVITY_VERSION, runs: [...current, record], setups: activity.setups }, path);\n return record;\n}\n\nexport function registerLocalghostSetup(input: RegisterLocalghostSetupInput, path = getLocalghostActivityPath()) {\n const record: LocalghostSetupRecord = {\n id: input.id ?? createSetupId(input),\n cwd: input.cwd,\n projectName: input.projectName,\n updatedAt: new Date().toISOString(),\n ...(input.configPath ? { configPath: input.configPath } : {}),\n ...(input.caddyfilePath ? { caddyfilePath: input.caddyfilePath } : {}),\n ...(typeof input.https === \"boolean\" ? { https: input.https } : {}),\n entries: input.entries\n };\n const activity = pruneLocalghostActivity(path);\n const setups = activity.setups.filter((setup) => setup.id !== record.id);\n writeLocalghostActivity({ version: LOCALGHOST_ACTIVITY_VERSION, runs: activity.runs, setups: [...setups, record] }, path);\n return record;\n}\n\nexport function unregisterLocalghostRun(id: string, path = getLocalghostActivityPath()) {\n const activity = readLocalghostActivity(path);\n const runs = activity.runs.filter((run) => run.id !== id);\n\n if (runs.length !== activity.runs.length) {\n writeLocalghostActivity({ ...activity, version: LOCALGHOST_ACTIVITY_VERSION, runs }, path);\n }\n}\n\nexport function unregisterLocalghostSetup(options: { cwd: string; projectName?: string; configPath?: string }, path = getLocalghostActivityPath()) {\n const activity = readLocalghostActivity(path);\n const setups = activity.setups.filter((setup) => {\n if (setup.cwd !== options.cwd) return true;\n if (options.projectName && setup.projectName !== options.projectName) return true;\n if (options.configPath && setup.configPath !== options.configPath) return true;\n return false;\n });\n\n if (setups.length !== activity.setups.length) {\n writeLocalghostActivity({ ...activity, version: LOCALGHOST_ACTIVITY_VERSION, setups }, path);\n }\n}\n","import { existsSync, readFileSync, readdirSync } from \"node:fs\";\nimport { basename, join, resolve } from \"node:path\";\nimport { parseDevHosts } from \"./parse.js\";\n\nexport const LOCALGHOST_CONFIG_FILE = \".localghost\";\n\nexport type ConfigPattern = string | RegExp;\n\nexport type ReadDevHostsOptions = {\n cwd?: string;\n fileName?: string;\n configFiles?: string[];\n configPattern?: ConfigPattern;\n};\n\nexport type ResolvedDevHostsPath = {\n path: string;\n fileName: string;\n exists: boolean;\n searchedFiles: string[];\n configPattern?: ConfigPattern;\n};\n\nfunction unique(values: string[]) {\n return [...new Set(values.filter(Boolean))];\n}\n\nfunction toRegExp(pattern: ConfigPattern) {\n return typeof pattern === \"string\" ? new RegExp(pattern) : pattern;\n}\n\nfunction findPatternMatches(cwd: string, pattern: ConfigPattern) {\n const matcher = toRegExp(pattern);\n\n return readdirSync(cwd, { withFileTypes: true })\n .filter((entry) => entry.isFile())\n .map((entry) => entry.name)\n .filter((name) => {\n matcher.lastIndex = 0;\n return matcher.test(name);\n })\n .sort();\n}\n\nexport function getConfigFileCandidates(options: ReadDevHostsOptions = {}) {\n const cwd = options.cwd ?? process.cwd();\n const exactFiles = unique([\n ...(options.fileName ? [options.fileName] : []),\n ...(options.configFiles ?? [])\n ]);\n const patternFiles = options.configPattern ? findPatternMatches(cwd, options.configPattern) : [];\n const candidates = unique([...exactFiles, ...patternFiles]);\n\n if (candidates.length > 0) return candidates;\n if (exactFiles.length > 0 || options.configPattern) return [];\n return [LOCALGHOST_CONFIG_FILE];\n}\n\nexport function resolveDevHostsPath(options: ReadDevHostsOptions = {}): ResolvedDevHostsPath {\n const cwd = options.cwd ?? process.cwd();\n const searchedFiles = getConfigFileCandidates(options);\n\n for (const fileName of searchedFiles) {\n const path = resolve(cwd, fileName);\n if (existsSync(path)) {\n return {\n path,\n fileName: basename(fileName),\n exists: true,\n searchedFiles,\n ...(options.configPattern ? { configPattern: options.configPattern } : {})\n };\n }\n }\n\n const fileName = searchedFiles[0] ?? LOCALGHOST_CONFIG_FILE;\n\n return {\n path: resolve(cwd, fileName),\n fileName: basename(fileName),\n exists: false,\n searchedFiles,\n ...(options.configPattern ? { configPattern: options.configPattern } : {})\n };\n}\n\nexport function getDevHostsPath(options: ReadDevHostsOptions = {}) {\n return resolveDevHostsPath(options).path;\n}\n\nfunction formatSearchedFiles(files: string[], pattern?: ConfigPattern) {\n if (files.length > 0) return files.map((file) => `\\`${file}\\``).join(\", \");\n if (pattern) return `files matching ${pattern.toString()}`;\n return `\\`${LOCALGHOST_CONFIG_FILE}\\``;\n}\n\nexport function readDevHosts(options: ReadDevHostsOptions | string = {}) {\n const resolvedOptions = typeof options === \"string\" ? { cwd: options } : options;\n const resolvedPath = resolveDevHostsPath(resolvedOptions);\n\n if (!resolvedPath.exists) {\n const cwd = resolvedOptions.cwd ?? process.cwd();\n throw new Error(\n `Missing Localghost config in ${cwd}. Looked for ${formatSearchedFiles(resolvedPath.searchedFiles, resolvedPath.configPattern)}. Run \\`localghost init\\` or pass --config/--config-pattern.`\n );\n }\n\n return parseDevHosts(readFileSync(resolvedPath.path, \"utf8\"), resolvedPath.fileName);\n}\n\nexport function getProjectName(cwd = process.cwd()) {\n try {\n const pkg = JSON.parse(readFileSync(join(cwd, \"package.json\"), \"utf8\")) as { name?: unknown };\n const name = typeof pkg.name === \"string\" && pkg.name ? pkg.name : \"app\";\n return sanitizeProjectName(name.replace(/^@/, \"\"));\n } catch {\n return \"app\";\n }\n}\n\nexport function sanitizeProjectName(value: string) {\n const sanitized = value.replace(/[^\\w.-]+/g, \"-\");\n let start = 0;\n let end = sanitized.length;\n\n while (start < end && sanitized.charCodeAt(start) === 45) start += 1;\n while (end > start && sanitized.charCodeAt(end - 1) === 45) end -= 1;\n\n const projectName = sanitized.slice(start, end);\n return projectName || \"app\";\n}\n","export type DevHostEntry = {\n host: string;\n port: number;\n target: string;\n};\n\nconst HOST_PATTERN = /^(?=.{1,253}$)(?!-)[a-z0-9-]+(\\.[a-z0-9-]+)*\\.?$/i;\n\nexport function parseDevHosts(input: string, fileName = \".localghost\"): DevHostEntry[] {\n const entries: DevHostEntry[] = [];\n\n input.split(/\\r?\\n/).forEach((rawLine, index) => {\n const line = rawLine.replace(/#.*/, \"\").trim();\n\n if (!line) {\n return;\n }\n\n const parts = line.split(/\\s+/);\n const host = parts[0];\n const portRaw = parts[1];\n\n if (!host || !portRaw || parts.length > 2) {\n throw new Error(`Invalid ${fileName} line ${index + 1}: \"${rawLine}\"`);\n }\n\n if (!HOST_PATTERN.test(host)) {\n throw new Error(`Invalid host on line ${index + 1}: \"${host}\"`);\n }\n\n const port = Number(portRaw);\n\n if (!Number.isInteger(port) || port < 1 || port > 65535) {\n throw new Error(`Invalid port on line ${index + 1}: \"${portRaw}\"`);\n }\n\n entries.push({\n host: host.toLowerCase().replace(/\\.$/, \"\"),\n port,\n target: `127.0.0.1:${port}`\n });\n });\n\n return entries;\n}\n\nexport function findLocalMdnsHosts(entries: DevHostEntry[]): string[] {\n return [...new Set(entries.map((entry) => entry.host).filter((host) => host.endsWith(\".local\")))];\n}\n","export function renderLocalghostBanner() {\n return [\n \" .-.\",\n \" (o o) LOCALGHOST\",\n \" | O \\\\ friendly local domains\",\n \" \\\\ \\\\\",\n \" `~~~'\"\n ].join(\"\\n\");\n}\n\nexport function renderCompactLocalghostBanner() {\n return [\n \" .--.\",\n \" ( oo ) localghost\",\n \" \\\\__/ friendly local domains\"\n ].join(\"\\n\");\n}\n","import { dirname, join } from \"node:path\";\nimport { execa } from \"execa\";\nimport { writeTextFile } from \"./fs.js\";\nimport type { DevHostEntry } from \"./parse.js\";\n\nexport type CaddyModeOptions = {\n https?: boolean;\n};\n\nexport type CaddyProcessStopResult = {\n stopped: number[];\n alreadyExited: number[];\n failed: Array<{ pid: number; error: unknown }>;\n};\n\nexport type CaddyProcessKiller = (pid: number, signal: NodeJS.Signals) => void;\n\nfunction shouldShowCaddyLogs() {\n return [\"1\", \"true\", \"yes\", \"on\"].includes((process.env.LOCALGHOST_CADDY_VERBOSE ?? \"\").toLowerCase());\n}\n\nfunction caddyStdio() {\n return shouldShowCaddyLogs() ? \"inherit\" as const : \"pipe\" as const;\n}\n\nfunction groupByPort(entries: DevHostEntry[]) {\n const groups = new Map<number, DevHostEntry[]>();\n\n for (const entry of entries) {\n const group = groups.get(entry.port) ?? [];\n group.push(entry);\n groups.set(entry.port, group);\n }\n\n return groups;\n}\n\nexport function getCaddyfilePath(cwd = process.cwd()) {\n return join(cwd, \"ops/local/Caddyfile\");\n}\n\nexport function renderCaddyfile(entries: DevHostEntry[], options: CaddyModeOptions = {}) {\n const groups = groupByPort(entries);\n const https = options.https === true;\n const blocks = [...groups.entries()]\n .sort(([leftPort], [rightPort]) => leftPort - rightPort)\n .map(([port, group]) => {\n const hosts = group\n .map((entry) => (https ? entry.host : `http://${entry.host}`))\n .sort()\n .join(\", \");\n\n return `${hosts} {\n\\treverse_proxy 127.0.0.1:${port}\n}`;\n });\n\n const globalOptions = https\n ? `{\n local_certs\n}\n\n`\n : \"\";\n\n return `${globalOptions}${blocks.join(\"\\n\\n\")}\n`;\n}\n\nexport async function writeCaddyfile(entries: DevHostEntry[], cwd = process.cwd(), options: CaddyModeOptions = {}) {\n const path = getCaddyfilePath(cwd);\n writeTextFile(path, renderCaddyfile(entries, options));\n return path;\n}\n\nexport async function validateCaddyfile(path: string) {\n await execa(\"caddy\", [\"validate\", \"--config\", path], {\n cwd: dirname(path),\n stdio: caddyStdio()\n });\n}\n\nexport async function runCaddy(path: string) {\n await execa(\"caddy\", [\"run\", \"--config\", path], {\n cwd: dirname(path),\n stdio: caddyStdio()\n });\n}\n\nexport function startCaddy(path: string) {\n return execa(\"caddy\", [\"run\", \"--config\", path], {\n cwd: dirname(path),\n stdio: caddyStdio(),\n detached: process.platform !== \"win32\"\n });\n}\n\nexport function stopCaddyProcesses(\n pids: Iterable<number>,\n killProcess: CaddyProcessKiller = (pid, signal) => process.kill(pid, signal)\n): CaddyProcessStopResult {\n const result: CaddyProcessStopResult = {\n stopped: [],\n alreadyExited: [],\n failed: []\n };\n\n for (const pid of new Set(pids)) {\n try {\n killProcess(pid, \"SIGINT\");\n result.stopped.push(pid);\n } catch (error) {\n if (error instanceof Error && \"code\" in error && error.code === \"ESRCH\") {\n result.alreadyExited.push(pid);\n } else {\n result.failed.push({ pid, error });\n }\n }\n }\n\n return result;\n}\n\nexport async function trustCaddy(path: string) {\n await execa(\"caddy\", [\"trust\", \"--config\", path], {\n cwd: dirname(path),\n stdio: \"inherit\"\n });\n}\n","import { mkdirSync, readFileSync, writeFileSync } from \"node:fs\";\nimport { dirname } from \"node:path\";\n\nexport function readTextFile(path: string) {\n return readFileSync(path, \"utf8\");\n}\n\nexport function writeTextFile(path: string, value: string) {\n mkdirSync(dirname(path), { recursive: true });\n writeFileSync(path, value, \"utf8\");\n return path;\n}\n","import { existsSync, readFileSync } from \"node:fs\";\nimport { isAbsolute, join, relative, resolve } from \"node:path\";\n\nexport type LocalghostPackageManager = \"npm\" | \"pnpm\" | \"yarn\" | \"bun\";\n\nexport type DetectedDevCommand = {\n command: string[];\n source: \"config\" | \"script\";\n packageManager?: LocalghostPackageManager;\n script?: string;\n};\n\nexport type LocalghostServiceOptions = {\n name: string;\n cwd: string;\n host: string;\n port: number;\n command?: string[];\n};\n\nexport type DetectedDevService = {\n name: string;\n cwd: string;\n relativeCwd: string;\n host: string;\n requestedPort: number;\n command: string[];\n commandSource: DetectedDevCommand[\"source\"];\n};\n\ntype PackageJson = {\n packageManager?: unknown;\n scripts?: unknown;\n};\n\nfunction readPackageJson(cwd: string): PackageJson {\n const path = join(cwd, \"package.json\");\n if (!existsSync(path)) {\n throw new Error(`No package.json found in ${cwd}. Pass an explicit command with \\`localghost run -- <command>\\`.`);\n }\n\n try {\n return JSON.parse(readFileSync(path, \"utf8\")) as PackageJson;\n } catch {\n throw new Error(`Could not parse ${path}.`);\n }\n}\n\nexport function detectDevPackageManager(cwd: string, packageManager: unknown): LocalghostPackageManager {\n if (typeof packageManager === \"string\") {\n const name = packageManager.split(\"@\")[0];\n if (name === \"npm\" || name === \"pnpm\" || name === \"yarn\" || name === \"bun\") return name;\n }\n\n if (existsSync(join(cwd, \"pnpm-lock.yaml\"))) return \"pnpm\";\n if (existsSync(join(cwd, \"yarn.lock\"))) return \"yarn\";\n if (existsSync(join(cwd, \"bun.lock\")) || existsSync(join(cwd, \"bun.lockb\"))) return \"bun\";\n return \"npm\";\n}\n\nfunction scriptCommand(packageManager: LocalghostPackageManager, script: string) {\n if (packageManager === \"yarn\") return [\"yarn\", script];\n return [packageManager, \"run\", script];\n}\n\nfunction invokesLocalghost(script: string) {\n return /(^|[\\s;&|])(?:npm\\s+exec\\s+|pnpm\\s+exec\\s+|bunx\\s+|npx\\s+)?localghost(?:\\s|$)/.test(script);\n}\n\nexport function detectDevCommand(options: {\n cwd?: string;\n command?: string[];\n} = {}): DetectedDevCommand {\n const cwd = options.cwd ?? process.cwd();\n\n if (options.command) {\n if (options.command.length === 0 || options.command.some((part) => typeof part !== \"string\" || part.length === 0)) {\n throw new Error(\"localghost.config.mjs command must be a non-empty array of strings.\");\n }\n if (invokesLocalghost(options.command.join(\" \"))) {\n throw new Error(\"localghost.config.mjs command cannot invoke Localghost recursively.\");\n }\n return { command: [...options.command], source: \"config\" };\n }\n\n const pkg = readPackageJson(cwd);\n const scripts = typeof pkg.scripts === \"object\" && pkg.scripts ? pkg.scripts as Record<string, unknown> : {};\n const packageManager = detectDevPackageManager(cwd, pkg.packageManager);\n\n for (const script of [\"dev:raw\", \"dev\"]) {\n const value = scripts[script];\n if (typeof value !== \"string\" || invokesLocalghost(value)) continue;\n return {\n command: scriptCommand(packageManager, script),\n source: \"script\",\n packageManager,\n script\n };\n }\n\n throw new Error([\n `Could not detect a safe development command in ${join(cwd, \"package.json\")}.`,\n \"Add a non-recursive dev or dev:raw script, configure command in localghost.config.mjs,\",\n \"or pass an explicit command with `localghost run -- <command>`.\"\n ].join(\" \"));\n}\n\nexport function formatDetectedDevCommand(detected: DetectedDevCommand) {\n const command = detected.command.map((part) => (\n /^[A-Za-z0-9_./:@=-]+$/.test(part) ? part : JSON.stringify(part)\n )).join(\" \");\n const source = detected.source === \"config\"\n ? \"localghost.config.mjs\"\n : `package.json#scripts.${detected.script}`;\n return `${command} (${source})`;\n}\n\nfunction assertServicePath(root: string, serviceCwd: string, name: string) {\n const cwd = resolve(root, serviceCwd);\n const relativeCwd = relative(root, cwd);\n if (isAbsolute(relativeCwd) || relativeCwd === \"..\" || relativeCwd.startsWith(`..${process.platform === \"win32\" ? \"\\\\\" : \"/\"}`)) {\n throw new Error(`Service ${name} cwd must stay inside the project root.`);\n }\n return { cwd, relativeCwd: relativeCwd || \".\" };\n}\n\nexport function detectDevServices(options: {\n cwd?: string;\n services: LocalghostServiceOptions[];\n}) {\n const root = options.cwd ?? process.cwd();\n if (options.services.length === 0) throw new Error(\"services must contain at least one service.\");\n\n const names = new Set<string>();\n const hosts = new Set<string>();\n\n return options.services.map((service, index): DetectedDevService => {\n if (!service || typeof service !== \"object\") throw new Error(`Service at index ${index} must be an object.`);\n if (!service.name || names.has(service.name)) throw new Error(`Service name must be unique: ${service.name || `<index ${index}>`}.`);\n if (!/^[a-zA-Z0-9][a-zA-Z0-9_-]*$/.test(service.name)) throw new Error(`Invalid service name: ${service.name}.`);\n if (!service.host || hosts.has(service.host)) throw new Error(`Service host must be unique: ${service.host || `<index ${index}>`}.`);\n if (!Number.isInteger(service.port) || service.port < 1 || service.port > 65_535) {\n throw new Error(`Invalid port for service ${service.name}: ${service.port}.`);\n }\n\n names.add(service.name);\n hosts.add(service.host);\n const path = assertServicePath(root, service.cwd, service.name);\n const detected = detectDevCommand({\n cwd: path.cwd,\n ...(service.command ? { command: service.command } : {})\n });\n\n return {\n name: service.name,\n ...path,\n host: service.host,\n requestedPort: service.port,\n command: detected.command,\n commandSource: detected.source\n };\n });\n}\n\nexport function formatDetectedDevServices(services: DetectedDevService[]) {\n return [\n `Localghost detected ${services.length} services:`,\n ...services.map((service) => (\n `${service.name}: ${service.command.map((part) => (\n /^[A-Za-z0-9_./:@=-]+$/.test(part) ? part : JSON.stringify(part)\n )).join(\" \")} (${service.relativeCwd}, ${service.host} -> ${service.requestedPort})`\n ))\n ].join(\"\\n\");\n}\n","import { existsSync, readFileSync } from \"node:fs\";\nimport { join } from \"node:path\";\nimport { pathToFileURL } from \"node:url\";\nimport {\n getProjectName,\n readDevHosts,\n resolveDevHostsPath,\n sanitizeProjectName,\n type ConfigPattern,\n type ReadDevHostsOptions\n} from \"./config.js\";\nimport { findAvailablePort } from \"./port.js\";\nimport { createLocalghostRegistry } from \"./registry.js\";\nimport type { DevHostEntry } from \"./parse.js\";\nimport type { LocalghostServiceOptions } from \"./command.js\";\nimport { resolveGhostTunnelConfig, type GhostTunnelConfig, type GhostTunnelOptions } from \"./tunnel.js\";\n\nexport type LocalghostContextOptions = {\n cwd?: string;\n project?: string;\n localghostConfig?: string | false;\n fileName?: string;\n configFiles?: string[];\n configPattern?: ConfigPattern;\n port?: number;\n https?: boolean;\n bindHost?: string | boolean;\n primaryHost?: string;\n dynamicPort?: boolean;\n reservePort?: boolean;\n instanceKey?: string;\n reservedPorts?: Iterable<number>;\n registryOwnerToken?: string;\n autoRepair?: boolean;\n command?: string[];\n services?: LocalghostServiceOptions[];\n wwwAlias?: boolean;\n ghostTunnel?: GhostTunnelOptions;\n};\n\nexport type LocalghostContext = {\n cwd: string;\n projectName: string;\n readOptions: ReadDevHostsOptions;\n configPath: string;\n configFileName: string;\n configEntries: DevHostEntry[];\n entries: DevHostEntry[];\n hosts: string[];\n requestedPort: number;\n port: number;\n dynamicPort: boolean;\n autoRepair: boolean;\n bindHost: string | boolean;\n primaryHost: string;\n https: boolean;\n wwwAlias: boolean;\n ghostTunnel: GhostTunnelConfig;\n projectConfigPath?: string;\n releasePort?: () => Promise<boolean>;\n};\n\nexport type LocalghostProjectConfig = Omit<LocalghostContextOptions, \"cwd\" | \"localghostConfig\">;\n\nexport type LocalghostProjectConfigResult = {\n config: LocalghostProjectConfig;\n path?: string;\n};\n\nconst LOCALGHOST_PROJECT_CONFIG_FILES = [\n \"localghost.config.mjs\",\n \"localghost.config.js\",\n \"localghost.config.cjs\"\n];\n\nfunction parsePort(value: string | undefined) {\n if (!value) return undefined;\n const port = Number.parseInt(value, 10);\n return Number.isInteger(port) && port > 0 && port <= 65535 ? port : undefined;\n}\n\nfunction envPort() {\n return parsePort(process.env.LOCALGHOST_PORT) ?? parsePort(process.env.VITE_PORT);\n}\n\nfunction envDynamicPort() {\n const value = process.env.LOCALGHOST_DYNAMIC_PORT;\n if (!value) return undefined;\n return [\"1\", \"true\", \"yes\", \"on\"].includes(value.toLowerCase());\n}\n\nfunction envHttps() {\n const value = process.env.LOCALGHOST_HTTPS;\n if (!value) return undefined;\n return [\"1\", \"true\", \"yes\", \"on\"].includes(value.toLowerCase());\n}\n\nfunction getPackageName(cwd: string) {\n try {\n const pkg = JSON.parse(readFileSync(join(cwd, \"package.json\"), \"utf8\")) as { name?: unknown };\n return typeof pkg.name === \"string\" ? pkg.name : undefined;\n } catch {\n return undefined;\n }\n}\n\nfunction getPackageOwner(cwd: string) {\n const packageName = getPackageName(cwd);\n if (!packageName?.startsWith(\"@\")) return undefined;\n return packageName.slice(1).split(\"/\")[0];\n}\n\nfunction getLocalOwner(cwd: string) {\n return sanitizeProjectName(process.env.LOCALGHOST_OWNER ?? getPackageOwner(cwd) ?? process.env.USER ?? process.env.USERNAME ?? \"local\");\n}\n\nfunction getRouteName(primaryHost: string, fallback: string) {\n return sanitizeProjectName(primaryHost.split(\".\")[0] ?? fallback);\n}\n\nfunction readOptionsFromContext(options: LocalghostContextOptions): ReadDevHostsOptions {\n return {\n cwd: options.cwd ?? process.cwd(),\n ...(options.fileName ? { fileName: options.fileName } : {}),\n ...(options.configFiles ? { configFiles: options.configFiles } : {}),\n ...(options.configPattern ? { configPattern: options.configPattern } : {})\n };\n}\n\nfunction withRuntimePort(entries: DevHostEntry[], requestedPort: number, port: number) {\n if (requestedPort === port) return entries;\n\n const hasRequestedPort = entries.some((entry) => entry.port === requestedPort);\n if (!hasRequestedPort) return entries;\n\n return entries.map((entry) => (\n entry.port === requestedPort\n ? { ...entry, port, target: `127.0.0.1:${port}` }\n : entry\n ));\n}\n\nfunction uniqueHosts(entries: DevHostEntry[]) {\n return [...new Set(entries.map((entry) => entry.host))];\n}\n\nfunction isAliasableHost(host: string) {\n return host.includes(\".\") && !host.startsWith(\"www.\") && !host.includes(\":\");\n}\n\nexport function getDefaultWwwAlias(host: string) {\n return isAliasableHost(host) ? `www.${host}` : null;\n}\n\nexport function addDefaultWwwAliases(entries: DevHostEntry[]) {\n const seen = new Set(entries.map((entry) => entry.host));\n const aliases: DevHostEntry[] = [];\n\n for (const entry of entries) {\n const alias = getDefaultWwwAlias(entry.host);\n if (alias && !seen.has(alias)) {\n aliases.push({ host: alias, port: entry.port, target: `127.0.0.1:${entry.port}` });\n seen.add(alias);\n }\n }\n\n return [...entries, ...aliases];\n}\n\nfunction defined<T extends Record<string, unknown>>(input: T) {\n return Object.fromEntries(Object.entries(input).filter(([, value]) => typeof value !== \"undefined\")) as Partial<T>;\n}\n\nexport async function readLocalghostProjectConfig(options: {\n cwd?: string;\n configFile?: string | false;\n} = {}): Promise<LocalghostProjectConfigResult> {\n const cwd = options.cwd ?? process.cwd();\n if (options.configFile === false) return { config: {} };\n\n const candidates = options.configFile ? [options.configFile] : LOCALGHOST_PROJECT_CONFIG_FILES;\n const path = candidates.map((candidate) => resolveDevHostsPath({ cwd, fileName: candidate }).path).find((candidate) => existsSync(candidate));\n if (!path) return { config: {} };\n\n const imported = await import(`${pathToFileURL(path).href}?localghost=${Date.now()}`);\n const config = (imported.default ?? imported) as LocalghostProjectConfig;\n\n return { config, path };\n}\n\nexport function defineLocalghostConfig<T extends LocalghostContextOptions>(config: T) {\n return config;\n}\n\nexport async function resolveLocalghostContext(options: LocalghostContextOptions = {}): Promise<LocalghostContext> {\n const cwd = options.cwd ?? process.cwd();\n const projectConfig = await readLocalghostProjectConfig({\n cwd,\n ...(typeof options.localghostConfig !== \"undefined\" ? { configFile: options.localghostConfig } : {})\n });\n const merged = {\n ...projectConfig.config,\n ...defined(options)\n } as LocalghostContextOptions;\n const readOptions = readOptionsFromContext({ ...merged, cwd });\n const resolvedPath = resolveDevHostsPath(readOptions);\n const configEntries = readDevHosts(readOptions);\n const requestedPort = merged.port ?? envPort() ?? configEntries[0]?.port ?? 5173;\n const dynamicPort = merged.dynamicPort ?? envDynamicPort() ?? true;\n const autoRepair = merged.autoRepair ?? true;\n const bindHost = merged.bindHost ?? \"127.0.0.1\";\n const probeHost = typeof bindHost === \"string\" ? bindHost : \"127.0.0.1\";\n let port = requestedPort;\n let releasePort: (() => Promise<boolean>) | undefined;\n const reservePort = merged.reservePort ?? false;\n const instanceKey = merged.instanceKey ?? \"run\";\n if (reservePort && dynamicPort) {\n const registry = createLocalghostRegistry({ cwd, ...(merged.registryOwnerToken ? { ownerToken: merged.registryOwnerToken } : {}) });\n const lease = await registry.acquirePort({\n projectCwd: cwd,\n instanceKey,\n startPort: requestedPort,\n host: probeHost,\n ...(options.reservedPorts ? { reservedPorts: options.reservedPorts } : {})\n });\n port = lease.port;\n releasePort = () => registry.releasePort({ projectCwd: cwd, instanceKey });\n } else if (dynamicPort) {\n port = await findAvailablePort(requestedPort, { host: probeHost });\n }\n const wwwAlias = merged.wwwAlias ?? true;\n const entries = wwwAlias\n ? addDefaultWwwAliases(withRuntimePort(configEntries, requestedPort, port))\n : withRuntimePort(configEntries, requestedPort, port);\n const hosts = uniqueHosts(entries);\n const primaryHost =\n merged.primaryHost ??\n entries.find((entry) => entry.port === port)?.host ??\n hosts[0] ??\n `${sanitizeProjectName(getProjectName(cwd))}.localhost`;\n const projectName = sanitizeProjectName(merged.project ?? getProjectName(cwd));\n const ghostTunnel = resolveGhostTunnelConfig(merged.ghostTunnel, {\n route: getRouteName(primaryHost, projectName),\n project: projectName,\n owner: getLocalOwner(cwd)\n });\n\n return {\n cwd,\n projectName,\n readOptions,\n configPath: resolvedPath.path,\n configFileName: resolvedPath.fileName,\n configEntries,\n entries,\n hosts,\n requestedPort,\n port,\n dynamicPort,\n autoRepair,\n bindHost,\n primaryHost,\n https: merged.https ?? envHttps() ?? false,\n wwwAlias,\n ghostTunnel,\n ...(projectConfig.path ? { projectConfigPath: projectConfig.path } : {}),\n ...(releasePort ? { releasePort } : {})\n };\n}\n","import { createServer } from \"node:net\";\n\nexport type FindAvailablePortOptions = {\n host?: string;\n maxAttempts?: number;\n};\n\nexport async function isPortAvailable(port: number, host = \"127.0.0.1\") {\n return new Promise<boolean>((resolve) => {\n const server = createServer();\n\n server.once(\"error\", () => {\n resolve(false);\n });\n\n server.once(\"listening\", () => {\n server.close(() => resolve(true));\n });\n\n server.listen(port, host);\n });\n}\n\nexport async function findAvailablePort(startPort: number, options: FindAvailablePortOptions = {}) {\n const host = options.host ?? \"127.0.0.1\";\n const maxAttempts = options.maxAttempts ?? 50;\n\n for (let offset = 0; offset < maxAttempts; offset += 1) {\n const port = startPort + offset;\n if (await isPortAvailable(port, host)) {\n return port;\n }\n }\n\n throw new Error(`No available port found from ${startPort} to ${startPort + maxAttempts - 1}.`);\n}\n","import { randomUUID } from \"node:crypto\";\nimport { mkdir, open, readFile, rename, rm, stat, unlink, writeFile } from \"node:fs/promises\";\nimport { homedir } from \"node:os\";\nimport { join, normalize, resolve } from \"node:path\";\nimport { isPortAvailable } from \"./port.js\";\n\nexport const LOCALGHOST_REGISTRY_FILE = \"registry.json\";\nexport const LOCALGHOST_REGISTRY_LOCK_FILE = \"registry.lock\";\n\nexport type PortAvailabilityCheck = (port: number, host?: string) => boolean | Promise<boolean>;\n\nexport type LocalghostRegistryEntry = {\n projectCwd: string;\n instanceKey: string;\n port: number;\n updatedAt: number;\n};\n\nexport type LocalghostLease = {\n projectCwd: string;\n instanceKey: string;\n port: number;\n pid: number;\n acquiredAt: number;\n expiresAt: number;\n ownerToken: string;\n};\n\nexport type LocalghostRegistryData = {\n version: 1;\n allocations: LocalghostRegistryEntry[];\n leases: LocalghostLease[];\n};\n\nexport type LocalghostRegistryOptions = {\n stateRoot?: string;\n cwd?: string;\n pid?: number;\n ownerToken?: string;\n now?: () => number;\n isProcessRunning?: (pid: number) => boolean;\n availabilityCheck?: PortAvailabilityCheck;\n lockTimeoutMs?: number;\n lockRetryMs?: number;\n lockStaleMs?: number;\n};\n\nexport type AcquireLocalghostPortOptions = {\n projectCwd?: string;\n instanceKey: string;\n startPort?: number;\n maxAttempts?: number;\n reservedPorts?: Iterable<number>;\n leaseTtlMs?: number;\n host?: string;\n};\n\nexport type LocalghostRegistry = {\n root: string;\n registryPath: string;\n lockPath: string;\n ownerToken: string;\n acquirePort(options: AcquireLocalghostPortOptions): Promise<LocalghostLease>;\n releasePort(options: { projectCwd?: string; instanceKey: string }): Promise<boolean>;\n read(): Promise<LocalghostRegistryData>;\n prune(): Promise<{ removedLeases: number }>;\n};\n\ntype RegistryLock = { pid: number; createdAt: number; token: string };\n\nfunction defaultProcessRunning(pid: number) {\n if (pid <= 0) return false;\n try {\n process.kill(pid, 0);\n return true;\n } catch (error) {\n return (error as NodeJS.ErrnoException).code === \"EPERM\";\n }\n}\n\nexport function getLocalghostRegistryRoot(env: NodeJS.ProcessEnv = process.env) {\n return resolve(env.LOCALGHOST_HOME || join(homedir(), \".localghost\"));\n}\n\nexport function canonicalizeLocalghostProjectCwd(cwd = process.cwd()) {\n return normalize(resolve(cwd));\n}\n\nfunction emptyRegistry(): LocalghostRegistryData {\n return { version: 1, allocations: [], leases: [] };\n}\n\nfunction leaseKey(projectCwd: string, instanceKey: string) {\n return `${projectCwd}\\u0000${instanceKey}`;\n}\n\nfunction validRegistry(value: unknown): value is LocalghostRegistryData {\n if (!value || typeof value !== \"object\") return false;\n const candidate = value as Partial<LocalghostRegistryData>;\n return candidate.version === 1 && Array.isArray(candidate.allocations) && Array.isArray(candidate.leases);\n}\n\nfunction pruneRegistry(registry: LocalghostRegistryData, now: number, isRunning: (pid: number) => boolean) {\n registry.leases = registry.leases.filter((lease) => lease.expiresAt > now && isRunning(lease.pid));\n}\n\nasync function readJson(path: string) {\n try {\n return JSON.parse(await readFile(path, \"utf8\")) as unknown;\n } catch (error) {\n if ((error as NodeJS.ErrnoException).code === \"ENOENT\") return undefined;\n return undefined;\n }\n}\n\nexport function createLocalghostRegistry(options: LocalghostRegistryOptions = {}): LocalghostRegistry {\n const root = resolve(options.stateRoot ?? getLocalghostRegistryRoot());\n const registryPath = join(root, LOCALGHOST_REGISTRY_FILE);\n const lockPath = join(root, LOCALGHOST_REGISTRY_LOCK_FILE);\n const cwd = canonicalizeLocalghostProjectCwd(options.cwd);\n const now = options.now ?? Date.now;\n const pid = options.pid ?? process.pid;\n const ownerToken = options.ownerToken ?? randomUUID();\n const isRunning = options.isProcessRunning ?? defaultProcessRunning;\n const availabilityCheck = options.availabilityCheck ?? isPortAvailable;\n const lockTimeoutMs = options.lockTimeoutMs ?? 5000;\n const lockRetryMs = options.lockRetryMs ?? 25;\n const lockStaleMs = options.lockStaleMs ?? 30000;\n\n async function readRegistry() {\n const value = await readJson(registryPath);\n return validRegistry(value) ? value : emptyRegistry();\n }\n\n async function writeRegistry(registry: LocalghostRegistryData) {\n await mkdir(root, { recursive: true });\n const temporaryPath = join(root, `.registry.${process.pid}.${randomUUID()}.tmp`);\n await writeFile(temporaryPath, `${JSON.stringify(registry, null, 2)}\\n`, { mode: 0o600 });\n await rename(temporaryPath, registryPath);\n }\n\n async function lock() {\n await mkdir(root, { recursive: true });\n const deadline = now() + lockTimeoutMs;\n const token = randomUUID();\n while (true) {\n try {\n const handle = await open(lockPath, \"wx\", 0o600);\n await handle.writeFile(`${JSON.stringify({ pid, createdAt: now(), token } satisfies RegistryLock)}\\n`);\n await handle.close();\n return async () => {\n const current = await readJson(lockPath);\n if ((current as RegistryLock | undefined)?.token === token) await unlink(lockPath).catch(() => undefined);\n };\n } catch (error) {\n if ((error as NodeJS.ErrnoException).code !== \"EEXIST\") throw error;\n const lockInfo = await readJson(lockPath) as RegistryLock | undefined;\n let stale = false;\n if (lockInfo && typeof lockInfo.pid === \"number\") {\n stale = !isRunning(lockInfo.pid) && now() - lockInfo.createdAt >= 0;\n } else {\n try {\n stale = now() - (await stat(lockPath)).mtimeMs > lockStaleMs;\n } catch {\n continue;\n }\n }\n if (stale) {\n await rm(lockPath, { force: true }).catch(() => undefined);\n continue;\n }\n if (now() >= deadline) throw new Error(`Timed out waiting for Localghost registry lock: ${lockPath}`);\n await new Promise((resolveDelay) => setTimeout(resolveDelay, lockRetryMs));\n }\n }\n }\n\n async function withLock<T>(operation: (registry: LocalghostRegistryData) => Promise<T>) {\n const releaseLock = await lock();\n try {\n const registry = await readRegistry();\n pruneRegistry(registry, now(), isRunning);\n return await operation(registry);\n } finally {\n await releaseLock();\n }\n }\n\n return {\n root,\n registryPath,\n lockPath,\n ownerToken,\n read: readRegistry,\n async prune() {\n const releaseLock = await lock();\n try {\n const registry = await readRegistry();\n const before = registry.leases.length;\n pruneRegistry(registry, now(), isRunning);\n await writeRegistry(registry);\n return { removedLeases: before - registry.leases.length };\n } finally {\n await releaseLock();\n }\n },\n async acquirePort(acquireOptions) {\n const projectCwd = canonicalizeLocalghostProjectCwd(acquireOptions.projectCwd ?? cwd);\n if (!acquireOptions.instanceKey) throw new Error(\"instanceKey is required\");\n return withLock(async (registry) => {\n const key = leaseKey(projectCwd, acquireOptions.instanceKey);\n const existing = registry.allocations.find((entry) => leaseKey(entry.projectCwd, entry.instanceKey) === key);\n const reserved = new Set(acquireOptions.reservedPorts ?? []);\n const activePorts = new Set(registry.leases.map((lease) => lease.port));\n const port = existing?.port;\n const ownsActiveLease = registry.leases.some((lease) => lease.port === port && leaseKey(lease.projectCwd, lease.instanceKey) === key && lease.ownerToken === ownerToken);\n const reusable = port !== undefined && !reserved.has(port) &&\n (!activePorts.has(port) || ownsActiveLease) &&\n (ownsActiveLease || await availabilityCheck(port, acquireOptions.host));\n let selectedPort = reusable ? port : undefined;\n if (selectedPort === undefined) {\n const startPort = acquireOptions.startPort ?? 3000;\n const maxAttempts = acquireOptions.maxAttempts ?? 50;\n for (let offset = 0; offset < maxAttempts; offset += 1) {\n const candidate = startPort + offset;\n if (reserved.has(candidate) || activePorts.has(candidate)) continue;\n if (await availabilityCheck(candidate, acquireOptions.host)) {\n selectedPort = candidate;\n break;\n }\n }\n if (selectedPort === undefined) throw new Error(`No available registry port found from ${startPort} to ${startPort + maxAttempts - 1}.`);\n }\n const timestamp = now();\n const entry = existing ?? { projectCwd, instanceKey: acquireOptions.instanceKey, port: selectedPort, updatedAt: timestamp };\n entry.port = selectedPort;\n entry.updatedAt = timestamp;\n if (!existing) registry.allocations.push(entry);\n registry.leases = registry.leases.filter((lease) => leaseKey(lease.projectCwd, lease.instanceKey) !== key);\n const lease = { projectCwd, instanceKey: acquireOptions.instanceKey, port: selectedPort, pid, acquiredAt: timestamp, expiresAt: timestamp + (acquireOptions.leaseTtlMs ?? 30 * 60 * 1000), ownerToken };\n registry.leases.push(lease);\n await writeRegistry(registry);\n return lease;\n });\n },\n async releasePort(releaseOptions) {\n const projectCwd = canonicalizeLocalghostProjectCwd(releaseOptions.projectCwd ?? cwd);\n return withLock(async (registry) => {\n const key = leaseKey(projectCwd, releaseOptions.instanceKey);\n const before = registry.leases.length;\n registry.leases = registry.leases.filter((lease) => leaseKey(lease.projectCwd, lease.instanceKey) !== key || lease.ownerToken !== ownerToken);\n if (registry.leases.length !== before) await writeRegistry(registry);\n return registry.leases.length !== before;\n });\n }\n };\n}\n","import { domainToASCII } from \"node:url\";\n\nexport type GhostTunnelNamespaceTag = \"route\" | \"project\" | \"owner\" | string;\n\nexport type GhostTunnelNamespaceOptions = readonly GhostTunnelNamespaceTag[] | {\n tags?: readonly GhostTunnelNamespaceTag[];\n separator?: string;\n spreadTag?: GhostTunnelNamespaceTag | false;\n};\n\nexport type GhostTunnelNamespaceConfig = {\n tags: GhostTunnelNamespaceTag[];\n separator: string;\n spreadTag?: GhostTunnelNamespaceTag;\n};\n\nexport type GhostTunnelNamespaceValues = Record<string, string> & {\n route?: string;\n project?: string;\n owner?: string;\n};\n\nexport type GhostTunnelPreviewOptions = {\n domain?: string;\n route: string;\n project: string;\n owner: string;\n values?: GhostTunnelNamespaceValues;\n path?: string;\n protocol?: \"http\" | \"https\";\n};\n\nexport type GhostTunnelMode = \"manual\" | \"public\";\n\nexport type GhostTunnelDomainOptions = string | readonly string[];\n\nexport type GhostTunnelAdapterProvider = \"vercel\";\nexport type GhostTunnelAdapterStrategy = \"same-project\" | \"separate-relay\";\nexport type GhostTunnelTransportKind = \"none\" | \"ip\" | \"tunnel\";\nexport type GhostTunnelAdapterTransport = GhostTunnelTransportKind;\nexport type GhostTunnelTunnelStoreProvider = \"vercel-redis\" | \"redis\";\nexport type GhostTunnelTunnelStoreEnv = \"auto\";\n\nexport type GhostTunnelTunnelStoreOptions = {\n provider?: GhostTunnelTunnelStoreProvider;\n env?: GhostTunnelTunnelStoreEnv;\n namespace?: string;\n};\n\nexport type GhostTunnelTransportOptions =\n | GhostTunnelTransportKind\n | {\n kind?: \"none\";\n }\n | {\n kind: \"ip\";\n allowPrivateNetworkAddress?: boolean;\n }\n | {\n kind: \"tunnel\";\n store?: GhostTunnelTunnelStoreOptions;\n waitMs?: number;\n pollIntervalMs?: number;\n routeTtlSeconds?: number;\n requestTtlSeconds?: number;\n maxRequestBodyBytes?: number;\n maxResponseBodyBytes?: number;\n };\n\nexport type GhostTunnelTransportConfig =\n | {\n kind: \"none\";\n }\n | {\n kind: \"ip\";\n allowPrivateNetworkAddress: boolean;\n }\n | {\n kind: \"tunnel\";\n store: Required<Pick<GhostTunnelTunnelStoreOptions, \"provider\" | \"env\" | \"namespace\">>;\n waitMs: number;\n pollIntervalMs: number;\n routeTtlSeconds: number;\n requestTtlSeconds: number;\n maxRequestBodyBytes: number;\n maxResponseBodyBytes: number;\n };\n\nexport type GhostTunnelAdapterOptions = GhostTunnelAdapterProvider | {\n provider: GhostTunnelAdapterProvider;\n strategy?: GhostTunnelAdapterStrategy;\n};\n\nexport type GhostTunnelOptions = false | GhostTunnelMode | {\n enabled?: boolean;\n mode?: GhostTunnelMode;\n domains?: GhostTunnelDomainOptions;\n subdomain?: string;\n namespace?: GhostTunnelNamespaceOptions;\n preview?: GhostTunnelPreviewOptions;\n requireHttps?: boolean;\n requireAuth?: boolean;\n adapter?: GhostTunnelAdapterOptions;\n transport?: GhostTunnelTransportOptions;\n};\n\nexport type GhostTunnelConfig = {\n enabled: boolean;\n mode: GhostTunnelMode;\n domains: string[];\n subdomain: string;\n namespace: GhostTunnelNamespaceConfig;\n preview?: GhostTunnelPreviewOptions;\n previewUrl?: string;\n displayUrl?: string;\n displayUrls: string[];\n requireHttps: boolean;\n requireAuth: boolean;\n transport: GhostTunnelTransportConfig;\n adapter?: {\n provider: GhostTunnelAdapterProvider;\n strategy: GhostTunnelAdapterStrategy;\n };\n};\n\nexport type GhostTunnelDisplayDefaults = {\n domain?: string;\n route?: string;\n project?: string;\n owner?: string;\n values?: GhostTunnelNamespaceValues;\n};\n\nexport type GhostTunnelRoute = {\n host: string;\n slug: string;\n namespace: GhostTunnelNamespaceValues;\n entryHost: string;\n wildcardHost: string;\n domain: string;\n};\n\nexport type ConstructGhostTunnelUrlInput = {\n domain: string;\n route: string;\n project: string;\n owner: string;\n values?: GhostTunnelNamespaceValues;\n path?: string;\n searchParams?: Record<string, string | number | boolean | null | undefined> | URLSearchParams;\n protocol?: \"http\" | \"https\";\n ghostTunnel?: GhostTunnelOptions | GhostTunnelConfig;\n};\n\nconst DEFAULT_GHOST_TUNNEL_SUBDOMAIN = \"ghost\";\nconst DEFAULT_GHOST_TUNNEL_NAMESPACE_TAGS = [\"route\", \"project\", \"owner\"] as const;\nconst DEFAULT_GHOST_TUNNEL_NAMESPACE_SEPARATOR = \"-\";\nconst DEFAULT_GHOST_TUNNEL_MODE: GhostTunnelMode = \"manual\";\nconst DEFAULT_GHOST_TUNNEL_ADAPTER_STRATEGY: GhostTunnelAdapterStrategy = \"same-project\";\nconst DEFAULT_GHOST_TUNNEL_TRANSPORT_KIND: GhostTunnelTransportKind = \"none\";\nconst DEFAULT_GHOST_TUNNEL_TUNNEL_STORE_PROVIDER: GhostTunnelTunnelStoreProvider = \"vercel-redis\";\nconst DEFAULT_GHOST_TUNNEL_TUNNEL_STORE_ENV: GhostTunnelTunnelStoreEnv = \"auto\";\nconst DEFAULT_GHOST_TUNNEL_TUNNEL_STORE_NAMESPACE = \"localghost\";\nconst DEFAULT_GHOST_TUNNEL_TUNNEL_WAIT_MS = 25_000;\nconst DEFAULT_GHOST_TUNNEL_TUNNEL_POLL_INTERVAL_MS = 250;\nconst DEFAULT_GHOST_TUNNEL_TUNNEL_ROUTE_TTL_SECONDS = 30;\nconst DEFAULT_GHOST_TUNNEL_TUNNEL_REQUEST_TTL_SECONDS = 60;\nconst DEFAULT_GHOST_TUNNEL_TUNNEL_MAX_REQUEST_BODY_BYTES = 1024 * 1024;\nconst DEFAULT_GHOST_TUNNEL_TUNNEL_MAX_RESPONSE_BODY_BYTES = 5 * 1024 * 1024;\n\ntype GhostTunnelLegacyAdapterOptions = {\n provider: GhostTunnelAdapterProvider;\n strategy?: GhostTunnelAdapterStrategy;\n transport?: GhostTunnelTransportOptions;\n};\n\nfunction isResolvedGhostTunnelConfig(value: GhostTunnelOptions | GhostTunnelConfig | undefined): value is GhostTunnelConfig {\n return typeof value === \"object\" && value !== null && \"enabled\" in value;\n}\n\nfunction toGhostTunnelConfig(options: GhostTunnelOptions | GhostTunnelConfig | undefined) {\n return isResolvedGhostTunnelConfig(options) ? options : resolveGhostTunnelConfig(options);\n}\n\nfunction stripHostPort(value: string) {\n const trimmed = value.trim().toLowerCase();\n if (trimmed.startsWith(\"[\") || trimmed.includes(\"/\")) return \"\";\n\n const portSeparator = trimmed.lastIndexOf(\":\");\n if (portSeparator === -1) return trimmed;\n\n const port = trimmed.slice(portSeparator + 1);\n return /^\\d+$/.test(port) ? trimmed.slice(0, portSeparator) : trimmed;\n}\n\nfunction normalizeDomain(value: string) {\n const host = stripHostPort(value.replace(/^\\*\\./, \"\"));\n const ascii = domainToASCII(host);\n if (!ascii || ascii.length > 253 || ascii.includes(\"..\")) return null;\n if (ascii.startsWith(\".\") || ascii.endsWith(\".\")) return null;\n if (ascii.includes(\"*\")) return null;\n if (!ascii.split(\".\").every(isValidHostLabel)) return null;\n return ascii;\n}\n\nfunction isValidHostLabel(value: string) {\n return value.length > 0 && value.length <= 63 && /^[a-z0-9](?:[a-z0-9-]*[a-z0-9])?$/.test(value);\n}\n\nfunction isValidNamespaceTag(value: string) {\n return /^[a-z][a-z0-9_]*$/i.test(value);\n}\n\nfunction isNamespaceTagList(options: GhostTunnelNamespaceOptions | undefined): options is readonly GhostTunnelNamespaceTag[] {\n return Array.isArray(options);\n}\n\nfunction assertValidSubdomain(value: string) {\n if (!isValidHostLabel(value)) {\n throw new Error(`Invalid ghost tunnel subdomain: ${value}`);\n }\n}\n\nfunction normalizeDomains(domains: GhostTunnelDomainOptions | undefined) {\n const values = typeof domains === \"string\" ? [domains] : [...(domains ?? [])];\n const normalized = values.map((value) => value.trim()).filter(Boolean).map((value) => {\n const domain = normalizeDomain(value);\n if (!domain) throw new Error(`Invalid ghost tunnel domain: ${value}`);\n return domain;\n });\n\n return [...new Set(normalized)];\n}\n\nfunction parseGhostTunnelMode(value: GhostTunnelMode | undefined) {\n return value ?? DEFAULT_GHOST_TUNNEL_MODE;\n}\n\nfunction parseGhostTunnelAdapterStrategy(value: GhostTunnelAdapterStrategy | undefined) {\n if (typeof value === \"undefined\") return DEFAULT_GHOST_TUNNEL_ADAPTER_STRATEGY;\n if (value === \"same-project\" || value === \"separate-relay\") return value;\n throw new Error(`Unsupported ghost tunnel adapter strategy: ${String(value)}`);\n}\n\nfunction parseGhostTunnelTransportKind(value: GhostTunnelTransportKind | undefined) {\n if (typeof value === \"undefined\") return DEFAULT_GHOST_TUNNEL_TRANSPORT_KIND;\n if (value === \"none\" || value === \"ip\" || value === \"tunnel\") return value;\n throw new Error(`Unsupported ghost tunnel transport: ${String(value)}`);\n}\n\nfunction parsePositiveInteger(value: number | undefined, fallback: number, name: string) {\n if (typeof value === \"undefined\") return fallback;\n if (!Number.isInteger(value) || value < 1) {\n throw new Error(`Invalid ghost tunnel ${name}: ${value}`);\n }\n return value;\n}\n\nfunction parseTunnelStoreProvider(value: GhostTunnelTunnelStoreProvider | undefined) {\n if (typeof value === \"undefined\") return DEFAULT_GHOST_TUNNEL_TUNNEL_STORE_PROVIDER;\n if (value === \"vercel-redis\" || value === \"redis\") return value;\n throw new Error(`Unsupported ghost tunnel tunnel store provider: ${String(value)}`);\n}\n\nfunction parseTunnelStoreEnv(value: GhostTunnelTunnelStoreEnv | undefined) {\n if (typeof value === \"undefined\") return DEFAULT_GHOST_TUNNEL_TUNNEL_STORE_ENV;\n if (value === \"auto\") return value;\n throw new Error(`Unsupported ghost tunnel tunnel store env: ${String(value)}`);\n}\n\nfunction parseTunnelStoreNamespace(value: string | undefined) {\n const namespace = value ?? DEFAULT_GHOST_TUNNEL_TUNNEL_STORE_NAMESPACE;\n if (!/^[a-z][a-z0-9:_-]{0,63}$/i.test(namespace)) {\n throw new Error(`Invalid ghost tunnel tunnel store namespace: ${namespace}`);\n }\n return namespace;\n}\n\nfunction resolveGhostTunnelAdapter(\n input: GhostTunnelAdapterOptions | GhostTunnelLegacyAdapterOptions | GhostTunnelConfig[\"adapter\"] | undefined\n): GhostTunnelConfig[\"adapter\"] {\n if (!input) return undefined;\n\n const provider = typeof input === \"string\" ? input : input.provider;\n if (provider !== \"vercel\") {\n throw new Error(`Unsupported ghost tunnel adapter provider: ${String(provider)}`);\n }\n\n return {\n provider,\n strategy: typeof input === \"string\" ? DEFAULT_GHOST_TUNNEL_ADAPTER_STRATEGY : parseGhostTunnelAdapterStrategy(input.strategy)\n };\n}\n\nfunction getLegacyGhostTunnelTransport(\n input: GhostTunnelAdapterOptions | GhostTunnelLegacyAdapterOptions | GhostTunnelConfig[\"adapter\"] | undefined\n) {\n if (!input || typeof input === \"string\" || !(\"transport\" in input)) return undefined;\n return input.transport;\n}\n\nfunction resolveGhostTunnelTransport(\n input: GhostTunnelTransportOptions | GhostTunnelTransportConfig | undefined\n): GhostTunnelTransportConfig {\n if (!input) {\n return { kind: \"none\" };\n }\n\n const kind = typeof input === \"string\"\n ? parseGhostTunnelTransportKind(input)\n : parseGhostTunnelTransportKind(input.kind);\n\n if (kind === \"ip\") {\n return {\n kind,\n allowPrivateNetworkAddress: typeof input === \"string\" ? false : input.kind === \"ip\" ? input.allowPrivateNetworkAddress ?? false : false\n };\n }\n\n if (kind === \"tunnel\") {\n const config: Extract<GhostTunnelTransportOptions, { kind: \"tunnel\" }> | Extract<GhostTunnelTransportConfig, { kind: \"tunnel\" }> | undefined =\n typeof input === \"string\" || input.kind !== \"tunnel\" ? undefined : input;\n const store = config?.store ?? {};\n return {\n kind,\n store: {\n provider: parseTunnelStoreProvider(store.provider),\n env: parseTunnelStoreEnv(store.env),\n namespace: parseTunnelStoreNamespace(store.namespace)\n },\n waitMs: parsePositiveInteger(config?.waitMs, DEFAULT_GHOST_TUNNEL_TUNNEL_WAIT_MS, \"tunnel waitMs\"),\n pollIntervalMs: parsePositiveInteger(config?.pollIntervalMs, DEFAULT_GHOST_TUNNEL_TUNNEL_POLL_INTERVAL_MS, \"tunnel pollIntervalMs\"),\n routeTtlSeconds: parsePositiveInteger(config?.routeTtlSeconds, DEFAULT_GHOST_TUNNEL_TUNNEL_ROUTE_TTL_SECONDS, \"tunnel routeTtlSeconds\"),\n requestTtlSeconds: parsePositiveInteger(config?.requestTtlSeconds, DEFAULT_GHOST_TUNNEL_TUNNEL_REQUEST_TTL_SECONDS, \"tunnel requestTtlSeconds\"),\n maxRequestBodyBytes: parsePositiveInteger(config?.maxRequestBodyBytes, DEFAULT_GHOST_TUNNEL_TUNNEL_MAX_REQUEST_BODY_BYTES, \"tunnel maxRequestBodyBytes\"),\n maxResponseBodyBytes: parsePositiveInteger(config?.maxResponseBodyBytes, DEFAULT_GHOST_TUNNEL_TUNNEL_MAX_RESPONSE_BODY_BYTES, \"tunnel maxResponseBodyBytes\")\n };\n }\n\n return { kind: \"none\" };\n}\n\nfunction resolveNamespaceConfig(options: GhostTunnelNamespaceOptions | undefined): GhostTunnelNamespaceConfig {\n const tags = isNamespaceTagList(options)\n ? [...options]\n : [...(options?.tags ?? DEFAULT_GHOST_TUNNEL_NAMESPACE_TAGS)];\n let separator = DEFAULT_GHOST_TUNNEL_NAMESPACE_SEPARATOR;\n let spreadTag: GhostTunnelNamespaceTag | false | undefined = tags.includes(\"project\") ? \"project\" : undefined;\n if (options && !isNamespaceTagList(options)) {\n separator = options.separator ?? DEFAULT_GHOST_TUNNEL_NAMESPACE_SEPARATOR;\n spreadTag = options.spreadTag === false ? false : options.spreadTag ?? spreadTag;\n }\n\n if (tags.length === 0) {\n throw new Error(\"Ghost tunnel namespace must include at least one tag.\");\n }\n\n for (const tag of tags) {\n if (!isValidNamespaceTag(tag)) {\n throw new Error(`Invalid ghost tunnel namespace tag: ${tag}`);\n }\n }\n\n if (spreadTag && !tags.includes(spreadTag)) {\n throw new Error(`Ghost tunnel namespace spreadTag must be listed in tags: ${spreadTag}`);\n }\n\n if (!separator || separator.length > 8 || !/^[a-z0-9-]+$/.test(separator)) {\n throw new Error(`Invalid ghost tunnel namespace separator: ${separator}`);\n }\n\n return {\n tags,\n separator,\n ...(spreadTag ? { spreadTag } : {})\n };\n}\n\nfunction normalizeNamespaceValue(tag: string, value: string, separator: string, options: { allowSeparator?: boolean } = {}) {\n const normalized = normalizeDomain(value);\n if (!normalized || normalized.includes(\".\")) {\n throw new Error(`Invalid ghost tunnel namespace value for ${tag}: ${value}`);\n }\n\n if (!options.allowSeparator && normalized.includes(separator)) {\n throw new Error(`Ghost tunnel namespace value for ${tag} cannot include separator \"${separator}\": ${value}`);\n }\n\n return normalized;\n}\n\nfunction createNamespaceSlug(config: GhostTunnelNamespaceConfig, values: GhostTunnelNamespaceValues) {\n const parts = config.tags.map((tag) => {\n const value = values[tag];\n if (!value) {\n throw new Error(`Missing ghost tunnel namespace value: ${tag}`);\n }\n\n return normalizeNamespaceValue(tag, value, config.separator, { allowSeparator: tag === config.spreadTag });\n });\n\n const slug = parts.join(config.separator);\n if (!isValidHostLabel(slug)) {\n throw new Error(`Ghost tunnel namespace is too long for a DNS label: ${slug}`);\n }\n\n return slug;\n}\n\nfunction createNamespaceDisplaySlug(config: GhostTunnelNamespaceConfig, values: GhostTunnelNamespaceValues = {}) {\n return config.tags.map((tag) => {\n const value = values[tag];\n if (!value) return `<${tag}>`;\n\n try {\n return normalizeNamespaceValue(tag, value, config.separator, { allowSeparator: tag === config.spreadTag });\n } catch {\n return `<${tag}>`;\n }\n }).join(config.separator);\n}\n\nfunction getPreviewDefaults(preview: GhostTunnelPreviewOptions | undefined, defaults: GhostTunnelDisplayDefaults | undefined) {\n return {\n domain: preview?.domain ?? defaults?.domain,\n route: preview?.route ?? defaults?.route,\n project: preview?.project ?? defaults?.project,\n owner: preview?.owner ?? defaults?.owner,\n values: {\n ...(defaults?.values ?? {}),\n ...(preview?.values ?? {})\n },\n path: preview?.path,\n protocol: preview?.protocol\n };\n}\n\nfunction getDisplayValues(input: ReturnType<typeof getPreviewDefaults>): GhostTunnelNamespaceValues {\n return {\n ...(input.route ? { route: input.route } : {}),\n ...(input.project ? { project: input.project } : {}),\n ...(input.owner ? { owner: input.owner } : {}),\n ...input.values\n };\n}\n\nfunction getDisplayDefaults(defaults?: GhostTunnelDisplayDefaults) {\n return defaults;\n}\n\nfunction createDisplayUrl(config: GhostTunnelConfig, defaults?: GhostTunnelDisplayDefaults, domain?: string) {\n const input = getPreviewDefaults(config.preview, getDisplayDefaults(defaults));\n const protocol = input.protocol ?? \"https\";\n const slug = createNamespaceDisplaySlug(config.namespace, getDisplayValues(input));\n const entryHost = domain\n ? getGhostTunnelEntryHost(domain, config)\n : input.domain\n ? getGhostTunnelEntryHost(input.domain, config)\n : `${config.subdomain}.*`;\n const url = `${protocol}://${slug}.${entryHost}/`;\n\n if (!input.path) return url;\n return `${url}${input.path.replace(/^\\/+/, \"\")}`;\n}\n\nfunction createDisplayUrls(config: GhostTunnelConfig, defaults?: GhostTunnelDisplayDefaults) {\n const displayDefaults = getDisplayDefaults(defaults);\n const domains = config.domains.length > 0\n ? config.domains\n : displayDefaults?.domain\n ? [displayDefaults.domain]\n : [];\n const urls = domains.length > 0\n ? domains.map((domain) => createDisplayUrl(config, displayDefaults, domain))\n : [createDisplayUrl(config, displayDefaults)];\n\n return [...new Set(urls)];\n}\n\nfunction maybeConstructPreviewUrl(config: GhostTunnelConfig, defaults?: GhostTunnelDisplayDefaults) {\n if (!config.preview) return undefined;\n\n const input = getPreviewDefaults(config.preview, defaults);\n if (!input.domain || !input.route || !input.project || !input.owner) return undefined;\n\n return constructGhostTunnelUrl({\n domain: input.domain,\n route: input.route,\n project: input.project,\n owner: input.owner,\n values: input.values,\n ...(input.path ? { path: input.path } : {}),\n ...(input.protocol ? { protocol: input.protocol } : {}),\n ghostTunnel: config\n });\n}\n\nfunction parseNamespaceSlug(slug: string, config: GhostTunnelNamespaceConfig): GhostTunnelNamespaceValues | null {\n const parts = slug.split(config.separator);\n if (parts.length < config.tags.length) return null;\n if (parts.length !== config.tags.length && !config.spreadTag) return null;\n\n const namespace: GhostTunnelNamespaceValues = {};\n const spreadIndex = config.spreadTag ? config.tags.indexOf(config.spreadTag) : -1;\n const spreadWidth = spreadIndex >= 0 ? parts.length - config.tags.length + 1 : 1;\n\n let partIndex = 0;\n for (const [tagIndex, tag] of config.tags.entries()) {\n const value = tagIndex === spreadIndex\n ? parts.slice(partIndex, partIndex + spreadWidth).join(config.separator)\n : parts[partIndex];\n if (!value || !isValidHostLabel(value)) return null;\n if (tagIndex !== spreadIndex && value.includes(config.separator)) return null;\n namespace[tag] = value;\n partIndex += tagIndex === spreadIndex ? spreadWidth : 1;\n }\n\n return namespace;\n}\n\nexport function resolveGhostTunnelConfig(options: GhostTunnelOptions | undefined, defaults?: GhostTunnelDisplayDefaults): GhostTunnelConfig {\n if (options === false || typeof options === \"undefined\") {\n return {\n enabled: false,\n mode: DEFAULT_GHOST_TUNNEL_MODE,\n domains: [],\n subdomain: DEFAULT_GHOST_TUNNEL_SUBDOMAIN,\n namespace: resolveNamespaceConfig(undefined),\n displayUrls: [],\n requireHttps: true,\n requireAuth: true,\n transport: resolveGhostTunnelTransport(undefined)\n };\n }\n\n const config = typeof options === \"string\"\n ? { mode: options }\n : options;\n const subdomain = config.subdomain ?? DEFAULT_GHOST_TUNNEL_SUBDOMAIN;\n assertValidSubdomain(subdomain);\n const domains = normalizeDomains(config.domains);\n const enabled = config.enabled ?? true;\n const adapter = resolveGhostTunnelAdapter(config.adapter);\n const transport = resolveGhostTunnelTransport(config.transport ?? getLegacyGhostTunnelTransport(config.adapter));\n\n const resolved: GhostTunnelConfig = {\n enabled,\n mode: parseGhostTunnelMode(config.mode),\n domains,\n subdomain,\n namespace: resolveNamespaceConfig(config.namespace),\n ...(config.preview ? { preview: config.preview } : {}),\n displayUrls: [],\n requireHttps: config.requireHttps ?? true,\n requireAuth: config.requireAuth ?? true,\n transport,\n ...(adapter ? { adapter } : {})\n };\n\n if (!enabled) {\n return resolved;\n }\n\n const previewUrl = maybeConstructPreviewUrl(resolved, defaults);\n const displayUrls = previewUrl ? [previewUrl] : createDisplayUrls(resolved, defaults);\n\n return {\n ...resolved,\n displayUrls,\n ...(displayUrls[0] ? { displayUrl: displayUrls[0] } : {}),\n ...(previewUrl ? { previewUrl } : {})\n };\n}\n\nexport function getGhostTunnelEntryHost(domain: string, options: GhostTunnelOptions | GhostTunnelConfig = {}) {\n const config = toGhostTunnelConfig(options);\n const normalizedDomain = normalizeDomain(domain);\n if (!normalizedDomain) {\n throw new Error(`Invalid ghost tunnel domain: ${domain}`);\n }\n\n return `${config.subdomain}.${normalizedDomain}`;\n}\n\nexport function getGhostTunnelWildcardHost(domain: string, options: GhostTunnelOptions | GhostTunnelConfig = {}) {\n return `*.${getGhostTunnelEntryHost(domain, options)}`;\n}\n\nexport function constructGhostTunnelHost(input: Omit<ConstructGhostTunnelUrlInput, \"path\" | \"searchParams\" | \"protocol\">) {\n const config = toGhostTunnelConfig(input.ghostTunnel ?? {});\n if (!config.enabled) {\n throw new Error(\"Ghost tunnel is not enabled.\");\n }\n\n const namespaceValues: GhostTunnelNamespaceValues = {\n route: input.route,\n project: input.project,\n owner: input.owner,\n ...(input.values ?? {})\n };\n const slug = createNamespaceSlug(config.namespace, namespaceValues);\n\n return `${slug}.${getGhostTunnelEntryHost(input.domain, config)}`;\n}\n\nexport function constructGhostTunnelUrl(input: ConstructGhostTunnelUrlInput) {\n const protocol = input.protocol ?? \"https\";\n const host = constructGhostTunnelHost(input);\n const url = new URL(`${protocol}://${host}/`);\n\n if (input.path) {\n url.pathname = `/${input.path.replace(/^\\/+/, \"\")}`;\n }\n\n if (input.searchParams instanceof URLSearchParams) {\n url.search = input.searchParams.toString();\n } else if (input.searchParams) {\n for (const [key, value] of Object.entries(input.searchParams)) {\n if (typeof value !== \"undefined\" && value !== null) {\n url.searchParams.set(key, String(value));\n }\n }\n }\n\n return url.toString();\n}\n\nexport const constructGhostTunnelURL = constructGhostTunnelUrl;\n\nexport function getGhostTunnelDefaultDisplayUrl(options: GhostTunnelOptions | GhostTunnelConfig = {}, defaults?: GhostTunnelDisplayDefaults) {\n const config = toGhostTunnelConfig(options);\n if (!config.enabled) return null;\n return createDisplayUrl(config, defaults);\n}\n\nexport function getGhostTunnelDisplayUrl(options: GhostTunnelOptions | GhostTunnelConfig | undefined, defaults?: GhostTunnelDisplayDefaults) {\n const config = toGhostTunnelConfig(options);\n if (!config.enabled) return null;\n return config.displayUrl ?? config.previewUrl ?? getGhostTunnelDefaultDisplayUrl(config, defaults);\n}\n\nexport function getGhostTunnelDisplayUrls(options: GhostTunnelOptions | GhostTunnelConfig | undefined, defaults?: GhostTunnelDisplayDefaults) {\n const config = toGhostTunnelConfig(options);\n if (!config.enabled) return [];\n if (config.displayUrls.length > 0) return config.displayUrls;\n const displayUrl = getGhostTunnelDisplayUrl(config, defaults);\n return displayUrl ? [displayUrl] : [];\n}\n\nexport function getGhostTunnelPreviewUrl(options: GhostTunnelOptions | GhostTunnelConfig | undefined) {\n const config = toGhostTunnelConfig(options);\n if (!config.enabled) return null;\n return config.previewUrl ?? maybeConstructPreviewUrl(config) ?? null;\n}\n\nexport function parseGhostTunnelHost(host: string, domain: string, options: GhostTunnelOptions | GhostTunnelConfig = {}): GhostTunnelRoute | null {\n const config = toGhostTunnelConfig(options);\n if (!config.enabled) return null;\n\n const normalizedHost = normalizeDomain(host);\n const normalizedDomain = normalizeDomain(domain);\n if (!normalizedHost || !normalizedDomain) return null;\n\n const entryHost = getGhostTunnelEntryHost(normalizedDomain, config);\n const suffix = `.${entryHost}`;\n if (!normalizedHost.endsWith(suffix)) return null;\n\n const slug = normalizedHost.slice(0, -suffix.length);\n if (!isValidHostLabel(slug)) return null;\n const namespace = parseNamespaceSlug(slug, config.namespace);\n if (!namespace) return null;\n\n return {\n host: normalizedHost,\n slug,\n namespace,\n entryHost,\n wildcardHost: `*.${entryHost}`,\n domain: normalizedDomain\n };\n}\n\nexport function assertSecureGhostTunnelRequest(input: {\n host: string;\n domain: string;\n protocol: \"http\" | \"https\";\n ghostTunnel: GhostTunnelOptions | GhostTunnelConfig | undefined;\n authenticated?: boolean;\n}) {\n const config = toGhostTunnelConfig(input.ghostTunnel);\n\n if (!config.enabled) {\n throw new Error(\"Ghost tunnel is not enabled.\");\n }\n\n if (config.requireHttps && input.protocol !== \"https\") {\n throw new Error(\"Ghost tunnel requests must use HTTPS.\");\n }\n\n if (config.requireAuth && input.authenticated !== true) {\n throw new Error(\"Ghost tunnel requests must be authenticated.\");\n }\n\n const route = parseGhostTunnelHost(input.host, input.domain, config);\n if (!route) {\n throw new Error(`Host is not a valid ghost tunnel host for ${input.domain}.`);\n }\n\n return route;\n}\n","import { execa } from \"execa\";\nimport { isPortAvailable } from \"./port.js\";\nimport { canonicalizeLocalghostProjectCwd, createLocalghostRegistry } from \"./registry.js\";\nimport { isProcessRunning } from \"./activity.js\";\nimport { resolveLocalghostContext } from \"./context.js\";\nimport type { ConfigPattern } from \"./config.js\";\n\nexport type DoctorResult = {\n ok: boolean;\n caddy: {\n found: boolean;\n version?: string;\n installHint: string;\n };\n ports: {\n configured?: number;\n available?: boolean;\n registryPath: string;\n staleLeases: Array<{ projectCwd: string; instanceKey: string; port: number; pid: number }>;\n duplicateAllocations: Array<{ port: number; projects: string[] }>;\n currentAllocation?: { projectCwd: string; instanceKey: string; port: number };\n };\n};\n\nexport type DoctorOptions = {\n cwd?: string;\n configFiles?: string[];\n configPattern?: ConfigPattern;\n};\n\nexport async function checkCaddy(): Promise<DoctorResult[\"caddy\"]> {\n try {\n const result = await execa(\"caddy\", [\"version\"], { reject: false });\n const version = [result.stdout, result.stderr].filter(Boolean).join(\"\\n\").trim();\n\n return {\n found: result.exitCode === 0,\n ...(version ? { version } : {}),\n installHint: \"brew install caddy\"\n };\n } catch {\n return {\n found: false,\n installHint: \"brew install caddy\"\n };\n }\n}\n\nexport async function runDoctor(options: DoctorOptions = {}): Promise<DoctorResult> {\n const caddy = await checkCaddy();\n const cwd = options.cwd ?? process.cwd();\n const registry = createLocalghostRegistry({ cwd });\n const data = await registry.read();\n const now = Date.now();\n const staleLeases = data.leases\n .filter((lease) => lease.expiresAt <= now || !isProcessRunning(lease.pid))\n .map(({ projectCwd, instanceKey, port, pid }) => ({ projectCwd, instanceKey, port, pid }));\n const allocationsByPort = new Map<number, string[]>();\n for (const allocation of data.allocations) {\n const projects = allocationsByPort.get(allocation.port) ?? [];\n projects.push(`${allocation.projectCwd}#${allocation.instanceKey}`);\n allocationsByPort.set(allocation.port, projects);\n }\n const duplicateAllocations = [...allocationsByPort.entries()]\n .filter(([, projects]) => projects.length > 1)\n .map(([port, projects]) => ({ port, projects }));\n let configured: number | undefined;\n let available: boolean | undefined;\n try {\n const context = await resolveLocalghostContext({\n cwd,\n ...(options.configFiles ? { configFiles: options.configFiles } : {}),\n ...(options.configPattern ? { configPattern: options.configPattern } : {}),\n dynamicPort: false\n });\n configured = context.requestedPort;\n available = await isPortAvailable(configured);\n } catch {\n // The existing Caddy check remains useful even when project config is invalid.\n }\n const currentProjectCwd = canonicalizeLocalghostProjectCwd(cwd);\n const currentAllocation = data.allocations.find((allocation) => allocation.projectCwd === currentProjectCwd);\n return {\n ok: caddy.found && available !== false && staleLeases.length === 0 && duplicateAllocations.length === 0,\n caddy,\n ports: {\n ...(configured !== undefined ? { configured } : {}),\n ...(available !== undefined ? { available } : {}),\n registryPath: registry.registryPath,\n staleLeases,\n duplicateAllocations,\n ...(currentAllocation ? {\n currentAllocation: {\n projectCwd: currentAllocation.projectCwd,\n instanceKey: currentAllocation.instanceKey,\n port: currentAllocation.port\n }\n } : {})\n }\n };\n}\n","export type LocalghostEnvironment = NodeJS.ProcessEnv;\n\nconst PRODUCTION_ENV_KEYS = [\"NODE_ENV\", \"VERCEL_ENV\", \"NETLIFY\", \"CF_PAGES_BRANCH\", \"LOCALGHOST_ENV\"] as const;\n\nexport function getProductionReason(env: LocalghostEnvironment = process.env) {\n if (env.LOCALGHOST_ENV === \"production\") return \"LOCALGHOST_ENV=production\";\n if (env.NODE_ENV === \"production\") return \"NODE_ENV=production\";\n if (env.VERCEL_ENV === \"production\") return \"VERCEL_ENV=production\";\n if (env.NETLIFY === \"true\" && env.CONTEXT === \"production\") return \"NETLIFY=true and CONTEXT=production\";\n if (env.CF_PAGES_BRANCH && env.CF_PAGES_BRANCH === env.CF_PAGES_PRODUCTION_BRANCH) {\n return \"CF_PAGES_BRANCH matches CF_PAGES_PRODUCTION_BRANCH\";\n }\n\n return null;\n}\n\nexport function isProductionLike(env: LocalghostEnvironment = process.env) {\n return getProductionReason(env) !== null;\n}\n\nexport function assertLocalDevelopment(command: string, env: LocalghostEnvironment = process.env) {\n const reason = getProductionReason(env);\n if (!reason) return;\n\n throw new Error(`Localghost only runs in local development. Refusing \\`${command}\\` because ${reason}.`);\n}\n\nexport function getProductionEnvKeys() {\n return PRODUCTION_ENV_KEYS;\n}\n","import { readDevHosts, resolveDevHostsPath, type ReadDevHostsOptions } from \"./config.js\";\nimport type { DevHostEntry } from \"./parse.js\";\n\nexport const LOCALGHOST_GHOST_TUNNEL_FILE = \".ghosttunnel\";\n\nexport type ReadGhostTunnelOptions = ReadDevHostsOptions;\n\nfunction toGhostTunnelOptions(options: ReadGhostTunnelOptions | string = {}): ReadGhostTunnelOptions {\n const resolved = typeof options === \"string\" ? { cwd: options } : options;\n\n return {\n ...resolved,\n fileName: resolved.fileName ?? LOCALGHOST_GHOST_TUNNEL_FILE\n };\n}\n\nfunction normalizeHost(value: string) {\n return value.trim().toLowerCase().replace(/\\.$/, \"\");\n}\n\nexport function resolveGhostTunnelPath(options: ReadGhostTunnelOptions | string = {}) {\n return resolveDevHostsPath(toGhostTunnelOptions(options));\n}\n\nexport function getGhostTunnelPath(options: ReadGhostTunnelOptions | string = {}) {\n return resolveGhostTunnelPath(options).path;\n}\n\nexport function readGhostTunnelEntries(options: ReadGhostTunnelOptions | string = {}) {\n return readDevHosts(toGhostTunnelOptions(options));\n}\n\nexport function listGhostTunnelEntries(options: ReadGhostTunnelOptions | string = {}) {\n const resolved = resolveGhostTunnelPath(options);\n if (!resolved.exists) return [] satisfies DevHostEntry[];\n return readGhostTunnelEntries(options);\n}\n\nexport function findGhostTunnelEntry(host: string, options: ReadGhostTunnelOptions | string = {}) {\n const normalizedHost = normalizeHost(host);\n return listGhostTunnelEntries(options).find((entry) => entry.host === normalizedHost);\n}\n","import { randomUUID } from \"node:crypto\";\nimport { assertRelayLocalTarget, stripRelayForwardHeaders, type RelayLocalTarget } from \"./relay.js\";\nimport {\n createGhostTunnelRouteHeartbeat,\n decodeGhostTunnelBody,\n encodeGhostTunnelBody,\n type GhostTunnelQueuedRequest,\n type GhostTunnelQueuedResponse,\n type GhostTunnelStore\n} from \"./ghost-tunnel-store.js\";\nimport type { DevHostEntry } from \"./parse.js\";\n\nexport type GhostTunnelAgentOptions = {\n entries: DevHostEntry[];\n store: GhostTunnelStore;\n agentId?: string;\n targetHost?: string;\n routeTtlSeconds?: number;\n requestTtlSeconds?: number;\n pollIntervalMs?: number;\n maxResponseBodyBytes?: number;\n signal?: AbortSignal;\n fetch?: typeof fetch;\n log?: (message: string) => void;\n};\n\nexport type GhostTunnelAgent = {\n agentId: string;\n stop(): void;\n done: Promise<void>;\n};\n\nexport type ServeGhostTunnelLocalRequestInput = {\n request: GhostTunnelQueuedRequest;\n target: Required<RelayLocalTarget>;\n maxResponseBodyBytes: number;\n fetch?: typeof fetch;\n};\n\nfunction isStopped(signal: AbortSignal | undefined, localSignal: AbortSignal) {\n return localSignal.aborted || signal?.aborted === true;\n}\n\nfunction wait(ms: number, signal: AbortSignal | undefined, localSignal: AbortSignal) {\n if (isStopped(signal, localSignal)) return Promise.resolve();\n\n return new Promise<void>((resolve) => {\n const timeout = setTimeout(resolve, ms);\n const stop = () => {\n clearTimeout(timeout);\n resolve();\n };\n signal?.addEventListener(\"abort\", stop, { once: true });\n localSignal.addEventListener(\"abort\", stop, { once: true });\n });\n}\n\nfunction toHeaderRecord(headers: Headers) {\n const result: Record<string, string> = {};\n headers.forEach((value, name) => {\n result[name] = value;\n });\n return result;\n}\n\nfunction hasRequestBody(method: string) {\n return method !== \"GET\" && method !== \"HEAD\";\n}\n\nexport async function serveGhostTunnelLocalRequest(input: ServeGhostTunnelLocalRequestInput): Promise<GhostTunnelQueuedResponse> {\n const fetchImpl = input.fetch ?? fetch;\n const localUrl = new URL(`${input.target.protocol}://${input.target.host}:${input.target.port}/`);\n const requestPath = new URL(input.request.path, \"http://localghost.invalid\");\n localUrl.pathname = requestPath.pathname;\n localUrl.search = requestPath.search;\n\n try {\n const body = hasRequestBody(input.request.method) ? decodeGhostTunnelBody(input.request.bodyBase64) : undefined;\n const response = await fetchImpl(localUrl, {\n method: input.request.method,\n headers: {\n ...stripRelayForwardHeaders(input.request.headers),\n \"x-forwarded-host\": input.request.host,\n \"x-localghost-tunnel\": \"1\"\n },\n ...(body ? { body } : {})\n });\n const responseBody = Buffer.from(await response.arrayBuffer());\n if (responseBody.byteLength > input.maxResponseBodyBytes) {\n throw new Error(`Ghost Tunnel response exceeded ${input.maxResponseBodyBytes} bytes.`);\n }\n\n return {\n id: input.request.id,\n status: response.status,\n headers: toHeaderRecord(response.headers),\n createdAt: new Date().toISOString(),\n ...(responseBody.byteLength > 0 ? { bodyBase64: encodeGhostTunnelBody(responseBody) } : {})\n };\n } catch (error) {\n return {\n id: input.request.id,\n status: 502,\n headers: {\n \"content-type\": \"text/plain; charset=utf-8\",\n \"cache-control\": \"no-store\"\n },\n createdAt: new Date().toISOString(),\n error: error instanceof Error ? error.message : String(error),\n bodyBase64: encodeGhostTunnelBody(\"Ghost Tunnel local target failed.\")\n };\n }\n}\n\nasync function heartbeatRoutes(input: {\n entries: DevHostEntry[];\n store: GhostTunnelStore;\n agentId: string;\n targetHost: string;\n routeTtlSeconds: number;\n}) {\n for (const entry of input.entries) {\n const target = assertRelayLocalTarget({ host: input.targetHost, port: entry.port });\n await input.store.heartbeatRoute(createGhostTunnelRouteHeartbeat({\n host: entry.host,\n agentId: input.agentId,\n target,\n ttlSeconds: input.routeTtlSeconds\n }), input.routeTtlSeconds);\n }\n}\n\nasync function claimAndServe(input: {\n entry: DevHostEntry;\n store: GhostTunnelStore;\n targetHost: string;\n requestTtlSeconds: number;\n maxResponseBodyBytes: number;\n fetch?: typeof fetch;\n}) {\n const request = await input.store.claimRequest(input.entry.host);\n if (!request) return false;\n\n const target = assertRelayLocalTarget({ host: input.targetHost, port: input.entry.port });\n const response = await serveGhostTunnelLocalRequest({\n request,\n target,\n maxResponseBodyBytes: input.maxResponseBodyBytes,\n ...(input.fetch ? { fetch: input.fetch } : {})\n });\n await input.store.writeResponse(response, input.requestTtlSeconds);\n return true;\n}\n\nexport function startGhostTunnelAgent(options: GhostTunnelAgentOptions): GhostTunnelAgent {\n const controller = new AbortController();\n const localSignal = controller.signal;\n const signal = options.signal;\n const agentId = options.agentId ?? `localghost-${randomUUID()}`;\n const targetHost = options.targetHost ?? \"127.0.0.1\";\n const routeTtlSeconds = options.routeTtlSeconds ?? 30;\n const requestTtlSeconds = options.requestTtlSeconds ?? 60;\n const pollIntervalMs = options.pollIntervalMs ?? 500;\n const maxResponseBodyBytes = options.maxResponseBodyBytes ?? 5 * 1024 * 1024;\n\n const done = (async () => {\n if (options.entries.length === 0) {\n throw new Error(\"Ghost Tunnel agent requires at least one .ghosttunnel entry.\");\n }\n\n options.log?.(`localghost tunnel agent ${agentId}`);\n for (const entry of options.entries) {\n options.log?.(` ${entry.host} -> ${targetHost}:${entry.port}`);\n }\n\n let lastHeartbeat = 0;\n while (!isStopped(signal, localSignal)) {\n const now = Date.now();\n if (now - lastHeartbeat >= Math.max(1000, Math.floor(routeTtlSeconds * 1000 / 3))) {\n await heartbeatRoutes({\n entries: options.entries,\n store: options.store,\n agentId,\n targetHost,\n routeTtlSeconds\n });\n lastHeartbeat = now;\n }\n\n let served = false;\n for (const entry of options.entries) {\n served = await claimAndServe({\n entry,\n store: options.store,\n targetHost,\n requestTtlSeconds,\n maxResponseBodyBytes,\n ...(options.fetch ? { fetch: options.fetch } : {})\n }) || served;\n }\n\n if (!served) {\n await wait(pollIntervalMs, signal, localSignal);\n }\n }\n })();\n\n return {\n agentId,\n stop() {\n controller.abort();\n },\n done\n };\n}\n","import { createHmac, timingSafeEqual } from \"node:crypto\";\nimport { domainToASCII } from \"node:url\";\n\nexport type RelayProtocol = \"http\" | \"https\";\nexport type RelayAccessMode = \"private\" | \"public\";\n\nexport type RelayLocalTarget = {\n protocol?: RelayProtocol;\n host: string;\n port: number;\n};\n\nexport type RelayLimits = {\n requestBodyBytes: number;\n responseBytes: number;\n timeoutMs: number;\n maxConcurrentRequests: number;\n perRouteRequestsPerMinute: number;\n perIpRequestsPerMinute: number;\n};\n\nexport type RelayTargetPolicy = {\n allowedHosts: string[];\n blockedPorts: number[];\n allowPrivateNetworkTargets: boolean;\n};\n\nexport type RelayRouteClaim = {\n host: string;\n scope: string;\n expiresAt: string;\n agentId: string;\n};\n\nexport type SignedRelayRouteClaim = {\n payload: RelayRouteClaim;\n token: string;\n};\n\nexport type RelayRouteRegistrationInput = {\n authorizationHeader?: string | null;\n agentToken: string;\n claimToken: string;\n signingSecret: string;\n expectedScope: string;\n target: RelayLocalTarget;\n access?: RelayAccessMode;\n publicMode?: boolean;\n passwordProtected?: boolean;\n authRequired?: boolean;\n now?: Date;\n targetPolicy?: Partial<RelayTargetPolicy>;\n limits?: Partial<RelayLimits>;\n};\n\nexport type ActiveRelayRoute = {\n host: string;\n scope: string;\n agentId: string;\n expiresAt: string;\n target: Required<RelayLocalTarget>;\n access: RelayAccessMode;\n passwordProtected: boolean;\n authRequired: boolean;\n limits: RelayLimits;\n};\n\nexport type RelayOfflineResponse = {\n status: 503;\n headers: Record<string, string>;\n body: string;\n};\n\nexport const DEFAULT_RELAY_ALLOWED_TARGET_HOSTS = [\"localhost\", \"127.0.0.1\", \"::1\"] as const;\nexport const DEFAULT_RELAY_BLOCKED_PORTS = [22, 2375, 2376, 5432, 6379, 9200, 9229, 27017] as const;\n\nexport const DEFAULT_RELAY_LIMITS: RelayLimits = {\n requestBodyBytes: 5 * 1024 * 1024,\n responseBytes: 25 * 1024 * 1024,\n timeoutMs: 30_000,\n maxConcurrentRequests: 20,\n perRouteRequestsPerMinute: 120,\n perIpRequestsPerMinute: 60\n};\n\nexport const DEFAULT_RELAY_TARGET_POLICY: RelayTargetPolicy = {\n allowedHosts: [...DEFAULT_RELAY_ALLOWED_TARGET_HOSTS],\n blockedPorts: [...DEFAULT_RELAY_BLOCKED_PORTS],\n allowPrivateNetworkTargets: false\n};\n\nconst HOP_BY_HOP_HEADERS = new Set([\n \"connection\",\n \"keep-alive\",\n \"proxy-authenticate\",\n \"proxy-authorization\",\n \"te\",\n \"trailer\",\n \"transfer-encoding\",\n \"upgrade\"\n]);\n\nconst SENSITIVE_HEADERS = new Set([\"authorization\", \"cookie\", \"set-cookie\"]);\nconst TOKEN_QUERY_PATTERN = /(token|secret|key|password|session|jwt|auth)/i;\nconst HOST_PATTERN = /^(?=.{1,253}$)(?!-)[a-z0-9-]+(\\.[a-z0-9-]+)*$/i;\nconst IPV4_PATTERN = /^\\d{1,3}(?:\\.\\d{1,3}){3}$/;\n\nfunction base64UrlEncode(value: string | Buffer) {\n return Buffer.from(value).toString(\"base64url\");\n}\n\nfunction base64UrlDecode(value: string) {\n return Buffer.from(value, \"base64url\").toString(\"utf8\");\n}\n\nfunction signPayload(payload: string, secret: string) {\n return createHmac(\"sha256\", secret).update(payload).digest(\"base64url\");\n}\n\nfunction secureEqual(left: string, right: string) {\n const leftBuffer = Buffer.from(left);\n const rightBuffer = Buffer.from(right);\n return leftBuffer.length === rightBuffer.length && timingSafeEqual(leftBuffer, rightBuffer);\n}\n\nfunction normalizeHost(host: string) {\n const trimmed = host.trim().toLowerCase().replace(/\\.$/, \"\");\n if (!trimmed || trimmed.includes(\"*\") || trimmed.includes(\"/\") || trimmed.includes(\":\")) return null;\n const ascii = domainToASCII(trimmed);\n if (!ascii || ascii.includes(\"..\")) return null;\n return HOST_PATTERN.test(ascii) ? ascii : null;\n}\n\nfunction normalizeTargetHost(host: string) {\n const trimmed = host.trim().toLowerCase();\n if (trimmed === \"::1\" || trimmed === \"[::1]\") return \"::1\";\n if (trimmed.includes(\"/\") || trimmed.includes(\"*\")) return null;\n if (IPV4_PATTERN.test(trimmed)) return isValidIpv4(trimmed) ? trimmed : null;\n return normalizeHost(trimmed);\n}\n\nfunction isValidIpv4(value: string) {\n return value.split(\".\").every((part) => {\n const octet = Number(part);\n return Number.isInteger(octet) && octet >= 0 && octet <= 255 && String(octet) === part;\n });\n}\n\nfunction isPrivateIpv4(value: string) {\n if (!isValidIpv4(value)) return false;\n const [first = 0, second = 0] = value.split(\".\").map((part) => Number(part));\n return (\n first === 10 ||\n first === 127 ||\n (first === 172 && second >= 16 && second <= 31) ||\n (first === 192 && second === 168) ||\n (first === 169 && second === 254)\n );\n}\n\nfunction isLocalTargetHost(host: string) {\n return host === \"localhost\" || host === \"127.0.0.1\" || host === \"::1\";\n}\n\nfunction mergeTargetPolicy(policy: Partial<RelayTargetPolicy> | undefined): RelayTargetPolicy {\n return {\n allowedHosts: policy?.allowedHosts ?? DEFAULT_RELAY_TARGET_POLICY.allowedHosts,\n blockedPorts: policy?.blockedPorts ?? DEFAULT_RELAY_TARGET_POLICY.blockedPorts,\n allowPrivateNetworkTargets: policy?.allowPrivateNetworkTargets ?? DEFAULT_RELAY_TARGET_POLICY.allowPrivateNetworkTargets\n };\n}\n\nfunction mergeLimits(limits: Partial<RelayLimits> | undefined): RelayLimits {\n const merged = {\n ...DEFAULT_RELAY_LIMITS,\n ...(limits ?? {})\n };\n\n for (const [key, value] of Object.entries(merged)) {\n if (!Number.isInteger(value) || value < 1) {\n throw new Error(`Invalid relay limit ${key}: ${value}`);\n }\n }\n\n return merged;\n}\n\nexport function assertExactRelayHost(host: string) {\n const normalized = normalizeHost(host);\n if (!normalized) {\n throw new Error(`Relay route claims must use an exact hostname: ${host}`);\n }\n return normalized;\n}\n\nexport function assertRelayLocalTarget(target: RelayLocalTarget, policyInput?: Partial<RelayTargetPolicy>): Required<RelayLocalTarget> {\n if (!target || typeof target !== \"object\") {\n throw new Error(\"Relay target must be an explicit local target object.\");\n }\n\n const policy = mergeTargetPolicy(policyInput);\n const host = normalizeTargetHost(target.host);\n if (!host) {\n throw new Error(`Invalid relay target host: ${target.host}`);\n }\n\n if (!Number.isInteger(target.port) || target.port < 1 || target.port > 65535) {\n throw new Error(`Invalid relay target port: ${target.port}`);\n }\n\n const protocol = target.protocol ?? \"http\";\n if (protocol !== \"http\" && protocol !== \"https\") {\n throw new Error(`Invalid relay target protocol: ${String(protocol)}`);\n }\n\n if (policy.blockedPorts.includes(target.port)) {\n throw new Error(`Relay target port is blocked: ${target.port}`);\n }\n\n const allowedHosts = new Set(policy.allowedHosts.map((allowedHost) => normalizeTargetHost(allowedHost)).filter((value): value is string => Boolean(value)));\n if (!allowedHosts.has(host)) {\n throw new Error(`Relay target host is not explicitly allowed: ${host}`);\n }\n\n if (!policy.allowPrivateNetworkTargets && !isLocalTargetHost(host) && (host === \"::1\" || isPrivateIpv4(host))) {\n throw new Error(`Private-network relay target requires explicit opt-in: ${host}`);\n }\n\n return {\n protocol,\n host,\n port: target.port\n };\n}\n\nexport function authenticateRelayAgentToken(input: {\n authorizationHeader?: string | null;\n agentToken: string;\n}) {\n const expected = `Bearer ${input.agentToken}`;\n return typeof input.authorizationHeader === \"string\" && secureEqual(input.authorizationHeader, expected);\n}\n\nexport function signRelayRouteClaim(claim: RelayRouteClaim, signingSecret: string): SignedRelayRouteClaim {\n const payload: RelayRouteClaim = {\n ...claim,\n host: assertExactRelayHost(claim.host)\n };\n if (!payload.scope) throw new Error(\"Relay route claim requires a scope.\");\n if (!payload.agentId) throw new Error(\"Relay route claim requires an agentId.\");\n if (Number.isNaN(Date.parse(payload.expiresAt))) throw new Error(\"Relay route claim requires a valid expiresAt.\");\n\n const encodedPayload = base64UrlEncode(JSON.stringify(payload));\n const signature = signPayload(encodedPayload, signingSecret);\n return {\n payload,\n token: `${encodedPayload}.${signature}`\n };\n}\n\nexport function verifyRelayRouteClaim(token: string, signingSecret: string, options: {\n expectedScope: string;\n now?: Date;\n}): RelayRouteClaim {\n const [encodedPayload, signature] = token.split(\".\");\n if (!encodedPayload || !signature || token.split(\".\").length !== 2) {\n throw new Error(\"Invalid relay route claim token.\");\n }\n\n const expectedSignature = signPayload(encodedPayload, signingSecret);\n if (!secureEqual(signature, expectedSignature)) {\n throw new Error(\"Invalid relay route claim signature.\");\n }\n\n const parsed = JSON.parse(base64UrlDecode(encodedPayload)) as RelayRouteClaim;\n const host = assertExactRelayHost(parsed.host);\n if (parsed.scope !== options.expectedScope) {\n throw new Error(\"Relay route claim scope mismatch.\");\n }\n\n const now = options.now ?? new Date();\n if (Date.parse(parsed.expiresAt) <= now.getTime()) {\n throw new Error(\"Relay route claim has expired.\");\n }\n\n if (!parsed.agentId) {\n throw new Error(\"Relay route claim requires an agentId.\");\n }\n\n return { ...parsed, host };\n}\n\nexport function createRelayRouteRegistration(input: RelayRouteRegistrationInput): ActiveRelayRoute {\n if (!authenticateRelayAgentToken({\n agentToken: input.agentToken,\n ...(typeof input.authorizationHeader !== \"undefined\" ? { authorizationHeader: input.authorizationHeader } : {})\n })) {\n throw new Error(\"Relay route registration requires an authenticated local agent.\");\n }\n\n const claim = verifyRelayRouteClaim(input.claimToken, input.signingSecret, {\n expectedScope: input.expectedScope,\n ...(input.now ? { now: input.now } : {})\n });\n const target = assertRelayLocalTarget(input.target, input.targetPolicy);\n const access = input.publicMode === true ? \"public\" : input.access ?? \"private\";\n const passwordProtected = input.passwordProtected ?? false;\n const authRequired = input.authRequired ?? false;\n\n if (access === \"public\" && input.publicMode !== true) {\n throw new Error(\"Relay public mode must be explicitly enabled.\");\n }\n\n if (access === \"private\" && !passwordProtected && !authRequired) {\n throw new Error(\"Private relay previews require password or auth.\");\n }\n\n return {\n host: claim.host,\n scope: claim.scope,\n agentId: claim.agentId,\n expiresAt: claim.expiresAt,\n target,\n access,\n passwordProtected,\n authRequired,\n limits: mergeLimits(input.limits)\n };\n}\n\nexport function isRelayRouteActive(route: ActiveRelayRoute, options: {\n agentConnected: boolean;\n now?: Date;\n}) {\n if (!options.agentConnected) return false;\n return Date.parse(route.expiresAt) > (options.now ?? new Date()).getTime();\n}\n\nexport function stripRelayForwardHeaders(headers: Record<string, string | string[] | undefined>) {\n const stripped: Record<string, string | string[]> = {};\n\n for (const [name, value] of Object.entries(headers)) {\n if (typeof value === \"undefined\") continue;\n const lowerName = name.toLowerCase();\n if (HOP_BY_HOP_HEADERS.has(lowerName)) continue;\n if (lowerName.startsWith(\"x-localghost-\")) continue;\n stripped[name] = value;\n }\n\n return stripped;\n}\n\nexport function redactRelayHeaders(headers: Record<string, string | string[] | undefined>) {\n const redacted: Record<string, string | string[]> = {};\n\n for (const [name, value] of Object.entries(headers)) {\n if (typeof value === \"undefined\") continue;\n redacted[name] = SENSITIVE_HEADERS.has(name.toLowerCase()) ? \"[redacted]\" : value;\n }\n\n return redacted;\n}\n\nexport function redactRelayLogUrl(input: string) {\n const url = new URL(input, \"http://localghost.invalid\");\n for (const key of [...url.searchParams.keys()]) {\n if (TOKEN_QUERY_PATTERN.test(key)) {\n url.searchParams.set(key, \"[redacted]\");\n }\n }\n\n return input.startsWith(\"http://\") || input.startsWith(\"https://\")\n ? url.toString()\n : `${url.pathname}${url.search}`;\n}\n\nexport function renderRelayOfflineResponse(): RelayOfflineResponse {\n return {\n status: 503,\n headers: {\n \"content-type\": \"text/html; charset=utf-8\",\n \"cache-control\": \"no-store\"\n },\n body: [\n \"<!doctype html>\",\n \"<html>\",\n \"<head><meta charset=\\\"utf-8\\\"><title>Preview offline</title></head>\",\n \"<body><h1>Preview offline</h1><p>The local agent is not connected. Try again later.</p></body>\",\n \"</html>\"\n ].join(\"\")\n };\n}\n","import { randomUUID } from \"node:crypto\";\nimport type { RelayLocalTarget } from \"./relay.js\";\n\nexport const DEFAULT_GHOST_TUNNEL_RESPONSE_TTL_SECONDS = 60;\n\nexport type GhostTunnelStoreEnv = Record<string, string | undefined>;\n\nexport type GhostTunnelQueuedRequest = {\n id: string;\n host: string;\n method: string;\n path: string;\n headers: Record<string, string>;\n createdAt: string;\n expiresAt: string;\n bodyBase64?: string;\n};\n\nexport type GhostTunnelQueuedResponse = {\n id: string;\n status: number;\n headers: Record<string, string>;\n createdAt: string;\n bodyBase64?: string;\n error?: string;\n};\n\nexport type GhostTunnelRouteHeartbeat = {\n host: string;\n agentId: string;\n target: Required<RelayLocalTarget>;\n updatedAt: string;\n expiresAt: string;\n};\n\nexport type GhostTunnelStore = {\n heartbeatRoute(route: GhostTunnelRouteHeartbeat, ttlSeconds: number): Promise<void>;\n getRoute(host: string): Promise<GhostTunnelRouteHeartbeat | null>;\n enqueueRequest(request: GhostTunnelQueuedRequest, ttlSeconds: number): Promise<void>;\n claimRequest(host: string): Promise<GhostTunnelQueuedRequest | null>;\n writeResponse(response: GhostTunnelQueuedResponse, ttlSeconds: number): Promise<void>;\n readResponse(requestId: string): Promise<GhostTunnelQueuedResponse | null>;\n cleanup(requestId: string): Promise<void>;\n};\n\nexport type RedisGhostTunnelStoreOptions = {\n url: string;\n token: string;\n namespace?: string;\n fetch?: typeof fetch;\n};\n\nexport type RedisGhostTunnelEnvResolution = {\n url: string;\n token: string;\n source: \"localghost\" | \"upstash\" | \"vercel-kv\" | \"redis\";\n};\n\nfunction base64Encode(value: Buffer) {\n return value.toString(\"base64\");\n}\n\nexport function encodeGhostTunnelBody(value: Buffer | Uint8Array | string) {\n return base64Encode(Buffer.isBuffer(value) ? value : Buffer.from(value));\n}\n\nexport function decodeGhostTunnelBody(value: string | undefined) {\n return value ? Buffer.from(value, \"base64\") : undefined;\n}\n\nexport function createGhostTunnelQueuedRequest(input: {\n host: string;\n method: string;\n path: string;\n headers?: Record<string, string>;\n body?: Buffer | Uint8Array | string;\n ttlSeconds: number;\n now?: Date;\n}): GhostTunnelQueuedRequest {\n const now = input.now ?? new Date();\n const bodyBase64 = typeof input.body === \"undefined\" ? undefined : encodeGhostTunnelBody(input.body);\n\n return {\n id: randomUUID(),\n host: input.host,\n method: input.method.toUpperCase(),\n path: input.path,\n headers: input.headers ?? {},\n createdAt: now.toISOString(),\n expiresAt: new Date(now.getTime() + input.ttlSeconds * 1000).toISOString(),\n ...(bodyBase64 ? { bodyBase64 } : {})\n };\n}\n\nexport function createGhostTunnelRouteHeartbeat(input: {\n host: string;\n agentId: string;\n target: Required<RelayLocalTarget>;\n ttlSeconds: number;\n now?: Date;\n}): GhostTunnelRouteHeartbeat {\n const now = input.now ?? new Date();\n\n return {\n host: input.host,\n agentId: input.agentId,\n target: input.target,\n updatedAt: now.toISOString(),\n expiresAt: new Date(now.getTime() + input.ttlSeconds * 1000).toISOString()\n };\n}\n\nfunction isExpired(expiresAt: string, now = new Date()) {\n const timestamp = Date.parse(expiresAt);\n return Number.isNaN(timestamp) || timestamp <= now.getTime();\n}\n\nfunction serializeJson(value: unknown) {\n return JSON.stringify(value);\n}\n\nfunction parseJson<T>(value: unknown): T | null {\n if (typeof value !== \"string\") return null;\n try {\n return JSON.parse(value) as T;\n } catch {\n return null;\n }\n}\n\nfunction keyPart(value: string) {\n return value.toLowerCase().replace(/[^a-z0-9._:-]/g, \"_\");\n}\n\nfunction removeTrailingSlashes(value: string) {\n let end = value.length;\n while (end > 0 && value.charCodeAt(end - 1) === 47) end -= 1;\n return value.slice(0, end);\n}\n\nclass MemoryGhostTunnelStore implements GhostTunnelStore {\n private readonly routes = new Map<string, GhostTunnelRouteHeartbeat>();\n private readonly queues = new Map<string, GhostTunnelQueuedRequest[]>();\n private readonly responses = new Map<string, { value: GhostTunnelQueuedResponse; expiresAt: string }>();\n\n async heartbeatRoute(route: GhostTunnelRouteHeartbeat): Promise<void> {\n this.routes.set(route.host, route);\n }\n\n async getRoute(host: string): Promise<GhostTunnelRouteHeartbeat | null> {\n const route = this.routes.get(host);\n if (!route) return null;\n if (!isExpired(route.expiresAt)) return route;\n this.routes.delete(host);\n return null;\n }\n\n async enqueueRequest(request: GhostTunnelQueuedRequest): Promise<void> {\n const queue = this.queues.get(request.host) ?? [];\n queue.push(request);\n this.queues.set(request.host, queue);\n }\n\n async claimRequest(host: string): Promise<GhostTunnelQueuedRequest | null> {\n const queue = this.queues.get(host) ?? [];\n\n while (queue.length > 0) {\n const request = queue.shift();\n if (request && !isExpired(request.expiresAt)) {\n return request;\n }\n }\n\n return null;\n }\n\n async writeResponse(response: GhostTunnelQueuedResponse, ttlSeconds: number): Promise<void> {\n this.responses.set(response.id, {\n value: response,\n expiresAt: new Date(Date.now() + ttlSeconds * 1000).toISOString()\n });\n }\n\n async readResponse(requestId: string): Promise<GhostTunnelQueuedResponse | null> {\n const response = this.responses.get(requestId);\n if (!response) return null;\n if (!isExpired(response.expiresAt)) return response.value;\n this.responses.delete(requestId);\n return null;\n }\n\n async cleanup(requestId: string): Promise<void> {\n this.responses.delete(requestId);\n }\n}\n\nexport function createMemoryGhostTunnelStore(): GhostTunnelStore {\n return new MemoryGhostTunnelStore();\n}\n\nclass RedisGhostTunnelStore implements GhostTunnelStore {\n private readonly url: string;\n private readonly token: string;\n private readonly namespace: string;\n private readonly fetchImpl: typeof fetch;\n\n constructor(options: RedisGhostTunnelStoreOptions) {\n this.url = removeTrailingSlashes(options.url);\n this.token = options.token;\n this.namespace = options.namespace ?? \"localghost\";\n this.fetchImpl = options.fetch ?? fetch;\n }\n\n private key(kind: \"route\" | \"queue\" | \"response\", id: string) {\n return `${this.namespace}:ghost-tunnel:${kind}:${keyPart(id)}`;\n }\n\n private async command<T>(command: string, ...args: Array<string | number>): Promise<T | null> {\n const response = await this.fetchImpl(this.url, {\n method: \"POST\",\n headers: {\n authorization: `Bearer ${this.token}`,\n \"content-type\": \"application/json\"\n },\n body: JSON.stringify([command, ...args])\n });\n\n if (!response.ok) {\n throw new Error(`Redis Ghost Tunnel command failed: ${response.status} ${response.statusText}`);\n }\n\n const payload = await response.json() as { result?: unknown; error?: string };\n if (payload.error) {\n throw new Error(`Redis Ghost Tunnel command failed: ${payload.error}`);\n }\n\n return (typeof payload.result === \"undefined\" ? null : payload.result) as T | null;\n }\n\n async heartbeatRoute(route: GhostTunnelRouteHeartbeat, ttlSeconds: number): Promise<void> {\n await this.command(\"SET\", this.key(\"route\", route.host), serializeJson(route), \"EX\", ttlSeconds);\n }\n\n async getRoute(host: string): Promise<GhostTunnelRouteHeartbeat | null> {\n const route = parseJson<GhostTunnelRouteHeartbeat>(await this.command<string>(\"GET\", this.key(\"route\", host)));\n return route && !isExpired(route.expiresAt) ? route : null;\n }\n\n async enqueueRequest(request: GhostTunnelQueuedRequest, ttlSeconds: number): Promise<void> {\n const queueKey = this.key(\"queue\", request.host);\n await this.command(\"RPUSH\", queueKey, serializeJson(request));\n await this.command(\"EXPIRE\", queueKey, ttlSeconds);\n }\n\n async claimRequest(host: string): Promise<GhostTunnelQueuedRequest | null> {\n const queueKey = this.key(\"queue\", host);\n\n while (true) {\n const request = parseJson<GhostTunnelQueuedRequest>(await this.command<string>(\"LPOP\", queueKey));\n if (!request) return null;\n if (!isExpired(request.expiresAt)) return request;\n }\n }\n\n async writeResponse(response: GhostTunnelQueuedResponse, ttlSeconds: number): Promise<void> {\n await this.command(\"SET\", this.key(\"response\", response.id), serializeJson(response), \"EX\", ttlSeconds);\n }\n\n async readResponse(requestId: string): Promise<GhostTunnelQueuedResponse | null> {\n return parseJson<GhostTunnelQueuedResponse>(await this.command<string>(\"GET\", this.key(\"response\", requestId)));\n }\n\n async cleanup(requestId: string): Promise<void> {\n await this.command(\"DEL\", this.key(\"response\", requestId));\n }\n}\n\nexport function createRedisGhostTunnelStore(options: RedisGhostTunnelStoreOptions): GhostTunnelStore {\n return new RedisGhostTunnelStore(options);\n}\n\nexport function resolveRedisGhostTunnelEnv(env: GhostTunnelStoreEnv = process.env): RedisGhostTunnelEnvResolution {\n const candidates: Array<RedisGhostTunnelEnvResolution | null> = [\n env.LOCALGHOST_REDIS_REST_URL && env.LOCALGHOST_REDIS_REST_TOKEN\n ? { url: env.LOCALGHOST_REDIS_REST_URL, token: env.LOCALGHOST_REDIS_REST_TOKEN, source: \"localghost\" }\n : null,\n env.UPSTASH_REDIS_REST_URL && env.UPSTASH_REDIS_REST_TOKEN\n ? { url: env.UPSTASH_REDIS_REST_URL, token: env.UPSTASH_REDIS_REST_TOKEN, source: \"upstash\" }\n : null,\n env.KV_REST_API_URL && env.KV_REST_API_TOKEN\n ? { url: env.KV_REST_API_URL, token: env.KV_REST_API_TOKEN, source: \"vercel-kv\" }\n : null,\n env.REDIS_REST_API_URL && env.REDIS_REST_API_TOKEN\n ? { url: env.REDIS_REST_API_URL, token: env.REDIS_REST_API_TOKEN, source: \"redis\" }\n : null\n ];\n const match = candidates.find((candidate): candidate is RedisGhostTunnelEnvResolution => Boolean(candidate));\n\n if (!match) {\n throw new Error(\"Ghost Tunnel Redis transport requires REST env vars: UPSTASH_REDIS_REST_URL/UPSTASH_REDIS_REST_TOKEN, KV_REST_API_URL/KV_REST_API_TOKEN, or LOCALGHOST_REDIS_REST_URL/LOCALGHOST_REDIS_REST_TOKEN.\");\n }\n\n return match;\n}\n\nexport function createRedisGhostTunnelStoreFromEnv(input: {\n env?: GhostTunnelStoreEnv;\n namespace?: string;\n fetch?: typeof fetch;\n} = {}): GhostTunnelStore {\n const resolved = resolveRedisGhostTunnelEnv(input.env);\n return createRedisGhostTunnelStore({\n url: resolved.url,\n token: resolved.token,\n ...(input.namespace ? { namespace: input.namespace } : {}),\n ...(input.fetch ? { fetch: input.fetch } : {})\n });\n}\n","import { writeFileSync } from \"node:fs\";\nimport { tmpdir } from \"node:os\";\nimport { join } from \"node:path\";\nimport { execa } from \"execa\";\nimport { sanitizeProjectName } from \"./config.js\";\nimport { readTextFile } from \"./fs.js\";\nimport type { DevHostEntry } from \"./parse.js\";\n\nexport type UpdateSystemHostsResult = {\n changed: boolean;\n hostsPath: string;\n tempPath?: string;\n};\n\nexport type RemoveSystemHostsResult = UpdateSystemHostsResult & {\n removed: boolean;\n};\n\nfunction escapeRegExp(value: string) {\n return value.replace(/[.*+?^${}()|[\\]\\\\]/g, \"\\\\$&\");\n}\n\nfunction getManagedBlockPattern(projectName: string) {\n const sanitizedProjectName = sanitizeProjectName(projectName);\n const start = `# localghost:start ${sanitizedProjectName}`;\n const end = `# localghost:end ${sanitizedProjectName}`;\n return new RegExp(`${escapeRegExp(start)}[\\\\s\\\\S]*?${escapeRegExp(end)}\\\\n?`, \"m\");\n}\n\nexport function getSystemHostsPath(env: NodeJS.ProcessEnv = process.env) {\n if (env.LOCALGHOST_HOSTS_PATH) return env.LOCALGHOST_HOSTS_PATH;\n return process.platform === \"win32\" ? \"C:\\\\Windows\\\\System32\\\\drivers\\\\etc\\\\hosts\" : \"/etc/hosts\";\n}\n\nexport function renderHostsBlock(projectName: string, entries: DevHostEntry[]) {\n const sanitizedProjectName = sanitizeProjectName(projectName);\n const hosts = [...new Set(entries.map((entry) => entry.host))].sort();\n\n return [\n `# localghost:start ${sanitizedProjectName}`,\n ...hosts.map((host) => `127.0.0.1 ${host}`),\n `# localghost:end ${sanitizedProjectName}`,\n \"\"\n ].join(\"\\n\");\n}\n\nexport function upsertManagedBlock(existing: string, projectName: string, block: string) {\n const pattern = getManagedBlockPattern(projectName);\n\n if (pattern.test(existing)) {\n return existing.replace(pattern, block);\n }\n\n return `${existing.trimEnd()}\\n\\n${block}`;\n}\n\nexport function removeManagedBlock(existing: string, projectName: string) {\n const pattern = getManagedBlockPattern(projectName);\n\n if (!pattern.test(existing)) {\n return existing;\n }\n\n return existing.replace(pattern, \"\").replace(/\\n{3,}/g, \"\\n\\n\").trimEnd() + \"\\n\";\n}\n\nasync function writeSystemHostsFile(hostsPath: string, next: string, projectName: string) {\n const sanitizedProjectName = sanitizeProjectName(projectName);\n const tempPath = join(tmpdir(), `localghost-${sanitizedProjectName}-hosts`);\n writeFileSync(tempPath, next, \"utf8\");\n\n if (process.env.LOCALGHOST_HOSTS_PATH) {\n writeFileSync(hostsPath, next, \"utf8\");\n return tempPath;\n }\n\n if (process.platform === \"win32\") {\n throw new Error(`Windows support: run as administrator and copy ${tempPath} to ${hostsPath}.`);\n }\n\n await execa(\"sudo\", [\"cp\", tempPath, hostsPath], { stdio: \"inherit\" });\n\n return tempPath;\n}\n\nexport async function updateSystemHosts(projectName: string, entries: DevHostEntry[]): Promise<UpdateSystemHostsResult> {\n const sanitizedProjectName = sanitizeProjectName(projectName);\n const hostsPath = getSystemHostsPath();\n const existing = readTextFile(hostsPath);\n const block = renderHostsBlock(sanitizedProjectName, entries);\n const next = upsertManagedBlock(existing, sanitizedProjectName, block);\n\n if (next === existing) {\n return { changed: false, hostsPath };\n }\n\n const tempPath = await writeSystemHostsFile(hostsPath, next, sanitizedProjectName);\n\n return { changed: true, hostsPath, tempPath };\n}\n\nexport async function removeSystemHosts(projectName: string): Promise<RemoveSystemHostsResult> {\n const sanitizedProjectName = sanitizeProjectName(projectName);\n const hostsPath = getSystemHostsPath();\n const existing = readTextFile(hostsPath);\n const next = removeManagedBlock(existing, sanitizedProjectName);\n\n if (next === existing) {\n return { changed: false, removed: false, hostsPath };\n }\n\n const tempPath = await writeSystemHostsFile(hostsPath, next, sanitizedProjectName);\n\n return { changed: true, removed: true, hostsPath, tempPath };\n}\n","import { existsSync, readFileSync, writeFileSync } from \"node:fs\";\nimport { join } from \"node:path\";\nimport { getProjectName, LOCALGHOST_CONFIG_FILE, sanitizeProjectName } from \"./config.js\";\nimport { writeTextFile } from \"./fs.js\";\n\nexport type PackageManager = \"npm\" | \"yarn\" | \"pnpm\" | \"bun\";\n\nexport type InitOptions = {\n cwd?: string;\n host?: string;\n port?: number;\n apiHost?: string;\n apiPort?: number;\n force?: boolean;\n packageManager?: PackageManager;\n writeScripts?: boolean;\n configFile?: string;\n};\n\nexport type InitResult = {\n configPath: string;\n configCreated: boolean;\n packageJsonPath?: string;\n packageJsonChanged: boolean;\n packageManager: PackageManager;\n nextSteps: string[];\n};\n\nexport function detectPackageManager(cwd = process.cwd()): PackageManager {\n if (existsSync(join(cwd, \"pnpm-lock.yaml\"))) return \"pnpm\";\n if (existsSync(join(cwd, \"yarn.lock\"))) return \"yarn\";\n if (existsSync(join(cwd, \"bun.lock\")) || existsSync(join(cwd, \"bun.lockb\"))) return \"bun\";\n return \"npm\";\n}\n\nexport function packageRunCommand(packageManager: PackageManager, script: string): string {\n if (packageManager === \"yarn\") return `yarn ${script}`;\n if (packageManager === \"pnpm\") return `pnpm ${script}`;\n if (packageManager === \"bun\") return `bun run ${script}`;\n return `npm run ${script}`;\n}\n\nexport function packageAddCommand(packageManager: PackageManager, packageName = \"@hamedb89/localghost\"): string {\n if (packageManager === \"yarn\") return `yarn add -D ${packageName}`;\n if (packageManager === \"pnpm\") return `pnpm add -D ${packageName}`;\n if (packageManager === \"bun\") return `bun add -d ${packageName}`;\n return `npm install -D ${packageName}`;\n}\n\nfunction renderConfig(options: Required<Pick<InitOptions, \"host\" | \"port\" | \"apiHost\" | \"apiPort\">>) {\n return [\n \"# Buh. Friendly names for local services.\",\n \"# Format: <host> <port>\",\n `${options.host} ${options.port}`,\n `www.${options.host} ${options.port}`,\n `${options.apiHost} ${options.apiPort}`,\n \"\"\n ].join(\"\\n\");\n}\n\nfunction readPackageJson(path: string): Record<string, unknown> | null {\n try {\n return JSON.parse(readFileSync(path, \"utf8\")) as Record<string, unknown>;\n } catch {\n return null;\n }\n}\n\nfunction shellQuote(value: string) {\n if (/^[A-Za-z0-9_./:-]+$/.test(value)) return value;\n return `'${value.replace(/'/g, `'\"'\"'`)}'`;\n}\n\nfunction getConfigFlag(configFile: string) {\n return configFile === LOCALGHOST_CONFIG_FILE ? \"\" : ` --config ${shellQuote(configFile)}`;\n}\n\nfunction updatePackageScripts(packageJsonPath: string, configFile: string): boolean {\n const pkg = readPackageJson(packageJsonPath);\n if (!pkg) return false;\n\n const scripts = typeof pkg.scripts === \"object\" && pkg.scripts ? (pkg.scripts as Record<string, unknown>) : {};\n const configFlag = getConfigFlag(configFile);\n const nextScripts = {\n ...scripts,\n \"localghost:setup\": scripts[\"localghost:setup\"] ?? `localghost setup${configFlag}`,\n \"localghost:proxy\": scripts[\"localghost:proxy\"] ?? `localghost dev${configFlag}`,\n \"localghost:proxy:https\": scripts[\"localghost:proxy:https\"] ?? `localghost dev${configFlag} --https`,\n \"localghost:run\": scripts[\"localghost:run\"] ?? `localghost run${configFlag} --`,\n \"localghost:ready\": scripts[\"localghost:ready\"] ?? `localghost status${configFlag} --ready`,\n \"localghost:repair\": scripts[\"localghost:repair\"] ?? `localghost repair${configFlag}`,\n \"localghost:trust\": scripts[\"localghost:trust\"] ?? `localghost trust${configFlag}`,\n \"localghost:ps\": scripts[\"localghost:ps\"] ?? \"localghost ps\",\n \"localghost:print\": scripts[\"localghost:print\"] ?? `localghost print${configFlag}`,\n \"localghost:routes\": scripts[\"localghost:routes\"] ?? `localghost routes${configFlag}`,\n \"localghost:status\": scripts[\"localghost:status\"] ?? \"localghost status\",\n \"localghost:reset\": scripts[\"localghost:reset\"] ?? \"localghost reset\",\n \"localghost:teardown\": scripts[\"localghost:teardown\"] ?? \"localghost teardown\",\n \"localghost:doctor\": scripts[\"localghost:doctor\"] ?? \"localghost doctor\",\n \"localghost:update\": scripts[\"localghost:update\"] ?? \"localghost update\",\n \"caddy:setup\": scripts[\"caddy:setup\"] ?? `localghost setup${configFlag}`,\n \"caddy:dev\": scripts[\"caddy:dev\"] ?? `localghost dev${configFlag}`\n };\n\n const changed = JSON.stringify(scripts) !== JSON.stringify(nextScripts);\n if (!changed) return false;\n\n pkg.scripts = nextScripts;\n writeFileSync(packageJsonPath, `${JSON.stringify(pkg, null, 2)}\\n`, \"utf8\");\n return true;\n}\n\nexport function initLocalghost(options: InitOptions = {}): InitResult {\n const cwd = options.cwd ?? process.cwd();\n const projectName = sanitizeProjectName(getProjectName(cwd).split(\"/\").pop() ?? \"app\");\n const host = options.host ?? `${projectName}.localhost`;\n const port = options.port ?? 5173;\n const apiHost = options.apiHost ?? `api.${host}`;\n const apiPort = options.apiPort ?? 8787;\n const packageManager = options.packageManager ?? detectPackageManager(cwd);\n const configFile = options.configFile ?? LOCALGHOST_CONFIG_FILE;\n const configPath = join(cwd, configFile);\n const configExists = existsSync(configPath);\n\n if (configExists && !options.force) {\n return {\n configPath,\n configCreated: false,\n packageJsonChanged: false,\n packageManager,\n nextSteps: [\n packageRunCommand(packageManager, \"localghost:doctor\"),\n packageRunCommand(packageManager, \"localghost:setup\"),\n packageRunCommand(packageManager, \"localghost:ready\"),\n packageRunCommand(packageManager, \"localghost:proxy\")\n ]\n };\n }\n\n writeTextFile(configPath, renderConfig({ host, port, apiHost, apiPort }));\n\n const packageJsonPath = join(cwd, \"package.json\");\n const packageJsonChanged = options.writeScripts ? updatePackageScripts(packageJsonPath, configFile) : false;\n\n return {\n configPath,\n configCreated: true,\n ...(existsSync(packageJsonPath) ? { packageJsonPath } : {}),\n packageJsonChanged,\n packageManager,\n nextSteps: [\n packageRunCommand(packageManager, \"localghost:doctor\"),\n packageRunCommand(packageManager, \"localghost:setup\"),\n packageRunCommand(packageManager, \"localghost:ready\"),\n packageRunCommand(packageManager, \"localghost:proxy\")\n ]\n };\n}\n","export const LOCALGHOST_AGENT_GUIDE = `# Localghost agent guide\n\nLocalghost owns the local development proxy and the app process boundary.\n\n## Preferred repository setup\n\nFor a normal repository, use this package script:\n\n \"dev\": \"localghost\"\n\nFor an explicit app command, keep the raw command separate:\n\n \"dev\": \"localghost run -- vite\"\n \"dev:raw\": \"vite\"\n\nUse \\`localghost dev\\` only when the Caddy proxy should run without starting the app.\n\n## Useful commands\n\n- \\`localghost\\`: detect and run the repository development command.\n- \\`localghost run -- <command>\\`: wrap an explicit app command.\n- \\`localghost dev\\`: run only the local Caddy proxy.\n- \\`localghost status --ready\\`: check project setup.\n- \\`localghost repair\\`: repair managed hosts and Caddy setup.\n- \\`localghost ps --json\\`: inspect Localghost-managed repositories, instances, and ports.\n- \\`localghost routes\\`: inspect hostname-to-port routing.\n- \\`localghost doctor\\`: check machine prerequisites, ports, and registry state.\n- \\`localghost repair --reallocate-port\\`: move an occupied project port to a stable available port.\n\n## Configuration\n\n- Commit repository defaults in \\`localghost.config.mjs\\`.\n- Keep hostname and requested-port routes in \\`.localghost\\`.\n- CLI flags override repository configuration for one invocation.\n- Localghost remembers active project and instance port assignments in user state under \\`~/.localghost\\`.\n- Do not edit the registry manually and do not start Caddy separately.\n\n## Port behavior\n\nLocalghost remembers ports by canonical repository path and instance key. Concurrent Localghost instances receive distinct ports. The operating-system bind check remains authoritative when another tool already owns a port.\n`;\n\nexport function formatLocalghostAgentGuide(format: \"text\" | \"json\" = \"text\") {\n if (format === \"json\") {\n return JSON.stringify({\n preferredScript: \"localghost\",\n explicitScript: \"localghost run -- <command>\",\n proxyOnlyCommand: \"localghost dev\",\n inspectionCommands: [\"localghost status --ready\", \"localghost ps --json\", \"localghost routes\", \"localghost doctor\"],\n projectConfig: \"localghost.config.mjs\",\n routeConfig: \".localghost\",\n userState: \"~/.localghost\"\n }, null, 2);\n }\n\n return LOCALGHOST_AGENT_GUIDE;\n}\n","import { stdin as input, stdout as output } from \"node:process\";\nimport { createInterface } from \"node:readline/promises\";\n\nexport function canPrompt() {\n return Boolean(input.isTTY && output.isTTY);\n}\n\nexport async function withPrompt<T>(run: (prompt: (question: string) => Promise<string>) => Promise<T>) {\n const rl = createInterface({ input, output });\n try {\n return await run((question) => rl.question(question));\n } finally {\n rl.close();\n }\n}\n\nexport async function confirm(question: string, defaultValue = true) {\n return withPrompt(async (prompt) => {\n const suffix = defaultValue ? \" [Y/n] \" : \" [y/N] \";\n const answer = (await prompt(`${question}${suffix}`)).trim().toLowerCase();\n if (!answer) return defaultValue;\n return answer === \"y\" || answer === \"yes\";\n });\n}\n\nexport async function ask(question: string, defaultValue?: string) {\n return withPrompt(async (prompt) => {\n const suffix = defaultValue ? ` (${defaultValue}) ` : \" \";\n const answer = (await prompt(`${question}${suffix}`)).trim();\n return answer || defaultValue || \"\";\n });\n}\n","import type { DevHostEntry } from \"./parse.js\";\nimport type { GhostTunnelConfig } from \"./tunnel.js\";\n\nexport type DomainRoute = {\n host: string;\n port: number;\n url: string;\n upstream: string;\n};\n\nexport type DomainRouteOptions = {\n https?: boolean;\n};\n\nexport type GhostTunnelFormatOptions = {\n color?: boolean;\n label?: \"configured\" | \"expected\" | \"ready\" | \"running\";\n verbose?: boolean;\n};\n\nconst ansi = {\n cyan: \"\\u001b[36m\",\n dim: \"\\u001b[2m\",\n green: \"\\u001b[32m\",\n reset: \"\\u001b[0m\",\n yellow: \"\\u001b[33m\"\n};\n\nfunction colorize(value: string, color: string, enabled: boolean) {\n return enabled ? `${color}${value}${ansi.reset}` : value;\n}\n\nfunction colorizeUrl(value: string, enabled: boolean) {\n if (!enabled) return value;\n return colorize(value.replace(/\\*/g, `${ansi.yellow}*${ansi.cyan}`), ansi.cyan, enabled);\n}\n\nexport function getDomainRoutes(entries: DevHostEntry[], options: DomainRouteOptions = {}): DomainRoute[] {\n const protocol = options.https === true ? \"https\" : \"http\";\n\n return [...entries]\n .sort((left, right) => left.host.localeCompare(right.host) || left.port - right.port)\n .map((entry) => ({\n host: entry.host,\n port: entry.port,\n url: `${protocol}://${entry.host}/`,\n upstream: `http://${entry.target}`\n }));\n}\n\nexport function formatDomainRoutes(entries: DevHostEntry[], options: DomainRouteOptions = {}) {\n const routes = getDomainRoutes(entries, options);\n\n if (routes.length === 0) {\n return \"localghost routes\\n no routes\";\n }\n\n return [\n \"localghost routes\",\n ...routes.map((route) => ` ${route.url} -> ${route.upstream}`)\n ].join(\"\\n\");\n}\n\nexport function formatGhostTunnel(config: GhostTunnelConfig, options: GhostTunnelFormatOptions = {}) {\n if (!config.enabled) return null;\n\n const color = options.color === true;\n const label = options.label ?? \"expected\";\n const labelColor = label === \"running\" ? ansi.green : ansi.dim;\n const lines = [\n \"localghost ghost tunnel\",\n ` mode: ${config.mode}`\n ];\n const urls = config.displayUrls.length > 0\n ? config.displayUrls\n : config.displayUrl\n ? [config.displayUrl]\n : [];\n\n if (urls.length === 0) {\n lines.push(` ${label}: unavailable`);\n } else if (urls.length === 1) {\n lines.push(` ${colorize(label, labelColor, color)}: ${colorizeUrl(urls[0]!, color)}`);\n } else {\n lines.push(` ${colorize(label, labelColor, color)}:`);\n for (const url of urls) {\n lines.push(` ${colorizeUrl(url, color)}`);\n }\n }\n\n if (options.verbose) {\n lines.push(` domains: ${config.domains.length > 0 ? config.domains.join(\", \") : \"*\"}`);\n lines.push(` access: ${config.requireAuth ? \"auth required\" : \"app decides\"}`);\n lines.push(` protocol: ${config.requireHttps ? \"https required\" : \"http allowed\"}`);\n lines.push(` transport: ${config.transport.kind}`);\n }\n\n return lines.join(\"\\n\");\n}\n","import { existsSync } from \"node:fs\";\nimport { join } from \"node:path\";\nimport { readTextFile, writeTextFile } from \"./fs.js\";\nimport type { DevHostEntry } from \"./parse.js\";\n\nexport const LOCALGHOST_STATE_FILE = \"ops/local/localghost-state.json\";\n\nexport type LocalghostStateAction = \"setup\" | \"teardown\";\n\nexport type LocalghostState = {\n version: 1;\n action: LocalghostStateAction;\n updatedAt: string;\n projectName: string;\n cwd: string;\n configPath?: string;\n hostsPath?: string;\n hostsChanged?: boolean;\n hostsTempPath?: string;\n caddyfilePath?: string;\n caddyfileRemoved?: boolean;\n caddyHttps?: boolean;\n caddyTrustedAt?: string;\n caddyTrustPromptedAt?: string;\n entries?: DevHostEntry[];\n};\n\nexport type WriteLocalghostStateInput = Omit<LocalghostState, \"version\" | \"updatedAt\">;\n\nexport function getLocalghostStatePath(cwd = process.cwd()) {\n return join(cwd, LOCALGHOST_STATE_FILE);\n}\n\nexport function readLocalghostState(cwd = process.cwd()): LocalghostState | null {\n const path = getLocalghostStatePath(cwd);\n if (!existsSync(path)) return null;\n return JSON.parse(readTextFile(path)) as LocalghostState;\n}\n\nexport function writeLocalghostState(cwd: string, state: WriteLocalghostStateInput) {\n const path = getLocalghostStatePath(cwd);\n writeTextFile(path, `${JSON.stringify({ ...state, version: 1, updatedAt: new Date().toISOString() }, null, 2)}\\n`);\n return path;\n}\n\nexport function patchLocalghostState(cwd: string, patch: Partial<WriteLocalghostStateInput>) {\n const current = readLocalghostState(cwd);\n if (!current) return null;\n return writeLocalghostState(cwd, { ...(current as unknown as WriteLocalghostStateInput), ...patch });\n}\n","import { existsSync, mkdirSync, readFileSync, writeFileSync } from \"node:fs\";\nimport { homedir } from \"node:os\";\nimport { dirname, join } from \"node:path\";\n\nexport const LOCALGHOST_PACKAGE_NAME = \"@hamedb89/localghost\";\nexport const LOCALGHOST_VERSION = \"0.3.0\";\nexport const UPDATE_CHECK_CACHE_TTL_MS = 24 * 60 * 60 * 1000;\nexport const UPDATE_CHECK_NOTIFY_TTL_MS = 24 * 60 * 60 * 1000;\nexport const UPDATE_CHECK_TIMEOUT_MS = 900;\n\nexport type UpdateCheckCache = {\n checkedAt: string;\n latestVersion?: string;\n notifiedVersion?: string;\n notifiedAt?: string;\n};\n\nexport type UpdateCheckResult = {\n currentVersion: string;\n packageName: string;\n latestVersion?: string;\n updateAvailable: boolean;\n source: \"cache\" | \"registry\" | \"disabled\" | \"error\";\n error?: string;\n};\n\ntype RegistryPackageResponse = {\n \"dist-tags\"?: {\n latest?: unknown;\n };\n};\n\nfunction truthyEnv(value: string | undefined) {\n return value === \"1\" || value === \"true\" || value === \"yes\";\n}\n\nexport function isUpdateCheckDisabled(env: NodeJS.ProcessEnv = process.env) {\n return truthyEnv(env.LOCALGHOST_NO_UPDATE_CHECK);\n}\n\nexport function getUpdateCheckCachePath(env: NodeJS.ProcessEnv = process.env) {\n if (env.LOCALGHOST_UPDATE_CHECK_CACHE) return env.LOCALGHOST_UPDATE_CHECK_CACHE;\n\n const cacheRoot = env.XDG_CACHE_HOME || join(homedir(), \".cache\");\n return join(cacheRoot, \"localghost\", \"update-check.json\");\n}\n\nfunction readCache(path = getUpdateCheckCachePath()): UpdateCheckCache | null {\n if (!existsSync(path)) return null;\n\n try {\n return JSON.parse(readFileSync(path, \"utf8\")) as UpdateCheckCache;\n } catch {\n return null;\n }\n}\n\nfunction writeCache(cache: UpdateCheckCache, path = getUpdateCheckCachePath()) {\n try {\n mkdirSync(dirname(path), { recursive: true });\n writeFileSync(path, `${JSON.stringify(cache, null, 2)}\\n`, \"utf8\");\n } catch {\n // Update checks should never make the real command fail.\n }\n}\n\nfunction ageMs(date: string | undefined, now = Date.now()) {\n if (!date) return Number.POSITIVE_INFINITY;\n const time = Date.parse(date);\n return Number.isFinite(time) ? now - time : Number.POSITIVE_INFINITY;\n}\n\nfunction isCacheFresh(cache: UpdateCheckCache | null, ttlMs: number, now = Date.now()) {\n return Boolean(cache?.latestVersion && ageMs(cache.checkedAt, now) >= 0 && ageMs(cache.checkedAt, now) < ttlMs);\n}\n\ntype ParsedVersion = {\n major: number;\n minor: number;\n patch: number;\n prerelease?: string;\n};\n\nfunction parseVersion(version: string): ParsedVersion | null {\n const match = version.trim().replace(/^v/, \"\").match(/^(\\d+)\\.(\\d+)\\.(\\d+)(?:-([0-9A-Za-z.-]+))?$/);\n if (!match) return null;\n\n return {\n major: Number(match[1]),\n minor: Number(match[2]),\n patch: Number(match[3]),\n ...(match[4] ? { prerelease: match[4] } : {})\n };\n}\n\nexport function compareVersions(a: string, b: string) {\n const left = parseVersion(a);\n const right = parseVersion(b);\n\n if (!left || !right) return a.localeCompare(b);\n\n for (const key of [\"major\", \"minor\", \"patch\"] as const) {\n if (left[key] !== right[key]) return left[key] > right[key] ? 1 : -1;\n }\n\n if (left.prerelease === right.prerelease) return 0;\n if (!left.prerelease) return 1;\n if (!right.prerelease) return -1;\n return left.prerelease.localeCompare(right.prerelease);\n}\n\nexport function isNewerVersion(candidate: string | undefined, current = LOCALGHOST_VERSION) {\n return Boolean(candidate && compareVersions(candidate, current) > 0);\n}\n\nasync function fetchLatestVersion(packageName: string, timeoutMs: number) {\n const encodedName = packageName.startsWith(\"@\") ? `@${packageName.slice(1).replaceAll(\"/\", \"%2f\")}` : packageName;\n const response = await fetch(`https://registry.npmjs.org/${encodedName}`, {\n signal: AbortSignal.timeout(timeoutMs),\n headers: {\n accept: \"application/vnd.npm.install-v1+json\"\n }\n });\n\n if (!response.ok) throw new Error(`npm registry returned ${response.status}`);\n\n const data = (await response.json()) as RegistryPackageResponse;\n const latest = data[\"dist-tags\"]?.latest;\n if (typeof latest !== \"string\" || latest.length === 0) throw new Error(\"npm registry response did not include latest dist-tag\");\n\n return latest;\n}\n\nexport async function checkForUpdate(options: {\n force?: boolean;\n packageName?: string;\n currentVersion?: string;\n timeoutMs?: number;\n cachePath?: string;\n env?: NodeJS.ProcessEnv;\n} = {}): Promise<UpdateCheckResult> {\n const env = options.env ?? process.env;\n const packageName = options.packageName ?? LOCALGHOST_PACKAGE_NAME;\n const currentVersion = options.currentVersion ?? LOCALGHOST_VERSION;\n const cachePath = options.cachePath ?? getUpdateCheckCachePath(env);\n\n if (!options.force && isUpdateCheckDisabled(env)) {\n return {\n currentVersion,\n packageName,\n updateAvailable: false,\n source: \"disabled\"\n };\n }\n\n const cache = readCache(cachePath);\n if (!options.force && isCacheFresh(cache, UPDATE_CHECK_CACHE_TTL_MS)) {\n const latestVersion = cache?.latestVersion;\n return {\n currentVersion,\n packageName,\n ...(latestVersion ? { latestVersion } : {}),\n updateAvailable: isNewerVersion(latestVersion, currentVersion),\n source: \"cache\"\n };\n }\n\n try {\n const latestVersion = await fetchLatestVersion(packageName, options.timeoutMs ?? UPDATE_CHECK_TIMEOUT_MS);\n writeCache({ checkedAt: new Date().toISOString(), latestVersion }, cachePath);\n\n return {\n currentVersion,\n packageName,\n latestVersion,\n updateAvailable: isNewerVersion(latestVersion, currentVersion),\n source: \"registry\"\n };\n } catch (error) {\n const latestVersion = cache?.latestVersion;\n return {\n currentVersion,\n packageName,\n ...(latestVersion ? { latestVersion } : {}),\n updateAvailable: isNewerVersion(latestVersion, currentVersion),\n source: \"error\",\n error: error instanceof Error ? error.message : String(error)\n };\n }\n}\n\nexport function formatUpdateMessage(result: UpdateCheckResult) {\n if (!result.updateAvailable || !result.latestVersion) return null;\n\n return [\n `localghost ${result.latestVersion} is available. Current: ${result.currentVersion}`,\n `Update with: npm i -g ${result.packageName}@latest`\n ].join(\"\\n\");\n}\n\nexport function shouldNotifyAboutUpdate(result: UpdateCheckResult, cachePath = getUpdateCheckCachePath(), now = Date.now()) {\n if (!result.updateAvailable || !result.latestVersion) return false;\n\n const cache = readCache(cachePath);\n if (cache?.notifiedVersion !== result.latestVersion) return true;\n\n return ageMs(cache.notifiedAt, now) >= UPDATE_CHECK_NOTIFY_TTL_MS;\n}\n\nexport function markUpdateNotified(result: UpdateCheckResult, cachePath = getUpdateCheckCachePath()) {\n if (!result.latestVersion) return;\n\n const cache = readCache(cachePath) ?? { checkedAt: new Date().toISOString() };\n writeCache(\n {\n ...cache,\n latestVersion: result.latestVersion,\n notifiedVersion: result.latestVersion,\n notifiedAt: new Date().toISOString()\n },\n cachePath\n );\n}\n\nexport async function maybeNotifyAboutUpdate(options: { disabled?: boolean } = {}) {\n if (options.disabled) return;\n\n const cachePath = getUpdateCheckCachePath();\n const result = await checkForUpdate({ cachePath });\n if (!shouldNotifyAboutUpdate(result, cachePath)) return;\n\n const message = formatUpdateMessage(result);\n if (!message) return;\n\n console.warn(`\\n${message}`);\n markUpdateNotified(result, cachePath);\n}\n","import type { ChildProcess } from \"node:child_process\";\n\nexport type ProcessSignal = NodeJS.Signals;\nexport type ProcessKiller = (pid: number, signal: ProcessSignal) => void;\n\nexport function signalManagedProcessPid(\n pid: number | undefined,\n signal: ProcessSignal,\n killProcess: ProcessKiller = (value, processSignal) => process.kill(value, processSignal)\n) {\n if (typeof pid !== \"number\" || !Number.isInteger(pid) || pid < 1) return false;\n\n try {\n // Detached POSIX children lead their own process group.\n killProcess(process.platform === \"win32\" ? pid : -pid, signal);\n return true;\n } catch (error) {\n if (error instanceof Error && \"code\" in error && error.code === \"ESRCH\") return false;\n throw error;\n }\n}\n\nexport function signalManagedProcess(child: Pick<ChildProcess, \"pid\" | \"kill\" | \"killed\">, signal: ProcessSignal) {\n if (process.platform === \"win32\") {\n if (!child.killed) child.kill(signal);\n return true;\n }\n\n return signalManagedProcessPid(child.pid, signal);\n}\n"],"mappings":"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","names":["existsSync","readFileSync","input","existsSync","readFileSync","join","input","fileName","existsSync","readFileSync","join","dirname","join","mkdirSync","readFileSync","writeFileSync","dirname","join","dirname","dirname","existsSync","readFileSync","join","resolve","existsSync","readFileSync","join","resolve","homedir","join","resolve","resolve","join","homedir","entry","lease","input","input","readFileSync","join","input","existsSync","execa","execa","randomUUID","domainToASCII","HOST_PATTERN","domainToASCII","HOST_PATTERN","randomUUID","input","input","resolve","input","randomUUID","writeFileSync","join","execa","join","writeFileSync","execa","existsSync","readFileSync","writeFileSync","join","existsSync","join","readPackageJson","readFileSync","writeFileSync","join","existsSync","existsSync","join","join","existsSync","existsSync","mkdirSync","readFileSync","writeFileSync","homedir","dirname","join","execa","parsePort","readFileSync","existsSync","wait","resolve","execa","input"]}
1
+ {"version":3,"sources":["../src/cli.ts","../src/activity.ts","../src/config.ts","../src/parse.ts","../src/brand.ts","../src/caddy.ts","../src/fs.ts","../src/command.ts","../src/context.ts","../src/port.ts","../src/registry.ts","../src/tunnel.ts","../src/doctor.ts","../src/env.ts","../src/ghost-file.ts","../src/ghost-agent.ts","../src/relay.ts","../src/ghost-tunnel-store.ts","../src/hosts-file.ts","../src/init.ts","../src/guide.ts","../src/prompt.ts","../src/routes.ts","../src/state.ts","../src/update-check.ts","../src/process.ts"],"sourcesContent":["#!/usr/bin/env node\n\nimport { existsSync, readFileSync, unlinkSync } from \"node:fs\";\nimport { Command, InvalidArgumentError } from \"commander\";\nimport {\n getLocalghostActivityPath,\n listLocalghostSetups,\n listLocalghostRuns,\n registerLocalghostRun,\n registerLocalghostSetup,\n unregisterLocalghostSetup,\n unregisterLocalghostRun,\n type LocalghostRunRecord,\n type LocalghostSetupRecord\n} from \"./activity.js\";\nimport { getProjectName, readDevHosts, resolveDevHostsPath, sanitizeProjectName, type ReadDevHostsOptions } from \"./config.js\";\nimport { renderLocalghostBanner } from \"./brand.js\";\nimport { getCaddyfilePath, renderCaddyfile, stopCaddyProcesses, validateCaddyfile, writeCaddyfile, startCaddy, trustCaddy } from \"./caddy.js\";\nimport {\n detectDevCommand,\n detectDevServices,\n formatDetectedDevCommand,\n formatDetectedDevServices,\n type DetectedDevService\n} from \"./command.js\";\nimport { readLocalghostProjectConfig, resolveLocalghostContext } from \"./context.js\";\nimport { checkCaddy, runDoctor } from \"./doctor.js\";\nimport { assertLocalDevelopment } from \"./env.js\";\nimport { listGhostTunnelEntries } from \"./ghost-file.js\";\nimport { startGhostTunnelAgent } from \"./ghost-agent.js\";\nimport { createRedisGhostTunnelStoreFromEnv } from \"./ghost-tunnel-store.js\";\nimport { getSystemHostsPath, removeSystemHosts, renderHostsBlock, updateSystemHosts } from \"./hosts-file.js\";\nimport { detectPackageManager, initLocalghost, type PackageManager } from \"./init.js\";\nimport { formatLocalghostAgentGuide } from \"./guide.js\";\nimport { findLocalMdnsHosts, type DevHostEntry } from \"./parse.js\";\nimport { isPortAvailable } from \"./port.js\";\nimport { createLocalghostRegistry } from \"./registry.js\";\nimport { canPrompt, confirm } from \"./prompt.js\";\nimport { formatDomainRoutes, formatGhostTunnel } from \"./routes.js\";\nimport { getLocalghostStatePath, patchLocalghostState, readLocalghostState, writeLocalghostState } from \"./state.js\";\nimport { checkForUpdate, formatUpdateMessage, LOCALGHOST_VERSION, maybeNotifyAboutUpdate } from \"./update-check.js\";\nimport type { GhostTunnelConfig } from \"./tunnel.js\";\nimport { execa } from \"execa\";\nimport { signalManagedProcess, signalManagedProcessPid } from \"./process.js\";\n\nfunction warnAboutLocalMdns(entries: ReturnType<typeof readDevHosts>) {\n const localHosts = findLocalMdnsHosts(entries);\n\n if (localHosts.length > 0) {\n console.warn(\n `Warning: .local can collide with mDNS/Bonjour. Prefer .localhost for dev hosts: ${localHosts.join(\", \")}`\n );\n }\n}\n\nfunction shouldColor() {\n return process.stdout.isTTY && !process.env.NO_COLOR;\n}\n\nfunction printLocalghostBanner() {\n console.log(renderLocalghostBanner());\n console.log(\"\");\n}\n\nfunction logDomainRoutes(\n entries: ReturnType<typeof readDevHosts>,\n options: { https?: boolean; ghostTunnel?: GhostTunnelConfig; verbose?: boolean } = {}\n) {\n console.log(formatDomainRoutes(entries, options));\n if (options.ghostTunnel?.enabled) {\n console.log(formatGhostTunnel(options.ghostTunnel, {\n color: shouldColor(),\n label: \"expected\",\n verbose: options.verbose === true\n }));\n }\n}\n\nfunction parsePort(value: string) {\n const port = Number.parseInt(value, 10);\n if (!Number.isInteger(port) || port < 1 || port > 65535) {\n throw new InvalidArgumentError(\"Port must be a number between 1 and 65535.\");\n }\n\n return port;\n}\n\nfunction parsePackageManager(value: string): PackageManager {\n if (value === \"npm\" || value === \"yarn\" || value === \"pnpm\" || value === \"bun\") return value;\n throw new InvalidArgumentError(\"Package manager must be npm, pnpm, yarn, or bun.\");\n}\n\ntype ReleaseBump = \"patch\" | \"minor\" | \"major\";\n\nfunction parseReleaseBump(value: string): ReleaseBump {\n if (value === \"patch\" || value === \"minor\" || value === \"major\") return value;\n throw new InvalidArgumentError(\"Release bump must be patch, minor, or major.\");\n}\n\nfunction collect(value: string, previous: string[] = []) {\n return [...previous, value];\n}\n\nfunction parseBooleanLike(value: string | boolean) {\n if (value === true) return true;\n if (value === false) return false;\n const normalized = value.toLowerCase();\n if ([\"1\", \"true\", \"yes\", \"y\", \"on\"].includes(normalized)) return true;\n if ([\"0\", \"false\", \"no\", \"n\", \"off\"].includes(normalized)) return false;\n throw new InvalidArgumentError(\"Value must be yes or no.\");\n}\n\ntype ConfigCliOptions = {\n cwd: string;\n config?: string[];\n configPattern?: string;\n};\n\ntype ProxyModeCliOptions = {\n https?: boolean;\n ssl?: boolean;\n};\n\ntype TrustCliOptions = {\n trust?: boolean;\n};\n\ntype AutoRepairCliOptions = {\n autoRepair?: boolean;\n};\n\ntype CleanCaddyCliOptions = {\n cleanCaddy?: boolean;\n};\n\nfunction contextOptionsFromCli(options: ConfigCliOptions & { project?: string } & ProxyModeCliOptions & AutoRepairCliOptions) {\n return {\n cwd: options.cwd,\n ...(options.project ? { project: options.project } : {}),\n ...(options.config && options.config.length > 0 ? { configFiles: options.config } : {}),\n ...(options.configPattern ? { configPattern: options.configPattern } : {}),\n ...(useHttps(options) ? { https: true } : {}),\n ...(typeof options.autoRepair === \"boolean\" ? { autoRepair: options.autoRepair } : {})\n };\n}\n\nfunction readOptionsFromCli(options: ConfigCliOptions): ReadDevHostsOptions {\n return {\n cwd: options.cwd,\n ...(options.config && options.config.length > 0 ? { configFiles: options.config } : {}),\n ...(options.configPattern ? { configPattern: options.configPattern } : {})\n };\n}\n\nasync function assertCaddyReady() {\n const caddy = await checkCaddy();\n if (caddy.found) return;\n\n throw new Error([\n \"Caddy was not found.\",\n `Install it with: ${caddy.installHint}`,\n \"Localghost will not install it for you. No surprise spells.\"\n ].join(\"\\n\"));\n}\n\nfunction cleanManagedCaddyProcesses() {\n const runs = listLocalghostRuns();\n const legacyPids = runs.flatMap((run) => run.caddyPid && !run.caddyPgid ? [run.caddyPid] : []);\n const managedPgid = runs.flatMap((run) => run.caddyPgid ? [run.caddyPgid] : []);\n const legacyResult = stopCaddyProcesses(legacyPids);\n const managedResult = stopCaddyProcesses(managedPgid, signalManagedProcessPid);\n const result = {\n stopped: [...legacyResult.stopped, ...managedResult.stopped],\n alreadyExited: [...legacyResult.alreadyExited, ...managedResult.alreadyExited],\n failed: [...legacyResult.failed, ...managedResult.failed]\n };\n\n for (const run of runs) {\n const caddyIdentity = run.caddyPgid ?? run.caddyPid;\n if (caddyIdentity && (result.stopped.includes(caddyIdentity) || result.alreadyExited.includes(caddyIdentity))) {\n unregisterLocalghostRun(run.id);\n }\n }\n\n if (result.stopped.length > 0) {\n console.log(`Stopped ${result.stopped.length} Localghost-managed Caddy process${result.stopped.length === 1 ? \"\" : \"es\"}.`);\n }\n if (result.alreadyExited.length > 0) {\n console.log(`Removed ${result.alreadyExited.length} stale Localghost Caddy record${result.alreadyExited.length === 1 ? \"\" : \"s\"}.`);\n }\n if (result.failed.length > 0) {\n throw new Error(`Could not stop Localghost-managed Caddy PID(s): ${result.failed.map(({ pid }) => pid).join(\", \")}.`);\n }\n}\n\nfunction existingTrustMarkers(cwd: string) {\n const state = readLocalghostState(cwd);\n return {\n ...(state?.caddyTrustedAt ? { caddyTrustedAt: state.caddyTrustedAt } : {}),\n ...(state?.caddyTrustPromptedAt ? { caddyTrustPromptedAt: state.caddyTrustPromptedAt } : {})\n };\n}\n\nfunction explainHostsPassword() {\n console.log(\"Localghost may ask for your password to update its managed block in /etc/hosts.\");\n console.log(\"It will only touch the lines between # localghost:start and # localghost:end.\");\n}\n\nfunction explainTrustPassword() {\n console.log(\"Localghost can trust Caddy's local HTTPS CA so browsers stop showing local certificate warnings.\");\n console.log(\"macOS may ask for your password to add that local CA to Keychain.\");\n console.log(\"This only affects Caddy's local development certificates on this machine.\");\n}\n\nfunction useHttps(options: ProxyModeCliOptions) {\n return options.https === true || options.ssl === true;\n}\n\nfunction getSetupCommand(options: { https?: boolean; config?: string[]; configPattern?: string }) {\n const configFlags = [\n ...(options.config ?? []).map((config) => ` --config ${config}`),\n ...(options.configPattern ? [` --config-pattern ${options.configPattern}`] : [])\n ].join(\"\");\n return `localghost setup${configFlags}${options.https ? \" --https\" : \"\"}`;\n}\n\nfunction getSetupReadiness(options: ConfigCliOptions & {\n project?: string;\n https?: boolean;\n ignoreCaddyfile?: boolean;\n entries?: DevHostEntry[];\n configPath?: string;\n projectName?: string;\n}) {\n const projectName = sanitizeProjectName(options.projectName ?? options.project ?? getProjectName(options.cwd));\n const readOptions = readOptionsFromCli(options);\n const entries = options.entries ?? readDevHosts(readOptions);\n const configPath = options.configPath ?? resolveDevHostsPath(readOptions).path;\n const caddyfilePath = getCaddyfilePath(options.cwd);\n const statePath = getLocalghostStatePath(options.cwd);\n const state = readLocalghostState(options.cwd);\n const https = options.https === true;\n const reasons: string[] = [];\n\n if (!state) {\n reasons.push(`No Localghost setup state found at ${statePath}.`);\n } else {\n if (state.action !== \"setup\") reasons.push(`Last Localghost action is ${state.action}, not setup.`);\n if (state.projectName !== projectName) reasons.push(`Setup state is for project ${state.projectName}, not ${projectName}.`);\n if (state.configPath !== configPath) reasons.push(`Setup state points at ${state.configPath ?? \"no config\"}, not ${configPath}.`);\n }\n\n const hostsPath = getSystemHostsPath();\n try {\n const hosts = readFileSync(hostsPath, \"utf8\");\n const expectedHostsBlock = renderHostsBlock(projectName, entries).trimEnd();\n if (!hosts.includes(expectedHostsBlock)) {\n reasons.push(`The Localghost hosts block in ${hostsPath} is missing or stale.`);\n }\n } catch (error) {\n const message = error instanceof Error ? error.message : String(error);\n reasons.push(`Could not read ${hostsPath}: ${message}`);\n }\n\n if (!options.ignoreCaddyfile) {\n if (!existsSync(caddyfilePath)) {\n reasons.push(`Missing Caddyfile at ${caddyfilePath}.`);\n } else {\n const expectedCaddyfile = renderCaddyfile(entries, { https });\n const currentCaddyfile = readFileSync(caddyfilePath, \"utf8\");\n if (currentCaddyfile !== expectedCaddyfile) {\n reasons.push(`Caddyfile at ${caddyfilePath} is stale for ${https ? \"HTTPS\" : \"HTTP\"} mode.`);\n }\n }\n }\n\n return {\n ready: reasons.length === 0,\n reasons,\n entries,\n projectName,\n configPath,\n caddyfilePath,\n statePath,\n setupCommand: getSetupCommand(options)\n };\n}\n\nasync function runSetupFromReadiness(\n cwd: string,\n https: boolean,\n readiness: ReturnType<typeof getSetupReadiness>\n) {\n explainHostsPassword();\n const hostsResult = await updateSystemHosts(readiness.projectName, readiness.entries);\n const caddyfilePath = await writeCaddyfile(readiness.entries, cwd, { https });\n await validateCaddyfile(caddyfilePath);\n writeLocalghostState(cwd, {\n action: \"setup\",\n projectName: readiness.projectName,\n cwd,\n configPath: readiness.configPath,\n hostsPath: hostsResult.hostsPath,\n hostsChanged: hostsResult.changed,\n ...(hostsResult.tempPath ? { hostsTempPath: hostsResult.tempPath } : {}),\n caddyfilePath,\n caddyHttps: https,\n ...existingTrustMarkers(cwd),\n entries: readiness.entries\n });\n registerLocalghostSetup({\n cwd,\n projectName: readiness.projectName,\n configPath: readiness.configPath,\n caddyfilePath,\n https,\n entries: readiness.entries\n });\n}\n\nfunction wait(ms: number) {\n return new Promise((resolve) => setTimeout(resolve, ms));\n}\n\nasync function runTrust(cwd: string, caddyfilePath: string) {\n await wait(350);\n try {\n await trustCaddy(caddyfilePath);\n } catch {\n await wait(750);\n await trustCaddy(caddyfilePath);\n }\n\n patchLocalghostState(cwd, { caddyTrustedAt: new Date().toISOString() });\n console.log(\"Local HTTPS trust is ready.\");\n}\n\nasync function maybeTrustCaddy(\n options: {\n cwd: string;\n https: boolean;\n caddyfilePath: string;\n trust?: boolean;\n }\n) {\n if (!options.https) return;\n\n const state = readLocalghostState(options.cwd);\n if (!options.trust && state?.caddyTrustedAt) return;\n\n let shouldTrust = options.trust === true;\n\n if (!shouldTrust) {\n if (state?.caddyTrustPromptedAt || !canPrompt()) return;\n\n explainTrustPassword();\n shouldTrust = await confirm(\"Trust local HTTPS certificates now?\", true);\n }\n\n if (!shouldTrust) {\n patchLocalghostState(options.cwd, { caddyTrustPromptedAt: new Date().toISOString() });\n console.log(\"Okay. Localghost will still run HTTPS, but the browser may show a certificate warning.\");\n console.log(\"Run localghost trust when you want to trust Caddy's local CA.\");\n return;\n }\n\n await runTrust(options.cwd, options.caddyfilePath);\n}\n\ntype LocalghostRouteView = {\n host: string;\n port: number;\n target: string;\n listening: boolean;\n};\n\ntype LocalghostInstanceView = {\n id: string;\n cwd: string;\n projectName: string;\n running: boolean;\n mode: LocalghostRunRecord[\"mode\"] | \"setup\";\n updatedAt?: string;\n startedAt?: string;\n pid?: number;\n caddyPid?: number;\n childPid?: number;\n childCommand?: string[];\n configPath?: string;\n caddyfilePath?: string;\n https?: boolean;\n routes: LocalghostRouteView[];\n};\n\nfunction maybePid(pid: number | undefined) {\n return typeof pid === \"number\" && Number.isInteger(pid) && pid > 0 ? pid : undefined;\n}\n\nfunction registerCleanup(id: string) {\n let cleaned = false;\n const cleanup = () => {\n if (cleaned) return;\n cleaned = true;\n unregisterLocalghostRun(id);\n };\n\n process.once(\"exit\", cleanup);\n\n return () => {\n cleanup();\n process.off(\"exit\", cleanup);\n };\n}\n\nfunction registerSignalShutdown(stop: () => void) {\n let requested = false;\n const request = () => {\n if (requested) return;\n requested = true;\n stop();\n };\n\n process.once(\"SIGINT\", request);\n process.once(\"SIGTERM\", request);\n\n return () => {\n process.off(\"SIGINT\", request);\n process.off(\"SIGTERM\", request);\n request();\n };\n}\n\nasync function resolveServiceRuntimeEntries(\n services: DetectedDevService[],\n dynamicPort: boolean,\n projectCwd: string\n) {\n const usedPorts = new Set<number>();\n const resolved: Array<DetectedDevService & { port: number; entry: DevHostEntry }> = [];\n const registry = dynamicPort ? createLocalghostRegistry({ cwd: projectCwd, ownerToken: `${process.pid}:services:${projectCwd}` }) : undefined;\n\n for (const service of services) {\n let port = service.requestedPort;\n if (dynamicPort) {\n const lease = await registry!.acquirePort({\n instanceKey: `service:${service.name}`,\n startPort: service.requestedPort,\n reservedPorts: usedPorts\n });\n port = lease.port;\n } else if (usedPorts.has(port)) {\n throw new Error(`Services cannot start separate commands on the same fixed port: ${port}.`);\n }\n\n usedPorts.add(port);\n resolved.push({\n ...service,\n port,\n entry: {\n host: service.host,\n port,\n target: `127.0.0.1:${port}`\n } satisfies DevHostEntry\n });\n }\n\n return {\n services: resolved,\n release: async () => {\n if (!registry) return;\n await Promise.all(resolved.map((service) => registry.releasePort({ instanceKey: `service:${service.name}` })));\n }\n };\n}\n\nasync function waitForServicePorts(entries: DevHostEntry[], timeoutMs = 10_000) {\n const deadline = Date.now() + timeoutMs;\n const ports = [...new Set(entries.map((entry) => entry.port))];\n\n while (Date.now() < deadline) {\n const availability = await Promise.all(ports.map((port) => isPortAvailable(port)));\n if (availability.every((available) => !available)) return true;\n await wait(50);\n }\n\n return false;\n}\n\nasync function waitForPortsToBeAvailable(entries: DevHostEntry[], timeoutMs = 10_000) {\n const deadline = Date.now() + timeoutMs;\n const ports = [...new Set(entries.map((entry) => entry.port))];\n\n while (Date.now() < deadline) {\n const availability = await Promise.all(ports.map((port) => isPortAvailable(port)));\n if (availability.every(Boolean)) return true;\n await wait(50);\n }\n\n return false;\n}\n\nasync function waitForProcessShutdown(\n processes: Promise<unknown>[],\n forceStop: (signal: NodeJS.Signals) => void,\n timeoutMs = 10_000\n) {\n const settled = Promise.allSettled(processes);\n const completed = await Promise.race([\n settled.then(() => true),\n wait(timeoutMs).then(() => false)\n ]);\n if (completed) return true;\n\n console.warn(\"Localghost: timed out waiting for managed processes to stop; escalating termination.\");\n forceStop(\"SIGTERM\");\n const terminated = await Promise.race([\n settled.then(() => true),\n wait(2_000).then(() => false)\n ]);\n if (terminated) return true;\n\n forceStop(\"SIGKILL\");\n await Promise.race([settled, wait(1_000)]);\n return false;\n}\n\nasync function runDetectedServices(options: {\n cwd: string;\n services: DetectedDevService[];\n configPath: string;\n projectName: string;\n https: boolean;\n dynamicPort: boolean;\n autoRepair: boolean;\n}) {\n assertLocalDevelopment(\"run\");\n await assertCaddyReady();\n\n const runtime = await resolveServiceRuntimeEntries(options.services, options.dynamicPort, options.cwd);\n try {\n const runtimeServices = runtime.services;\n const entries = runtimeServices.map((service) => service.entry);\n const readiness = getSetupReadiness({\n cwd: options.cwd,\n https: options.https,\n ignoreCaddyfile: true,\n entries,\n configPath: options.configPath,\n projectName: options.projectName\n });\n\n if (!readiness.ready) {\n if (!options.autoRepair) {\n throw new Error([\n \"Localghost setup is missing or stale.\",\n ...readiness.reasons.map((reason) => `- ${reason}`),\n \"Automatic repair is disabled. Enable autoRepair or run localghost repair.\"\n ].join(\"\\n\"));\n }\n console.log(\"Localghost setup is stale; repairing it now.\");\n await runSetupFromReadiness(options.cwd, options.https, readiness);\n }\n\n for (const service of runtimeServices) {\n if (service.port !== service.requestedPort) {\n console.log(`${service.name}: port ${service.requestedPort} is busy; using ${service.port}.`);\n }\n }\n\n const caddyfile = await writeCaddyfile(entries, options.cwd, { https: options.https });\n await validateCaddyfile(caddyfile);\n const caddy = startCaddy(caddyfile);\n const caddyExit = caddy.catch((error: unknown) => {\n if (!caddy.killed) throw error;\n });\n const children = runtimeServices.map((service) => execa(service.command[0]!, service.command.slice(1), {\n cwd: service.cwd,\n stdio: \"inherit\",\n detached: process.platform !== \"win32\",\n env: {\n ...process.env,\n LOCALGHOST_PORT: String(service.port),\n LOCALGHOST_DYNAMIC_PORT: options.dynamicPort ? \"1\" : \"0\",\n LOCALGHOST_SERVICE: service.name,\n VITE_PORT: String(service.port)\n }\n }));\n const caddyPid = maybePid(caddy.pid);\n const runRecord = registerLocalghostRun({\n mode: \"run\",\n cwd: options.cwd,\n projectName: options.projectName,\n configPath: options.configPath,\n caddyfilePath: caddyfile,\n ...(caddyPid ? { caddyPid } : {}),\n ...(caddyPid ? { caddyPgid: caddyPid } : {}),\n childCommand: [\"services\", ...runtimeServices.map((service) => service.name)],\n https: options.https,\n dynamicPort: options.dynamicPort,\n entries\n });\n const cleanupRun = registerCleanup(runRecord.id);\n const processExit = Promise.race([caddyExit, ...children]);\n const stopManaged = (signal: NodeJS.Signals) => {\n for (const child of children) {\n signalManagedProcess(child, signal);\n }\n signalManagedProcess(caddy, signal);\n };\n const finishShutdown = registerSignalShutdown(() => stopManaged(\"SIGINT\"));\n\n try {\n const ready = await Promise.race([\n waitForServicePorts(entries),\n processExit.then(() => false)\n ]);\n if (ready) {\n console.log(\"\");\n logDomainRoutes(entries, { https: options.https });\n }\n await processExit;\n } finally {\n finishShutdown();\n await waitForProcessShutdown(\n [caddyExit, ...children],\n stopManaged\n );\n if (!(await waitForPortsToBeAvailable(entries))) {\n console.warn(\"Localghost: timed out waiting for service ports to be released.\");\n stopManaged(\"SIGTERM\");\n if (!(await waitForPortsToBeAvailable(entries, 2_000))) {\n stopManaged(\"SIGKILL\");\n }\n }\n cleanupRun();\n }\n } finally {\n await runtime.release();\n }\n}\n\nasync function getRouteViews(entries: DevHostEntry[]): Promise<LocalghostRouteView[]> {\n const portStatus = new Map<number, boolean>();\n\n for (const entry of entries) {\n if (!portStatus.has(entry.port)) {\n portStatus.set(entry.port, !(await isPortAvailable(entry.port)));\n }\n }\n\n return entries.map((entry) => ({\n host: entry.host,\n port: entry.port,\n target: `127.0.0.1:${entry.port}`,\n listening: portStatus.get(entry.port) ?? false\n }));\n}\n\nfunction setupKey(input: Pick<LocalghostSetupRecord, \"cwd\" | \"projectName\" | \"configPath\">) {\n return `${input.projectName}:${input.cwd}:${input.configPath ?? \"\"}`;\n}\n\nfunction runKey(input: Pick<LocalghostRunRecord, \"cwd\" | \"projectName\" | \"configPath\">) {\n return `${input.projectName}:${input.cwd}:${input.configPath ?? \"\"}`;\n}\n\nasync function getInstanceViews(setups: LocalghostSetupRecord[], runs: LocalghostRunRecord[]): Promise<LocalghostInstanceView[]> {\n const runBySetup = new Map(runs.map((run) => [runKey(run), run]));\n const instances: LocalghostInstanceView[] = [];\n\n for (const setup of setups) {\n const run = runBySetup.get(setupKey(setup));\n if (run) {\n instances.push(await getRunInstanceView(run, setup));\n runBySetup.delete(setupKey(setup));\n continue;\n }\n\n instances.push({\n id: setup.id,\n cwd: setup.cwd,\n projectName: setup.projectName,\n running: false,\n mode: \"setup\",\n updatedAt: setup.updatedAt,\n ...(setup.configPath ? { configPath: setup.configPath } : {}),\n ...(setup.caddyfilePath ? { caddyfilePath: setup.caddyfilePath } : {}),\n ...(typeof setup.https === \"boolean\" ? { https: setup.https } : {}),\n routes: await getRouteViews(setup.entries)\n });\n }\n\n for (const run of runBySetup.values()) {\n instances.push(await getRunInstanceView(run));\n }\n\n return instances.sort((left, right) => {\n if (left.running !== right.running) return left.running ? -1 : 1;\n return left.projectName.localeCompare(right.projectName);\n });\n}\n\nasync function getRunInstanceView(run: LocalghostRunRecord, setup?: LocalghostSetupRecord): Promise<LocalghostInstanceView> {\n return {\n id: setup?.id ?? run.id,\n cwd: run.cwd,\n projectName: run.projectName,\n running: true,\n mode: run.mode,\n updatedAt: setup?.updatedAt ?? run.updatedAt,\n startedAt: run.startedAt,\n pid: run.pid,\n ...(run.caddyPid ? { caddyPid: run.caddyPid } : {}),\n ...(run.childPid ? { childPid: run.childPid } : {}),\n ...(run.childCommand ? { childCommand: run.childCommand } : {}),\n ...(run.configPath ? { configPath: run.configPath } : {}),\n ...(run.caddyfilePath ? { caddyfilePath: run.caddyfilePath } : {}),\n ...(typeof run.https === \"boolean\" ? { https: run.https } : {}),\n routes: await getRouteViews(run.entries)\n };\n}\n\nfunction formatInstanceViews(instances: LocalghostInstanceView[]) {\n if (instances.length === 0) return \"No Localghost setups found.\";\n\n const lines = [\"localghost ps\"];\n for (const instance of instances) {\n const command = instance.childCommand?.length ? ` ${instance.childCommand.join(\" \")}` : \"\";\n const mode = command ? `${instance.mode}:${command}` : instance.mode === \"setup\" ? \"\" : instance.mode;\n lines.push(\"\");\n lines.push(`${instance.projectName} ${instance.running ? \"running\" : \"setup\"}${mode ? ` ${mode}` : \"\"}`);\n lines.push(` cwd: ${instance.cwd}`);\n if (instance.pid) {\n lines.push(` pid: ${instance.pid}${instance.caddyPid ? `, caddy: ${instance.caddyPid}` : \"\"}${instance.childPid ? `, child: ${instance.childPid}` : \"\"}`);\n }\n if (instance.startedAt) lines.push(` started: ${instance.startedAt}`);\n if (!instance.startedAt && instance.updatedAt) lines.push(` setup: ${instance.updatedAt}`);\n for (const route of instance.routes) {\n lines.push(` ${route.host} -> ${route.target} (${route.listening ? \"listening\" : \"not listening\"})`);\n }\n }\n\n return lines.join(\"\\n\");\n}\n\nconst program = new Command();\n\nprogram\n .name(\"localghost\")\n .description(\"Buh. Friendly local hostnames for app repos.\")\n .version(LOCALGHOST_VERSION)\n .option(\"--no-update-check\", \"Skip the npm update check for this run\");\n\nprogram.hook(\"postAction\", async (_thisCommand, actionCommand) => {\n if ([\"update\", \"upgrade\", \"release\"].includes(actionCommand.name())) return;\n\n const options = program.opts<{ updateCheck?: boolean }>();\n await maybeNotifyAboutUpdate({ disabled: options.updateCheck === false });\n});\n\nprogram\n .command(\"init\")\n .description(\"Create a .localghost config for this project\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .option(\"--config <file>\", \"Config file to create\", \".localghost\")\n .option(\"--host <host>\", \"Primary local hostname\")\n .option(\"--port <number>\", \"Primary app port\", parsePort)\n .option(\"--api-host <host>\", \"API local hostname\")\n .option(\"--api-port <number>\", \"API port\", parsePort)\n .option(\"--package-manager <npm|pnpm|yarn|bun>\", \"Package manager for suggested commands\", parsePackageManager)\n .option(\"--write-scripts\", \"Add localghost scripts to package.json\")\n .option(\"--force\", \"Overwrite an existing config file\")\n .action((options: {\n cwd: string;\n config: string;\n host?: string;\n port?: number;\n apiHost?: string;\n apiPort?: number;\n packageManager?: PackageManager;\n writeScripts?: boolean;\n force?: boolean;\n }) => {\n const result = initLocalghost({ ...options, configFile: options.config });\n\n if (result.configCreated) {\n console.log(`Buh. Created ${result.configPath}`);\n } else {\n console.log(`${result.configPath} already exists. Use --force to rewrite it.`);\n }\n\n if (options.writeScripts) {\n if (result.packageJsonChanged) {\n console.log(`Updated ${result.packageJsonPath}`);\n } else if (result.packageJsonPath) {\n console.log(`${result.packageJsonPath} already has localghost scripts.`);\n } else {\n console.log(\"No package.json found; skipped script setup.\");\n }\n }\n\n console.log(\"Next:\");\n for (const step of result.nextSteps) {\n console.log(` ${step}`);\n }\n });\n\nprogram\n .command(\"guide\")\n .description(\"Explain the recommended Localghost workflow to humans or agents\")\n .option(\"--agent\", \"Print the agent-oriented workflow guide\")\n .option(\"--json\", \"Print the guide as JSON\")\n .action((options: { agent?: boolean; json?: boolean }) => {\n console.log(formatLocalghostAgentGuide(options.json ? \"json\" : \"text\"));\n });\n\nprogram\n .command(\"doctor\")\n .description(\"Check machine prerequisites, ports, and Localghost registry state\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .option(\"--config <file>\", \"Config file to inspect. Can be repeated.\", collect, [])\n .option(\"--config-pattern <regex>\", \"Regex for config filenames in the project root\")\n .option(\"--json\", \"Print raw JSON\")\n .action(async (options: ConfigCliOptions & { json?: boolean }) => {\n const result = await runDoctor({\n cwd: options.cwd,\n ...(options.config && options.config.length > 0 ? { configFiles: options.config } : {}),\n ...(options.configPattern ? { configPattern: options.configPattern } : {})\n });\n\n if (options.json) {\n console.log(JSON.stringify(result, null, 2));\n if (!result.ok) process.exitCode = 1;\n return;\n }\n\n if (result.caddy.found) {\n console.log(`Caddy: ${result.caddy.version ?? \"found\"}`);\n } else {\n console.log(\"Caddy: missing\");\n console.log(`Run: ${result.caddy.installHint}`);\n console.log(\"Localghost will not install it for you. No surprise spells.\");\n }\n\n if (result.ports.configured === undefined) {\n console.log(\"Port: could not resolve project configuration.\");\n } else {\n console.log(`Port ${result.ports.configured}: ${result.ports.available ? \"available\" : \"occupied\"}`);\n }\n if (result.ports.staleLeases.length > 0) {\n console.log(`Registry: ${result.ports.staleLeases.length} stale lease(s); run localghost repair --prune-registry.`);\n }\n for (const duplicate of result.ports.duplicateAllocations) {\n console.log(`Registry: port ${duplicate.port} is allocated to ${duplicate.projects.join(\", \")}.`);\n }\n\n if (!result.ok) {\n process.exitCode = 1;\n }\n });\n\nprogram\n .command(\"update\")\n .description(\"Check npm for a newer localghost release\")\n .option(\"--json\", \"Print raw JSON\")\n .action(async (options: { json?: boolean }) => {\n const result = await checkForUpdate({ force: true, timeoutMs: 5000 });\n\n if (options.json) {\n console.log(JSON.stringify(result, null, 2));\n return;\n }\n\n const message = formatUpdateMessage(result);\n if (message) {\n console.log(message);\n return;\n }\n\n if (result.source === \"error\") {\n console.log(`Could not check npm for updates: ${result.error ?? \"unknown error\"}`);\n process.exitCode = 1;\n return;\n }\n\n console.log(`localghost is up to date. Current: ${result.currentVersion}`);\n });\n\nprogram\n .command(\"upgrade\")\n .description(\"Install or update Localghost in the current repository\")\n .option(\"--cwd <path>\", \"Consumer repository\", process.cwd())\n .action(async (options: { cwd: string }) => {\n const packageManager = detectPackageManager(options.cwd);\n const packageName = \"@hamedb89/localghost@latest\";\n const args = packageManager === \"yarn\"\n ? [\"add\", \"--dev\", packageName]\n : packageManager === \"pnpm\"\n ? [\"add\", \"--save-dev\", packageName]\n : packageManager === \"bun\"\n ? [\"add\", \"--dev\", packageName]\n : [\"install\", \"--save-dev\", packageName];\n\n console.log(`Upgrading ${packageName} with ${packageManager}...`);\n await execa(packageManager, args, { cwd: options.cwd, stdio: \"inherit\" });\n console.log(`Localghost is upgraded in ${options.cwd}.`);\n });\n\nprogram\n .command(\"release\")\n .description(\"Dispatch an automated Localghost CLI release\")\n .argument(\"[bump]\", \"Semantic version increment: patch, minor, or major (default: patch)\", parseReleaseBump, \"patch\")\n .action(async (bump: ReleaseBump) => {\n const repository = \"hamedb89/localghost\";\n\n try {\n await execa(\"gh\", [\n \"workflow\",\n \"run\",\n \"release.yml\",\n \"--repo\",\n repository,\n \"--ref\",\n \"main\",\n \"-f\",\n `bump=${bump}`\n ]);\n } catch (error) {\n const detail = error instanceof Error ? error.message : String(error);\n throw new Error(\n `Could not dispatch the Localghost release workflow. Install and authenticate GitHub CLI with \\`gh auth login\\`, then retry.\\n${detail}`\n );\n }\n\n console.log(`Dispatched a ${bump} Localghost release from main.`);\n console.log(`Track it at https://github.com/${repository}/actions/workflows/release.yml`);\n });\n\nprogram\n .command(\"setup\")\n .description(\"Update /etc/hosts and generate/validate Caddyfile\")\n .option(\"--project <name>\", \"Managed /etc/hosts block name\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .option(\"--config <file>\", \"Config file to look for. Can be repeated.\", collect, [])\n .option(\"--config-pattern <regex>\", \"Regex for config filenames in the project root\")\n .option(\"--https\", \"Generate a local HTTPS Caddy proxy with Caddy local certificates\")\n .option(\"--ssl\", \"Alias for --https\")\n .action(async (options: ConfigCliOptions & { project?: string } & ProxyModeCliOptions) => {\n assertLocalDevelopment(\"setup\");\n printLocalghostBanner();\n await assertCaddyReady();\n\n const context = await resolveLocalghostContext({ ...contextOptionsFromCli(options), dynamicPort: false });\n const https = context.https;\n const projectName = context.projectName;\n const configPath = context.configPath;\n const entries = context.entries;\n\n warnAboutLocalMdns(entries);\n logDomainRoutes(entries, { https, ghostTunnel: context.ghostTunnel });\n\n explainHostsPassword();\n const hostsResult = await updateSystemHosts(projectName, entries);\n\n if (hostsResult.changed) {\n console.log(`Updated ${hostsResult.hostsPath}`);\n } else {\n console.log(`${hostsResult.hostsPath} already up to date`);\n }\n\n const caddyfile = await writeCaddyfile(entries, options.cwd, { https });\n await validateCaddyfile(caddyfile);\n\n const statePath = writeLocalghostState(options.cwd, {\n action: \"setup\",\n projectName,\n cwd: options.cwd,\n configPath,\n hostsPath: hostsResult.hostsPath,\n hostsChanged: hostsResult.changed,\n ...(hostsResult.tempPath ? { hostsTempPath: hostsResult.tempPath } : {}),\n caddyfilePath: caddyfile,\n caddyHttps: https,\n ...existingTrustMarkers(options.cwd),\n entries\n });\n registerLocalghostSetup({\n cwd: options.cwd,\n projectName,\n configPath,\n caddyfilePath: caddyfile,\n https,\n entries\n });\n\n console.log(`Generated ${caddyfile}`);\n console.log(`Mode ${https ? \"HTTPS\" : \"HTTP\"}`);\n console.log(`State ${statePath}`);\n console.log(\"Setup complete.\");\n });\n\nprogram\n .command(\"trust\")\n .description(\"Trust Caddy's local HTTPS CA for this project's HTTPS proxy\")\n .option(\"--project <name>\", \"Managed /etc/hosts block name\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .option(\"--config <file>\", \"Config file to look for. Can be repeated.\", collect, [])\n .option(\"--config-pattern <regex>\", \"Regex for config filenames in the project root\")\n .option(\"--https\", \"Use HTTPS mode for the Caddyfile\")\n .option(\"--ssl\", \"Alias for --https\")\n .action(async (options: ConfigCliOptions & { project?: string } & ProxyModeCliOptions) => {\n assertLocalDevelopment(\"trust\");\n await assertCaddyReady();\n\n const context = await resolveLocalghostContext({ ...contextOptionsFromCli(options), dynamicPort: false });\n if (!context.https) {\n throw new Error(\"Localghost HTTPS is not enabled for this context. Set https: true in localghost.config.mjs or pass --https.\");\n }\n\n warnAboutLocalMdns(context.entries);\n logDomainRoutes(context.entries, { https: true, ghostTunnel: context.ghostTunnel });\n explainTrustPassword();\n\n const caddyfile = await writeCaddyfile(context.entries, options.cwd, { https: true });\n await validateCaddyfile(caddyfile);\n await runTrust(options.cwd, caddyfile);\n });\n\nprogram\n .command(\"repair\")\n .description(\"Reconcile stale setup, ports, registry state, and optional HTTPS trust\")\n .option(\"--project <name>\", \"Managed /etc/hosts block name\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .option(\"--config <file>\", \"Config file to look for. Can be repeated.\", collect, [])\n .option(\"--config-pattern <regex>\", \"Regex for config filenames in the project root\")\n .option(\"--https\", \"Repair an HTTPS Caddy setup\")\n .option(\"--ssl\", \"Alias for --https\")\n .option(\"--trust\", \"Re-run Caddy's local HTTPS trust step\")\n .option(\"--reallocate-port\", \"Persist a stable replacement for an occupied port\")\n .option(\"--prune-registry\", \"Remove expired or dead registry leases\")\n .action(async (\n options: ConfigCliOptions & { project?: string; reallocatePort?: boolean; pruneRegistry?: boolean } & ProxyModeCliOptions & TrustCliOptions\n ) => {\n assertLocalDevelopment(\"repair\");\n printLocalghostBanner();\n await assertCaddyReady();\n\n const registry = createLocalghostRegistry({ cwd: options.cwd });\n if (options.pruneRegistry) {\n const result = await registry.prune();\n console.log(`Pruned ${result.removedLeases} stale registry lease${result.removedLeases === 1 ? \"\" : \"s\"}.`);\n }\n const context = await resolveLocalghostContext({\n ...contextOptionsFromCli(options),\n dynamicPort: options.reallocatePort ? true : false,\n ...(options.reallocatePort ? { reservePort: true, instanceKey: \"run\" } : {})\n });\n const readiness = getSetupReadiness({\n ...options,\n https: context.https,\n entries: context.entries,\n configPath: context.configPath,\n projectName: context.projectName\n });\n\n if (options.trust && !context.https) {\n throw new Error(\"Cannot repair HTTPS trust unless HTTPS is enabled. Pass --https or configure https: true.\");\n }\n\n warnAboutLocalMdns(context.entries);\n logDomainRoutes(context.entries, { https: context.https, ghostTunnel: context.ghostTunnel });\n try {\n await runSetupFromReadiness(options.cwd, context.https, readiness);\n\n if (options.trust) {\n await runTrust(options.cwd, readiness.caddyfilePath);\n }\n\n if (context.port !== context.requestedPort) {\n console.log(`Reallocated port ${context.requestedPort} -> ${context.port}.`);\n }\n console.log(`Repaired hosts: ${getSystemHostsPath()}`);\n console.log(`Repaired Caddyfile: ${readiness.caddyfilePath}`);\n console.log(`Repaired state: ${readiness.statePath}`);\n console.log(\"Repair complete.\");\n } finally {\n await context.releasePort?.();\n }\n });\n\nprogram\n .command(\"reset\")\n .description(\"Remove Localghost setup state without deleting .localghost\")\n .option(\"--project <name>\", \"Managed /etc/hosts block name\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .action(async (options: { project?: string; cwd: string }) => {\n assertLocalDevelopment(\"reset\");\n\n const projectName = sanitizeProjectName(options.project ?? getProjectName(options.cwd));\n const caddyfilePath = getCaddyfilePath(options.cwd);\n const statePath = getLocalghostStatePath(options.cwd);\n\n explainHostsPassword();\n const hostsResult = await removeSystemHosts(projectName);\n\n if (existsSync(caddyfilePath)) {\n unlinkSync(caddyfilePath);\n console.log(`Removed ${caddyfilePath}`);\n } else {\n console.log(`${caddyfilePath} was not present`);\n }\n\n if (existsSync(statePath)) {\n unlinkSync(statePath);\n console.log(`Removed ${statePath}`);\n } else {\n console.log(`${statePath} was not present`);\n }\n\n if (hostsResult.removed) {\n console.log(`Removed Localghost hosts block from ${hostsResult.hostsPath}`);\n } else {\n console.log(`No Localghost hosts block found in ${hostsResult.hostsPath}`);\n }\n\n unregisterLocalghostSetup({ cwd: options.cwd, projectName });\n console.log(\".localghost was left in place. Run localghost setup when you are ready.\");\n });\n\nprogram\n .command(\"teardown\")\n .description(\"Remove Localghost's managed /etc/hosts block\")\n .option(\"--project <name>\", \"Managed /etc/hosts block name\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .option(\"--remove-caddyfile\", \"Also remove ops/local/Caddyfile\")\n .action(async (options: { project?: string; cwd: string; removeCaddyfile?: boolean }) => {\n assertLocalDevelopment(\"teardown\");\n const projectName = sanitizeProjectName(options.project ?? getProjectName(options.cwd));\n explainHostsPassword();\n const hostsResult = await removeSystemHosts(projectName);\n const caddyfilePath = getCaddyfilePath(options.cwd);\n let caddyfileRemoved = false;\n\n if (options.removeCaddyfile && existsSync(caddyfilePath)) {\n unlinkSync(caddyfilePath);\n caddyfileRemoved = true;\n }\n\n const statePath = writeLocalghostState(options.cwd, {\n action: \"teardown\",\n projectName,\n cwd: options.cwd,\n hostsPath: hostsResult.hostsPath,\n hostsChanged: hostsResult.changed,\n ...(hostsResult.tempPath ? { hostsTempPath: hostsResult.tempPath } : {}),\n caddyfilePath,\n caddyfileRemoved\n });\n\n if (hostsResult.removed) {\n console.log(`Removed Localghost hosts block from ${hostsResult.hostsPath}`);\n } else {\n console.log(`No Localghost hosts block found in ${hostsResult.hostsPath}`);\n }\n\n if (options.removeCaddyfile) {\n console.log(caddyfileRemoved ? `Removed ${caddyfilePath}` : `${caddyfilePath} was not present`);\n }\n\n unregisterLocalghostSetup({ cwd: options.cwd, projectName });\n console.log(`State ${statePath}`);\n });\n\nprogram\n .command(\"status\")\n .description(\"Print Localghost's project-local state file\")\n .option(\"--project <name>\", \"Managed /etc/hosts block name\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .option(\"--config <file>\", \"Config file to look for. Can be repeated.\", collect, [])\n .option(\"--config-pattern <regex>\", \"Regex for config filenames in the project root\")\n .option(\"--ready\", \"Exit non-zero when setup is missing or stale\")\n .option(\"--https\", \"Check setup readiness for HTTPS mode\")\n .option(\"--ssl\", \"Alias for --https\")\n .option(\"--json\", \"Print raw JSON\")\n .action(async (options: ConfigCliOptions & { project?: string; ready?: boolean; json?: boolean } & ProxyModeCliOptions) => {\n const state = readLocalghostState(options.cwd);\n const statePath = getLocalghostStatePath(options.cwd);\n const context = await resolveLocalghostContext({ ...contextOptionsFromCli(options), dynamicPort: false });\n const readiness = getSetupReadiness({\n ...options,\n https: context.https,\n entries: context.entries,\n configPath: context.configPath,\n projectName: context.projectName\n });\n\n if (options.json) {\n console.log(JSON.stringify({ state, setup: readiness }, null, 2));\n return;\n }\n\n if (!state) {\n console.log(`No Localghost state found at ${statePath}`);\n } else {\n console.log(`State: ${statePath}`);\n console.log(`Last action: ${state.action}`);\n console.log(`Updated: ${state.updatedAt}`);\n console.log(`Project: ${state.projectName}`);\n if (state.configPath) console.log(`Config: ${state.configPath}`);\n if (state.hostsPath) console.log(`Hosts: ${state.hostsPath}`);\n if (state.caddyfilePath) console.log(`Caddyfile: ${state.caddyfilePath}`);\n if (typeof state.caddyHttps === \"boolean\") console.log(`Mode: ${state.caddyHttps ? \"HTTPS\" : \"HTTP\"}`);\n if (state.caddyTrustedAt) console.log(`HTTPS trust: yes (${state.caddyTrustedAt})`);\n if (!state.caddyTrustedAt && state.caddyTrustPromptedAt) console.log(`HTTPS trust: not enabled (asked ${state.caddyTrustPromptedAt})`);\n if (typeof state.caddyfileRemoved === \"boolean\") console.log(`Caddyfile removed: ${state.caddyfileRemoved}`);\n }\n\n if (readiness.ready) {\n console.log(\"Setup ready: yes\");\n return;\n }\n\n console.log(\"Setup ready: no\");\n for (const reason of readiness.reasons) {\n console.log(` - ${reason}`);\n }\n console.log(`Run: ${readiness.setupCommand}`);\n\n if (options.ready) {\n process.exitCode = 1;\n }\n });\n\nprogram\n .command(\"routes\")\n .description(\"Print domain to upstream routes\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .option(\"--config <file>\", \"Config file to look for. Can be repeated.\", collect, [])\n .option(\"--config-pattern <regex>\", \"Regex for config filenames in the project root\")\n .option(\"--http\", \"Print domain URLs with http instead of https\")\n .option(\"--https\", \"Print domain URLs with https\")\n .option(\"--ssl\", \"Alias for --https\")\n .option(\"--verbose\", \"Print Ghost Tunnel mode, domains, and guardrails\")\n .action(async (options: ConfigCliOptions & { http?: boolean; verbose?: boolean } & ProxyModeCliOptions) => {\n const context = await resolveLocalghostContext({ ...contextOptionsFromCli(options), dynamicPort: false });\n warnAboutLocalMdns(context.entries);\n console.log(formatDomainRoutes(context.entries, { https: options.http ? false : context.https }));\n if (context.ghostTunnel.enabled) {\n console.log(formatGhostTunnel(context.ghostTunnel, {\n color: shouldColor(),\n label: \"expected\",\n verbose: options.verbose === true\n }));\n }\n });\n\nprogram\n .command(\"dev\")\n .description(\"Run the Localghost Caddy proxy, repairing stale setup when needed\")\n .option(\"--project <name>\", \"Managed /etc/hosts block name\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .option(\"--config <file>\", \"Config file to look for. Can be repeated.\", collect, [])\n .option(\"--config-pattern <regex>\", \"Regex for config filenames in the project root\")\n .option(\"--https\", \"Run a local HTTPS proxy with Caddy local certificates\")\n .option(\"--ssl\", \"Alias for --https\")\n .option(\"--setup\", \"Alias for automatic repair when setup is missing or stale\")\n .option(\"--auto-repair [yes|no]\", \"Repair stale setup before starting (default: yes)\", parseBooleanLike)\n .option(\"--clean-caddy\", \"Stop Localghost-managed Caddy processes before starting\")\n .option(\"--trust\", \"Trust Caddy's local HTTPS CA before starting the proxy\")\n .action(async (\n options: ConfigCliOptions & { project?: string; setup?: boolean } & ProxyModeCliOptions & TrustCliOptions & AutoRepairCliOptions & CleanCaddyCliOptions\n ) => {\n assertLocalDevelopment(\"dev\");\n await assertCaddyReady();\n\n if (options.cleanCaddy) cleanManagedCaddyProcesses();\n\n const context = await resolveLocalghostContext({ ...contextOptionsFromCli(options), dynamicPort: false });\n const https = context.https;\n const readiness = getSetupReadiness({\n ...options,\n https,\n entries: context.entries,\n configPath: context.configPath,\n projectName: context.projectName\n });\n\n if (!readiness.ready) {\n if (!options.setup && !context.autoRepair) {\n throw new Error(\n [\n \"Localghost setup is missing or stale.\",\n ...readiness.reasons.map((reason) => `- ${reason}`),\n `Run: ${readiness.setupCommand}`,\n \"Automatic repair is disabled. Rerun without --auto-repair=no or run localghost repair.\"\n ].join(\"\\n\")\n );\n }\n\n console.log(\"Localghost setup is stale; repairing it now.\");\n await runSetupFromReadiness(options.cwd, https, readiness);\n }\n\n warnAboutLocalMdns(readiness.entries);\n logDomainRoutes(readiness.entries, { https, ghostTunnel: context.ghostTunnel });\n\n const caddyfile = await writeCaddyfile(readiness.entries, options.cwd, { https });\n await validateCaddyfile(caddyfile);\n const caddy = startCaddy(caddyfile);\n try {\n await maybeTrustCaddy({\n cwd: options.cwd,\n https,\n caddyfilePath: caddyfile,\n ...(typeof options.trust === \"boolean\" ? { trust: options.trust } : {})\n });\n } catch (error) {\n signalManagedProcess(caddy, \"SIGINT\");\n throw error;\n }\n const caddyPid = maybePid(caddy.pid);\n const runRecord = registerLocalghostRun({\n mode: \"dev\",\n cwd: options.cwd,\n projectName: readiness.projectName,\n configPath: readiness.configPath,\n caddyfilePath: caddyfile,\n ...(caddyPid ? { caddyPid } : {}),\n ...(caddyPid ? { caddyPgid: caddyPid } : {}),\n https,\n entries: readiness.entries\n });\n const cleanupRun = registerCleanup(runRecord.id);\n\n try {\n await caddy;\n } finally {\n cleanupRun();\n }\n });\n\nprogram\n .command(\"run\")\n .description(\"Run Caddy and a dev command from the same Localghost context\")\n .option(\"--project <name>\", \"Managed /etc/hosts block name\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .option(\"--config <file>\", \"Config file to look for. Can be repeated.\", collect, [])\n .option(\"--config-pattern <regex>\", \"Regex for config filenames in the project root\")\n .option(\"--port <number>\", \"Initial app port\", parsePort)\n .option(\"--https\", \"Run a local HTTPS proxy with Caddy local certificates\")\n .option(\"--ssl\", \"Alias for --https\")\n .option(\"--setup\", \"Alias for automatic repair when setup is missing or stale\")\n .option(\"--auto-repair [yes|no]\", \"Repair stale setup before starting (default: yes)\", parseBooleanLike)\n .option(\"--clean-caddy\", \"Stop Localghost-managed Caddy processes before starting\")\n .option(\"--trust\", \"Trust Caddy's local HTTPS CA before starting the child command\")\n .option(\"--dynamic-port [yes|no]\", \"Use the requested port if free, otherwise continue upward\", parseBooleanLike)\n .argument(\"<command...>\", \"Command to run after --, for example: localghost run -- vite\")\n .action(async (\n command: string[],\n options: ConfigCliOptions & { project?: string; port?: number; setup?: boolean; dynamicPort?: boolean } & ProxyModeCliOptions & TrustCliOptions & AutoRepairCliOptions & CleanCaddyCliOptions\n ) => {\n assertLocalDevelopment(\"run\");\n await assertCaddyReady();\n\n if (options.cleanCaddy) cleanManagedCaddyProcesses();\n\n const context = await resolveLocalghostContext({\n cwd: options.cwd,\n ...(options.project ? { project: options.project } : {}),\n ...(options.config && options.config.length > 0 ? { configFiles: options.config } : {}),\n ...(options.configPattern ? { configPattern: options.configPattern } : {}),\n ...(options.port ? { port: options.port } : {}),\n reservePort: true,\n instanceKey: \"run\",\n ...(useHttps(options) ? { https: true } : {}),\n ...(typeof options.dynamicPort === \"boolean\" ? { dynamicPort: options.dynamicPort } : {}),\n ...(typeof options.autoRepair === \"boolean\" ? { autoRepair: options.autoRepair } : {})\n });\n const https = context.https;\n const readiness = getSetupReadiness({\n ...options,\n https,\n ignoreCaddyfile: true,\n entries: context.entries,\n configPath: context.configPath,\n projectName: context.projectName\n });\n\n if (!readiness.ready) {\n if (!options.setup && !context.autoRepair) {\n throw new Error(\n [\n \"Localghost setup is missing or stale.\",\n ...readiness.reasons.map((reason) => `- ${reason}`),\n `Run: ${readiness.setupCommand}`,\n \"Automatic repair is disabled. Rerun without --auto-repair=no or run localghost repair.\"\n ].join(\"\\n\")\n );\n }\n\n console.log(\"Localghost setup is stale; repairing it now.\");\n await runSetupFromReadiness(options.cwd, https, readiness);\n console.log(`Repair complete. Setup state: ${getLocalghostStatePath(options.cwd)}`);\n }\n\n if (context.dynamicPort && context.port !== context.requestedPort) {\n console.log(`Port ${context.requestedPort} is busy; using ${context.port}.`);\n }\n\n warnAboutLocalMdns(context.entries);\n logDomainRoutes(context.entries, { https, ghostTunnel: context.ghostTunnel });\n\n const caddyfile = await writeCaddyfile(context.entries, options.cwd, { https });\n await validateCaddyfile(caddyfile);\n const caddy = startCaddy(caddyfile);\n const caddyExit = caddy.catch((error: unknown) => {\n if (!caddy.killed) throw error;\n });\n try {\n await maybeTrustCaddy({\n cwd: options.cwd,\n https,\n caddyfilePath: caddyfile,\n ...(typeof options.trust === \"boolean\" ? { trust: options.trust } : {})\n });\n } catch (error) {\n signalManagedProcess(caddy, \"SIGINT\");\n throw error;\n }\n const [binary, ...args] = command;\n if (!binary) {\n throw new Error(\"Missing command. Use: localghost run -- vite\");\n }\n\n const child = execa(binary, args, {\n cwd: options.cwd,\n stdio: \"inherit\",\n detached: process.platform !== \"win32\",\n env: {\n ...process.env,\n LOCALGHOST_PORT: String(context.port),\n LOCALGHOST_DYNAMIC_PORT: context.dynamicPort ? \"1\" : \"0\",\n VITE_PORT: String(context.port)\n }\n });\n const caddyPid = maybePid(caddy.pid);\n const childPid = maybePid(child.pid);\n const runRecord = registerLocalghostRun({\n mode: \"run\",\n cwd: context.cwd,\n projectName: context.projectName,\n configPath: context.configPath,\n caddyfilePath: caddyfile,\n ...(caddyPid ? { caddyPid } : {}),\n ...(caddyPid ? { caddyPgid: caddyPid } : {}),\n ...(childPid ? { childPid } : {}),\n childCommand: command,\n https,\n requestedPort: context.requestedPort,\n port: context.port,\n dynamicPort: context.dynamicPort,\n entries: context.entries\n });\n const cleanupRun = registerCleanup(runRecord.id);\n\n const stopManaged = (signal: NodeJS.Signals) => {\n signalManagedProcess(child, signal);\n signalManagedProcess(caddy, signal);\n };\n const finishShutdown = registerSignalShutdown(() => stopManaged(\"SIGINT\"));\n\n try {\n await Promise.race([child, caddyExit]);\n } finally {\n finishShutdown();\n await waitForProcessShutdown(\n [child, caddyExit],\n stopManaged\n );\n if (!(await waitForPortsToBeAvailable(context.entries))) {\n console.warn(\"Localghost: timed out waiting for service ports to be released.\");\n stopManaged(\"SIGTERM\");\n if (!(await waitForPortsToBeAvailable(context.entries, 2_000))) {\n stopManaged(\"SIGKILL\");\n }\n }\n cleanupRun();\n await context.releasePort?.();\n }\n });\n\nprogram\n .command(\"tunnel\")\n .description(\"Run the experimental local Ghost Tunnel agent\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .option(\"--config <file>\", \"Config file to look for. Can be repeated.\", collect, [])\n .option(\"--config-pattern <regex>\", \"Regex for config filenames in the project root\")\n .option(\"--ghost-config <file>\", \"Exact Ghost Tunnel route file\", \".ghosttunnel\")\n .option(\"--target-host <host>\", \"Local target host for .ghosttunnel ports\", \"127.0.0.1\")\n .action(async (options: ConfigCliOptions & { ghostConfig: string; targetHost: string }) => {\n assertLocalDevelopment(\"tunnel\");\n\n const context = await resolveLocalghostContext({\n cwd: options.cwd,\n ...(options.config && options.config.length > 0 ? { configFiles: options.config } : {}),\n ...(options.configPattern ? { configPattern: options.configPattern } : {}),\n dynamicPort: false\n });\n if (!context.ghostTunnel.enabled) {\n throw new Error(\"Ghost Tunnel is not enabled in localghost.config.mjs.\");\n }\n if (context.ghostTunnel.transport.kind !== \"tunnel\") {\n throw new Error(`Ghost Tunnel transport must be tunnel for localghost tunnel. Current: ${context.ghostTunnel.transport.kind}`);\n }\n\n const entries = listGhostTunnelEntries({\n cwd: options.cwd,\n fileName: options.ghostConfig\n });\n if (entries.length === 0) {\n throw new Error(`No exact Ghost Tunnel routes found in ${options.ghostConfig}.`);\n }\n\n const transport = context.ghostTunnel.transport;\n const store = createRedisGhostTunnelStoreFromEnv({\n namespace: transport.store.namespace\n });\n const controller = new AbortController();\n const stop = () => controller.abort();\n process.once(\"SIGINT\", stop);\n process.once(\"SIGTERM\", stop);\n\n const agent = startGhostTunnelAgent({\n entries,\n store,\n targetHost: options.targetHost,\n routeTtlSeconds: transport.routeTtlSeconds,\n requestTtlSeconds: transport.requestTtlSeconds,\n pollIntervalMs: transport.pollIntervalMs,\n maxResponseBodyBytes: transport.maxResponseBodyBytes,\n signal: controller.signal,\n log: (message) => console.log(message)\n });\n\n try {\n await agent.done;\n } finally {\n process.off(\"SIGINT\", stop);\n process.off(\"SIGTERM\", stop);\n }\n });\n\nprogram\n .command(\"ps\")\n .description(\"Show Localghost setups and currently running sessions\")\n .option(\"--json\", \"Print raw JSON\")\n .action(async (options: { json?: boolean }) => {\n const setups = listLocalghostSetups();\n const runs = listLocalghostRuns();\n const instances = await getInstanceViews(setups, runs);\n\n if (options.json) {\n console.log(JSON.stringify({ activityPath: getLocalghostActivityPath(), setups, runs, instances }, null, 2));\n return;\n }\n\n console.log(formatInstanceViews(instances));\n });\n\nprogram\n .command(\"print\")\n .description(\"Print parsed host config\")\n .option(\"--cwd <path>\", \"Project directory\", process.cwd())\n .option(\"--config <file>\", \"Config file to look for. Can be repeated.\", collect, [])\n .option(\"--config-pattern <regex>\", \"Regex for config filenames in the project root\")\n .action((options: ConfigCliOptions) => {\n const entries = readDevHosts(readOptionsFromCli(options));\n warnAboutLocalMdns(entries);\n console.log(JSON.stringify(entries, null, 2));\n });\n\nfunction readImplicitInvocation(args: string[]) {\n if (args.some((arg) => arg === \"--help\" || arg === \"-h\" || arg === \"--version\" || arg === \"-V\")) return null;\n\n let cwd = process.cwd();\n let dryRun = false;\n let updateCheck = true;\n const forwardedArgs: string[] = [];\n\n for (let index = 0; index < args.length; index += 1) {\n const arg = args[index];\n if (!arg) continue;\n if (arg === \"--dry-run\") {\n dryRun = true;\n continue;\n }\n if (arg === \"--no-update-check\") {\n updateCheck = false;\n continue;\n }\n if ([\"--clean-caddy\", \"--https\", \"--ssl\", \"--setup\", \"--trust\"].includes(arg)) {\n forwardedArgs.push(arg);\n continue;\n }\n if (arg === \"--auto-repair\" || arg === \"--dynamic-port\") {\n const value = args[index + 1];\n forwardedArgs.push(arg);\n if (value && !value.startsWith(\"--\")) {\n forwardedArgs.push(value);\n index += 1;\n }\n continue;\n }\n if (arg === \"--port\" || arg === \"--project\" || arg === \"--config\" || arg === \"--config-pattern\") {\n const value = args[index + 1];\n if (!value) throw new Error(`${arg} requires a value.`);\n forwardedArgs.push(arg, value);\n index += 1;\n continue;\n }\n if ([\"--auto-repair=\", \"--dynamic-port=\", \"--port=\", \"--project=\", \"--config=\", \"--config-pattern=\"].some((prefix) => arg.startsWith(prefix))) {\n forwardedArgs.push(arg);\n continue;\n }\n if (arg === \"--cwd\") {\n const value = args[index + 1];\n if (!value) throw new Error(\"--cwd requires a path.\");\n cwd = value;\n index += 1;\n continue;\n }\n if (arg.startsWith(\"--cwd=\")) {\n cwd = arg.slice(\"--cwd=\".length);\n continue;\n }\n return null;\n }\n\n return { cwd, dryRun, updateCheck, forwardedArgs };\n}\n\nfunction hasForwardedFlag(args: string[], ...flags: string[]) {\n return args.some((arg) => flags.includes(arg));\n}\n\nfunction forwardedBoolean(args: string[], name: string) {\n const inline = args.find((arg) => arg.startsWith(`${name}=`));\n if (inline) return parseBooleanLike(inline.slice(name.length + 1));\n return args.includes(name) ? true : undefined;\n}\n\nasync function main() {\n const implicit = readImplicitInvocation(process.argv.slice(2));\n if (!implicit) {\n await program.parseAsync();\n return;\n }\n\n const projectConfig = await readLocalghostProjectConfig({ cwd: implicit.cwd });\n printLocalghostBanner();\n if (projectConfig.config.services) {\n if (!projectConfig.path) throw new Error(\"Multi-service configuration must come from localghost.config.mjs.\");\n const services = detectDevServices({\n cwd: implicit.cwd,\n services: projectConfig.config.services\n });\n console.log(formatDetectedDevServices(services));\n if (implicit.dryRun) return;\n\n if (hasForwardedFlag(implicit.forwardedArgs, \"--clean-caddy\")) cleanManagedCaddyProcesses();\n\n await runDetectedServices({\n cwd: implicit.cwd,\n services,\n configPath: projectConfig.path,\n projectName: sanitizeProjectName(projectConfig.config.project ?? getProjectName(implicit.cwd)),\n https: hasForwardedFlag(implicit.forwardedArgs, \"--https\", \"--ssl\") || (projectConfig.config.https ?? false),\n dynamicPort: forwardedBoolean(implicit.forwardedArgs, \"--dynamic-port\") ?? projectConfig.config.dynamicPort ?? true,\n autoRepair: forwardedBoolean(implicit.forwardedArgs, \"--auto-repair\") ?? projectConfig.config.autoRepair ?? true\n });\n await maybeNotifyAboutUpdate({ disabled: !implicit.updateCheck });\n return;\n }\n\n const detected = detectDevCommand({\n cwd: implicit.cwd,\n ...(projectConfig.config.command ? { command: projectConfig.config.command } : {})\n });\n console.log(`Localghost detected: ${formatDetectedDevCommand(detected)}`);\n\n if (implicit.dryRun) return;\n\n await program.parseAsync([\n process.argv[0] ?? process.execPath,\n process.argv[1] ?? \"localghost\",\n ...(implicit.updateCheck ? [] : [\"--no-update-check\"]),\n \"run\",\n ...implicit.forwardedArgs,\n \"--cwd\",\n implicit.cwd,\n \"--\",\n ...detected.command\n ]);\n}\n\nmain()\n .then(() => {\n process.exit(process.exitCode ?? 0);\n })\n .catch((error: unknown) => {\n const message = error instanceof Error ? error.message : String(error);\n console.error(message);\n process.exit(1);\n });\n","import { existsSync, mkdirSync, readFileSync, writeFileSync } from \"node:fs\";\nimport { homedir } from \"node:os\";\nimport { dirname, join } from \"node:path\";\nimport type { DevHostEntry } from \"./parse.js\";\n\nexport const LOCALGHOST_ACTIVITY_VERSION = 1;\n\nexport type LocalghostRunMode = \"dev\" | \"run\" | \"vite\";\n\nexport type LocalghostRunRecord = {\n id: string;\n mode: LocalghostRunMode;\n pid: number;\n cwd: string;\n projectName: string;\n startedAt: string;\n updatedAt: string;\n configPath?: string;\n caddyfilePath?: string;\n caddyPid?: number;\n caddyPgid?: number;\n childPid?: number;\n childCommand?: string[];\n https?: boolean;\n requestedPort?: number;\n port?: number;\n dynamicPort?: boolean;\n entries: DevHostEntry[];\n};\n\nexport type LocalghostSetupRecord = {\n id: string;\n cwd: string;\n projectName: string;\n updatedAt: string;\n configPath?: string;\n caddyfilePath?: string;\n https?: boolean;\n entries: DevHostEntry[];\n};\n\nexport type LocalghostActivity = {\n version: typeof LOCALGHOST_ACTIVITY_VERSION;\n runs: LocalghostRunRecord[];\n setups: LocalghostSetupRecord[];\n};\n\nexport type RegisterLocalghostRunInput = Omit<LocalghostRunRecord, \"id\" | \"pid\" | \"startedAt\" | \"updatedAt\"> & {\n id?: string;\n pid?: number;\n startedAt?: string;\n};\n\nexport type RegisterLocalghostSetupInput = Omit<LocalghostSetupRecord, \"id\" | \"updatedAt\"> & {\n id?: string;\n};\n\nexport function getLocalghostActivityPath(env: NodeJS.ProcessEnv = process.env) {\n if (env.LOCALGHOST_ACTIVITY_PATH) return env.LOCALGHOST_ACTIVITY_PATH;\n\n const stateRoot = env.XDG_STATE_HOME || join(homedir(), \".local/state\");\n return join(stateRoot, \"localghost\", \"activity.json\");\n}\n\nexport function isProcessRunning(pid: number) {\n if (!Number.isInteger(pid) || pid < 1) return false;\n\n try {\n process.kill(pid, 0);\n return true;\n } catch (error) {\n const code = typeof error === \"object\" && error !== null && \"code\" in error ? error.code : undefined;\n return code === \"EPERM\";\n }\n}\n\nfunction emptyActivity(): LocalghostActivity {\n return { version: LOCALGHOST_ACTIVITY_VERSION, runs: [], setups: [] };\n}\n\nexport function readLocalghostActivity(path = getLocalghostActivityPath()): LocalghostActivity {\n if (!existsSync(path)) return emptyActivity();\n\n try {\n const parsed = JSON.parse(readFileSync(path, \"utf8\")) as Partial<LocalghostActivity>;\n return {\n version: LOCALGHOST_ACTIVITY_VERSION,\n runs: Array.isArray(parsed.runs) ? parsed.runs : [],\n setups: Array.isArray(parsed.setups) ? parsed.setups : []\n };\n } catch {\n return emptyActivity();\n }\n}\n\nexport function writeLocalghostActivity(activity: LocalghostActivity, path = getLocalghostActivityPath()) {\n mkdirSync(dirname(path), { recursive: true });\n writeFileSync(path, `${JSON.stringify(activity, null, 2)}\\n`, \"utf8\");\n return path;\n}\n\nfunction createRunId(input: Pick<RegisterLocalghostRunInput, \"mode\" | \"cwd\" | \"projectName\">, pid: number) {\n return `${input.projectName}:${input.mode}:${pid}:${Date.now()}`;\n}\n\nfunction createSetupId(input: Pick<RegisterLocalghostSetupInput, \"cwd\" | \"projectName\" | \"configPath\">) {\n return `${input.projectName}:${input.cwd}:${input.configPath ?? \"\"}`;\n}\n\nexport function pruneLocalghostActivity(path = getLocalghostActivityPath()) {\n const activity = readLocalghostActivity(path);\n const activeRuns = activity.runs.filter((run) => isProcessRunning(run.pid));\n const pruned = activeRuns.length !== activity.runs.length;\n\n if (pruned) {\n writeLocalghostActivity({ ...activity, version: LOCALGHOST_ACTIVITY_VERSION, runs: activeRuns }, path);\n }\n\n return {\n path,\n pruned,\n runs: activeRuns,\n setups: activity.setups\n };\n}\n\nexport function listLocalghostRuns(path = getLocalghostActivityPath()) {\n return pruneLocalghostActivity(path).runs;\n}\n\nexport function listLocalghostSetups(path = getLocalghostActivityPath()) {\n return pruneLocalghostActivity(path).setups;\n}\n\nexport function registerLocalghostRun(input: RegisterLocalghostRunInput, path = getLocalghostActivityPath()) {\n const now = new Date().toISOString();\n const pid = input.pid ?? process.pid;\n const record: LocalghostRunRecord = {\n id: input.id ?? createRunId(input, pid),\n mode: input.mode,\n pid,\n cwd: input.cwd,\n projectName: input.projectName,\n startedAt: input.startedAt ?? now,\n updatedAt: now,\n ...(input.configPath ? { configPath: input.configPath } : {}),\n ...(input.caddyfilePath ? { caddyfilePath: input.caddyfilePath } : {}),\n ...(input.caddyPid ? { caddyPid: input.caddyPid } : {}),\n ...(input.caddyPgid ? { caddyPgid: input.caddyPgid } : {}),\n ...(input.childPid ? { childPid: input.childPid } : {}),\n ...(input.childCommand ? { childCommand: input.childCommand } : {}),\n ...(typeof input.https === \"boolean\" ? { https: input.https } : {}),\n ...(input.requestedPort ? { requestedPort: input.requestedPort } : {}),\n ...(input.port ? { port: input.port } : {}),\n ...(typeof input.dynamicPort === \"boolean\" ? { dynamicPort: input.dynamicPort } : {}),\n entries: input.entries\n };\n const current = pruneLocalghostActivity(path).runs.filter((run) => run.id !== record.id);\n const activity = readLocalghostActivity(path);\n writeLocalghostActivity({ version: LOCALGHOST_ACTIVITY_VERSION, runs: [...current, record], setups: activity.setups }, path);\n return record;\n}\n\nexport function registerLocalghostSetup(input: RegisterLocalghostSetupInput, path = getLocalghostActivityPath()) {\n const record: LocalghostSetupRecord = {\n id: input.id ?? createSetupId(input),\n cwd: input.cwd,\n projectName: input.projectName,\n updatedAt: new Date().toISOString(),\n ...(input.configPath ? { configPath: input.configPath } : {}),\n ...(input.caddyfilePath ? { caddyfilePath: input.caddyfilePath } : {}),\n ...(typeof input.https === \"boolean\" ? { https: input.https } : {}),\n entries: input.entries\n };\n const activity = pruneLocalghostActivity(path);\n const setups = activity.setups.filter((setup) => setup.id !== record.id);\n writeLocalghostActivity({ version: LOCALGHOST_ACTIVITY_VERSION, runs: activity.runs, setups: [...setups, record] }, path);\n return record;\n}\n\nexport function unregisterLocalghostRun(id: string, path = getLocalghostActivityPath()) {\n const activity = readLocalghostActivity(path);\n const runs = activity.runs.filter((run) => run.id !== id);\n\n if (runs.length !== activity.runs.length) {\n writeLocalghostActivity({ ...activity, version: LOCALGHOST_ACTIVITY_VERSION, runs }, path);\n }\n}\n\nexport function unregisterLocalghostSetup(options: { cwd: string; projectName?: string; configPath?: string }, path = getLocalghostActivityPath()) {\n const activity = readLocalghostActivity(path);\n const setups = activity.setups.filter((setup) => {\n if (setup.cwd !== options.cwd) return true;\n if (options.projectName && setup.projectName !== options.projectName) return true;\n if (options.configPath && setup.configPath !== options.configPath) return true;\n return false;\n });\n\n if (setups.length !== activity.setups.length) {\n writeLocalghostActivity({ ...activity, version: LOCALGHOST_ACTIVITY_VERSION, setups }, path);\n }\n}\n","import { existsSync, readFileSync, readdirSync } from \"node:fs\";\nimport { basename, join, resolve } from \"node:path\";\nimport { parseDevHosts } from \"./parse.js\";\n\nexport const LOCALGHOST_CONFIG_FILE = \".localghost\";\n\nexport type ConfigPattern = string | RegExp;\n\nexport type ReadDevHostsOptions = {\n cwd?: string;\n fileName?: string;\n configFiles?: string[];\n configPattern?: ConfigPattern;\n};\n\nexport type ResolvedDevHostsPath = {\n path: string;\n fileName: string;\n exists: boolean;\n searchedFiles: string[];\n configPattern?: ConfigPattern;\n};\n\nfunction unique(values: string[]) {\n return [...new Set(values.filter(Boolean))];\n}\n\nfunction toRegExp(pattern: ConfigPattern) {\n return typeof pattern === \"string\" ? new RegExp(pattern) : pattern;\n}\n\nfunction findPatternMatches(cwd: string, pattern: ConfigPattern) {\n const matcher = toRegExp(pattern);\n\n return readdirSync(cwd, { withFileTypes: true })\n .filter((entry) => entry.isFile())\n .map((entry) => entry.name)\n .filter((name) => {\n matcher.lastIndex = 0;\n return matcher.test(name);\n })\n .sort();\n}\n\nexport function getConfigFileCandidates(options: ReadDevHostsOptions = {}) {\n const cwd = options.cwd ?? process.cwd();\n const exactFiles = unique([\n ...(options.fileName ? [options.fileName] : []),\n ...(options.configFiles ?? [])\n ]);\n const patternFiles = options.configPattern ? findPatternMatches(cwd, options.configPattern) : [];\n const candidates = unique([...exactFiles, ...patternFiles]);\n\n if (candidates.length > 0) return candidates;\n if (exactFiles.length > 0 || options.configPattern) return [];\n return [LOCALGHOST_CONFIG_FILE];\n}\n\nexport function resolveDevHostsPath(options: ReadDevHostsOptions = {}): ResolvedDevHostsPath {\n const cwd = options.cwd ?? process.cwd();\n const searchedFiles = getConfigFileCandidates(options);\n\n for (const fileName of searchedFiles) {\n const path = resolve(cwd, fileName);\n if (existsSync(path)) {\n return {\n path,\n fileName: basename(fileName),\n exists: true,\n searchedFiles,\n ...(options.configPattern ? { configPattern: options.configPattern } : {})\n };\n }\n }\n\n const fileName = searchedFiles[0] ?? LOCALGHOST_CONFIG_FILE;\n\n return {\n path: resolve(cwd, fileName),\n fileName: basename(fileName),\n exists: false,\n searchedFiles,\n ...(options.configPattern ? { configPattern: options.configPattern } : {})\n };\n}\n\nexport function getDevHostsPath(options: ReadDevHostsOptions = {}) {\n return resolveDevHostsPath(options).path;\n}\n\nfunction formatSearchedFiles(files: string[], pattern?: ConfigPattern) {\n if (files.length > 0) return files.map((file) => `\\`${file}\\``).join(\", \");\n if (pattern) return `files matching ${pattern.toString()}`;\n return `\\`${LOCALGHOST_CONFIG_FILE}\\``;\n}\n\nexport function readDevHosts(options: ReadDevHostsOptions | string = {}) {\n const resolvedOptions = typeof options === \"string\" ? { cwd: options } : options;\n const resolvedPath = resolveDevHostsPath(resolvedOptions);\n\n if (!resolvedPath.exists) {\n const cwd = resolvedOptions.cwd ?? process.cwd();\n throw new Error(\n `Missing Localghost config in ${cwd}. Looked for ${formatSearchedFiles(resolvedPath.searchedFiles, resolvedPath.configPattern)}. Run \\`localghost init\\` or pass --config/--config-pattern.`\n );\n }\n\n return parseDevHosts(readFileSync(resolvedPath.path, \"utf8\"), resolvedPath.fileName);\n}\n\nexport function getProjectName(cwd = process.cwd()) {\n try {\n const pkg = JSON.parse(readFileSync(join(cwd, \"package.json\"), \"utf8\")) as { name?: unknown };\n const name = typeof pkg.name === \"string\" && pkg.name ? pkg.name : \"app\";\n return sanitizeProjectName(name.replace(/^@/, \"\"));\n } catch {\n return \"app\";\n }\n}\n\nexport function sanitizeProjectName(value: string) {\n const sanitized = value.replace(/[^\\w.-]+/g, \"-\");\n let start = 0;\n let end = sanitized.length;\n\n while (start < end && sanitized.charCodeAt(start) === 45) start += 1;\n while (end > start && sanitized.charCodeAt(end - 1) === 45) end -= 1;\n\n const projectName = sanitized.slice(start, end);\n return projectName || \"app\";\n}\n","export type DevHostEntry = {\n host: string;\n port: number;\n target: string;\n};\n\nconst HOST_PATTERN = /^(?=.{1,253}$)(?!-)[a-z0-9-]+(\\.[a-z0-9-]+)*\\.?$/i;\n\nexport function parseDevHosts(input: string, fileName = \".localghost\"): DevHostEntry[] {\n const entries: DevHostEntry[] = [];\n\n input.split(/\\r?\\n/).forEach((rawLine, index) => {\n const line = rawLine.replace(/#.*/, \"\").trim();\n\n if (!line) {\n return;\n }\n\n const parts = line.split(/\\s+/);\n const host = parts[0];\n const portRaw = parts[1];\n\n if (!host || !portRaw || parts.length > 2) {\n throw new Error(`Invalid ${fileName} line ${index + 1}: \"${rawLine}\"`);\n }\n\n if (!HOST_PATTERN.test(host)) {\n throw new Error(`Invalid host on line ${index + 1}: \"${host}\"`);\n }\n\n const port = Number(portRaw);\n\n if (!Number.isInteger(port) || port < 1 || port > 65535) {\n throw new Error(`Invalid port on line ${index + 1}: \"${portRaw}\"`);\n }\n\n entries.push({\n host: host.toLowerCase().replace(/\\.$/, \"\"),\n port,\n target: `127.0.0.1:${port}`\n });\n });\n\n return entries;\n}\n\nexport function findLocalMdnsHosts(entries: DevHostEntry[]): string[] {\n return [...new Set(entries.map((entry) => entry.host).filter((host) => host.endsWith(\".local\")))];\n}\n","export function renderLocalghostBanner() {\n return [\n \" .-.\",\n \" (o o) LOCALGHOST\",\n \" | O \\\\ friendly local domains\",\n \" \\\\ \\\\\",\n \" `~~~'\"\n ].join(\"\\n\");\n}\n\nexport function renderCompactLocalghostBanner() {\n return [\n \" .--.\",\n \" ( oo ) localghost\",\n \" \\\\__/ friendly local domains\"\n ].join(\"\\n\");\n}\n","import { dirname, join } from \"node:path\";\nimport { execa } from \"execa\";\nimport { writeTextFile } from \"./fs.js\";\nimport type { DevHostEntry } from \"./parse.js\";\n\nexport type CaddyModeOptions = {\n https?: boolean;\n};\n\nexport type CaddyProcessStopResult = {\n stopped: number[];\n alreadyExited: number[];\n failed: Array<{ pid: number; error: unknown }>;\n};\n\nexport type CaddyProcessKiller = (pid: number, signal: NodeJS.Signals) => void;\n\nfunction shouldShowCaddyLogs() {\n return [\"1\", \"true\", \"yes\", \"on\"].includes((process.env.LOCALGHOST_CADDY_VERBOSE ?? \"\").toLowerCase());\n}\n\nfunction caddyStdio() {\n return shouldShowCaddyLogs() ? \"inherit\" as const : \"pipe\" as const;\n}\n\nfunction groupByPort(entries: DevHostEntry[]) {\n const groups = new Map<number, DevHostEntry[]>();\n\n for (const entry of entries) {\n const group = groups.get(entry.port) ?? [];\n group.push(entry);\n groups.set(entry.port, group);\n }\n\n return groups;\n}\n\nexport function getCaddyfilePath(cwd = process.cwd()) {\n return join(cwd, \"ops/local/Caddyfile\");\n}\n\nexport function renderCaddyfile(entries: DevHostEntry[], options: CaddyModeOptions = {}) {\n const groups = groupByPort(entries);\n const https = options.https === true;\n const blocks = [...groups.entries()]\n .sort(([leftPort], [rightPort]) => leftPort - rightPort)\n .map(([port, group]) => {\n const hosts = group\n .map((entry) => (https ? entry.host : `http://${entry.host}`))\n .sort()\n .join(\", \");\n\n return `${hosts} {\n\\treverse_proxy 127.0.0.1:${port}\n}`;\n });\n\n const globalOptions = https\n ? `{\n local_certs\n}\n\n`\n : \"\";\n\n return `${globalOptions}${blocks.join(\"\\n\\n\")}\n`;\n}\n\nexport async function writeCaddyfile(entries: DevHostEntry[], cwd = process.cwd(), options: CaddyModeOptions = {}) {\n const path = getCaddyfilePath(cwd);\n writeTextFile(path, renderCaddyfile(entries, options));\n return path;\n}\n\nexport async function validateCaddyfile(path: string) {\n await execa(\"caddy\", [\"validate\", \"--config\", path], {\n cwd: dirname(path),\n stdio: caddyStdio()\n });\n}\n\nexport async function runCaddy(path: string) {\n await execa(\"caddy\", [\"run\", \"--config\", path], {\n cwd: dirname(path),\n stdio: caddyStdio()\n });\n}\n\nexport function startCaddy(path: string) {\n return execa(\"caddy\", [\"run\", \"--config\", path], {\n cwd: dirname(path),\n stdio: caddyStdio(),\n detached: process.platform !== \"win32\"\n });\n}\n\nexport function stopCaddyProcesses(\n pids: Iterable<number>,\n killProcess: CaddyProcessKiller = (pid, signal) => process.kill(pid, signal)\n): CaddyProcessStopResult {\n const result: CaddyProcessStopResult = {\n stopped: [],\n alreadyExited: [],\n failed: []\n };\n\n for (const pid of new Set(pids)) {\n try {\n killProcess(pid, \"SIGINT\");\n result.stopped.push(pid);\n } catch (error) {\n if (error instanceof Error && \"code\" in error && error.code === \"ESRCH\") {\n result.alreadyExited.push(pid);\n } else {\n result.failed.push({ pid, error });\n }\n }\n }\n\n return result;\n}\n\nexport async function trustCaddy(path: string) {\n await execa(\"caddy\", [\"trust\", \"--config\", path], {\n cwd: dirname(path),\n stdio: \"inherit\"\n });\n}\n","import { mkdirSync, readFileSync, writeFileSync } from \"node:fs\";\nimport { dirname } from \"node:path\";\n\nexport function readTextFile(path: string) {\n return readFileSync(path, \"utf8\");\n}\n\nexport function writeTextFile(path: string, value: string) {\n mkdirSync(dirname(path), { recursive: true });\n writeFileSync(path, value, \"utf8\");\n return path;\n}\n","import { existsSync, readFileSync } from \"node:fs\";\nimport { isAbsolute, join, relative, resolve } from \"node:path\";\n\nexport type LocalghostPackageManager = \"npm\" | \"pnpm\" | \"yarn\" | \"bun\";\n\nexport type DetectedDevCommand = {\n command: string[];\n source: \"config\" | \"script\";\n packageManager?: LocalghostPackageManager;\n script?: string;\n};\n\nexport type LocalghostServiceOptions = {\n name: string;\n cwd: string;\n host: string;\n port: number;\n command?: string[];\n};\n\nexport type DetectedDevService = {\n name: string;\n cwd: string;\n relativeCwd: string;\n host: string;\n requestedPort: number;\n command: string[];\n commandSource: DetectedDevCommand[\"source\"];\n};\n\ntype PackageJson = {\n packageManager?: unknown;\n scripts?: unknown;\n};\n\nfunction readPackageJson(cwd: string): PackageJson {\n const path = join(cwd, \"package.json\");\n if (!existsSync(path)) {\n throw new Error(`No package.json found in ${cwd}. Pass an explicit command with \\`localghost run -- <command>\\`.`);\n }\n\n try {\n return JSON.parse(readFileSync(path, \"utf8\")) as PackageJson;\n } catch {\n throw new Error(`Could not parse ${path}.`);\n }\n}\n\nexport function detectDevPackageManager(cwd: string, packageManager: unknown): LocalghostPackageManager {\n if (typeof packageManager === \"string\") {\n const name = packageManager.split(\"@\")[0];\n if (name === \"npm\" || name === \"pnpm\" || name === \"yarn\" || name === \"bun\") return name;\n }\n\n if (existsSync(join(cwd, \"pnpm-lock.yaml\"))) return \"pnpm\";\n if (existsSync(join(cwd, \"yarn.lock\"))) return \"yarn\";\n if (existsSync(join(cwd, \"bun.lock\")) || existsSync(join(cwd, \"bun.lockb\"))) return \"bun\";\n return \"npm\";\n}\n\nfunction scriptCommand(packageManager: LocalghostPackageManager, script: string) {\n if (packageManager === \"yarn\") return [\"yarn\", script];\n return [packageManager, \"run\", script];\n}\n\nfunction invokesLocalghost(script: string) {\n return /(^|[\\s;&|])(?:npm\\s+exec\\s+|pnpm\\s+exec\\s+|bunx\\s+|npx\\s+)?localghost(?:\\s|$)/.test(script);\n}\n\nexport function detectDevCommand(options: {\n cwd?: string;\n command?: string[];\n} = {}): DetectedDevCommand {\n const cwd = options.cwd ?? process.cwd();\n\n if (options.command) {\n if (options.command.length === 0 || options.command.some((part) => typeof part !== \"string\" || part.length === 0)) {\n throw new Error(\"localghost.config.mjs command must be a non-empty array of strings.\");\n }\n if (invokesLocalghost(options.command.join(\" \"))) {\n throw new Error(\"localghost.config.mjs command cannot invoke Localghost recursively.\");\n }\n return { command: [...options.command], source: \"config\" };\n }\n\n const pkg = readPackageJson(cwd);\n const scripts = typeof pkg.scripts === \"object\" && pkg.scripts ? pkg.scripts as Record<string, unknown> : {};\n const packageManager = detectDevPackageManager(cwd, pkg.packageManager);\n\n for (const script of [\"dev:raw\", \"dev\"]) {\n const value = scripts[script];\n if (typeof value !== \"string\" || invokesLocalghost(value)) continue;\n return {\n command: scriptCommand(packageManager, script),\n source: \"script\",\n packageManager,\n script\n };\n }\n\n throw new Error([\n `Could not detect a safe development command in ${join(cwd, \"package.json\")}.`,\n \"Add a non-recursive dev or dev:raw script, configure command in localghost.config.mjs,\",\n \"or pass an explicit command with `localghost run -- <command>`.\"\n ].join(\" \"));\n}\n\nexport function formatDetectedDevCommand(detected: DetectedDevCommand) {\n const command = detected.command.map((part) => (\n /^[A-Za-z0-9_./:@=-]+$/.test(part) ? part : JSON.stringify(part)\n )).join(\" \");\n const source = detected.source === \"config\"\n ? \"localghost.config.mjs\"\n : `package.json#scripts.${detected.script}`;\n return `${command} (${source})`;\n}\n\nfunction assertServicePath(root: string, serviceCwd: string, name: string) {\n const cwd = resolve(root, serviceCwd);\n const relativeCwd = relative(root, cwd);\n if (isAbsolute(relativeCwd) || relativeCwd === \"..\" || relativeCwd.startsWith(`..${process.platform === \"win32\" ? \"\\\\\" : \"/\"}`)) {\n throw new Error(`Service ${name} cwd must stay inside the project root.`);\n }\n return { cwd, relativeCwd: relativeCwd || \".\" };\n}\n\nexport function detectDevServices(options: {\n cwd?: string;\n services: LocalghostServiceOptions[];\n}) {\n const root = options.cwd ?? process.cwd();\n if (options.services.length === 0) throw new Error(\"services must contain at least one service.\");\n\n const names = new Set<string>();\n const hosts = new Set<string>();\n\n return options.services.map((service, index): DetectedDevService => {\n if (!service || typeof service !== \"object\") throw new Error(`Service at index ${index} must be an object.`);\n if (!service.name || names.has(service.name)) throw new Error(`Service name must be unique: ${service.name || `<index ${index}>`}.`);\n if (!/^[a-zA-Z0-9][a-zA-Z0-9_-]*$/.test(service.name)) throw new Error(`Invalid service name: ${service.name}.`);\n if (!service.host || hosts.has(service.host)) throw new Error(`Service host must be unique: ${service.host || `<index ${index}>`}.`);\n if (!Number.isInteger(service.port) || service.port < 1 || service.port > 65_535) {\n throw new Error(`Invalid port for service ${service.name}: ${service.port}.`);\n }\n\n names.add(service.name);\n hosts.add(service.host);\n const path = assertServicePath(root, service.cwd, service.name);\n const detected = detectDevCommand({\n cwd: path.cwd,\n ...(service.command ? { command: service.command } : {})\n });\n\n return {\n name: service.name,\n ...path,\n host: service.host,\n requestedPort: service.port,\n command: detected.command,\n commandSource: detected.source\n };\n });\n}\n\nexport function formatDetectedDevServices(services: DetectedDevService[]) {\n return [\n `Localghost detected ${services.length} services:`,\n ...services.map((service) => (\n `${service.name}: ${service.command.map((part) => (\n /^[A-Za-z0-9_./:@=-]+$/.test(part) ? part : JSON.stringify(part)\n )).join(\" \")} (${service.relativeCwd}, ${service.host} -> ${service.requestedPort})`\n ))\n ].join(\"\\n\");\n}\n","import { existsSync, readFileSync } from \"node:fs\";\nimport { join } from \"node:path\";\nimport { pathToFileURL } from \"node:url\";\nimport {\n getProjectName,\n readDevHosts,\n resolveDevHostsPath,\n sanitizeProjectName,\n type ConfigPattern,\n type ReadDevHostsOptions\n} from \"./config.js\";\nimport { findAvailablePort } from \"./port.js\";\nimport { createLocalghostRegistry } from \"./registry.js\";\nimport type { DevHostEntry } from \"./parse.js\";\nimport type { LocalghostServiceOptions } from \"./command.js\";\nimport { resolveGhostTunnelConfig, type GhostTunnelConfig, type GhostTunnelOptions } from \"./tunnel.js\";\n\nexport type LocalghostContextOptions = {\n cwd?: string;\n project?: string;\n localghostConfig?: string | false;\n fileName?: string;\n configFiles?: string[];\n configPattern?: ConfigPattern;\n port?: number;\n https?: boolean;\n bindHost?: string | boolean;\n primaryHost?: string;\n dynamicPort?: boolean;\n reservePort?: boolean;\n instanceKey?: string;\n reservedPorts?: Iterable<number>;\n registryOwnerToken?: string;\n autoRepair?: boolean;\n command?: string[];\n services?: LocalghostServiceOptions[];\n wwwAlias?: boolean;\n ghostTunnel?: GhostTunnelOptions;\n};\n\nexport type LocalghostContext = {\n cwd: string;\n projectName: string;\n readOptions: ReadDevHostsOptions;\n configPath: string;\n configFileName: string;\n configEntries: DevHostEntry[];\n entries: DevHostEntry[];\n hosts: string[];\n requestedPort: number;\n port: number;\n dynamicPort: boolean;\n autoRepair: boolean;\n bindHost: string | boolean;\n primaryHost: string;\n https: boolean;\n wwwAlias: boolean;\n ghostTunnel: GhostTunnelConfig;\n projectConfigPath?: string;\n releasePort?: () => Promise<boolean>;\n};\n\nexport type LocalghostProjectConfig = Omit<LocalghostContextOptions, \"cwd\" | \"localghostConfig\">;\n\nexport type LocalghostProjectConfigResult = {\n config: LocalghostProjectConfig;\n path?: string;\n};\n\nconst LOCALGHOST_PROJECT_CONFIG_FILES = [\n \"localghost.config.mjs\",\n \"localghost.config.js\",\n \"localghost.config.cjs\"\n];\n\nfunction parsePort(value: string | undefined) {\n if (!value) return undefined;\n const port = Number.parseInt(value, 10);\n return Number.isInteger(port) && port > 0 && port <= 65535 ? port : undefined;\n}\n\nfunction envPort() {\n return parsePort(process.env.LOCALGHOST_PORT) ?? parsePort(process.env.VITE_PORT);\n}\n\nfunction envDynamicPort() {\n const value = process.env.LOCALGHOST_DYNAMIC_PORT;\n if (!value) return undefined;\n return [\"1\", \"true\", \"yes\", \"on\"].includes(value.toLowerCase());\n}\n\nfunction envHttps() {\n const value = process.env.LOCALGHOST_HTTPS;\n if (!value) return undefined;\n return [\"1\", \"true\", \"yes\", \"on\"].includes(value.toLowerCase());\n}\n\nfunction getPackageName(cwd: string) {\n try {\n const pkg = JSON.parse(readFileSync(join(cwd, \"package.json\"), \"utf8\")) as { name?: unknown };\n return typeof pkg.name === \"string\" ? pkg.name : undefined;\n } catch {\n return undefined;\n }\n}\n\nfunction getPackageOwner(cwd: string) {\n const packageName = getPackageName(cwd);\n if (!packageName?.startsWith(\"@\")) return undefined;\n return packageName.slice(1).split(\"/\")[0];\n}\n\nfunction getLocalOwner(cwd: string) {\n return sanitizeProjectName(process.env.LOCALGHOST_OWNER ?? getPackageOwner(cwd) ?? process.env.USER ?? process.env.USERNAME ?? \"local\");\n}\n\nfunction getRouteName(primaryHost: string, fallback: string) {\n return sanitizeProjectName(primaryHost.split(\".\")[0] ?? fallback);\n}\n\nfunction readOptionsFromContext(options: LocalghostContextOptions): ReadDevHostsOptions {\n return {\n cwd: options.cwd ?? process.cwd(),\n ...(options.fileName ? { fileName: options.fileName } : {}),\n ...(options.configFiles ? { configFiles: options.configFiles } : {}),\n ...(options.configPattern ? { configPattern: options.configPattern } : {})\n };\n}\n\nfunction withRuntimePort(entries: DevHostEntry[], requestedPort: number, port: number) {\n if (requestedPort === port) return entries;\n\n const hasRequestedPort = entries.some((entry) => entry.port === requestedPort);\n if (!hasRequestedPort) return entries;\n\n return entries.map((entry) => (\n entry.port === requestedPort\n ? { ...entry, port, target: `127.0.0.1:${port}` }\n : entry\n ));\n}\n\nfunction uniqueHosts(entries: DevHostEntry[]) {\n return [...new Set(entries.map((entry) => entry.host))];\n}\n\nfunction isAliasableHost(host: string) {\n return host.includes(\".\") && !host.startsWith(\"www.\") && !host.includes(\":\");\n}\n\nexport function getDefaultWwwAlias(host: string) {\n return isAliasableHost(host) ? `www.${host}` : null;\n}\n\nexport function addDefaultWwwAliases(entries: DevHostEntry[]) {\n const seen = new Set(entries.map((entry) => entry.host));\n const aliases: DevHostEntry[] = [];\n\n for (const entry of entries) {\n const alias = getDefaultWwwAlias(entry.host);\n if (alias && !seen.has(alias)) {\n aliases.push({ host: alias, port: entry.port, target: `127.0.0.1:${entry.port}` });\n seen.add(alias);\n }\n }\n\n return [...entries, ...aliases];\n}\n\nfunction defined<T extends Record<string, unknown>>(input: T) {\n return Object.fromEntries(Object.entries(input).filter(([, value]) => typeof value !== \"undefined\")) as Partial<T>;\n}\n\nexport async function readLocalghostProjectConfig(options: {\n cwd?: string;\n configFile?: string | false;\n} = {}): Promise<LocalghostProjectConfigResult> {\n const cwd = options.cwd ?? process.cwd();\n if (options.configFile === false) return { config: {} };\n\n const candidates = options.configFile ? [options.configFile] : LOCALGHOST_PROJECT_CONFIG_FILES;\n const path = candidates.map((candidate) => resolveDevHostsPath({ cwd, fileName: candidate }).path).find((candidate) => existsSync(candidate));\n if (!path) return { config: {} };\n\n const imported = await import(`${pathToFileURL(path).href}?localghost=${Date.now()}`);\n const config = (imported.default ?? imported) as LocalghostProjectConfig;\n\n return { config, path };\n}\n\nexport function defineLocalghostConfig<T extends LocalghostContextOptions>(config: T) {\n return config;\n}\n\nexport async function resolveLocalghostContext(options: LocalghostContextOptions = {}): Promise<LocalghostContext> {\n const cwd = options.cwd ?? process.cwd();\n const projectConfig = await readLocalghostProjectConfig({\n cwd,\n ...(typeof options.localghostConfig !== \"undefined\" ? { configFile: options.localghostConfig } : {})\n });\n const merged = {\n ...projectConfig.config,\n ...defined(options)\n } as LocalghostContextOptions;\n const readOptions = readOptionsFromContext({ ...merged, cwd });\n const resolvedPath = resolveDevHostsPath(readOptions);\n const configEntries = readDevHosts(readOptions);\n const requestedPort = merged.port ?? envPort() ?? configEntries[0]?.port ?? 5173;\n const dynamicPort = merged.dynamicPort ?? envDynamicPort() ?? true;\n const autoRepair = merged.autoRepair ?? true;\n const bindHost = merged.bindHost ?? \"127.0.0.1\";\n const probeHost = typeof bindHost === \"string\" ? bindHost : \"127.0.0.1\";\n let port = requestedPort;\n let releasePort: (() => Promise<boolean>) | undefined;\n const reservePort = merged.reservePort ?? false;\n const instanceKey = merged.instanceKey ?? \"run\";\n if (reservePort && dynamicPort) {\n const registry = createLocalghostRegistry({ cwd, ...(merged.registryOwnerToken ? { ownerToken: merged.registryOwnerToken } : {}) });\n const lease = await registry.acquirePort({\n projectCwd: cwd,\n instanceKey,\n startPort: requestedPort,\n host: probeHost,\n ...(options.reservedPorts ? { reservedPorts: options.reservedPorts } : {})\n });\n port = lease.port;\n releasePort = () => registry.releasePort({ projectCwd: cwd, instanceKey });\n } else if (dynamicPort) {\n port = await findAvailablePort(requestedPort, { host: probeHost });\n }\n const wwwAlias = merged.wwwAlias ?? true;\n const entries = wwwAlias\n ? addDefaultWwwAliases(withRuntimePort(configEntries, requestedPort, port))\n : withRuntimePort(configEntries, requestedPort, port);\n const hosts = uniqueHosts(entries);\n const primaryHost =\n merged.primaryHost ??\n entries.find((entry) => entry.port === port)?.host ??\n hosts[0] ??\n `${sanitizeProjectName(getProjectName(cwd))}.localhost`;\n const projectName = sanitizeProjectName(merged.project ?? getProjectName(cwd));\n const ghostTunnel = resolveGhostTunnelConfig(merged.ghostTunnel, {\n route: getRouteName(primaryHost, projectName),\n project: projectName,\n owner: getLocalOwner(cwd)\n });\n\n return {\n cwd,\n projectName,\n readOptions,\n configPath: resolvedPath.path,\n configFileName: resolvedPath.fileName,\n configEntries,\n entries,\n hosts,\n requestedPort,\n port,\n dynamicPort,\n autoRepair,\n bindHost,\n primaryHost,\n https: merged.https ?? envHttps() ?? false,\n wwwAlias,\n ghostTunnel,\n ...(projectConfig.path ? { projectConfigPath: projectConfig.path } : {}),\n ...(releasePort ? { releasePort } : {})\n };\n}\n","import { createServer } from \"node:net\";\n\nexport type FindAvailablePortOptions = {\n host?: string;\n maxAttempts?: number;\n};\n\nexport async function isPortAvailable(port: number, host = \"127.0.0.1\") {\n return new Promise<boolean>((resolve) => {\n const server = createServer();\n\n server.once(\"error\", () => {\n resolve(false);\n });\n\n server.once(\"listening\", () => {\n server.close(() => resolve(true));\n });\n\n server.listen(port, host);\n });\n}\n\nexport async function findAvailablePort(startPort: number, options: FindAvailablePortOptions = {}) {\n const host = options.host ?? \"127.0.0.1\";\n const maxAttempts = options.maxAttempts ?? 50;\n\n for (let offset = 0; offset < maxAttempts; offset += 1) {\n const port = startPort + offset;\n if (await isPortAvailable(port, host)) {\n return port;\n }\n }\n\n throw new Error(`No available port found from ${startPort} to ${startPort + maxAttempts - 1}.`);\n}\n","import { randomUUID } from \"node:crypto\";\nimport { mkdir, open, readFile, rename, rm, stat, unlink, writeFile } from \"node:fs/promises\";\nimport { homedir } from \"node:os\";\nimport { join, normalize, resolve } from \"node:path\";\nimport { isPortAvailable } from \"./port.js\";\n\nexport const LOCALGHOST_REGISTRY_FILE = \"registry.json\";\nexport const LOCALGHOST_REGISTRY_LOCK_FILE = \"registry.lock\";\n\nexport type PortAvailabilityCheck = (port: number, host?: string) => boolean | Promise<boolean>;\n\nexport type LocalghostRegistryEntry = {\n projectCwd: string;\n instanceKey: string;\n port: number;\n updatedAt: number;\n};\n\nexport type LocalghostLease = {\n projectCwd: string;\n instanceKey: string;\n port: number;\n pid: number;\n acquiredAt: number;\n expiresAt: number;\n ownerToken: string;\n};\n\nexport type LocalghostRegistryData = {\n version: 1;\n allocations: LocalghostRegistryEntry[];\n leases: LocalghostLease[];\n};\n\nexport type LocalghostRegistryOptions = {\n stateRoot?: string;\n cwd?: string;\n pid?: number;\n ownerToken?: string;\n now?: () => number;\n isProcessRunning?: (pid: number) => boolean;\n availabilityCheck?: PortAvailabilityCheck;\n lockTimeoutMs?: number;\n lockRetryMs?: number;\n lockStaleMs?: number;\n};\n\nexport type AcquireLocalghostPortOptions = {\n projectCwd?: string;\n instanceKey: string;\n startPort?: number;\n maxAttempts?: number;\n reservedPorts?: Iterable<number>;\n leaseTtlMs?: number;\n host?: string;\n};\n\nexport type LocalghostRegistry = {\n root: string;\n registryPath: string;\n lockPath: string;\n ownerToken: string;\n acquirePort(options: AcquireLocalghostPortOptions): Promise<LocalghostLease>;\n releasePort(options: { projectCwd?: string; instanceKey: string }): Promise<boolean>;\n read(): Promise<LocalghostRegistryData>;\n prune(): Promise<{ removedLeases: number }>;\n};\n\ntype RegistryLock = { pid: number; createdAt: number; token: string };\n\nfunction defaultProcessRunning(pid: number) {\n if (pid <= 0) return false;\n try {\n process.kill(pid, 0);\n return true;\n } catch (error) {\n return (error as NodeJS.ErrnoException).code === \"EPERM\";\n }\n}\n\nexport function getLocalghostRegistryRoot(env: NodeJS.ProcessEnv = process.env) {\n return resolve(env.LOCALGHOST_HOME || join(homedir(), \".localghost\"));\n}\n\nexport function canonicalizeLocalghostProjectCwd(cwd = process.cwd()) {\n return normalize(resolve(cwd));\n}\n\nfunction emptyRegistry(): LocalghostRegistryData {\n return { version: 1, allocations: [], leases: [] };\n}\n\nfunction leaseKey(projectCwd: string, instanceKey: string) {\n return `${projectCwd}\\u0000${instanceKey}`;\n}\n\nfunction validRegistry(value: unknown): value is LocalghostRegistryData {\n if (!value || typeof value !== \"object\") return false;\n const candidate = value as Partial<LocalghostRegistryData>;\n return candidate.version === 1 && Array.isArray(candidate.allocations) && Array.isArray(candidate.leases);\n}\n\nfunction pruneRegistry(registry: LocalghostRegistryData, now: number, isRunning: (pid: number) => boolean) {\n registry.leases = registry.leases.filter((lease) => lease.expiresAt > now && isRunning(lease.pid));\n}\n\nasync function readJson(path: string) {\n try {\n return JSON.parse(await readFile(path, \"utf8\")) as unknown;\n } catch (error) {\n if ((error as NodeJS.ErrnoException).code === \"ENOENT\") return undefined;\n return undefined;\n }\n}\n\nexport function createLocalghostRegistry(options: LocalghostRegistryOptions = {}): LocalghostRegistry {\n const root = resolve(options.stateRoot ?? getLocalghostRegistryRoot());\n const registryPath = join(root, LOCALGHOST_REGISTRY_FILE);\n const lockPath = join(root, LOCALGHOST_REGISTRY_LOCK_FILE);\n const cwd = canonicalizeLocalghostProjectCwd(options.cwd);\n const now = options.now ?? Date.now;\n const pid = options.pid ?? process.pid;\n const ownerToken = options.ownerToken ?? randomUUID();\n const isRunning = options.isProcessRunning ?? defaultProcessRunning;\n const availabilityCheck = options.availabilityCheck ?? isPortAvailable;\n const lockTimeoutMs = options.lockTimeoutMs ?? 5000;\n const lockRetryMs = options.lockRetryMs ?? 25;\n const lockStaleMs = options.lockStaleMs ?? 30000;\n\n async function readRegistry() {\n const value = await readJson(registryPath);\n return validRegistry(value) ? value : emptyRegistry();\n }\n\n async function writeRegistry(registry: LocalghostRegistryData) {\n await mkdir(root, { recursive: true });\n const temporaryPath = join(root, `.registry.${process.pid}.${randomUUID()}.tmp`);\n await writeFile(temporaryPath, `${JSON.stringify(registry, null, 2)}\\n`, { mode: 0o600 });\n await rename(temporaryPath, registryPath);\n }\n\n async function lock() {\n await mkdir(root, { recursive: true });\n const deadline = now() + lockTimeoutMs;\n const token = randomUUID();\n while (true) {\n try {\n const handle = await open(lockPath, \"wx\", 0o600);\n await handle.writeFile(`${JSON.stringify({ pid, createdAt: now(), token } satisfies RegistryLock)}\\n`);\n await handle.close();\n return async () => {\n const current = await readJson(lockPath);\n if ((current as RegistryLock | undefined)?.token === token) await unlink(lockPath).catch(() => undefined);\n };\n } catch (error) {\n if ((error as NodeJS.ErrnoException).code !== \"EEXIST\") throw error;\n const lockInfo = await readJson(lockPath) as RegistryLock | undefined;\n let stale = false;\n if (lockInfo && typeof lockInfo.pid === \"number\") {\n stale = !isRunning(lockInfo.pid) && now() - lockInfo.createdAt >= 0;\n } else {\n try {\n stale = now() - (await stat(lockPath)).mtimeMs > lockStaleMs;\n } catch {\n continue;\n }\n }\n if (stale) {\n await rm(lockPath, { force: true }).catch(() => undefined);\n continue;\n }\n if (now() >= deadline) throw new Error(`Timed out waiting for Localghost registry lock: ${lockPath}`);\n await new Promise((resolveDelay) => setTimeout(resolveDelay, lockRetryMs));\n }\n }\n }\n\n async function withLock<T>(operation: (registry: LocalghostRegistryData) => Promise<T>) {\n const releaseLock = await lock();\n try {\n const registry = await readRegistry();\n pruneRegistry(registry, now(), isRunning);\n return await operation(registry);\n } finally {\n await releaseLock();\n }\n }\n\n return {\n root,\n registryPath,\n lockPath,\n ownerToken,\n read: readRegistry,\n async prune() {\n const releaseLock = await lock();\n try {\n const registry = await readRegistry();\n const before = registry.leases.length;\n pruneRegistry(registry, now(), isRunning);\n await writeRegistry(registry);\n return { removedLeases: before - registry.leases.length };\n } finally {\n await releaseLock();\n }\n },\n async acquirePort(acquireOptions) {\n const projectCwd = canonicalizeLocalghostProjectCwd(acquireOptions.projectCwd ?? cwd);\n if (!acquireOptions.instanceKey) throw new Error(\"instanceKey is required\");\n return withLock(async (registry) => {\n const key = leaseKey(projectCwd, acquireOptions.instanceKey);\n const existing = registry.allocations.find((entry) => leaseKey(entry.projectCwd, entry.instanceKey) === key);\n const reserved = new Set(acquireOptions.reservedPorts ?? []);\n const activePorts = new Set(registry.leases.map((lease) => lease.port));\n const port = existing?.port;\n const ownsActiveLease = registry.leases.some((lease) => lease.port === port && leaseKey(lease.projectCwd, lease.instanceKey) === key && lease.ownerToken === ownerToken);\n const reusable = port !== undefined && !reserved.has(port) &&\n (!activePorts.has(port) || ownsActiveLease) &&\n (ownsActiveLease || await availabilityCheck(port, acquireOptions.host));\n let selectedPort = reusable ? port : undefined;\n if (selectedPort === undefined) {\n const startPort = acquireOptions.startPort ?? 3000;\n const maxAttempts = acquireOptions.maxAttempts ?? 50;\n for (let offset = 0; offset < maxAttempts; offset += 1) {\n const candidate = startPort + offset;\n if (reserved.has(candidate) || activePorts.has(candidate)) continue;\n if (await availabilityCheck(candidate, acquireOptions.host)) {\n selectedPort = candidate;\n break;\n }\n }\n if (selectedPort === undefined) throw new Error(`No available registry port found from ${startPort} to ${startPort + maxAttempts - 1}.`);\n }\n const timestamp = now();\n const entry = existing ?? { projectCwd, instanceKey: acquireOptions.instanceKey, port: selectedPort, updatedAt: timestamp };\n entry.port = selectedPort;\n entry.updatedAt = timestamp;\n if (!existing) registry.allocations.push(entry);\n registry.leases = registry.leases.filter((lease) => leaseKey(lease.projectCwd, lease.instanceKey) !== key);\n const lease = { projectCwd, instanceKey: acquireOptions.instanceKey, port: selectedPort, pid, acquiredAt: timestamp, expiresAt: timestamp + (acquireOptions.leaseTtlMs ?? 30 * 60 * 1000), ownerToken };\n registry.leases.push(lease);\n await writeRegistry(registry);\n return lease;\n });\n },\n async releasePort(releaseOptions) {\n const projectCwd = canonicalizeLocalghostProjectCwd(releaseOptions.projectCwd ?? cwd);\n return withLock(async (registry) => {\n const key = leaseKey(projectCwd, releaseOptions.instanceKey);\n const before = registry.leases.length;\n registry.leases = registry.leases.filter((lease) => leaseKey(lease.projectCwd, lease.instanceKey) !== key || lease.ownerToken !== ownerToken);\n if (registry.leases.length !== before) await writeRegistry(registry);\n return registry.leases.length !== before;\n });\n }\n };\n}\n","import { domainToASCII } from \"node:url\";\n\nexport type GhostTunnelNamespaceTag = \"route\" | \"project\" | \"owner\" | string;\n\nexport type GhostTunnelNamespaceOptions = readonly GhostTunnelNamespaceTag[] | {\n tags?: readonly GhostTunnelNamespaceTag[];\n separator?: string;\n spreadTag?: GhostTunnelNamespaceTag | false;\n};\n\nexport type GhostTunnelNamespaceConfig = {\n tags: GhostTunnelNamespaceTag[];\n separator: string;\n spreadTag?: GhostTunnelNamespaceTag;\n};\n\nexport type GhostTunnelNamespaceValues = Record<string, string> & {\n route?: string;\n project?: string;\n owner?: string;\n};\n\nexport type GhostTunnelPreviewOptions = {\n domain?: string;\n route: string;\n project: string;\n owner: string;\n values?: GhostTunnelNamespaceValues;\n path?: string;\n protocol?: \"http\" | \"https\";\n};\n\nexport type GhostTunnelMode = \"manual\" | \"public\";\n\nexport type GhostTunnelDomainOptions = string | readonly string[];\n\nexport type GhostTunnelAdapterProvider = \"vercel\";\nexport type GhostTunnelAdapterStrategy = \"same-project\" | \"separate-relay\";\nexport type GhostTunnelTransportKind = \"none\" | \"ip\" | \"tunnel\";\nexport type GhostTunnelAdapterTransport = GhostTunnelTransportKind;\nexport type GhostTunnelTunnelStoreProvider = \"vercel-redis\" | \"redis\";\nexport type GhostTunnelTunnelStoreEnv = \"auto\";\n\nexport type GhostTunnelTunnelStoreOptions = {\n provider?: GhostTunnelTunnelStoreProvider;\n env?: GhostTunnelTunnelStoreEnv;\n namespace?: string;\n};\n\nexport type GhostTunnelTransportOptions =\n | GhostTunnelTransportKind\n | {\n kind?: \"none\";\n }\n | {\n kind: \"ip\";\n allowPrivateNetworkAddress?: boolean;\n }\n | {\n kind: \"tunnel\";\n store?: GhostTunnelTunnelStoreOptions;\n waitMs?: number;\n pollIntervalMs?: number;\n routeTtlSeconds?: number;\n requestTtlSeconds?: number;\n maxRequestBodyBytes?: number;\n maxResponseBodyBytes?: number;\n };\n\nexport type GhostTunnelTransportConfig =\n | {\n kind: \"none\";\n }\n | {\n kind: \"ip\";\n allowPrivateNetworkAddress: boolean;\n }\n | {\n kind: \"tunnel\";\n store: Required<Pick<GhostTunnelTunnelStoreOptions, \"provider\" | \"env\" | \"namespace\">>;\n waitMs: number;\n pollIntervalMs: number;\n routeTtlSeconds: number;\n requestTtlSeconds: number;\n maxRequestBodyBytes: number;\n maxResponseBodyBytes: number;\n };\n\nexport type GhostTunnelAdapterOptions = GhostTunnelAdapterProvider | {\n provider: GhostTunnelAdapterProvider;\n strategy?: GhostTunnelAdapterStrategy;\n};\n\nexport type GhostTunnelOptions = false | GhostTunnelMode | {\n enabled?: boolean;\n mode?: GhostTunnelMode;\n domains?: GhostTunnelDomainOptions;\n subdomain?: string;\n namespace?: GhostTunnelNamespaceOptions;\n preview?: GhostTunnelPreviewOptions;\n requireHttps?: boolean;\n requireAuth?: boolean;\n adapter?: GhostTunnelAdapterOptions;\n transport?: GhostTunnelTransportOptions;\n};\n\nexport type GhostTunnelConfig = {\n enabled: boolean;\n mode: GhostTunnelMode;\n domains: string[];\n subdomain: string;\n namespace: GhostTunnelNamespaceConfig;\n preview?: GhostTunnelPreviewOptions;\n previewUrl?: string;\n displayUrl?: string;\n displayUrls: string[];\n requireHttps: boolean;\n requireAuth: boolean;\n transport: GhostTunnelTransportConfig;\n adapter?: {\n provider: GhostTunnelAdapterProvider;\n strategy: GhostTunnelAdapterStrategy;\n };\n};\n\nexport type GhostTunnelDisplayDefaults = {\n domain?: string;\n route?: string;\n project?: string;\n owner?: string;\n values?: GhostTunnelNamespaceValues;\n};\n\nexport type GhostTunnelRoute = {\n host: string;\n slug: string;\n namespace: GhostTunnelNamespaceValues;\n entryHost: string;\n wildcardHost: string;\n domain: string;\n};\n\nexport type ConstructGhostTunnelUrlInput = {\n domain: string;\n route: string;\n project: string;\n owner: string;\n values?: GhostTunnelNamespaceValues;\n path?: string;\n searchParams?: Record<string, string | number | boolean | null | undefined> | URLSearchParams;\n protocol?: \"http\" | \"https\";\n ghostTunnel?: GhostTunnelOptions | GhostTunnelConfig;\n};\n\nconst DEFAULT_GHOST_TUNNEL_SUBDOMAIN = \"ghost\";\nconst DEFAULT_GHOST_TUNNEL_NAMESPACE_TAGS = [\"route\", \"project\", \"owner\"] as const;\nconst DEFAULT_GHOST_TUNNEL_NAMESPACE_SEPARATOR = \"-\";\nconst DEFAULT_GHOST_TUNNEL_MODE: GhostTunnelMode = \"manual\";\nconst DEFAULT_GHOST_TUNNEL_ADAPTER_STRATEGY: GhostTunnelAdapterStrategy = \"same-project\";\nconst DEFAULT_GHOST_TUNNEL_TRANSPORT_KIND: GhostTunnelTransportKind = \"none\";\nconst DEFAULT_GHOST_TUNNEL_TUNNEL_STORE_PROVIDER: GhostTunnelTunnelStoreProvider = \"vercel-redis\";\nconst DEFAULT_GHOST_TUNNEL_TUNNEL_STORE_ENV: GhostTunnelTunnelStoreEnv = \"auto\";\nconst DEFAULT_GHOST_TUNNEL_TUNNEL_STORE_NAMESPACE = \"localghost\";\nconst DEFAULT_GHOST_TUNNEL_TUNNEL_WAIT_MS = 25_000;\nconst DEFAULT_GHOST_TUNNEL_TUNNEL_POLL_INTERVAL_MS = 250;\nconst DEFAULT_GHOST_TUNNEL_TUNNEL_ROUTE_TTL_SECONDS = 30;\nconst DEFAULT_GHOST_TUNNEL_TUNNEL_REQUEST_TTL_SECONDS = 60;\nconst DEFAULT_GHOST_TUNNEL_TUNNEL_MAX_REQUEST_BODY_BYTES = 1024 * 1024;\nconst DEFAULT_GHOST_TUNNEL_TUNNEL_MAX_RESPONSE_BODY_BYTES = 5 * 1024 * 1024;\n\ntype GhostTunnelLegacyAdapterOptions = {\n provider: GhostTunnelAdapterProvider;\n strategy?: GhostTunnelAdapterStrategy;\n transport?: GhostTunnelTransportOptions;\n};\n\nfunction isResolvedGhostTunnelConfig(value: GhostTunnelOptions | GhostTunnelConfig | undefined): value is GhostTunnelConfig {\n return typeof value === \"object\" && value !== null && \"enabled\" in value;\n}\n\nfunction toGhostTunnelConfig(options: GhostTunnelOptions | GhostTunnelConfig | undefined) {\n return isResolvedGhostTunnelConfig(options) ? options : resolveGhostTunnelConfig(options);\n}\n\nfunction stripHostPort(value: string) {\n const trimmed = value.trim().toLowerCase();\n if (trimmed.startsWith(\"[\") || trimmed.includes(\"/\")) return \"\";\n\n const portSeparator = trimmed.lastIndexOf(\":\");\n if (portSeparator === -1) return trimmed;\n\n const port = trimmed.slice(portSeparator + 1);\n return /^\\d+$/.test(port) ? trimmed.slice(0, portSeparator) : trimmed;\n}\n\nfunction normalizeDomain(value: string) {\n const host = stripHostPort(value.replace(/^\\*\\./, \"\"));\n const ascii = domainToASCII(host);\n if (!ascii || ascii.length > 253 || ascii.includes(\"..\")) return null;\n if (ascii.startsWith(\".\") || ascii.endsWith(\".\")) return null;\n if (ascii.includes(\"*\")) return null;\n if (!ascii.split(\".\").every(isValidHostLabel)) return null;\n return ascii;\n}\n\nfunction isValidHostLabel(value: string) {\n return value.length > 0 && value.length <= 63 && /^[a-z0-9](?:[a-z0-9-]*[a-z0-9])?$/.test(value);\n}\n\nfunction isValidNamespaceTag(value: string) {\n return /^[a-z][a-z0-9_]*$/i.test(value);\n}\n\nfunction isNamespaceTagList(options: GhostTunnelNamespaceOptions | undefined): options is readonly GhostTunnelNamespaceTag[] {\n return Array.isArray(options);\n}\n\nfunction assertValidSubdomain(value: string) {\n if (!isValidHostLabel(value)) {\n throw new Error(`Invalid ghost tunnel subdomain: ${value}`);\n }\n}\n\nfunction normalizeDomains(domains: GhostTunnelDomainOptions | undefined) {\n const values = typeof domains === \"string\" ? [domains] : [...(domains ?? [])];\n const normalized = values.map((value) => value.trim()).filter(Boolean).map((value) => {\n const domain = normalizeDomain(value);\n if (!domain) throw new Error(`Invalid ghost tunnel domain: ${value}`);\n return domain;\n });\n\n return [...new Set(normalized)];\n}\n\nfunction parseGhostTunnelMode(value: GhostTunnelMode | undefined) {\n return value ?? DEFAULT_GHOST_TUNNEL_MODE;\n}\n\nfunction parseGhostTunnelAdapterStrategy(value: GhostTunnelAdapterStrategy | undefined) {\n if (typeof value === \"undefined\") return DEFAULT_GHOST_TUNNEL_ADAPTER_STRATEGY;\n if (value === \"same-project\" || value === \"separate-relay\") return value;\n throw new Error(`Unsupported ghost tunnel adapter strategy: ${String(value)}`);\n}\n\nfunction parseGhostTunnelTransportKind(value: GhostTunnelTransportKind | undefined) {\n if (typeof value === \"undefined\") return DEFAULT_GHOST_TUNNEL_TRANSPORT_KIND;\n if (value === \"none\" || value === \"ip\" || value === \"tunnel\") return value;\n throw new Error(`Unsupported ghost tunnel transport: ${String(value)}`);\n}\n\nfunction parsePositiveInteger(value: number | undefined, fallback: number, name: string) {\n if (typeof value === \"undefined\") return fallback;\n if (!Number.isInteger(value) || value < 1) {\n throw new Error(`Invalid ghost tunnel ${name}: ${value}`);\n }\n return value;\n}\n\nfunction parseTunnelStoreProvider(value: GhostTunnelTunnelStoreProvider | undefined) {\n if (typeof value === \"undefined\") return DEFAULT_GHOST_TUNNEL_TUNNEL_STORE_PROVIDER;\n if (value === \"vercel-redis\" || value === \"redis\") return value;\n throw new Error(`Unsupported ghost tunnel tunnel store provider: ${String(value)}`);\n}\n\nfunction parseTunnelStoreEnv(value: GhostTunnelTunnelStoreEnv | undefined) {\n if (typeof value === \"undefined\") return DEFAULT_GHOST_TUNNEL_TUNNEL_STORE_ENV;\n if (value === \"auto\") return value;\n throw new Error(`Unsupported ghost tunnel tunnel store env: ${String(value)}`);\n}\n\nfunction parseTunnelStoreNamespace(value: string | undefined) {\n const namespace = value ?? DEFAULT_GHOST_TUNNEL_TUNNEL_STORE_NAMESPACE;\n if (!/^[a-z][a-z0-9:_-]{0,63}$/i.test(namespace)) {\n throw new Error(`Invalid ghost tunnel tunnel store namespace: ${namespace}`);\n }\n return namespace;\n}\n\nfunction resolveGhostTunnelAdapter(\n input: GhostTunnelAdapterOptions | GhostTunnelLegacyAdapterOptions | GhostTunnelConfig[\"adapter\"] | undefined\n): GhostTunnelConfig[\"adapter\"] {\n if (!input) return undefined;\n\n const provider = typeof input === \"string\" ? input : input.provider;\n if (provider !== \"vercel\") {\n throw new Error(`Unsupported ghost tunnel adapter provider: ${String(provider)}`);\n }\n\n return {\n provider,\n strategy: typeof input === \"string\" ? DEFAULT_GHOST_TUNNEL_ADAPTER_STRATEGY : parseGhostTunnelAdapterStrategy(input.strategy)\n };\n}\n\nfunction getLegacyGhostTunnelTransport(\n input: GhostTunnelAdapterOptions | GhostTunnelLegacyAdapterOptions | GhostTunnelConfig[\"adapter\"] | undefined\n) {\n if (!input || typeof input === \"string\" || !(\"transport\" in input)) return undefined;\n return input.transport;\n}\n\nfunction resolveGhostTunnelTransport(\n input: GhostTunnelTransportOptions | GhostTunnelTransportConfig | undefined\n): GhostTunnelTransportConfig {\n if (!input) {\n return { kind: \"none\" };\n }\n\n const kind = typeof input === \"string\"\n ? parseGhostTunnelTransportKind(input)\n : parseGhostTunnelTransportKind(input.kind);\n\n if (kind === \"ip\") {\n return {\n kind,\n allowPrivateNetworkAddress: typeof input === \"string\" ? false : input.kind === \"ip\" ? input.allowPrivateNetworkAddress ?? false : false\n };\n }\n\n if (kind === \"tunnel\") {\n const config: Extract<GhostTunnelTransportOptions, { kind: \"tunnel\" }> | Extract<GhostTunnelTransportConfig, { kind: \"tunnel\" }> | undefined =\n typeof input === \"string\" || input.kind !== \"tunnel\" ? undefined : input;\n const store = config?.store ?? {};\n return {\n kind,\n store: {\n provider: parseTunnelStoreProvider(store.provider),\n env: parseTunnelStoreEnv(store.env),\n namespace: parseTunnelStoreNamespace(store.namespace)\n },\n waitMs: parsePositiveInteger(config?.waitMs, DEFAULT_GHOST_TUNNEL_TUNNEL_WAIT_MS, \"tunnel waitMs\"),\n pollIntervalMs: parsePositiveInteger(config?.pollIntervalMs, DEFAULT_GHOST_TUNNEL_TUNNEL_POLL_INTERVAL_MS, \"tunnel pollIntervalMs\"),\n routeTtlSeconds: parsePositiveInteger(config?.routeTtlSeconds, DEFAULT_GHOST_TUNNEL_TUNNEL_ROUTE_TTL_SECONDS, \"tunnel routeTtlSeconds\"),\n requestTtlSeconds: parsePositiveInteger(config?.requestTtlSeconds, DEFAULT_GHOST_TUNNEL_TUNNEL_REQUEST_TTL_SECONDS, \"tunnel requestTtlSeconds\"),\n maxRequestBodyBytes: parsePositiveInteger(config?.maxRequestBodyBytes, DEFAULT_GHOST_TUNNEL_TUNNEL_MAX_REQUEST_BODY_BYTES, \"tunnel maxRequestBodyBytes\"),\n maxResponseBodyBytes: parsePositiveInteger(config?.maxResponseBodyBytes, DEFAULT_GHOST_TUNNEL_TUNNEL_MAX_RESPONSE_BODY_BYTES, \"tunnel maxResponseBodyBytes\")\n };\n }\n\n return { kind: \"none\" };\n}\n\nfunction resolveNamespaceConfig(options: GhostTunnelNamespaceOptions | undefined): GhostTunnelNamespaceConfig {\n const tags = isNamespaceTagList(options)\n ? [...options]\n : [...(options?.tags ?? DEFAULT_GHOST_TUNNEL_NAMESPACE_TAGS)];\n let separator = DEFAULT_GHOST_TUNNEL_NAMESPACE_SEPARATOR;\n let spreadTag: GhostTunnelNamespaceTag | false | undefined = tags.includes(\"project\") ? \"project\" : undefined;\n if (options && !isNamespaceTagList(options)) {\n separator = options.separator ?? DEFAULT_GHOST_TUNNEL_NAMESPACE_SEPARATOR;\n spreadTag = options.spreadTag === false ? false : options.spreadTag ?? spreadTag;\n }\n\n if (tags.length === 0) {\n throw new Error(\"Ghost tunnel namespace must include at least one tag.\");\n }\n\n for (const tag of tags) {\n if (!isValidNamespaceTag(tag)) {\n throw new Error(`Invalid ghost tunnel namespace tag: ${tag}`);\n }\n }\n\n if (spreadTag && !tags.includes(spreadTag)) {\n throw new Error(`Ghost tunnel namespace spreadTag must be listed in tags: ${spreadTag}`);\n }\n\n if (!separator || separator.length > 8 || !/^[a-z0-9-]+$/.test(separator)) {\n throw new Error(`Invalid ghost tunnel namespace separator: ${separator}`);\n }\n\n return {\n tags,\n separator,\n ...(spreadTag ? { spreadTag } : {})\n };\n}\n\nfunction normalizeNamespaceValue(tag: string, value: string, separator: string, options: { allowSeparator?: boolean } = {}) {\n const normalized = normalizeDomain(value);\n if (!normalized || normalized.includes(\".\")) {\n throw new Error(`Invalid ghost tunnel namespace value for ${tag}: ${value}`);\n }\n\n if (!options.allowSeparator && normalized.includes(separator)) {\n throw new Error(`Ghost tunnel namespace value for ${tag} cannot include separator \"${separator}\": ${value}`);\n }\n\n return normalized;\n}\n\nfunction createNamespaceSlug(config: GhostTunnelNamespaceConfig, values: GhostTunnelNamespaceValues) {\n const parts = config.tags.map((tag) => {\n const value = values[tag];\n if (!value) {\n throw new Error(`Missing ghost tunnel namespace value: ${tag}`);\n }\n\n return normalizeNamespaceValue(tag, value, config.separator, { allowSeparator: tag === config.spreadTag });\n });\n\n const slug = parts.join(config.separator);\n if (!isValidHostLabel(slug)) {\n throw new Error(`Ghost tunnel namespace is too long for a DNS label: ${slug}`);\n }\n\n return slug;\n}\n\nfunction createNamespaceDisplaySlug(config: GhostTunnelNamespaceConfig, values: GhostTunnelNamespaceValues = {}) {\n return config.tags.map((tag) => {\n const value = values[tag];\n if (!value) return `<${tag}>`;\n\n try {\n return normalizeNamespaceValue(tag, value, config.separator, { allowSeparator: tag === config.spreadTag });\n } catch {\n return `<${tag}>`;\n }\n }).join(config.separator);\n}\n\nfunction getPreviewDefaults(preview: GhostTunnelPreviewOptions | undefined, defaults: GhostTunnelDisplayDefaults | undefined) {\n return {\n domain: preview?.domain ?? defaults?.domain,\n route: preview?.route ?? defaults?.route,\n project: preview?.project ?? defaults?.project,\n owner: preview?.owner ?? defaults?.owner,\n values: {\n ...(defaults?.values ?? {}),\n ...(preview?.values ?? {})\n },\n path: preview?.path,\n protocol: preview?.protocol\n };\n}\n\nfunction getDisplayValues(input: ReturnType<typeof getPreviewDefaults>): GhostTunnelNamespaceValues {\n return {\n ...(input.route ? { route: input.route } : {}),\n ...(input.project ? { project: input.project } : {}),\n ...(input.owner ? { owner: input.owner } : {}),\n ...input.values\n };\n}\n\nfunction getDisplayDefaults(defaults?: GhostTunnelDisplayDefaults) {\n return defaults;\n}\n\nfunction createDisplayUrl(config: GhostTunnelConfig, defaults?: GhostTunnelDisplayDefaults, domain?: string) {\n const input = getPreviewDefaults(config.preview, getDisplayDefaults(defaults));\n const protocol = input.protocol ?? \"https\";\n const slug = createNamespaceDisplaySlug(config.namespace, getDisplayValues(input));\n const entryHost = domain\n ? getGhostTunnelEntryHost(domain, config)\n : input.domain\n ? getGhostTunnelEntryHost(input.domain, config)\n : `${config.subdomain}.*`;\n const url = `${protocol}://${slug}.${entryHost}/`;\n\n if (!input.path) return url;\n return `${url}${input.path.replace(/^\\/+/, \"\")}`;\n}\n\nfunction createDisplayUrls(config: GhostTunnelConfig, defaults?: GhostTunnelDisplayDefaults) {\n const displayDefaults = getDisplayDefaults(defaults);\n const domains = config.domains.length > 0\n ? config.domains\n : displayDefaults?.domain\n ? [displayDefaults.domain]\n : [];\n const urls = domains.length > 0\n ? domains.map((domain) => createDisplayUrl(config, displayDefaults, domain))\n : [createDisplayUrl(config, displayDefaults)];\n\n return [...new Set(urls)];\n}\n\nfunction maybeConstructPreviewUrl(config: GhostTunnelConfig, defaults?: GhostTunnelDisplayDefaults) {\n if (!config.preview) return undefined;\n\n const input = getPreviewDefaults(config.preview, defaults);\n if (!input.domain || !input.route || !input.project || !input.owner) return undefined;\n\n return constructGhostTunnelUrl({\n domain: input.domain,\n route: input.route,\n project: input.project,\n owner: input.owner,\n values: input.values,\n ...(input.path ? { path: input.path } : {}),\n ...(input.protocol ? { protocol: input.protocol } : {}),\n ghostTunnel: config\n });\n}\n\nfunction parseNamespaceSlug(slug: string, config: GhostTunnelNamespaceConfig): GhostTunnelNamespaceValues | null {\n const parts = slug.split(config.separator);\n if (parts.length < config.tags.length) return null;\n if (parts.length !== config.tags.length && !config.spreadTag) return null;\n\n const namespace: GhostTunnelNamespaceValues = {};\n const spreadIndex = config.spreadTag ? config.tags.indexOf(config.spreadTag) : -1;\n const spreadWidth = spreadIndex >= 0 ? parts.length - config.tags.length + 1 : 1;\n\n let partIndex = 0;\n for (const [tagIndex, tag] of config.tags.entries()) {\n const value = tagIndex === spreadIndex\n ? parts.slice(partIndex, partIndex + spreadWidth).join(config.separator)\n : parts[partIndex];\n if (!value || !isValidHostLabel(value)) return null;\n if (tagIndex !== spreadIndex && value.includes(config.separator)) return null;\n namespace[tag] = value;\n partIndex += tagIndex === spreadIndex ? spreadWidth : 1;\n }\n\n return namespace;\n}\n\nexport function resolveGhostTunnelConfig(options: GhostTunnelOptions | undefined, defaults?: GhostTunnelDisplayDefaults): GhostTunnelConfig {\n if (options === false || typeof options === \"undefined\") {\n return {\n enabled: false,\n mode: DEFAULT_GHOST_TUNNEL_MODE,\n domains: [],\n subdomain: DEFAULT_GHOST_TUNNEL_SUBDOMAIN,\n namespace: resolveNamespaceConfig(undefined),\n displayUrls: [],\n requireHttps: true,\n requireAuth: true,\n transport: resolveGhostTunnelTransport(undefined)\n };\n }\n\n const config = typeof options === \"string\"\n ? { mode: options }\n : options;\n const subdomain = config.subdomain ?? DEFAULT_GHOST_TUNNEL_SUBDOMAIN;\n assertValidSubdomain(subdomain);\n const domains = normalizeDomains(config.domains);\n const enabled = config.enabled ?? true;\n const adapter = resolveGhostTunnelAdapter(config.adapter);\n const transport = resolveGhostTunnelTransport(config.transport ?? getLegacyGhostTunnelTransport(config.adapter));\n\n const resolved: GhostTunnelConfig = {\n enabled,\n mode: parseGhostTunnelMode(config.mode),\n domains,\n subdomain,\n namespace: resolveNamespaceConfig(config.namespace),\n ...(config.preview ? { preview: config.preview } : {}),\n displayUrls: [],\n requireHttps: config.requireHttps ?? true,\n requireAuth: config.requireAuth ?? true,\n transport,\n ...(adapter ? { adapter } : {})\n };\n\n if (!enabled) {\n return resolved;\n }\n\n const previewUrl = maybeConstructPreviewUrl(resolved, defaults);\n const displayUrls = previewUrl ? [previewUrl] : createDisplayUrls(resolved, defaults);\n\n return {\n ...resolved,\n displayUrls,\n ...(displayUrls[0] ? { displayUrl: displayUrls[0] } : {}),\n ...(previewUrl ? { previewUrl } : {})\n };\n}\n\nexport function getGhostTunnelEntryHost(domain: string, options: GhostTunnelOptions | GhostTunnelConfig = {}) {\n const config = toGhostTunnelConfig(options);\n const normalizedDomain = normalizeDomain(domain);\n if (!normalizedDomain) {\n throw new Error(`Invalid ghost tunnel domain: ${domain}`);\n }\n\n return `${config.subdomain}.${normalizedDomain}`;\n}\n\nexport function getGhostTunnelWildcardHost(domain: string, options: GhostTunnelOptions | GhostTunnelConfig = {}) {\n return `*.${getGhostTunnelEntryHost(domain, options)}`;\n}\n\nexport function constructGhostTunnelHost(input: Omit<ConstructGhostTunnelUrlInput, \"path\" | \"searchParams\" | \"protocol\">) {\n const config = toGhostTunnelConfig(input.ghostTunnel ?? {});\n if (!config.enabled) {\n throw new Error(\"Ghost tunnel is not enabled.\");\n }\n\n const namespaceValues: GhostTunnelNamespaceValues = {\n route: input.route,\n project: input.project,\n owner: input.owner,\n ...(input.values ?? {})\n };\n const slug = createNamespaceSlug(config.namespace, namespaceValues);\n\n return `${slug}.${getGhostTunnelEntryHost(input.domain, config)}`;\n}\n\nexport function constructGhostTunnelUrl(input: ConstructGhostTunnelUrlInput) {\n const protocol = input.protocol ?? \"https\";\n const host = constructGhostTunnelHost(input);\n const url = new URL(`${protocol}://${host}/`);\n\n if (input.path) {\n url.pathname = `/${input.path.replace(/^\\/+/, \"\")}`;\n }\n\n if (input.searchParams instanceof URLSearchParams) {\n url.search = input.searchParams.toString();\n } else if (input.searchParams) {\n for (const [key, value] of Object.entries(input.searchParams)) {\n if (typeof value !== \"undefined\" && value !== null) {\n url.searchParams.set(key, String(value));\n }\n }\n }\n\n return url.toString();\n}\n\nexport const constructGhostTunnelURL = constructGhostTunnelUrl;\n\nexport function getGhostTunnelDefaultDisplayUrl(options: GhostTunnelOptions | GhostTunnelConfig = {}, defaults?: GhostTunnelDisplayDefaults) {\n const config = toGhostTunnelConfig(options);\n if (!config.enabled) return null;\n return createDisplayUrl(config, defaults);\n}\n\nexport function getGhostTunnelDisplayUrl(options: GhostTunnelOptions | GhostTunnelConfig | undefined, defaults?: GhostTunnelDisplayDefaults) {\n const config = toGhostTunnelConfig(options);\n if (!config.enabled) return null;\n return config.displayUrl ?? config.previewUrl ?? getGhostTunnelDefaultDisplayUrl(config, defaults);\n}\n\nexport function getGhostTunnelDisplayUrls(options: GhostTunnelOptions | GhostTunnelConfig | undefined, defaults?: GhostTunnelDisplayDefaults) {\n const config = toGhostTunnelConfig(options);\n if (!config.enabled) return [];\n if (config.displayUrls.length > 0) return config.displayUrls;\n const displayUrl = getGhostTunnelDisplayUrl(config, defaults);\n return displayUrl ? [displayUrl] : [];\n}\n\nexport function getGhostTunnelPreviewUrl(options: GhostTunnelOptions | GhostTunnelConfig | undefined) {\n const config = toGhostTunnelConfig(options);\n if (!config.enabled) return null;\n return config.previewUrl ?? maybeConstructPreviewUrl(config) ?? null;\n}\n\nexport function parseGhostTunnelHost(host: string, domain: string, options: GhostTunnelOptions | GhostTunnelConfig = {}): GhostTunnelRoute | null {\n const config = toGhostTunnelConfig(options);\n if (!config.enabled) return null;\n\n const normalizedHost = normalizeDomain(host);\n const normalizedDomain = normalizeDomain(domain);\n if (!normalizedHost || !normalizedDomain) return null;\n\n const entryHost = getGhostTunnelEntryHost(normalizedDomain, config);\n const suffix = `.${entryHost}`;\n if (!normalizedHost.endsWith(suffix)) return null;\n\n const slug = normalizedHost.slice(0, -suffix.length);\n if (!isValidHostLabel(slug)) return null;\n const namespace = parseNamespaceSlug(slug, config.namespace);\n if (!namespace) return null;\n\n return {\n host: normalizedHost,\n slug,\n namespace,\n entryHost,\n wildcardHost: `*.${entryHost}`,\n domain: normalizedDomain\n };\n}\n\nexport function assertSecureGhostTunnelRequest(input: {\n host: string;\n domain: string;\n protocol: \"http\" | \"https\";\n ghostTunnel: GhostTunnelOptions | GhostTunnelConfig | undefined;\n authenticated?: boolean;\n}) {\n const config = toGhostTunnelConfig(input.ghostTunnel);\n\n if (!config.enabled) {\n throw new Error(\"Ghost tunnel is not enabled.\");\n }\n\n if (config.requireHttps && input.protocol !== \"https\") {\n throw new Error(\"Ghost tunnel requests must use HTTPS.\");\n }\n\n if (config.requireAuth && input.authenticated !== true) {\n throw new Error(\"Ghost tunnel requests must be authenticated.\");\n }\n\n const route = parseGhostTunnelHost(input.host, input.domain, config);\n if (!route) {\n throw new Error(`Host is not a valid ghost tunnel host for ${input.domain}.`);\n }\n\n return route;\n}\n","import { execa } from \"execa\";\nimport { isPortAvailable } from \"./port.js\";\nimport { canonicalizeLocalghostProjectCwd, createLocalghostRegistry } from \"./registry.js\";\nimport { isProcessRunning } from \"./activity.js\";\nimport { resolveLocalghostContext } from \"./context.js\";\nimport type { ConfigPattern } from \"./config.js\";\n\nexport type DoctorResult = {\n ok: boolean;\n caddy: {\n found: boolean;\n version?: string;\n installHint: string;\n };\n ports: {\n configured?: number;\n available?: boolean;\n registryPath: string;\n staleLeases: Array<{ projectCwd: string; instanceKey: string; port: number; pid: number }>;\n duplicateAllocations: Array<{ port: number; projects: string[] }>;\n currentAllocation?: { projectCwd: string; instanceKey: string; port: number };\n };\n};\n\nexport type DoctorOptions = {\n cwd?: string;\n configFiles?: string[];\n configPattern?: ConfigPattern;\n};\n\nexport async function checkCaddy(): Promise<DoctorResult[\"caddy\"]> {\n try {\n const result = await execa(\"caddy\", [\"version\"], { reject: false });\n const version = [result.stdout, result.stderr].filter(Boolean).join(\"\\n\").trim();\n\n return {\n found: result.exitCode === 0,\n ...(version ? { version } : {}),\n installHint: \"brew install caddy\"\n };\n } catch {\n return {\n found: false,\n installHint: \"brew install caddy\"\n };\n }\n}\n\nexport async function runDoctor(options: DoctorOptions = {}): Promise<DoctorResult> {\n const caddy = await checkCaddy();\n const cwd = options.cwd ?? process.cwd();\n const registry = createLocalghostRegistry({ cwd });\n const data = await registry.read();\n const now = Date.now();\n const staleLeases = data.leases\n .filter((lease) => lease.expiresAt <= now || !isProcessRunning(lease.pid))\n .map(({ projectCwd, instanceKey, port, pid }) => ({ projectCwd, instanceKey, port, pid }));\n const allocationsByPort = new Map<number, string[]>();\n for (const allocation of data.allocations) {\n const projects = allocationsByPort.get(allocation.port) ?? [];\n projects.push(`${allocation.projectCwd}#${allocation.instanceKey}`);\n allocationsByPort.set(allocation.port, projects);\n }\n const duplicateAllocations = [...allocationsByPort.entries()]\n .filter(([, projects]) => projects.length > 1)\n .map(([port, projects]) => ({ port, projects }));\n let configured: number | undefined;\n let available: boolean | undefined;\n try {\n const context = await resolveLocalghostContext({\n cwd,\n ...(options.configFiles ? { configFiles: options.configFiles } : {}),\n ...(options.configPattern ? { configPattern: options.configPattern } : {}),\n dynamicPort: false\n });\n configured = context.requestedPort;\n available = await isPortAvailable(configured);\n } catch {\n // The existing Caddy check remains useful even when project config is invalid.\n }\n const currentProjectCwd = canonicalizeLocalghostProjectCwd(cwd);\n const currentAllocation = data.allocations.find((allocation) => allocation.projectCwd === currentProjectCwd);\n return {\n ok: caddy.found && available !== false && staleLeases.length === 0 && duplicateAllocations.length === 0,\n caddy,\n ports: {\n ...(configured !== undefined ? { configured } : {}),\n ...(available !== undefined ? { available } : {}),\n registryPath: registry.registryPath,\n staleLeases,\n duplicateAllocations,\n ...(currentAllocation ? {\n currentAllocation: {\n projectCwd: currentAllocation.projectCwd,\n instanceKey: currentAllocation.instanceKey,\n port: currentAllocation.port\n }\n } : {})\n }\n };\n}\n","export type LocalghostEnvironment = NodeJS.ProcessEnv;\n\nconst PRODUCTION_ENV_KEYS = [\"NODE_ENV\", \"VERCEL_ENV\", \"NETLIFY\", \"CF_PAGES_BRANCH\", \"LOCALGHOST_ENV\"] as const;\n\nexport function getProductionReason(env: LocalghostEnvironment = process.env) {\n if (env.LOCALGHOST_ENV === \"production\") return \"LOCALGHOST_ENV=production\";\n if (env.NODE_ENV === \"production\") return \"NODE_ENV=production\";\n if (env.VERCEL_ENV === \"production\") return \"VERCEL_ENV=production\";\n if (env.NETLIFY === \"true\" && env.CONTEXT === \"production\") return \"NETLIFY=true and CONTEXT=production\";\n if (env.CF_PAGES_BRANCH && env.CF_PAGES_BRANCH === env.CF_PAGES_PRODUCTION_BRANCH) {\n return \"CF_PAGES_BRANCH matches CF_PAGES_PRODUCTION_BRANCH\";\n }\n\n return null;\n}\n\nexport function isProductionLike(env: LocalghostEnvironment = process.env) {\n return getProductionReason(env) !== null;\n}\n\nexport function assertLocalDevelopment(command: string, env: LocalghostEnvironment = process.env) {\n const reason = getProductionReason(env);\n if (!reason) return;\n\n throw new Error(`Localghost only runs in local development. Refusing \\`${command}\\` because ${reason}.`);\n}\n\nexport function getProductionEnvKeys() {\n return PRODUCTION_ENV_KEYS;\n}\n","import { readDevHosts, resolveDevHostsPath, type ReadDevHostsOptions } from \"./config.js\";\nimport type { DevHostEntry } from \"./parse.js\";\n\nexport const LOCALGHOST_GHOST_TUNNEL_FILE = \".ghosttunnel\";\n\nexport type ReadGhostTunnelOptions = ReadDevHostsOptions;\n\nfunction toGhostTunnelOptions(options: ReadGhostTunnelOptions | string = {}): ReadGhostTunnelOptions {\n const resolved = typeof options === \"string\" ? { cwd: options } : options;\n\n return {\n ...resolved,\n fileName: resolved.fileName ?? LOCALGHOST_GHOST_TUNNEL_FILE\n };\n}\n\nfunction normalizeHost(value: string) {\n return value.trim().toLowerCase().replace(/\\.$/, \"\");\n}\n\nexport function resolveGhostTunnelPath(options: ReadGhostTunnelOptions | string = {}) {\n return resolveDevHostsPath(toGhostTunnelOptions(options));\n}\n\nexport function getGhostTunnelPath(options: ReadGhostTunnelOptions | string = {}) {\n return resolveGhostTunnelPath(options).path;\n}\n\nexport function readGhostTunnelEntries(options: ReadGhostTunnelOptions | string = {}) {\n return readDevHosts(toGhostTunnelOptions(options));\n}\n\nexport function listGhostTunnelEntries(options: ReadGhostTunnelOptions | string = {}) {\n const resolved = resolveGhostTunnelPath(options);\n if (!resolved.exists) return [] satisfies DevHostEntry[];\n return readGhostTunnelEntries(options);\n}\n\nexport function findGhostTunnelEntry(host: string, options: ReadGhostTunnelOptions | string = {}) {\n const normalizedHost = normalizeHost(host);\n return listGhostTunnelEntries(options).find((entry) => entry.host === normalizedHost);\n}\n","import { randomUUID } from \"node:crypto\";\nimport { assertRelayLocalTarget, stripRelayForwardHeaders, type RelayLocalTarget } from \"./relay.js\";\nimport {\n createGhostTunnelRouteHeartbeat,\n decodeGhostTunnelBody,\n encodeGhostTunnelBody,\n type GhostTunnelQueuedRequest,\n type GhostTunnelQueuedResponse,\n type GhostTunnelStore\n} from \"./ghost-tunnel-store.js\";\nimport type { DevHostEntry } from \"./parse.js\";\n\nexport type GhostTunnelAgentOptions = {\n entries: DevHostEntry[];\n store: GhostTunnelStore;\n agentId?: string;\n targetHost?: string;\n routeTtlSeconds?: number;\n requestTtlSeconds?: number;\n pollIntervalMs?: number;\n maxResponseBodyBytes?: number;\n signal?: AbortSignal;\n fetch?: typeof fetch;\n log?: (message: string) => void;\n};\n\nexport type GhostTunnelAgent = {\n agentId: string;\n stop(): void;\n done: Promise<void>;\n};\n\nexport type ServeGhostTunnelLocalRequestInput = {\n request: GhostTunnelQueuedRequest;\n target: Required<RelayLocalTarget>;\n maxResponseBodyBytes: number;\n fetch?: typeof fetch;\n};\n\nfunction isStopped(signal: AbortSignal | undefined, localSignal: AbortSignal) {\n return localSignal.aborted || signal?.aborted === true;\n}\n\nfunction wait(ms: number, signal: AbortSignal | undefined, localSignal: AbortSignal) {\n if (isStopped(signal, localSignal)) return Promise.resolve();\n\n return new Promise<void>((resolve) => {\n const timeout = setTimeout(resolve, ms);\n const stop = () => {\n clearTimeout(timeout);\n resolve();\n };\n signal?.addEventListener(\"abort\", stop, { once: true });\n localSignal.addEventListener(\"abort\", stop, { once: true });\n });\n}\n\nfunction toHeaderRecord(headers: Headers) {\n const result: Record<string, string> = {};\n headers.forEach((value, name) => {\n result[name] = value;\n });\n return result;\n}\n\nfunction hasRequestBody(method: string) {\n return method !== \"GET\" && method !== \"HEAD\";\n}\n\nexport async function serveGhostTunnelLocalRequest(input: ServeGhostTunnelLocalRequestInput): Promise<GhostTunnelQueuedResponse> {\n const fetchImpl = input.fetch ?? fetch;\n const localUrl = new URL(`${input.target.protocol}://${input.target.host}:${input.target.port}/`);\n const requestPath = new URL(input.request.path, \"http://localghost.invalid\");\n localUrl.pathname = requestPath.pathname;\n localUrl.search = requestPath.search;\n\n try {\n const body = hasRequestBody(input.request.method) ? decodeGhostTunnelBody(input.request.bodyBase64) : undefined;\n const response = await fetchImpl(localUrl, {\n method: input.request.method,\n headers: {\n ...stripRelayForwardHeaders(input.request.headers),\n \"x-forwarded-host\": input.request.host,\n \"x-localghost-tunnel\": \"1\"\n },\n ...(body ? { body } : {})\n });\n const responseBody = Buffer.from(await response.arrayBuffer());\n if (responseBody.byteLength > input.maxResponseBodyBytes) {\n throw new Error(`Ghost Tunnel response exceeded ${input.maxResponseBodyBytes} bytes.`);\n }\n\n return {\n id: input.request.id,\n status: response.status,\n headers: toHeaderRecord(response.headers),\n createdAt: new Date().toISOString(),\n ...(responseBody.byteLength > 0 ? { bodyBase64: encodeGhostTunnelBody(responseBody) } : {})\n };\n } catch (error) {\n return {\n id: input.request.id,\n status: 502,\n headers: {\n \"content-type\": \"text/plain; charset=utf-8\",\n \"cache-control\": \"no-store\"\n },\n createdAt: new Date().toISOString(),\n error: error instanceof Error ? error.message : String(error),\n bodyBase64: encodeGhostTunnelBody(\"Ghost Tunnel local target failed.\")\n };\n }\n}\n\nasync function heartbeatRoutes(input: {\n entries: DevHostEntry[];\n store: GhostTunnelStore;\n agentId: string;\n targetHost: string;\n routeTtlSeconds: number;\n}) {\n for (const entry of input.entries) {\n const target = assertRelayLocalTarget({ host: input.targetHost, port: entry.port });\n await input.store.heartbeatRoute(createGhostTunnelRouteHeartbeat({\n host: entry.host,\n agentId: input.agentId,\n target,\n ttlSeconds: input.routeTtlSeconds\n }), input.routeTtlSeconds);\n }\n}\n\nasync function claimAndServe(input: {\n entry: DevHostEntry;\n store: GhostTunnelStore;\n targetHost: string;\n requestTtlSeconds: number;\n maxResponseBodyBytes: number;\n fetch?: typeof fetch;\n}) {\n const request = await input.store.claimRequest(input.entry.host);\n if (!request) return false;\n\n const target = assertRelayLocalTarget({ host: input.targetHost, port: input.entry.port });\n const response = await serveGhostTunnelLocalRequest({\n request,\n target,\n maxResponseBodyBytes: input.maxResponseBodyBytes,\n ...(input.fetch ? { fetch: input.fetch } : {})\n });\n await input.store.writeResponse(response, input.requestTtlSeconds);\n return true;\n}\n\nexport function startGhostTunnelAgent(options: GhostTunnelAgentOptions): GhostTunnelAgent {\n const controller = new AbortController();\n const localSignal = controller.signal;\n const signal = options.signal;\n const agentId = options.agentId ?? `localghost-${randomUUID()}`;\n const targetHost = options.targetHost ?? \"127.0.0.1\";\n const routeTtlSeconds = options.routeTtlSeconds ?? 30;\n const requestTtlSeconds = options.requestTtlSeconds ?? 60;\n const pollIntervalMs = options.pollIntervalMs ?? 500;\n const maxResponseBodyBytes = options.maxResponseBodyBytes ?? 5 * 1024 * 1024;\n\n const done = (async () => {\n if (options.entries.length === 0) {\n throw new Error(\"Ghost Tunnel agent requires at least one .ghosttunnel entry.\");\n }\n\n options.log?.(`localghost tunnel agent ${agentId}`);\n for (const entry of options.entries) {\n options.log?.(` ${entry.host} -> ${targetHost}:${entry.port}`);\n }\n\n let lastHeartbeat = 0;\n while (!isStopped(signal, localSignal)) {\n const now = Date.now();\n if (now - lastHeartbeat >= Math.max(1000, Math.floor(routeTtlSeconds * 1000 / 3))) {\n await heartbeatRoutes({\n entries: options.entries,\n store: options.store,\n agentId,\n targetHost,\n routeTtlSeconds\n });\n lastHeartbeat = now;\n }\n\n let served = false;\n for (const entry of options.entries) {\n served = await claimAndServe({\n entry,\n store: options.store,\n targetHost,\n requestTtlSeconds,\n maxResponseBodyBytes,\n ...(options.fetch ? { fetch: options.fetch } : {})\n }) || served;\n }\n\n if (!served) {\n await wait(pollIntervalMs, signal, localSignal);\n }\n }\n })();\n\n return {\n agentId,\n stop() {\n controller.abort();\n },\n done\n };\n}\n","import { createHmac, timingSafeEqual } from \"node:crypto\";\nimport { domainToASCII } from \"node:url\";\n\nexport type RelayProtocol = \"http\" | \"https\";\nexport type RelayAccessMode = \"private\" | \"public\";\n\nexport type RelayLocalTarget = {\n protocol?: RelayProtocol;\n host: string;\n port: number;\n};\n\nexport type RelayLimits = {\n requestBodyBytes: number;\n responseBytes: number;\n timeoutMs: number;\n maxConcurrentRequests: number;\n perRouteRequestsPerMinute: number;\n perIpRequestsPerMinute: number;\n};\n\nexport type RelayTargetPolicy = {\n allowedHosts: string[];\n blockedPorts: number[];\n allowPrivateNetworkTargets: boolean;\n};\n\nexport type RelayRouteClaim = {\n host: string;\n scope: string;\n expiresAt: string;\n agentId: string;\n};\n\nexport type SignedRelayRouteClaim = {\n payload: RelayRouteClaim;\n token: string;\n};\n\nexport type RelayRouteRegistrationInput = {\n authorizationHeader?: string | null;\n agentToken: string;\n claimToken: string;\n signingSecret: string;\n expectedScope: string;\n target: RelayLocalTarget;\n access?: RelayAccessMode;\n publicMode?: boolean;\n passwordProtected?: boolean;\n authRequired?: boolean;\n now?: Date;\n targetPolicy?: Partial<RelayTargetPolicy>;\n limits?: Partial<RelayLimits>;\n};\n\nexport type ActiveRelayRoute = {\n host: string;\n scope: string;\n agentId: string;\n expiresAt: string;\n target: Required<RelayLocalTarget>;\n access: RelayAccessMode;\n passwordProtected: boolean;\n authRequired: boolean;\n limits: RelayLimits;\n};\n\nexport type RelayOfflineResponse = {\n status: 503;\n headers: Record<string, string>;\n body: string;\n};\n\nexport const DEFAULT_RELAY_ALLOWED_TARGET_HOSTS = [\"localhost\", \"127.0.0.1\", \"::1\"] as const;\nexport const DEFAULT_RELAY_BLOCKED_PORTS = [22, 2375, 2376, 5432, 6379, 9200, 9229, 27017] as const;\n\nexport const DEFAULT_RELAY_LIMITS: RelayLimits = {\n requestBodyBytes: 5 * 1024 * 1024,\n responseBytes: 25 * 1024 * 1024,\n timeoutMs: 30_000,\n maxConcurrentRequests: 20,\n perRouteRequestsPerMinute: 120,\n perIpRequestsPerMinute: 60\n};\n\nexport const DEFAULT_RELAY_TARGET_POLICY: RelayTargetPolicy = {\n allowedHosts: [...DEFAULT_RELAY_ALLOWED_TARGET_HOSTS],\n blockedPorts: [...DEFAULT_RELAY_BLOCKED_PORTS],\n allowPrivateNetworkTargets: false\n};\n\nconst HOP_BY_HOP_HEADERS = new Set([\n \"connection\",\n \"keep-alive\",\n \"proxy-authenticate\",\n \"proxy-authorization\",\n \"te\",\n \"trailer\",\n \"transfer-encoding\",\n \"upgrade\"\n]);\n\nconst SENSITIVE_HEADERS = new Set([\"authorization\", \"cookie\", \"set-cookie\"]);\nconst TOKEN_QUERY_PATTERN = /(token|secret|key|password|session|jwt|auth)/i;\nconst HOST_PATTERN = /^(?=.{1,253}$)(?!-)[a-z0-9-]+(\\.[a-z0-9-]+)*$/i;\nconst IPV4_PATTERN = /^\\d{1,3}(?:\\.\\d{1,3}){3}$/;\n\nfunction base64UrlEncode(value: string | Buffer) {\n return Buffer.from(value).toString(\"base64url\");\n}\n\nfunction base64UrlDecode(value: string) {\n return Buffer.from(value, \"base64url\").toString(\"utf8\");\n}\n\nfunction signPayload(payload: string, secret: string) {\n return createHmac(\"sha256\", secret).update(payload).digest(\"base64url\");\n}\n\nfunction secureEqual(left: string, right: string) {\n const leftBuffer = Buffer.from(left);\n const rightBuffer = Buffer.from(right);\n return leftBuffer.length === rightBuffer.length && timingSafeEqual(leftBuffer, rightBuffer);\n}\n\nfunction normalizeHost(host: string) {\n const trimmed = host.trim().toLowerCase().replace(/\\.$/, \"\");\n if (!trimmed || trimmed.includes(\"*\") || trimmed.includes(\"/\") || trimmed.includes(\":\")) return null;\n const ascii = domainToASCII(trimmed);\n if (!ascii || ascii.includes(\"..\")) return null;\n return HOST_PATTERN.test(ascii) ? ascii : null;\n}\n\nfunction normalizeTargetHost(host: string) {\n const trimmed = host.trim().toLowerCase();\n if (trimmed === \"::1\" || trimmed === \"[::1]\") return \"::1\";\n if (trimmed.includes(\"/\") || trimmed.includes(\"*\")) return null;\n if (IPV4_PATTERN.test(trimmed)) return isValidIpv4(trimmed) ? trimmed : null;\n return normalizeHost(trimmed);\n}\n\nfunction isValidIpv4(value: string) {\n return value.split(\".\").every((part) => {\n const octet = Number(part);\n return Number.isInteger(octet) && octet >= 0 && octet <= 255 && String(octet) === part;\n });\n}\n\nfunction isPrivateIpv4(value: string) {\n if (!isValidIpv4(value)) return false;\n const [first = 0, second = 0] = value.split(\".\").map((part) => Number(part));\n return (\n first === 10 ||\n first === 127 ||\n (first === 172 && second >= 16 && second <= 31) ||\n (first === 192 && second === 168) ||\n (first === 169 && second === 254)\n );\n}\n\nfunction isLocalTargetHost(host: string) {\n return host === \"localhost\" || host === \"127.0.0.1\" || host === \"::1\";\n}\n\nfunction mergeTargetPolicy(policy: Partial<RelayTargetPolicy> | undefined): RelayTargetPolicy {\n return {\n allowedHosts: policy?.allowedHosts ?? DEFAULT_RELAY_TARGET_POLICY.allowedHosts,\n blockedPorts: policy?.blockedPorts ?? DEFAULT_RELAY_TARGET_POLICY.blockedPorts,\n allowPrivateNetworkTargets: policy?.allowPrivateNetworkTargets ?? DEFAULT_RELAY_TARGET_POLICY.allowPrivateNetworkTargets\n };\n}\n\nfunction mergeLimits(limits: Partial<RelayLimits> | undefined): RelayLimits {\n const merged = {\n ...DEFAULT_RELAY_LIMITS,\n ...(limits ?? {})\n };\n\n for (const [key, value] of Object.entries(merged)) {\n if (!Number.isInteger(value) || value < 1) {\n throw new Error(`Invalid relay limit ${key}: ${value}`);\n }\n }\n\n return merged;\n}\n\nexport function assertExactRelayHost(host: string) {\n const normalized = normalizeHost(host);\n if (!normalized) {\n throw new Error(`Relay route claims must use an exact hostname: ${host}`);\n }\n return normalized;\n}\n\nexport function assertRelayLocalTarget(target: RelayLocalTarget, policyInput?: Partial<RelayTargetPolicy>): Required<RelayLocalTarget> {\n if (!target || typeof target !== \"object\") {\n throw new Error(\"Relay target must be an explicit local target object.\");\n }\n\n const policy = mergeTargetPolicy(policyInput);\n const host = normalizeTargetHost(target.host);\n if (!host) {\n throw new Error(`Invalid relay target host: ${target.host}`);\n }\n\n if (!Number.isInteger(target.port) || target.port < 1 || target.port > 65535) {\n throw new Error(`Invalid relay target port: ${target.port}`);\n }\n\n const protocol = target.protocol ?? \"http\";\n if (protocol !== \"http\" && protocol !== \"https\") {\n throw new Error(`Invalid relay target protocol: ${String(protocol)}`);\n }\n\n if (policy.blockedPorts.includes(target.port)) {\n throw new Error(`Relay target port is blocked: ${target.port}`);\n }\n\n const allowedHosts = new Set(policy.allowedHosts.map((allowedHost) => normalizeTargetHost(allowedHost)).filter((value): value is string => Boolean(value)));\n if (!allowedHosts.has(host)) {\n throw new Error(`Relay target host is not explicitly allowed: ${host}`);\n }\n\n if (!policy.allowPrivateNetworkTargets && !isLocalTargetHost(host) && (host === \"::1\" || isPrivateIpv4(host))) {\n throw new Error(`Private-network relay target requires explicit opt-in: ${host}`);\n }\n\n return {\n protocol,\n host,\n port: target.port\n };\n}\n\nexport function authenticateRelayAgentToken(input: {\n authorizationHeader?: string | null;\n agentToken: string;\n}) {\n const expected = `Bearer ${input.agentToken}`;\n return typeof input.authorizationHeader === \"string\" && secureEqual(input.authorizationHeader, expected);\n}\n\nexport function signRelayRouteClaim(claim: RelayRouteClaim, signingSecret: string): SignedRelayRouteClaim {\n const payload: RelayRouteClaim = {\n ...claim,\n host: assertExactRelayHost(claim.host)\n };\n if (!payload.scope) throw new Error(\"Relay route claim requires a scope.\");\n if (!payload.agentId) throw new Error(\"Relay route claim requires an agentId.\");\n if (Number.isNaN(Date.parse(payload.expiresAt))) throw new Error(\"Relay route claim requires a valid expiresAt.\");\n\n const encodedPayload = base64UrlEncode(JSON.stringify(payload));\n const signature = signPayload(encodedPayload, signingSecret);\n return {\n payload,\n token: `${encodedPayload}.${signature}`\n };\n}\n\nexport function verifyRelayRouteClaim(token: string, signingSecret: string, options: {\n expectedScope: string;\n now?: Date;\n}): RelayRouteClaim {\n const [encodedPayload, signature] = token.split(\".\");\n if (!encodedPayload || !signature || token.split(\".\").length !== 2) {\n throw new Error(\"Invalid relay route claim token.\");\n }\n\n const expectedSignature = signPayload(encodedPayload, signingSecret);\n if (!secureEqual(signature, expectedSignature)) {\n throw new Error(\"Invalid relay route claim signature.\");\n }\n\n const parsed = JSON.parse(base64UrlDecode(encodedPayload)) as RelayRouteClaim;\n const host = assertExactRelayHost(parsed.host);\n if (parsed.scope !== options.expectedScope) {\n throw new Error(\"Relay route claim scope mismatch.\");\n }\n\n const now = options.now ?? new Date();\n if (Date.parse(parsed.expiresAt) <= now.getTime()) {\n throw new Error(\"Relay route claim has expired.\");\n }\n\n if (!parsed.agentId) {\n throw new Error(\"Relay route claim requires an agentId.\");\n }\n\n return { ...parsed, host };\n}\n\nexport function createRelayRouteRegistration(input: RelayRouteRegistrationInput): ActiveRelayRoute {\n if (!authenticateRelayAgentToken({\n agentToken: input.agentToken,\n ...(typeof input.authorizationHeader !== \"undefined\" ? { authorizationHeader: input.authorizationHeader } : {})\n })) {\n throw new Error(\"Relay route registration requires an authenticated local agent.\");\n }\n\n const claim = verifyRelayRouteClaim(input.claimToken, input.signingSecret, {\n expectedScope: input.expectedScope,\n ...(input.now ? { now: input.now } : {})\n });\n const target = assertRelayLocalTarget(input.target, input.targetPolicy);\n const access = input.publicMode === true ? \"public\" : input.access ?? \"private\";\n const passwordProtected = input.passwordProtected ?? false;\n const authRequired = input.authRequired ?? false;\n\n if (access === \"public\" && input.publicMode !== true) {\n throw new Error(\"Relay public mode must be explicitly enabled.\");\n }\n\n if (access === \"private\" && !passwordProtected && !authRequired) {\n throw new Error(\"Private relay previews require password or auth.\");\n }\n\n return {\n host: claim.host,\n scope: claim.scope,\n agentId: claim.agentId,\n expiresAt: claim.expiresAt,\n target,\n access,\n passwordProtected,\n authRequired,\n limits: mergeLimits(input.limits)\n };\n}\n\nexport function isRelayRouteActive(route: ActiveRelayRoute, options: {\n agentConnected: boolean;\n now?: Date;\n}) {\n if (!options.agentConnected) return false;\n return Date.parse(route.expiresAt) > (options.now ?? new Date()).getTime();\n}\n\nexport function stripRelayForwardHeaders(headers: Record<string, string | string[] | undefined>) {\n const stripped: Record<string, string | string[]> = {};\n\n for (const [name, value] of Object.entries(headers)) {\n if (typeof value === \"undefined\") continue;\n const lowerName = name.toLowerCase();\n if (HOP_BY_HOP_HEADERS.has(lowerName)) continue;\n if (lowerName.startsWith(\"x-localghost-\")) continue;\n stripped[name] = value;\n }\n\n return stripped;\n}\n\nexport function redactRelayHeaders(headers: Record<string, string | string[] | undefined>) {\n const redacted: Record<string, string | string[]> = {};\n\n for (const [name, value] of Object.entries(headers)) {\n if (typeof value === \"undefined\") continue;\n redacted[name] = SENSITIVE_HEADERS.has(name.toLowerCase()) ? \"[redacted]\" : value;\n }\n\n return redacted;\n}\n\nexport function redactRelayLogUrl(input: string) {\n const url = new URL(input, \"http://localghost.invalid\");\n for (const key of [...url.searchParams.keys()]) {\n if (TOKEN_QUERY_PATTERN.test(key)) {\n url.searchParams.set(key, \"[redacted]\");\n }\n }\n\n return input.startsWith(\"http://\") || input.startsWith(\"https://\")\n ? url.toString()\n : `${url.pathname}${url.search}`;\n}\n\nexport function renderRelayOfflineResponse(): RelayOfflineResponse {\n return {\n status: 503,\n headers: {\n \"content-type\": \"text/html; charset=utf-8\",\n \"cache-control\": \"no-store\"\n },\n body: [\n \"<!doctype html>\",\n \"<html>\",\n \"<head><meta charset=\\\"utf-8\\\"><title>Preview offline</title></head>\",\n \"<body><h1>Preview offline</h1><p>The local agent is not connected. Try again later.</p></body>\",\n \"</html>\"\n ].join(\"\")\n };\n}\n","import { randomUUID } from \"node:crypto\";\nimport type { RelayLocalTarget } from \"./relay.js\";\n\nexport const DEFAULT_GHOST_TUNNEL_RESPONSE_TTL_SECONDS = 60;\n\nexport type GhostTunnelStoreEnv = Record<string, string | undefined>;\n\nexport type GhostTunnelQueuedRequest = {\n id: string;\n host: string;\n method: string;\n path: string;\n headers: Record<string, string>;\n createdAt: string;\n expiresAt: string;\n bodyBase64?: string;\n};\n\nexport type GhostTunnelQueuedResponse = {\n id: string;\n status: number;\n headers: Record<string, string>;\n createdAt: string;\n bodyBase64?: string;\n error?: string;\n};\n\nexport type GhostTunnelRouteHeartbeat = {\n host: string;\n agentId: string;\n target: Required<RelayLocalTarget>;\n updatedAt: string;\n expiresAt: string;\n};\n\nexport type GhostTunnelStore = {\n heartbeatRoute(route: GhostTunnelRouteHeartbeat, ttlSeconds: number): Promise<void>;\n getRoute(host: string): Promise<GhostTunnelRouteHeartbeat | null>;\n enqueueRequest(request: GhostTunnelQueuedRequest, ttlSeconds: number): Promise<void>;\n claimRequest(host: string): Promise<GhostTunnelQueuedRequest | null>;\n writeResponse(response: GhostTunnelQueuedResponse, ttlSeconds: number): Promise<void>;\n readResponse(requestId: string): Promise<GhostTunnelQueuedResponse | null>;\n cleanup(requestId: string): Promise<void>;\n};\n\nexport type RedisGhostTunnelStoreOptions = {\n url: string;\n token: string;\n namespace?: string;\n fetch?: typeof fetch;\n};\n\nexport type RedisGhostTunnelEnvResolution = {\n url: string;\n token: string;\n source: \"localghost\" | \"upstash\" | \"vercel-kv\" | \"redis\";\n};\n\nfunction base64Encode(value: Buffer) {\n return value.toString(\"base64\");\n}\n\nexport function encodeGhostTunnelBody(value: Buffer | Uint8Array | string) {\n return base64Encode(Buffer.isBuffer(value) ? value : Buffer.from(value));\n}\n\nexport function decodeGhostTunnelBody(value: string | undefined) {\n return value ? Buffer.from(value, \"base64\") : undefined;\n}\n\nexport function createGhostTunnelQueuedRequest(input: {\n host: string;\n method: string;\n path: string;\n headers?: Record<string, string>;\n body?: Buffer | Uint8Array | string;\n ttlSeconds: number;\n now?: Date;\n}): GhostTunnelQueuedRequest {\n const now = input.now ?? new Date();\n const bodyBase64 = typeof input.body === \"undefined\" ? undefined : encodeGhostTunnelBody(input.body);\n\n return {\n id: randomUUID(),\n host: input.host,\n method: input.method.toUpperCase(),\n path: input.path,\n headers: input.headers ?? {},\n createdAt: now.toISOString(),\n expiresAt: new Date(now.getTime() + input.ttlSeconds * 1000).toISOString(),\n ...(bodyBase64 ? { bodyBase64 } : {})\n };\n}\n\nexport function createGhostTunnelRouteHeartbeat(input: {\n host: string;\n agentId: string;\n target: Required<RelayLocalTarget>;\n ttlSeconds: number;\n now?: Date;\n}): GhostTunnelRouteHeartbeat {\n const now = input.now ?? new Date();\n\n return {\n host: input.host,\n agentId: input.agentId,\n target: input.target,\n updatedAt: now.toISOString(),\n expiresAt: new Date(now.getTime() + input.ttlSeconds * 1000).toISOString()\n };\n}\n\nfunction isExpired(expiresAt: string, now = new Date()) {\n const timestamp = Date.parse(expiresAt);\n return Number.isNaN(timestamp) || timestamp <= now.getTime();\n}\n\nfunction serializeJson(value: unknown) {\n return JSON.stringify(value);\n}\n\nfunction parseJson<T>(value: unknown): T | null {\n if (typeof value !== \"string\") return null;\n try {\n return JSON.parse(value) as T;\n } catch {\n return null;\n }\n}\n\nfunction keyPart(value: string) {\n return value.toLowerCase().replace(/[^a-z0-9._:-]/g, \"_\");\n}\n\nfunction removeTrailingSlashes(value: string) {\n let end = value.length;\n while (end > 0 && value.charCodeAt(end - 1) === 47) end -= 1;\n return value.slice(0, end);\n}\n\nclass MemoryGhostTunnelStore implements GhostTunnelStore {\n private readonly routes = new Map<string, GhostTunnelRouteHeartbeat>();\n private readonly queues = new Map<string, GhostTunnelQueuedRequest[]>();\n private readonly responses = new Map<string, { value: GhostTunnelQueuedResponse; expiresAt: string }>();\n\n async heartbeatRoute(route: GhostTunnelRouteHeartbeat): Promise<void> {\n this.routes.set(route.host, route);\n }\n\n async getRoute(host: string): Promise<GhostTunnelRouteHeartbeat | null> {\n const route = this.routes.get(host);\n if (!route) return null;\n if (!isExpired(route.expiresAt)) return route;\n this.routes.delete(host);\n return null;\n }\n\n async enqueueRequest(request: GhostTunnelQueuedRequest): Promise<void> {\n const queue = this.queues.get(request.host) ?? [];\n queue.push(request);\n this.queues.set(request.host, queue);\n }\n\n async claimRequest(host: string): Promise<GhostTunnelQueuedRequest | null> {\n const queue = this.queues.get(host) ?? [];\n\n while (queue.length > 0) {\n const request = queue.shift();\n if (request && !isExpired(request.expiresAt)) {\n return request;\n }\n }\n\n return null;\n }\n\n async writeResponse(response: GhostTunnelQueuedResponse, ttlSeconds: number): Promise<void> {\n this.responses.set(response.id, {\n value: response,\n expiresAt: new Date(Date.now() + ttlSeconds * 1000).toISOString()\n });\n }\n\n async readResponse(requestId: string): Promise<GhostTunnelQueuedResponse | null> {\n const response = this.responses.get(requestId);\n if (!response) return null;\n if (!isExpired(response.expiresAt)) return response.value;\n this.responses.delete(requestId);\n return null;\n }\n\n async cleanup(requestId: string): Promise<void> {\n this.responses.delete(requestId);\n }\n}\n\nexport function createMemoryGhostTunnelStore(): GhostTunnelStore {\n return new MemoryGhostTunnelStore();\n}\n\nclass RedisGhostTunnelStore implements GhostTunnelStore {\n private readonly url: string;\n private readonly token: string;\n private readonly namespace: string;\n private readonly fetchImpl: typeof fetch;\n\n constructor(options: RedisGhostTunnelStoreOptions) {\n this.url = removeTrailingSlashes(options.url);\n this.token = options.token;\n this.namespace = options.namespace ?? \"localghost\";\n this.fetchImpl = options.fetch ?? fetch;\n }\n\n private key(kind: \"route\" | \"queue\" | \"response\", id: string) {\n return `${this.namespace}:ghost-tunnel:${kind}:${keyPart(id)}`;\n }\n\n private async command<T>(command: string, ...args: Array<string | number>): Promise<T | null> {\n const response = await this.fetchImpl(this.url, {\n method: \"POST\",\n headers: {\n authorization: `Bearer ${this.token}`,\n \"content-type\": \"application/json\"\n },\n body: JSON.stringify([command, ...args])\n });\n\n if (!response.ok) {\n throw new Error(`Redis Ghost Tunnel command failed: ${response.status} ${response.statusText}`);\n }\n\n const payload = await response.json() as { result?: unknown; error?: string };\n if (payload.error) {\n throw new Error(`Redis Ghost Tunnel command failed: ${payload.error}`);\n }\n\n return (typeof payload.result === \"undefined\" ? null : payload.result) as T | null;\n }\n\n async heartbeatRoute(route: GhostTunnelRouteHeartbeat, ttlSeconds: number): Promise<void> {\n await this.command(\"SET\", this.key(\"route\", route.host), serializeJson(route), \"EX\", ttlSeconds);\n }\n\n async getRoute(host: string): Promise<GhostTunnelRouteHeartbeat | null> {\n const route = parseJson<GhostTunnelRouteHeartbeat>(await this.command<string>(\"GET\", this.key(\"route\", host)));\n return route && !isExpired(route.expiresAt) ? route : null;\n }\n\n async enqueueRequest(request: GhostTunnelQueuedRequest, ttlSeconds: number): Promise<void> {\n const queueKey = this.key(\"queue\", request.host);\n await this.command(\"RPUSH\", queueKey, serializeJson(request));\n await this.command(\"EXPIRE\", queueKey, ttlSeconds);\n }\n\n async claimRequest(host: string): Promise<GhostTunnelQueuedRequest | null> {\n const queueKey = this.key(\"queue\", host);\n\n while (true) {\n const request = parseJson<GhostTunnelQueuedRequest>(await this.command<string>(\"LPOP\", queueKey));\n if (!request) return null;\n if (!isExpired(request.expiresAt)) return request;\n }\n }\n\n async writeResponse(response: GhostTunnelQueuedResponse, ttlSeconds: number): Promise<void> {\n await this.command(\"SET\", this.key(\"response\", response.id), serializeJson(response), \"EX\", ttlSeconds);\n }\n\n async readResponse(requestId: string): Promise<GhostTunnelQueuedResponse | null> {\n return parseJson<GhostTunnelQueuedResponse>(await this.command<string>(\"GET\", this.key(\"response\", requestId)));\n }\n\n async cleanup(requestId: string): Promise<void> {\n await this.command(\"DEL\", this.key(\"response\", requestId));\n }\n}\n\nexport function createRedisGhostTunnelStore(options: RedisGhostTunnelStoreOptions): GhostTunnelStore {\n return new RedisGhostTunnelStore(options);\n}\n\nexport function resolveRedisGhostTunnelEnv(env: GhostTunnelStoreEnv = process.env): RedisGhostTunnelEnvResolution {\n const candidates: Array<RedisGhostTunnelEnvResolution | null> = [\n env.LOCALGHOST_REDIS_REST_URL && env.LOCALGHOST_REDIS_REST_TOKEN\n ? { url: env.LOCALGHOST_REDIS_REST_URL, token: env.LOCALGHOST_REDIS_REST_TOKEN, source: \"localghost\" }\n : null,\n env.UPSTASH_REDIS_REST_URL && env.UPSTASH_REDIS_REST_TOKEN\n ? { url: env.UPSTASH_REDIS_REST_URL, token: env.UPSTASH_REDIS_REST_TOKEN, source: \"upstash\" }\n : null,\n env.KV_REST_API_URL && env.KV_REST_API_TOKEN\n ? { url: env.KV_REST_API_URL, token: env.KV_REST_API_TOKEN, source: \"vercel-kv\" }\n : null,\n env.REDIS_REST_API_URL && env.REDIS_REST_API_TOKEN\n ? { url: env.REDIS_REST_API_URL, token: env.REDIS_REST_API_TOKEN, source: \"redis\" }\n : null\n ];\n const match = candidates.find((candidate): candidate is RedisGhostTunnelEnvResolution => Boolean(candidate));\n\n if (!match) {\n throw new Error(\"Ghost Tunnel Redis transport requires REST env vars: UPSTASH_REDIS_REST_URL/UPSTASH_REDIS_REST_TOKEN, KV_REST_API_URL/KV_REST_API_TOKEN, or LOCALGHOST_REDIS_REST_URL/LOCALGHOST_REDIS_REST_TOKEN.\");\n }\n\n return match;\n}\n\nexport function createRedisGhostTunnelStoreFromEnv(input: {\n env?: GhostTunnelStoreEnv;\n namespace?: string;\n fetch?: typeof fetch;\n} = {}): GhostTunnelStore {\n const resolved = resolveRedisGhostTunnelEnv(input.env);\n return createRedisGhostTunnelStore({\n url: resolved.url,\n token: resolved.token,\n ...(input.namespace ? { namespace: input.namespace } : {}),\n ...(input.fetch ? { fetch: input.fetch } : {})\n });\n}\n","import { writeFileSync } from \"node:fs\";\nimport { tmpdir } from \"node:os\";\nimport { join } from \"node:path\";\nimport { execa } from \"execa\";\nimport { sanitizeProjectName } from \"./config.js\";\nimport { readTextFile } from \"./fs.js\";\nimport type { DevHostEntry } from \"./parse.js\";\n\nexport type UpdateSystemHostsResult = {\n changed: boolean;\n hostsPath: string;\n tempPath?: string;\n};\n\nexport type RemoveSystemHostsResult = UpdateSystemHostsResult & {\n removed: boolean;\n};\n\nfunction escapeRegExp(value: string) {\n return value.replace(/[.*+?^${}()|[\\]\\\\]/g, \"\\\\$&\");\n}\n\nfunction getManagedBlockPattern(projectName: string) {\n const sanitizedProjectName = sanitizeProjectName(projectName);\n const start = `# localghost:start ${sanitizedProjectName}`;\n const end = `# localghost:end ${sanitizedProjectName}`;\n return new RegExp(`${escapeRegExp(start)}[\\\\s\\\\S]*?${escapeRegExp(end)}\\\\n?`, \"m\");\n}\n\nexport function getSystemHostsPath(env: NodeJS.ProcessEnv = process.env) {\n if (env.LOCALGHOST_HOSTS_PATH) return env.LOCALGHOST_HOSTS_PATH;\n return process.platform === \"win32\" ? \"C:\\\\Windows\\\\System32\\\\drivers\\\\etc\\\\hosts\" : \"/etc/hosts\";\n}\n\nexport function renderHostsBlock(projectName: string, entries: DevHostEntry[]) {\n const sanitizedProjectName = sanitizeProjectName(projectName);\n const hosts = [...new Set(entries.map((entry) => entry.host))].sort();\n\n return [\n `# localghost:start ${sanitizedProjectName}`,\n ...hosts.map((host) => `127.0.0.1 ${host}`),\n `# localghost:end ${sanitizedProjectName}`,\n \"\"\n ].join(\"\\n\");\n}\n\nexport function upsertManagedBlock(existing: string, projectName: string, block: string) {\n const pattern = getManagedBlockPattern(projectName);\n\n if (pattern.test(existing)) {\n return existing.replace(pattern, block);\n }\n\n return `${existing.trimEnd()}\\n\\n${block}`;\n}\n\nexport function removeManagedBlock(existing: string, projectName: string) {\n const pattern = getManagedBlockPattern(projectName);\n\n if (!pattern.test(existing)) {\n return existing;\n }\n\n return existing.replace(pattern, \"\").replace(/\\n{3,}/g, \"\\n\\n\").trimEnd() + \"\\n\";\n}\n\nasync function writeSystemHostsFile(hostsPath: string, next: string, projectName: string) {\n const sanitizedProjectName = sanitizeProjectName(projectName);\n const tempPath = join(tmpdir(), `localghost-${sanitizedProjectName}-hosts`);\n writeFileSync(tempPath, next, \"utf8\");\n\n if (process.env.LOCALGHOST_HOSTS_PATH) {\n writeFileSync(hostsPath, next, \"utf8\");\n return tempPath;\n }\n\n if (process.platform === \"win32\") {\n throw new Error(`Windows support: run as administrator and copy ${tempPath} to ${hostsPath}.`);\n }\n\n await execa(\"sudo\", [\"cp\", tempPath, hostsPath], { stdio: \"inherit\" });\n\n return tempPath;\n}\n\nexport async function updateSystemHosts(projectName: string, entries: DevHostEntry[]): Promise<UpdateSystemHostsResult> {\n const sanitizedProjectName = sanitizeProjectName(projectName);\n const hostsPath = getSystemHostsPath();\n const existing = readTextFile(hostsPath);\n const block = renderHostsBlock(sanitizedProjectName, entries);\n const next = upsertManagedBlock(existing, sanitizedProjectName, block);\n\n if (next === existing) {\n return { changed: false, hostsPath };\n }\n\n const tempPath = await writeSystemHostsFile(hostsPath, next, sanitizedProjectName);\n\n return { changed: true, hostsPath, tempPath };\n}\n\nexport async function removeSystemHosts(projectName: string): Promise<RemoveSystemHostsResult> {\n const sanitizedProjectName = sanitizeProjectName(projectName);\n const hostsPath = getSystemHostsPath();\n const existing = readTextFile(hostsPath);\n const next = removeManagedBlock(existing, sanitizedProjectName);\n\n if (next === existing) {\n return { changed: false, removed: false, hostsPath };\n }\n\n const tempPath = await writeSystemHostsFile(hostsPath, next, sanitizedProjectName);\n\n return { changed: true, removed: true, hostsPath, tempPath };\n}\n","import { existsSync, readFileSync, writeFileSync } from \"node:fs\";\nimport { join } from \"node:path\";\nimport { getProjectName, LOCALGHOST_CONFIG_FILE, sanitizeProjectName } from \"./config.js\";\nimport { writeTextFile } from \"./fs.js\";\n\nexport type PackageManager = \"npm\" | \"yarn\" | \"pnpm\" | \"bun\";\n\nexport type InitOptions = {\n cwd?: string;\n host?: string;\n port?: number;\n apiHost?: string;\n apiPort?: number;\n force?: boolean;\n packageManager?: PackageManager;\n writeScripts?: boolean;\n configFile?: string;\n};\n\nexport type InitResult = {\n configPath: string;\n configCreated: boolean;\n packageJsonPath?: string;\n packageJsonChanged: boolean;\n packageManager: PackageManager;\n nextSteps: string[];\n};\n\nexport function detectPackageManager(cwd = process.cwd()): PackageManager {\n if (existsSync(join(cwd, \"pnpm-lock.yaml\"))) return \"pnpm\";\n if (existsSync(join(cwd, \"yarn.lock\"))) return \"yarn\";\n if (existsSync(join(cwd, \"bun.lock\")) || existsSync(join(cwd, \"bun.lockb\"))) return \"bun\";\n return \"npm\";\n}\n\nexport function packageRunCommand(packageManager: PackageManager, script: string): string {\n if (packageManager === \"yarn\") return `yarn ${script}`;\n if (packageManager === \"pnpm\") return `pnpm ${script}`;\n if (packageManager === \"bun\") return `bun run ${script}`;\n return `npm run ${script}`;\n}\n\nexport function packageAddCommand(packageManager: PackageManager, packageName = \"@hamedb89/localghost\"): string {\n if (packageManager === \"yarn\") return `yarn add -D ${packageName}`;\n if (packageManager === \"pnpm\") return `pnpm add -D ${packageName}`;\n if (packageManager === \"bun\") return `bun add -d ${packageName}`;\n return `npm install -D ${packageName}`;\n}\n\nfunction renderConfig(options: Required<Pick<InitOptions, \"host\" | \"port\" | \"apiHost\" | \"apiPort\">>) {\n return [\n \"# Buh. Friendly names for local services.\",\n \"# Format: <host> <port>\",\n `${options.host} ${options.port}`,\n `www.${options.host} ${options.port}`,\n `${options.apiHost} ${options.apiPort}`,\n \"\"\n ].join(\"\\n\");\n}\n\nfunction readPackageJson(path: string): Record<string, unknown> | null {\n try {\n return JSON.parse(readFileSync(path, \"utf8\")) as Record<string, unknown>;\n } catch {\n return null;\n }\n}\n\nfunction shellQuote(value: string) {\n if (/^[A-Za-z0-9_./:-]+$/.test(value)) return value;\n return `'${value.replace(/'/g, `'\"'\"'`)}'`;\n}\n\nfunction getConfigFlag(configFile: string) {\n return configFile === LOCALGHOST_CONFIG_FILE ? \"\" : ` --config ${shellQuote(configFile)}`;\n}\n\nfunction hasLocalghostDependency(pkg: Record<string, unknown>) {\n return [\"dependencies\", \"devDependencies\", \"optionalDependencies\", \"peerDependencies\"].some((field) => {\n const dependencies = pkg[field];\n return typeof dependencies === \"object\" && dependencies !== null && \"@hamedb89/localghost\" in dependencies;\n });\n}\n\nfunction localghostCommand(packageManager: PackageManager, installed: boolean) {\n if (installed) return \"localghost\";\n if (packageManager === \"pnpm\") return \"pnpm dlx @hamedb89/localghost\";\n if (packageManager === \"yarn\") return \"yarn dlx @hamedb89/localghost\";\n if (packageManager === \"bun\") return \"bunx --package @hamedb89/localghost localghost\";\n return \"npm exec --yes --package=@hamedb89/localghost -- localghost\";\n}\n\nfunction updatePackageScripts(packageJsonPath: string, configFile: string, packageManager: PackageManager): boolean {\n const pkg = readPackageJson(packageJsonPath);\n if (!pkg) return false;\n\n const scripts = typeof pkg.scripts === \"object\" && pkg.scripts ? (pkg.scripts as Record<string, unknown>) : {};\n const configFlag = getConfigFlag(configFile);\n const command = localghostCommand(packageManager, hasLocalghostDependency(pkg));\n const nextScripts = {\n ...scripts,\n \"localghost:setup\": scripts[\"localghost:setup\"] ?? `${command} setup${configFlag}`,\n \"localghost:proxy\": scripts[\"localghost:proxy\"] ?? `${command} dev${configFlag}`,\n \"localghost:proxy:https\": scripts[\"localghost:proxy:https\"] ?? `${command} dev${configFlag} --https`,\n \"localghost:run\": scripts[\"localghost:run\"] ?? `${command} run${configFlag} --`,\n \"localghost:ready\": scripts[\"localghost:ready\"] ?? `${command} status${configFlag} --ready`,\n \"localghost:repair\": scripts[\"localghost:repair\"] ?? `${command} repair${configFlag}`,\n \"localghost:trust\": scripts[\"localghost:trust\"] ?? `${command} trust${configFlag}`,\n \"localghost:ps\": scripts[\"localghost:ps\"] ?? `${command} ps`,\n \"localghost:print\": scripts[\"localghost:print\"] ?? `${command} print${configFlag}`,\n \"localghost:routes\": scripts[\"localghost:routes\"] ?? `${command} routes${configFlag}`,\n \"localghost:status\": scripts[\"localghost:status\"] ?? `${command} status`,\n \"localghost:reset\": scripts[\"localghost:reset\"] ?? `${command} reset`,\n \"localghost:teardown\": scripts[\"localghost:teardown\"] ?? `${command} teardown`,\n \"localghost:doctor\": scripts[\"localghost:doctor\"] ?? `${command} doctor`,\n \"localghost:update\": scripts[\"localghost:update\"] ?? `${command} update`,\n \"caddy:setup\": scripts[\"caddy:setup\"] ?? `${command} setup${configFlag}`,\n \"caddy:dev\": scripts[\"caddy:dev\"] ?? `${command} dev${configFlag}`\n };\n\n const changed = JSON.stringify(scripts) !== JSON.stringify(nextScripts);\n if (!changed) return false;\n\n pkg.scripts = nextScripts;\n writeFileSync(packageJsonPath, `${JSON.stringify(pkg, null, 2)}\\n`, \"utf8\");\n return true;\n}\n\nexport function initLocalghost(options: InitOptions = {}): InitResult {\n const cwd = options.cwd ?? process.cwd();\n const projectName = sanitizeProjectName(getProjectName(cwd).split(\"/\").pop() ?? \"app\");\n const host = options.host ?? `${projectName}.localhost`;\n const port = options.port ?? 5173;\n const apiHost = options.apiHost ?? `api.${host}`;\n const apiPort = options.apiPort ?? 8787;\n const packageManager = options.packageManager ?? detectPackageManager(cwd);\n const configFile = options.configFile ?? LOCALGHOST_CONFIG_FILE;\n const configPath = join(cwd, configFile);\n const configExists = existsSync(configPath);\n\n if (configExists && !options.force) {\n return {\n configPath,\n configCreated: false,\n packageJsonChanged: false,\n packageManager,\n nextSteps: [\n packageRunCommand(packageManager, \"localghost:doctor\"),\n packageRunCommand(packageManager, \"localghost:setup\"),\n packageRunCommand(packageManager, \"localghost:ready\"),\n packageRunCommand(packageManager, \"localghost:proxy\")\n ]\n };\n }\n\n writeTextFile(configPath, renderConfig({ host, port, apiHost, apiPort }));\n\n const packageJsonPath = join(cwd, \"package.json\");\n const packageJsonChanged = options.writeScripts ? updatePackageScripts(packageJsonPath, configFile, packageManager) : false;\n\n return {\n configPath,\n configCreated: true,\n ...(existsSync(packageJsonPath) ? { packageJsonPath } : {}),\n packageJsonChanged,\n packageManager,\n nextSteps: [\n packageRunCommand(packageManager, \"localghost:doctor\"),\n packageRunCommand(packageManager, \"localghost:setup\"),\n packageRunCommand(packageManager, \"localghost:ready\"),\n packageRunCommand(packageManager, \"localghost:proxy\")\n ]\n };\n}\n","export const LOCALGHOST_AGENT_GUIDE = `# Localghost agent guide\n\nLocalghost owns the local development proxy and the app process boundary.\n\n## Preferred repository setup\n\nFor a normal repository with Localghost installed as a dev dependency, use this package script:\n\n \"dev\": \"localghost\"\n\nIf the repository does not have a local CLI yet, use the package-manager launcher:\n\n npm exec --yes --package=@hamedb89/localghost -- localghost\n pnpm dlx @hamedb89/localghost\n yarn dlx @hamedb89/localghost\n bunx --package @hamedb89/localghost localghost\n\nFor an explicit app command, keep the raw command separate:\n\n \"dev\": \"localghost run -- vite\"\n \"dev:raw\": \"vite\"\n\nUse \\`localghost dev\\` only when the Caddy proxy should run without starting the app.\n\n## Useful commands\n\n- \\`localghost\\`: detect and run the repository development command.\n- \\`localghost run -- <command>\\`: wrap an explicit app command.\n- \\`localghost dev\\`: run only the local Caddy proxy.\n- \\`localghost status --ready\\`: check project setup.\n- \\`localghost repair\\`: repair managed hosts and Caddy setup.\n- \\`localghost ps --json\\`: inspect Localghost-managed repositories, instances, and ports.\n- \\`localghost routes\\`: inspect hostname-to-port routing.\n- \\`localghost doctor\\`: check machine prerequisites, ports, and registry state.\n- \\`localghost repair --reallocate-port\\`: move an occupied project port to a stable available port.\n\n- \\`localghost update\\`: check npm for a newer Localghost release.\n- \\`localghost upgrade\\`: install or update Localghost as a repository dev dependency.\n\nUse \\`localghost\\` directly when the package is installed locally. Use \\`npm exec --yes --package=@hamedb89/localghost -- localghost <command>\\`, \\`pnpm dlx @hamedb89/localghost <command>\\`, \\`yarn dlx @hamedb89/localghost <command>\\`, or \\`bunx --package @hamedb89/localghost localghost <command>\\` when it is not.\n\n## Configuration\n\n- Commit repository defaults in \\`localghost.config.mjs\\`.\n- Keep hostname and requested-port routes in \\`.localghost\\`.\n- CLI flags override repository configuration for one invocation.\n- Localghost remembers active project and instance port assignments in user state under \\`~/.localghost\\`.\n- Do not edit the registry manually and do not start Caddy separately.\n\n## Port behavior\n\nLocalghost remembers ports by canonical repository path and instance key. Concurrent Localghost instances receive distinct ports. The operating-system bind check remains authoritative when another tool already owns a port.\n`;\n\nexport function formatLocalghostAgentGuide(format: \"text\" | \"json\" = \"text\") {\n if (format === \"json\") {\n return JSON.stringify({\n preferredScript: \"localghost\",\n packageInstall: \"npm install -D @hamedb89/localghost\",\n packageUpgrade: \"localghost upgrade\",\n packageLaunchers: {\n npm: \"npm exec --yes --package=@hamedb89/localghost -- localghost\",\n pnpm: \"pnpm dlx @hamedb89/localghost\",\n yarn: \"yarn dlx @hamedb89/localghost\",\n bun: \"bunx --package @hamedb89/localghost localghost\"\n },\n explicitScript: \"localghost run -- <command>\",\n proxyOnlyCommand: \"localghost dev\",\n inspectionCommands: [\"localghost status --ready\", \"localghost ps --json\", \"localghost routes\", \"localghost doctor\"],\n projectConfig: \"localghost.config.mjs\",\n routeConfig: \".localghost\",\n userState: \"~/.localghost\"\n }, null, 2);\n }\n\n return LOCALGHOST_AGENT_GUIDE;\n}\n","import { stdin as input, stdout as output } from \"node:process\";\nimport { createInterface } from \"node:readline/promises\";\n\nexport function canPrompt() {\n return Boolean(input.isTTY && output.isTTY);\n}\n\nexport async function withPrompt<T>(run: (prompt: (question: string) => Promise<string>) => Promise<T>) {\n const rl = createInterface({ input, output });\n try {\n return await run((question) => rl.question(question));\n } finally {\n rl.close();\n }\n}\n\nexport async function confirm(question: string, defaultValue = true) {\n return withPrompt(async (prompt) => {\n const suffix = defaultValue ? \" [Y/n] \" : \" [y/N] \";\n const answer = (await prompt(`${question}${suffix}`)).trim().toLowerCase();\n if (!answer) return defaultValue;\n return answer === \"y\" || answer === \"yes\";\n });\n}\n\nexport async function ask(question: string, defaultValue?: string) {\n return withPrompt(async (prompt) => {\n const suffix = defaultValue ? ` (${defaultValue}) ` : \" \";\n const answer = (await prompt(`${question}${suffix}`)).trim();\n return answer || defaultValue || \"\";\n });\n}\n","import type { DevHostEntry } from \"./parse.js\";\nimport type { GhostTunnelConfig } from \"./tunnel.js\";\n\nexport type DomainRoute = {\n host: string;\n port: number;\n url: string;\n upstream: string;\n};\n\nexport type DomainRouteOptions = {\n https?: boolean;\n};\n\nexport type GhostTunnelFormatOptions = {\n color?: boolean;\n label?: \"configured\" | \"expected\" | \"ready\" | \"running\";\n verbose?: boolean;\n};\n\nconst ansi = {\n cyan: \"\\u001b[36m\",\n dim: \"\\u001b[2m\",\n green: \"\\u001b[32m\",\n reset: \"\\u001b[0m\",\n yellow: \"\\u001b[33m\"\n};\n\nfunction colorize(value: string, color: string, enabled: boolean) {\n return enabled ? `${color}${value}${ansi.reset}` : value;\n}\n\nfunction colorizeUrl(value: string, enabled: boolean) {\n if (!enabled) return value;\n return colorize(value.replace(/\\*/g, `${ansi.yellow}*${ansi.cyan}`), ansi.cyan, enabled);\n}\n\nexport function getDomainRoutes(entries: DevHostEntry[], options: DomainRouteOptions = {}): DomainRoute[] {\n const protocol = options.https === true ? \"https\" : \"http\";\n\n return [...entries]\n .sort((left, right) => left.host.localeCompare(right.host) || left.port - right.port)\n .map((entry) => ({\n host: entry.host,\n port: entry.port,\n url: `${protocol}://${entry.host}/`,\n upstream: `http://${entry.target}`\n }));\n}\n\nexport function formatDomainRoutes(entries: DevHostEntry[], options: DomainRouteOptions = {}) {\n const routes = getDomainRoutes(entries, options);\n\n if (routes.length === 0) {\n return \"localghost routes\\n no routes\";\n }\n\n return [\n \"localghost routes\",\n ...routes.map((route) => ` ${route.url} -> ${route.upstream}`)\n ].join(\"\\n\");\n}\n\nexport function formatGhostTunnel(config: GhostTunnelConfig, options: GhostTunnelFormatOptions = {}) {\n if (!config.enabled) return null;\n\n const color = options.color === true;\n const label = options.label ?? \"expected\";\n const labelColor = label === \"running\" ? ansi.green : ansi.dim;\n const lines = [\n \"localghost ghost tunnel\",\n ` mode: ${config.mode}`\n ];\n const urls = config.displayUrls.length > 0\n ? config.displayUrls\n : config.displayUrl\n ? [config.displayUrl]\n : [];\n\n if (urls.length === 0) {\n lines.push(` ${label}: unavailable`);\n } else if (urls.length === 1) {\n lines.push(` ${colorize(label, labelColor, color)}: ${colorizeUrl(urls[0]!, color)}`);\n } else {\n lines.push(` ${colorize(label, labelColor, color)}:`);\n for (const url of urls) {\n lines.push(` ${colorizeUrl(url, color)}`);\n }\n }\n\n if (options.verbose) {\n lines.push(` domains: ${config.domains.length > 0 ? config.domains.join(\", \") : \"*\"}`);\n lines.push(` access: ${config.requireAuth ? \"auth required\" : \"app decides\"}`);\n lines.push(` protocol: ${config.requireHttps ? \"https required\" : \"http allowed\"}`);\n lines.push(` transport: ${config.transport.kind}`);\n }\n\n return lines.join(\"\\n\");\n}\n","import { existsSync } from \"node:fs\";\nimport { join } from \"node:path\";\nimport { readTextFile, writeTextFile } from \"./fs.js\";\nimport type { DevHostEntry } from \"./parse.js\";\n\nexport const LOCALGHOST_STATE_FILE = \"ops/local/localghost-state.json\";\n\nexport type LocalghostStateAction = \"setup\" | \"teardown\";\n\nexport type LocalghostState = {\n version: 1;\n action: LocalghostStateAction;\n updatedAt: string;\n projectName: string;\n cwd: string;\n configPath?: string;\n hostsPath?: string;\n hostsChanged?: boolean;\n hostsTempPath?: string;\n caddyfilePath?: string;\n caddyfileRemoved?: boolean;\n caddyHttps?: boolean;\n caddyTrustedAt?: string;\n caddyTrustPromptedAt?: string;\n entries?: DevHostEntry[];\n};\n\nexport type WriteLocalghostStateInput = Omit<LocalghostState, \"version\" | \"updatedAt\">;\n\nexport function getLocalghostStatePath(cwd = process.cwd()) {\n return join(cwd, LOCALGHOST_STATE_FILE);\n}\n\nexport function readLocalghostState(cwd = process.cwd()): LocalghostState | null {\n const path = getLocalghostStatePath(cwd);\n if (!existsSync(path)) return null;\n return JSON.parse(readTextFile(path)) as LocalghostState;\n}\n\nexport function writeLocalghostState(cwd: string, state: WriteLocalghostStateInput) {\n const path = getLocalghostStatePath(cwd);\n writeTextFile(path, `${JSON.stringify({ ...state, version: 1, updatedAt: new Date().toISOString() }, null, 2)}\\n`);\n return path;\n}\n\nexport function patchLocalghostState(cwd: string, patch: Partial<WriteLocalghostStateInput>) {\n const current = readLocalghostState(cwd);\n if (!current) return null;\n return writeLocalghostState(cwd, { ...(current as unknown as WriteLocalghostStateInput), ...patch });\n}\n","import { existsSync, mkdirSync, readFileSync, writeFileSync } from \"node:fs\";\nimport { homedir } from \"node:os\";\nimport { dirname, join } from \"node:path\";\n\nexport const LOCALGHOST_PACKAGE_NAME = \"@hamedb89/localghost\";\nexport const LOCALGHOST_VERSION = \"0.4.1\";\nexport const UPDATE_CHECK_CACHE_TTL_MS = 24 * 60 * 60 * 1000;\nexport const UPDATE_CHECK_NOTIFY_TTL_MS = 24 * 60 * 60 * 1000;\nexport const UPDATE_CHECK_TIMEOUT_MS = 900;\n\nexport type UpdateCheckCache = {\n checkedAt: string;\n latestVersion?: string;\n notifiedVersion?: string;\n notifiedAt?: string;\n};\n\nexport type UpdateCheckResult = {\n currentVersion: string;\n packageName: string;\n latestVersion?: string;\n updateAvailable: boolean;\n source: \"cache\" | \"registry\" | \"disabled\" | \"error\";\n error?: string;\n};\n\ntype RegistryPackageResponse = {\n \"dist-tags\"?: {\n latest?: unknown;\n };\n};\n\nfunction truthyEnv(value: string | undefined) {\n return value === \"1\" || value === \"true\" || value === \"yes\";\n}\n\nexport function isUpdateCheckDisabled(env: NodeJS.ProcessEnv = process.env) {\n return truthyEnv(env.LOCALGHOST_NO_UPDATE_CHECK);\n}\n\nexport function getUpdateCheckCachePath(env: NodeJS.ProcessEnv = process.env) {\n if (env.LOCALGHOST_UPDATE_CHECK_CACHE) return env.LOCALGHOST_UPDATE_CHECK_CACHE;\n\n const cacheRoot = env.XDG_CACHE_HOME || join(homedir(), \".cache\");\n return join(cacheRoot, \"localghost\", \"update-check.json\");\n}\n\nfunction readCache(path = getUpdateCheckCachePath()): UpdateCheckCache | null {\n if (!existsSync(path)) return null;\n\n try {\n return JSON.parse(readFileSync(path, \"utf8\")) as UpdateCheckCache;\n } catch {\n return null;\n }\n}\n\nfunction writeCache(cache: UpdateCheckCache, path = getUpdateCheckCachePath()) {\n try {\n mkdirSync(dirname(path), { recursive: true });\n writeFileSync(path, `${JSON.stringify(cache, null, 2)}\\n`, \"utf8\");\n } catch {\n // Update checks should never make the real command fail.\n }\n}\n\nfunction ageMs(date: string | undefined, now = Date.now()) {\n if (!date) return Number.POSITIVE_INFINITY;\n const time = Date.parse(date);\n return Number.isFinite(time) ? now - time : Number.POSITIVE_INFINITY;\n}\n\nfunction isCacheFresh(cache: UpdateCheckCache | null, ttlMs: number, now = Date.now()) {\n return Boolean(cache?.latestVersion && ageMs(cache.checkedAt, now) >= 0 && ageMs(cache.checkedAt, now) < ttlMs);\n}\n\ntype ParsedVersion = {\n major: number;\n minor: number;\n patch: number;\n prerelease?: string;\n};\n\nfunction parseVersion(version: string): ParsedVersion | null {\n const match = version.trim().replace(/^v/, \"\").match(/^(\\d+)\\.(\\d+)\\.(\\d+)(?:-([0-9A-Za-z.-]+))?$/);\n if (!match) return null;\n\n return {\n major: Number(match[1]),\n minor: Number(match[2]),\n patch: Number(match[3]),\n ...(match[4] ? { prerelease: match[4] } : {})\n };\n}\n\nexport function compareVersions(a: string, b: string) {\n const left = parseVersion(a);\n const right = parseVersion(b);\n\n if (!left || !right) return a.localeCompare(b);\n\n for (const key of [\"major\", \"minor\", \"patch\"] as const) {\n if (left[key] !== right[key]) return left[key] > right[key] ? 1 : -1;\n }\n\n if (left.prerelease === right.prerelease) return 0;\n if (!left.prerelease) return 1;\n if (!right.prerelease) return -1;\n return left.prerelease.localeCompare(right.prerelease);\n}\n\nexport function isNewerVersion(candidate: string | undefined, current = LOCALGHOST_VERSION) {\n return Boolean(candidate && compareVersions(candidate, current) > 0);\n}\n\nasync function fetchLatestVersion(packageName: string, timeoutMs: number) {\n const encodedName = packageName.startsWith(\"@\") ? `@${packageName.slice(1).replaceAll(\"/\", \"%2f\")}` : packageName;\n const response = await fetch(`https://registry.npmjs.org/${encodedName}`, {\n signal: AbortSignal.timeout(timeoutMs),\n headers: {\n accept: \"application/vnd.npm.install-v1+json\"\n }\n });\n\n if (!response.ok) throw new Error(`npm registry returned ${response.status}`);\n\n const data = (await response.json()) as RegistryPackageResponse;\n const latest = data[\"dist-tags\"]?.latest;\n if (typeof latest !== \"string\" || latest.length === 0) throw new Error(\"npm registry response did not include latest dist-tag\");\n\n return latest;\n}\n\nexport async function checkForUpdate(options: {\n force?: boolean;\n packageName?: string;\n currentVersion?: string;\n timeoutMs?: number;\n cachePath?: string;\n env?: NodeJS.ProcessEnv;\n} = {}): Promise<UpdateCheckResult> {\n const env = options.env ?? process.env;\n const packageName = options.packageName ?? LOCALGHOST_PACKAGE_NAME;\n const currentVersion = options.currentVersion ?? LOCALGHOST_VERSION;\n const cachePath = options.cachePath ?? getUpdateCheckCachePath(env);\n\n if (!options.force && isUpdateCheckDisabled(env)) {\n return {\n currentVersion,\n packageName,\n updateAvailable: false,\n source: \"disabled\"\n };\n }\n\n const cache = readCache(cachePath);\n if (!options.force && isCacheFresh(cache, UPDATE_CHECK_CACHE_TTL_MS)) {\n const latestVersion = cache?.latestVersion;\n return {\n currentVersion,\n packageName,\n ...(latestVersion ? { latestVersion } : {}),\n updateAvailable: isNewerVersion(latestVersion, currentVersion),\n source: \"cache\"\n };\n }\n\n try {\n const latestVersion = await fetchLatestVersion(packageName, options.timeoutMs ?? UPDATE_CHECK_TIMEOUT_MS);\n writeCache({ checkedAt: new Date().toISOString(), latestVersion }, cachePath);\n\n return {\n currentVersion,\n packageName,\n latestVersion,\n updateAvailable: isNewerVersion(latestVersion, currentVersion),\n source: \"registry\"\n };\n } catch (error) {\n const latestVersion = cache?.latestVersion;\n return {\n currentVersion,\n packageName,\n ...(latestVersion ? { latestVersion } : {}),\n updateAvailable: isNewerVersion(latestVersion, currentVersion),\n source: \"error\",\n error: error instanceof Error ? error.message : String(error)\n };\n }\n}\n\nexport function formatUpdateMessage(result: UpdateCheckResult) {\n if (!result.updateAvailable || !result.latestVersion) return null;\n\n return [\n `localghost ${result.latestVersion} is available. Current: ${result.currentVersion}`,\n \"Update a repository with: npm exec --yes --package=@hamedb89/localghost -- localghost upgrade\",\n \"If Localghost is already installed locally, run: localghost upgrade\"\n ].join(\"\\n\");\n}\n\nexport function shouldNotifyAboutUpdate(result: UpdateCheckResult, cachePath = getUpdateCheckCachePath(), now = Date.now()) {\n if (!result.updateAvailable || !result.latestVersion) return false;\n\n const cache = readCache(cachePath);\n if (cache?.notifiedVersion !== result.latestVersion) return true;\n\n return ageMs(cache.notifiedAt, now) >= UPDATE_CHECK_NOTIFY_TTL_MS;\n}\n\nexport function markUpdateNotified(result: UpdateCheckResult, cachePath = getUpdateCheckCachePath()) {\n if (!result.latestVersion) return;\n\n const cache = readCache(cachePath) ?? { checkedAt: new Date().toISOString() };\n writeCache(\n {\n ...cache,\n latestVersion: result.latestVersion,\n notifiedVersion: result.latestVersion,\n notifiedAt: new Date().toISOString()\n },\n cachePath\n );\n}\n\nexport async function maybeNotifyAboutUpdate(options: { disabled?: boolean } = {}) {\n if (options.disabled) return;\n\n const cachePath = getUpdateCheckCachePath();\n const result = await checkForUpdate({ cachePath });\n if (!shouldNotifyAboutUpdate(result, cachePath)) return;\n\n const message = formatUpdateMessage(result);\n if (!message) return;\n\n console.warn(`\\n${message}`);\n markUpdateNotified(result, cachePath);\n}\n","import type { ChildProcess } from \"node:child_process\";\n\nexport type ProcessSignal = NodeJS.Signals;\nexport type ProcessKiller = (pid: number, signal: ProcessSignal) => void;\n\nexport function signalManagedProcessPid(\n pid: number | undefined,\n signal: ProcessSignal,\n killProcess: ProcessKiller = (value, processSignal) => process.kill(value, processSignal)\n) {\n if (typeof pid !== \"number\" || !Number.isInteger(pid) || pid < 1) return false;\n\n try {\n // Detached POSIX children lead their own process group.\n killProcess(process.platform === \"win32\" ? pid : -pid, signal);\n return true;\n } catch (error) {\n if (error instanceof Error && \"code\" in error && error.code === \"ESRCH\") return false;\n throw error;\n }\n}\n\nexport function signalManagedProcess(child: Pick<ChildProcess, \"pid\" | \"kill\" | \"killed\">, signal: ProcessSignal) {\n if (process.platform === \"win32\") {\n if (!child.killed) child.kill(signal);\n return true;\n }\n\n return signalManagedProcessPid(child.pid, signal);\n}\n"],"mappings":"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","names":["existsSync","readFileSync","input","existsSync","readFileSync","join","input","fileName","existsSync","readFileSync","join","dirname","join","mkdirSync","readFileSync","writeFileSync","dirname","join","dirname","dirname","existsSync","readFileSync","join","resolve","existsSync","readFileSync","join","resolve","homedir","join","resolve","resolve","join","homedir","entry","lease","input","input","readFileSync","join","input","existsSync","execa","execa","randomUUID","domainToASCII","HOST_PATTERN","domainToASCII","HOST_PATTERN","randomUUID","input","input","resolve","input","randomUUID","writeFileSync","join","execa","join","writeFileSync","execa","existsSync","readFileSync","writeFileSync","join","existsSync","join","readPackageJson","readFileSync","writeFileSync","join","existsSync","existsSync","join","join","existsSync","existsSync","mkdirSync","readFileSync","writeFileSync","homedir","dirname","join","execa","parsePort","readFileSync","existsSync","wait","resolve","execa","input"]}