@quatronic/qore 0.1.0 → 0.1.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/README.md +145 -2
- package/dist/cli.js +1302 -243
- package/dist/cli.js.map +1 -1
- package/package.json +3 -1
- package/schema/qore.schema.json +17 -0
package/dist/cli.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/cli.ts","../src/cli/io.ts","../src/platform/browser.ts","../src/core/errors.ts","../src/cli/program.ts","../src/core/api/http.ts","../src/cli/render.ts","../src/core/api/meta.ts","../src/core/auth/oidc.ts","../src/core/auth/login.ts","../src/core/auth/tokenStore.ts","../src/core/profiles.ts","../src/core/api/client.ts","../src/core/auth/refresh.ts","../src/core/session.ts","../src/cli/commands/login.ts","../src/cli/commands/logout.ts","../src/cli/commands/tenant.ts","../src/cli/commands/version.ts","../src/cli/commands/whoami.ts","../src/cli/commands/index.ts","../src/cli/updateCheck.ts","../src/core/config.ts","../src/platform/keychain.ts","../src/platform/lock.ts","../src/platform/paths.ts","../src/version.ts"],"sourcesContent":["import { homedir } from \"node:os\"\nimport { EnvHttpProxyAgent, setGlobalDispatcher } from \"undici\"\nimport { isInteractive, processIo } from \"./cli/io.js\"\nimport { run } from \"./cli/program.js\"\nimport { COMMANDS } from \"./cli/commands/index.js\"\nimport { maybeNotifyUpdate } from \"./cli/updateCheck.js\"\nimport { abortableFetch } from \"./core/api/http.js\"\nimport { createOidc } from \"./core/auth/oidc.js\"\nimport { ConfigStore } from \"./core/config.js\"\nimport type { Deps } from \"./core/deps.js\"\nimport { OsKeychain } from \"./platform/keychain.js\"\nimport { fileLock } from \"./platform/lock.js\"\nimport { configDir } from \"./platform/paths.js\"\nimport { VERSION } from \"./version.js\"\n\nif (process.env.HTTPS_PROXY || process.env.https_proxy || process.env.HTTP_PROXY) setGlobalDispatcher(new EnvHttpProxyAgent())\n\nconst dir = configDir(process.env, process.platform, homedir())\nconst argv = process.argv.slice(2)\nconst json = argv.includes(\"--json\")\n// Ctrl+C: the first one aborts every in-flight request and prompt through `ac.signal`\n// (→ CancelledError → exit 130); a second one exits at once, whatever is still running.\nconst ac = new AbortController()\nprocess.on(\"SIGINT\", () => {\n if (ac.signal.aborted) process.exit(130)\n ac.abort()\n})\nconst fetch = abortableFetch(globalThis.fetch, ac.signal)\nconst deps: Deps = {\n fetch,\n keychain: new OsKeychain(),\n config: new ConfigStore(dir),\n withLock: fileLock(dir),\n now: () => new Date(),\n oidcFor: (issuer) => createOidc({ issuer, clientId: \"qore-cli\", fetch }),\n env: process.env,\n platform: process.platform,\n version: VERSION,\n}\nconst io = processIo(isInteractive({ stdinTTY: Boolean(process.stdin.isTTY), stdoutTTY: Boolean(process.stdout.isTTY),\n json, noInput: argv.includes(\"--no-input\"), env: process.env }))\nprocess.exitCode = await run(argv, deps, io, ac.signal, COMMANDS)\nif (!ac.signal.aborted) {\n try {\n await maybeNotifyUpdate(deps, io, { json })\n } catch {\n // an update check must never change the exit code\n }\n}\n","import { select } from \"@inquirer/prompts\"\nimport { createInterface } from \"node:readline\"\nimport { openBrowser } from \"../platform/browser.js\"\nimport { CancelledError } from \"../core/errors.js\"\n\nexport interface Io {\n out(s: string): void\n err(s: string): void\n interactive: boolean\n select<T>(msg: string, choices: { name: string; value: T; description?: string }[]): Promise<T>\n waitForEnter(msg: string, signal: AbortSignal): Promise<void>\n openUrl(url: string): Promise<boolean>\n}\n\nexport function isInteractive(o: { stdinTTY: boolean; stdoutTTY: boolean; json: boolean; noInput: boolean; env: NodeJS.ProcessEnv }): boolean {\n return o.stdinTTY && o.stdoutTTY && !o.json && !o.noInput && !o.env.CI\n}\n\nexport function processIo(interactive: boolean): Io {\n return {\n out: (s) => { process.stdout.write(s + \"\\n\") },\n err: (s) => { process.stderr.write(s + \"\\n\") },\n interactive,\n async select(message, choices) {\n try { return await select({ message, choices }) } catch (e) {\n if ((e as Error).name === \"ExitPromptError\") throw new CancelledError()\n throw e\n }\n },\n waitForEnter: createWaitForEnter(process.stdin, process.stderr),\n openUrl: openBrowser,\n }\n}\n\n/** Builds a `waitForEnter` bound to the given streams, so tests can drive it without a\n * real TTY. Readline puts a TTY's stdin in raw mode, which turns Ctrl+C into the\n * interface's own 'SIGINT' event rather than a process-level SIGINT (R16) — that must be\n * turned into a CancelledError itself, since `process.once(\"SIGINT\", …)` in cli.ts never\n * fires for it. `terminal: true` makes readline parse Ctrl+C the same way on any stream. */\nexport function createWaitForEnter(\n input: NodeJS.ReadableStream, output: NodeJS.WritableStream,\n): (message: string, signal: AbortSignal) => Promise<void> {\n return (message, signal) => new Promise((resolve, reject) => {\n const rl = createInterface({ input, output, terminal: true })\n const onAbort = () => { rl.close(); reject(new CancelledError()) }\n const done = () => { signal.removeEventListener(\"abort\", onAbort); rl.close(); resolve() }\n signal.addEventListener(\"abort\", onAbort, { once: true })\n rl.on(\"SIGINT\", () => { signal.removeEventListener(\"abort\", onAbort); rl.close(); reject(new CancelledError()) })\n rl.question(message, done)\n })\n}\n","import open from \"open\"\n\n/** Opens the URL; false when there is no display (SSH, container) or it fails. */\nexport async function openBrowser(url: string): Promise<boolean> {\n if (process.platform === \"linux\" && !process.env.DISPLAY && !process.env.WAYLAND_DISPLAY) return false\n try { await open(url); return true } catch { return false }\n}\n","export const EXIT = {\n QORE_INTERNAL: 1,\n QORE_KEYCHAIN_UNAVAILABLE: 1,\n QORE_KEYCHAIN_DENIED: 1,\n QORE_CONTEXT_REQUIRED: 2,\n QORE_CONTEXT_INVALID: 2,\n QORE_NOT_LOGGED_IN: 4,\n QORE_SESSION_EXPIRED: 4,\n QORE_LOGIN_EXPIRED: 4,\n QORE_LOGIN_DENIED: 4,\n QORE_CLOCK_SKEW: 4,\n QORE_TENANT_ACCESS_LOST: 5,\n QORE_RESOURCE_NOT_FOUND: 5,\n QORE_ACCESS_DENIED: 5,\n QORE_NO_DEVELOPER_ACCESS: 5,\n QORE_AUTH_UNAVAILABLE: 6,\n QORE_AUTH_BUSY: 6,\n QORE_API_UNREACHABLE: 6,\n QORE_API_UNAVAILABLE: 6,\n QORE_INCOMPATIBLE_SERVER: 7,\n QORE_UNSUPPORTED_BY_SERVER: 7,\n QORE_UPGRADE_REQUIRED: 7,\n QORE_PORTAL_UNTRUSTED: 7,\n QORE_RATE_LIMITED: 8,\n} as const\n\nexport type QoreErrorCode = keyof typeof EXIT\n\ntype Opts = {\n hint?: string\n status?: number\n requestId?: string\n candidates?: unknown[]\n serverCode?: string\n details?: Record<string, unknown>\n cause?: unknown\n}\n\nexport class QoreError extends Error {\n readonly code: QoreErrorCode\n readonly hint?: string\n readonly status?: number\n readonly requestId?: string\n readonly candidates?: unknown[]\n readonly serverCode?: string\n readonly details?: Record<string, unknown>\n\n constructor(code: QoreErrorCode, message: string, opts: Opts = {}) {\n super(message, opts.cause === undefined ? undefined : { cause: opts.cause })\n this.name = \"QoreError\"\n this.code = code\n this.hint = opts.hint\n this.status = opts.status\n this.requestId = opts.requestId\n this.candidates = opts.candidates\n this.serverCode = opts.serverCode\n this.details = opts.details\n }\n}\n\nexport class CancelledError extends Error {\n constructor() {\n super(\"Cancelled\")\n this.name = \"CancelledError\"\n }\n}\n\nexport function exitCodeFor(err: unknown): number {\n if (err instanceof CancelledError || (err instanceof Error && err.name === \"CancelledError\")) return 130\n if (err instanceof QoreError) return EXIT[err.code]\n return 1\n}\n\nexport function toJsonError(err: unknown): Record<string, unknown> {\n if (!(err instanceof QoreError)) {\n return { code: \"QORE_INTERNAL\", message: err instanceof Error ? err.message : String(err) }\n }\n const out: Record<string, unknown> = { code: err.code, message: err.message }\n for (const k of [\"hint\", \"status\", \"requestId\", \"candidates\", \"serverCode\", \"details\"] as const) {\n if (err[k] !== undefined) out[k] = err[k]\n }\n return out\n}\n","import { Command, CommanderError } from \"commander\"\nimport type { Deps } from \"../core/deps.js\"\nimport { isAbortError } from \"../core/api/http.js\"\nimport { CancelledError, exitCodeFor } from \"../core/errors.js\"\nimport type { Io } from \"./io.js\"\nimport pc from \"picocolors\"\nimport { renderError } from \"./render.js\"\n\n/** Detects --json before commander has parsed anything, so a parse error (thrown before\n * global opts exist) can still be rendered as JSON, and commander's own stderr line\n * can be suppressed in that mode. See ruling R12. */\nfunction jsonFromArgv(argv: string[]): boolean {\n return argv.some((a) => a === \"--json\" || a.startsWith(\"--json=\"))\n}\n\nexport type GlobalOpts = { portal?: string; json?: boolean; input?: boolean; verbose?: boolean; color?: boolean }\n\nexport type CommandContext = { deps: Deps; io: Io; signal: AbortSignal; opts: () => GlobalOpts }\n\nexport type Register = (program: Command, ctx: CommandContext) => void\n\n/** `--verbose`: request lines (method, path, status, request id; never a token) on stderr. */\nexport function requestLog(ctx: CommandContext): ((line: string) => void) | undefined {\n return ctx.opts().verbose ? (line) => ctx.io.err(line) : undefined\n}\n\nexport function buildProgram(deps: Deps, io: Io, signal: AbortSignal, register: Register[]): Command {\n const program = new Command(\"qore\")\n .description(\"Qore developer CLI\")\n .option(\"--portal <name|url>\", \"prod, staging, or a portal URL (default: the portal you last logged in to, else prod)\")\n .option(\"--json\", \"print exactly one JSON document on stdout\")\n .option(\"--no-input\", \"never prompt\")\n .option(\"--verbose\", \"log request lines (never secrets)\")\n .option(\"--no-color\", \"disable colours\")\n .exitOverride()\n .configureOutput({ writeOut: (s) => io.out(s.trimEnd()), writeErr: (s) => io.err(s.trimEnd()) })\n const ctx: CommandContext = { deps, io, signal, opts: () => program.opts<GlobalOpts>() }\n for (const r of register) r(program, ctx)\n return program\n}\n\nexport async function run(argv: string[], deps: Deps, io: Io, signal: AbortSignal, register: Register[]): Promise<number> {\n const json = jsonFromArgv(argv)\n // Commander may throw before global opts exist (e.g. an unknown option), and by default\n // writes its own message to stderr on the way there. In --json mode that would land\n // alongside our single JSON document, so suppress it here and render the error ourselves.\n const parseIo: Io = json ? { ...io, err: () => {} } : io\n const program = buildProgram(deps, parseIo, signal, register)\n try {\n await program.parseAsync(argv, { from: \"user\" })\n return 0\n } catch (caught) {\n // Once Ctrl+C has fired, any AbortError that escaped a mapping is that cancel.\n const e = signal.aborted && isAbortError(caught) ? new CancelledError() : caught\n if (e instanceof CommanderError) {\n if (e.exitCode === 0) return 0\n if (json) io.out(JSON.stringify({ ok: false, error: { code: \"QORE_CONTEXT_INVALID\", message: e.message } }))\n return 2\n }\n const opts = program.opts<GlobalOpts>()\n renderError(io, e, Boolean(opts.json), pc.isColorSupported && opts.color !== false)\n return exitCodeFor(e)\n }\n}\n","import { CancelledError, QoreError, type QoreErrorCode } from \"../errors.js\"\n\nexport type Fetch = (input: string | URL, init?: RequestInit) => Promise<Response>\n\n/** Every request also carries `signal` (the process's Ctrl+C signal), next to any signal\n * of the caller's own, so a cancel aborts whatever is in flight (spec §4). */\nexport function abortableFetch(fetch: Fetch, signal: AbortSignal): Fetch {\n return (input, init) => fetch(input, { ...init, signal: init?.signal ? AbortSignal.any([init.signal, signal]) : signal })\n}\n\nconst TLS = new Set([\"SELF_SIGNED_CERT_IN_CHAIN\", \"UNABLE_TO_GET_ISSUER_CERT_LOCALLY\",\n \"DEPTH_ZERO_SELF_SIGNED_CERT\", \"UNABLE_TO_VERIFY_LEAF_SIGNATURE\", \"CERT_HAS_EXPIRED\"])\n\nfunction causeCode(e: unknown): string | undefined {\n const c = (e as { cause?: { code?: unknown } })?.cause\n const code = c?.code ?? (e as { code?: unknown })?.code\n // DOMException carries a numeric legacy `code`; only errno-style strings are meaningful here.\n return typeof code === \"string\" ? code : undefined\n}\n\nexport function isAbortError(e: unknown): boolean {\n return (e as { name?: unknown } | null)?.name === \"AbortError\"\n}\n\n/** A failed fetch: a cancel (Ctrl+C aborted the request) or a network failure. */\nexport function fetchError(e: unknown, host: string): Error {\n return isAbortError(e) ? new CancelledError() : networkError(e, host)\n}\n\nexport function networkError(e: unknown, host: string): QoreError {\n const code = causeCode(e) ?? \"\"\n let reason = \"connect\"\n let hint = \"Check your network or VPN.\"\n if (code === \"ENOTFOUND\" || code === \"EAI_AGAIN\") {\n reason = \"dns\"; hint = `${host} could not be resolved. Check your network or VPN.`\n } else if (TLS.has(code)) {\n reason = \"tls\"\n hint = \"A proxy is re-signing TLS. Point NODE_EXTRA_CA_CERTS at your organisation's CA certificate.\"\n } else if (code.includes(\"TIMEOUT\") || code === \"ETIMEDOUT\") {\n reason = \"timeout\"\n } else if (!process.env.HTTPS_PROXY && !process.env.https_proxy) {\n hint = \"Check your network. Behind a corporate proxy, set HTTPS_PROXY.\"\n }\n return new QoreError(\"QORE_API_UNREACHABLE\", `Could not reach ${host}`, { hint, details: { reason, host, errno: code || undefined }, cause: e })\n}\n\nconst BY_SERVER_CODE: Record<string, QoreErrorCode> = {\n \"app.access.denied\": \"QORE_ACCESS_DENIED\",\n \"auth.scope.insufficient\": \"QORE_ACCESS_DENIED\",\n \"cli.upgrade_required\": \"QORE_UPGRADE_REQUIRED\",\n \"rate_limited\": \"QORE_RATE_LIMITED\",\n}\n\nfunction byStatus(status: number): QoreErrorCode {\n if (status === 403) return \"QORE_ACCESS_DENIED\"\n if (status === 404) return \"QORE_RESOURCE_NOT_FOUND\"\n if (status === 426) return \"QORE_UPGRADE_REQUIRED\"\n if (status === 429) return \"QORE_RATE_LIMITED\"\n if (status === 502 || status === 503 || status === 504) return \"QORE_API_UNAVAILABLE\"\n return \"QORE_INTERNAL\"\n}\n\nexport async function problemToError(res: Response): Promise<QoreError> {\n let body: { code?: string; title?: string; detail?: unknown } = {}\n try { body = (await res.json()) as typeof body } catch { /* not JSON */ }\n const serverCode = body.code\n const code = (serverCode && BY_SERVER_CODE[serverCode]) || byStatus(res.status)\n const requestId = res.headers.get(\"x-request-id\") ?? undefined\n const details: Record<string, unknown> = {}\n if (body.detail && typeof body.detail === \"object\") Object.assign(details, body.detail)\n const detail = typeof body.detail === \"string\" && body.detail ? body.detail : undefined\n if (detail) details.detail = detail\n const retry = res.headers.get(\"retry-after\")\n if (retry && /^\\d+$/.test(retry)) details.retryAfter = Number(retry)\n const hint =\n code === \"QORE_UPGRADE_REQUIRED\" ? \"Run: npm i -g @quatronic/qore\"\n : code === \"QORE_RATE_LIMITED\" ? `Wait ${details.retryAfter ?? \"a moment\"} s and retry.`\n : code === \"QORE_API_UNAVAILABLE\" ? \"Qore is temporarily unavailable; retry in a minute.\"\n : undefined\n // portal-api falls back to the title \"HTTP error\"; a server code is no message either.\n // Then the string detail is the most useful message there is.\n const genericTitle = !body.title || body.title === \"HTTP error\" || body.title === serverCode\n const message = (genericTitle && detail) || body.title || `Request failed (${res.status})`\n return new QoreError(code, message, {\n status: res.status, requestId, serverCode, hint,\n details: Object.keys(details).length ? details : undefined,\n })\n}\n","import pc, { createColors } from \"picocolors\"\nimport { QoreError, toJsonError } from \"../core/errors.js\"\nimport type { Io } from \"./io.js\"\n\nexport function renderJson(io: Io, data: unknown): void {\n io.out(JSON.stringify({ ok: true, data }))\n}\n\nexport function renderError(io: Io, err: unknown, json: boolean, colorEnabled = pc.isColorSupported): void {\n if (json) { io.out(JSON.stringify({ ok: false, error: toJsonError(err) })); return }\n if (err instanceof Error && err.name === \"CancelledError\") { io.err(\"Cancelled\"); return }\n const c = createColors(colorEnabled)\n const e = err instanceof QoreError ? err : new QoreError(\"QORE_INTERNAL\", err instanceof Error ? err.message : String(err))\n io.err(c.red(`Error: ${e.message}`))\n if (e.hint) io.err(e.hint)\n io.err(c.dim(`Code: ${e.code}${e.requestId ? ` (request ${e.requestId})` : \"\"}`))\n}\n","import { QoreError } from \"../errors.js\"\nimport type { PortalRef } from \"../profiles.js\"\nimport { fetchError, problemToError, type Fetch } from \"./http.js\"\nimport type { CliMeta } from \"./types.js\"\n\nconst SUPPORTED = [\"v1\"] as const\nconst SEMVER = /^(\\d+)\\.(\\d+)\\.(\\d+)(?:-([0-9A-Za-z.-]+))?/\n\nexport function compareVersions(a: string, b: string): number {\n const pa = SEMVER.exec(a), pb = SEMVER.exec(b)\n if (!pa || !pb) return 0\n for (let i = 1; i <= 3; i++) {\n const d = Number(pa[i]) - Number(pb[i])\n if (d !== 0) return d\n }\n if (pa[4] && !pb[4]) return -1\n if (!pa[4] && pb[4]) return 1\n return 0\n}\n\nexport async function fetchMeta(fetch: Fetch, apiOrigin: string): Promise<CliMeta> {\n let res: Response\n try { res = await fetch(`${apiOrigin}/api/cli/meta`, { headers: { accept: \"application/json\" } }) }\n catch (e) { throw fetchError(e, new URL(apiOrigin).host) }\n if (res.status === 404) {\n // No CLI surface at all: a portal-api from before the CLI (or the wrong URL).\n throw new QoreError(\"QORE_INCOMPATIBLE_SERVER\", \"This portal does not support the Qore CLI yet\", {\n status: 404, requestId: res.headers.get(\"x-request-id\") ?? undefined,\n hint: `Check the portal URL (${apiOrigin}); if it is right, the portal must be upgraded before qore can use it.`,\n })\n }\n if (!res.ok) throw await problemToError(res)\n return (await res.json()) as CliMeta\n}\n\nexport function negotiate(meta: CliMeta, portal: PortalRef, cliVersion: string): { apiVersion: \"v1\" } {\n if (portal.pinnedIssuer && meta.auth.issuer !== portal.pinnedIssuer) {\n throw new QoreError(\"QORE_PORTAL_UNTRUSTED\", `${portal.apiOrigin} names an unexpected identity provider`, {\n details: { expected: portal.pinnedIssuer, got: meta.auth.issuer },\n hint: \"Refusing to log in. Check the portal URL and your network.\",\n })\n }\n const apiVersion = SUPPORTED.find((v) => meta.apiVersions.includes(v))\n if (!apiVersion) {\n throw new QoreError(\"QORE_INCOMPATIBLE_SERVER\", \"This portal speaks no API version this qore knows\", {\n details: { server: meta.apiVersions, client: [...SUPPORTED] }, hint: \"Run: npm i -g @quatronic/qore\",\n })\n }\n if (!cliVersion.endsWith(\"-dev\") && compareVersions(cliVersion, meta.minCliVersion) < 0) {\n throw new QoreError(\"QORE_UPGRADE_REQUIRED\", `qore ${cliVersion} is too old for this portal (needs ${meta.minCliVersion})`, {\n hint: \"Run: npm i -g @quatronic/qore\",\n })\n }\n return { apiVersion }\n}\n","import * as oc from \"openid-client\"\nimport { CancelledError, QoreError } from \"../errors.js\"\nimport type { Fetch } from \"../api/http.js\"\nimport { isAbortError, networkError } from \"../api/http.js\"\n\nexport type DeviceStart = { userCode: string; verificationUri: string; verificationUriComplete?: string; expiresIn: number; handle: unknown }\nexport type TokenSet = { accessToken: string; refreshToken: string; expiresIn: number; scope: string; sub: string; email?: string }\n\nexport interface Oidc {\n startDevice(scope: string): Promise<DeviceStart>\n pollDevice(start: DeviceStart, signal: AbortSignal): Promise<TokenSet>\n refresh(rt: string, scope?: string): Promise<TokenSet>\n revoke(rt: string): Promise<void>\n}\n\nexport const LOGIN_SCOPE = \"openid profile email offline_access qore:read qore:local-env\"\n\nfunction decodeSub(accessToken: string): { sub: string; email?: string } {\n const part = accessToken.split(\".\")[1] ?? \"\"\n const claims = JSON.parse(Buffer.from(part, \"base64url\").toString(\"utf8\")) as { sub: string; email?: string }\n return { sub: claims.sub, email: claims.email }\n}\n\nfunction toTokenSet(t: oc.TokenEndpointResponse, fallbackRt?: string): TokenSet {\n const rt = t.refresh_token ?? fallbackRt\n if (!rt) throw new QoreError(\"QORE_INTERNAL\", \"Keycloak returned no refresh token\")\n return { accessToken: t.access_token, refreshToken: rt, expiresIn: t.expires_in ?? 600,\n scope: t.scope ?? \"\", ...decodeSub(t.access_token) }\n}\n\n/** Keycloak unreachable is QORE_AUTH_UNAVAILABLE (spec §7, §14; R19), not the portal's\n * QORE_API_UNREACHABLE — with the same network diagnosis (hint, reason, host). */\nfunction unreachable(e: unknown, host: string): QoreError {\n const n = networkError(e, host)\n return new QoreError(\"QORE_AUTH_UNAVAILABLE\", n.message, { hint: n.hint, details: n.details, cause: e })\n}\n\nexport function mapOidcError(e: unknown, host: string): Error {\n if (e instanceof QoreError || e instanceof CancelledError) return e\n // Ctrl+C aborts the request's signal; openid-client wraps that DOMException as\n // ClientError { code: \"OAUTH_ABORT\", cause }.\n if (isAbortError(e) || (e as { code?: unknown })?.code === \"OAUTH_ABORT\" || isAbortError((e as { cause?: unknown })?.cause)) {\n return new CancelledError()\n }\n const err = (e as { error?: string }).error\n if (err === \"access_denied\") return new QoreError(\"QORE_LOGIN_DENIED\", \"The login was denied in the browser\")\n if (err === \"expired_token\") return new QoreError(\"QORE_LOGIN_EXPIRED\", \"The login code expired\", { hint: \"Run `qore login` again.\" })\n if (err === \"invalid_grant\") return new QoreError(\"QORE_SESSION_EXPIRED\", \"Your session has ended\", { hint: \"Run `qore login`.\" })\n const status = (e as { status?: number }).status\n if (status && status >= 500) return new QoreError(\"QORE_AUTH_UNAVAILABLE\", \"Keycloak is unavailable\", { cause: e })\n if (e instanceof TypeError) return unreachable(e, host)\n // openid-client sometimes wraps the raw fetch TypeError (DNS/TLS/connect/timeout) one\n // level deep, e.g. `new ClientError(\"something went wrong\", { cause: err })`.\n const cause = (e as { cause?: unknown })?.cause\n if (cause instanceof TypeError) return unreachable(cause, host)\n return new QoreError(\"QORE_AUTH_UNAVAILABLE\", \"Login failed\", { cause: e })\n}\n\nexport async function createOidc(opts: { issuer: string; clientId: string; fetch: Fetch }): Promise<Oidc> {\n const host = new URL(opts.issuer).host\n const execute = new URL(opts.issuer).protocol === \"http:\" ? [oc.allowInsecureRequests] : []\n let config: oc.Configuration\n try {\n config = await oc.discovery(new URL(opts.issuer), opts.clientId, undefined, oc.None(), {\n execute, [oc.customFetch]: opts.fetch as unknown as oc.CustomFetch,\n })\n } catch (e) { throw mapOidcError(e, host) }\n\n return {\n async startDevice(scope) {\n try {\n const r = await oc.initiateDeviceAuthorization(config, { scope })\n return { userCode: r.user_code, verificationUri: r.verification_uri,\n verificationUriComplete: r.verification_uri_complete, expiresIn: r.expires_in, handle: r }\n } catch (e) { throw mapOidcError(e, host) }\n },\n async pollDevice(start, signal) {\n try {\n const t = await oc.pollDeviceAuthorizationGrant(config, start.handle as oc.DeviceAuthorizationResponse, undefined, { signal })\n return toTokenSet(t)\n } catch (e) { throw mapOidcError(e, host) }\n },\n async refresh(rt, scope) {\n try {\n const t = await oc.refreshTokenGrant(config, rt, scope ? { scope } : undefined)\n return toTokenSet(t, rt)\n } catch (e) { throw mapOidcError(e, host) }\n },\n async revoke(rt) {\n try { await oc.tokenRevocation(config, rt, { token_type_hint: \"refresh_token\" }) }\n catch (e) { throw mapOidcError(e, host) }\n },\n }\n}\n","import type { WithLock } from \"../../platform/lock.js\"\nimport type { DeviceStart, Oidc, TokenSet } from \"./oidc.js\"\nimport { LOGIN_SCOPE } from \"./oidc.js\"\nimport type { TokenStore } from \"./tokenStore.js\"\n\nexport async function deviceLogin(opts: {\n oidc: Oidc\n store: TokenStore\n now: () => Date\n /** Shows the code. Polling already runs meanwhile; `settled` aborts once it succeeds or\n * fails, so a prompt waiting on the user (who may have opened the URL themselves) can end. */\n onCode: (s: DeviceStart, settled: AbortSignal) => void | Promise<void>\n signal: AbortSignal\n withLock?: WithLock\n lockName?: string\n}): Promise<TokenSet> {\n // Probe the keychain first: an unusable or denied keychain must fail before the user\n // approves anything in the browser (Review Focus #4), not after.\n await opts.store.getRefresh()\n const start = await opts.oidc.startDevice(LOGIN_SCOPE)\n const stopPoll = new AbortController()\n const settled = new AbortController()\n const poll = opts.oidc.pollDevice(start, AbortSignal.any([opts.signal, stopPoll.signal]))\n .finally(() => settled.abort())\n // Awaited below; this only keeps a poll that fails while onCode runs from counting as unhandled.\n poll.catch(() => {})\n try {\n await opts.onCode(start, settled.signal)\n } catch (e) {\n stopPoll.abort()\n // Approved just before onCode failed: that session is never stored, so end it server-side.\n const late = await poll.catch(() => null)\n if (late) await opts.oidc.revoke(late.refreshToken).catch(() => {})\n throw e\n }\n const t = await poll\n const at = opts.now()\n const write = async () => {\n // Refresh first: a crash between the two writes then leaves a usable session.\n await opts.store.setRefresh({ rt: t.refreshToken, sub: t.sub, scope: t.scope, obtainedAt: at.toISOString() })\n await opts.store.setAccess({ at: t.accessToken, expiresAt: new Date(at.getTime() + t.expiresIn * 1000).toISOString() })\n }\n try {\n if (opts.withLock && opts.lockName) await opts.withLock(opts.lockName, write)\n else await write()\n } catch (e) {\n // The new session cannot be kept: end it server-side and drop any half-written entry.\n // Both best-effort; the original (keychain) error is what the user needs to see.\n await opts.oidc.revoke(t.refreshToken).catch(() => {})\n await opts.store.clear().catch(() => {})\n throw e\n }\n return t\n}\n","import type { Keychain } from \"../../platform/keychain.js\"\n\nexport type StoredRefresh = { rt: string; sub: string; scope: string; obtainedAt: string }\nexport type StoredAccess = { at: string; expiresAt: string }\n\nexport class TokenStore {\n constructor(private readonly kc: Keychain, private readonly hash: string) {}\n\n private async read<T>(suffix: string): Promise<T | null> {\n const raw = await this.kc.get(`${this.hash}:${suffix}`)\n if (raw === null) return null\n try { return JSON.parse(raw) as T } catch { return null }\n }\n\n getRefresh() { return this.read<StoredRefresh>(\"refresh\") }\n getAccess() { return this.read<StoredAccess>(\"access\") }\n setRefresh(v: StoredRefresh) { return this.kc.set(`${this.hash}:refresh`, JSON.stringify(v)) }\n setAccess(v: StoredAccess) { return this.kc.set(`${this.hash}:access`, JSON.stringify(v)) }\n async clear() {\n await this.kc.delete(`${this.hash}:access`)\n await this.kc.delete(`${this.hash}:refresh`)\n }\n}\n","import { createHash } from \"node:crypto\"\nimport { QoreError } from \"./errors.js\"\n\nexport type PortalRef = { apiOrigin: string; pinnedIssuer: string | null; builtin: \"prod\" | \"staging\" | null }\n\nexport const BUILTIN_PORTALS = {\n prod: {\n apiOrigin: \"https://api.quatronic.app\",\n pinnedIssuer: \"https://auth.quatronic.app/realms/platform-prod\",\n },\n staging: {\n apiOrigin: \"https://p01--portal-api-staging--hcywmtb2vksv.code.run\",\n pinnedIssuer: \"https://auth-staging.quatronic.app/realms/platform-staging\",\n },\n} as const satisfies Record<string, { apiOrigin: string; pinnedIssuer: string | null }>\n\nfunction builtinFor(origin: string): PortalRef | null {\n for (const [name, p] of Object.entries(BUILTIN_PORTALS)) {\n if (p.apiOrigin === origin) return { ...p, builtin: name as \"prod\" | \"staging\" }\n }\n return null\n}\n\nfunction toOrigin(raw: string): string {\n let url: URL\n try { url = new URL(raw) } catch {\n throw new QoreError(\"QORE_CONTEXT_INVALID\", `Not a portal name or URL: ${raw}`, {\n hint: \"Use --portal prod, --portal staging or --portal https://…\",\n })\n }\n const loopback = url.hostname === \"localhost\" || url.hostname === \"127.0.0.1\"\n if (url.protocol !== \"https:\" && !(url.protocol === \"http:\" && loopback)) {\n throw new QoreError(\"QORE_CONTEXT_INVALID\", \"A portal URL must use https (http only for localhost)\")\n }\n return url.origin.toLowerCase()\n}\n\nexport function resolvePortal(arg: string | undefined, defaultProfile: string | undefined): PortalRef {\n const chosen = arg ?? defaultProfile\n if (chosen === undefined || chosen === \"prod\") return { ...BUILTIN_PORTALS.prod, builtin: \"prod\" }\n if (chosen === \"staging\") return { ...BUILTIN_PORTALS.staging, builtin: \"staging\" }\n const origin = toOrigin(chosen)\n return builtinFor(origin) ?? { apiOrigin: origin, pinnedIssuer: null, builtin: null }\n}\n\nexport function profileHash(apiOrigin: string, issuer: string): string {\n return createHash(\"sha256\").update(`${apiOrigin}|${issuer}`).digest(\"hex\").slice(0, 16)\n}\n","import { QoreError } from \"../errors.js\"\nimport { fetchError, problemToError, type Fetch } from \"./http.js\"\n\nexport class QoreApiClient {\n constructor(private readonly o: {\n apiOrigin: string; fetch: Fetch; token: (force: boolean) => Promise<string>\n cliVersion: string; command: string; platform: string; onRequest?: (line: string) => void\n }) {}\n\n private async once(path: string, force: boolean): Promise<Response> {\n const token = await this.o.token(force)\n let res: Response\n try {\n res = await this.o.fetch(`${this.o.apiOrigin}${path}`, {\n headers: {\n authorization: `Bearer ${token}`,\n accept: \"application/json\",\n \"qore-cli-version\": this.o.cliVersion,\n \"qore-command\": this.o.command,\n \"user-agent\": `qore/${this.o.cliVersion} (${this.o.platform})`,\n },\n })\n } catch (e) { throw fetchError(e, new URL(this.o.apiOrigin).host) }\n this.o.onRequest?.(`GET ${path} → ${res.status}${res.headers.get(\"x-request-id\") ? ` (${res.headers.get(\"x-request-id\")})` : \"\"}`)\n return res\n }\n\n async get<T>(path: string): Promise<T> {\n let res = await this.once(path, false)\n if (res.status === 401) {\n res = await this.once(path, true)\n if (res.status === 401) {\n throw new QoreError(\"QORE_SESSION_EXPIRED\", \"The portal no longer accepts your session\", {\n hint: \"Run `qore login`.\", status: 401, requestId: res.headers.get(\"x-request-id\") ?? undefined,\n })\n }\n }\n if (!res.ok) throw await problemToError(res)\n return (await res.json()) as T\n }\n}\n","import { QoreError } from \"../errors.js\"\nimport type { WithLock } from \"../../platform/lock.js\"\nimport type { Oidc, TokenSet } from \"./oidc.js\"\nimport type { TokenStore } from \"./tokenStore.js\"\n\nconst SKEW_MS = 60_000\n\nexport class RefreshCoordinator {\n constructor(private readonly o: {\n store: TokenStore; oidc: () => Promise<Oidc>; withLock: WithLock; lockName: string; now: () => Date\n }) {}\n\n private fresh(expiresAt: string): boolean {\n return new Date(expiresAt).getTime() - this.o.now().getTime() > SKEW_MS\n }\n\n private async rotate(scope?: string): Promise<TokenSet> {\n let stored = await this.o.store.getRefresh()\n if (!stored) throw new QoreError(\"QORE_NOT_LOGGED_IN\", \"Not logged in\", { hint: \"Run `qore login`.\" })\n let t: TokenSet\n for (let attempt = 0; ; attempt++) {\n try {\n t = await (await this.o.oidc()).refresh(stored.rt, scope)\n break\n } catch (e) {\n if (!(e instanceof QoreError && e.code === \"QORE_SESSION_EXPIRED\")) throw e\n // Only the RT we presented was rejected. Another process may have rotated it\n // meanwhile (a stolen stale lock, a second config dir, a lost response): then the\n // stored RT is newer, so retry once with it instead of logging the user out.\n const now = await this.o.store.getRefresh()\n if (now && now.rt !== stored.rt) {\n if (attempt === 0) { stored = now; continue }\n throw e\n }\n await this.o.store.clear()\n throw e\n }\n }\n // Store the scope the token response reports: after a downscoped refresh the rotated RT\n // may carry only the narrowed scope, so never record the old full scope for it. An empty\n // response scope means \"as requested\" (RFC 6749 §5.1).\n await this.o.store.setRefresh({ rt: t.refreshToken, sub: t.sub, scope: t.scope || (scope ?? stored.scope), obtainedAt: this.o.now().toISOString() })\n return t\n }\n\n async accessToken(opts: { force?: boolean } = {}): Promise<string> {\n const seen = await this.o.store.getAccess()\n if (!opts.force && seen && this.fresh(seen.expiresAt)) return seen.at\n return this.o.withLock(this.o.lockName, async () => {\n const again = await this.o.store.getAccess()\n if (again && again.at !== seen?.at && this.fresh(again.expiresAt)) return again.at\n const t = await this.rotate()\n await this.o.store.setAccess({ at: t.accessToken, expiresAt: new Date(this.o.now().getTime() + t.expiresIn * 1000).toISOString() })\n return t.accessToken\n })\n }\n\n /** A token carrying only `scopes`, held in memory by the caller (qore mcp). */\n async downscoped(scopes: string[]): Promise<string> {\n return this.o.withLock(this.o.lockName, async () => (await this.rotate(scopes.join(\" \"))).accessToken)\n }\n}\n","import { QoreApiClient } from \"./api/client.js\"\nimport { RefreshCoordinator } from \"./auth/refresh.js\"\nimport { TokenStore } from \"./auth/tokenStore.js\"\nimport type { ProfileRecord } from \"./config.js\"\nimport type { Deps } from \"./deps.js\"\nimport { QoreError } from \"./errors.js\"\nimport { profileHash, type PortalRef } from \"./profiles.js\"\n\nexport function loginHint(portal: PortalRef): string {\n return portal.builtin === \"prod\" ? \"Run `qore login`.\" : `Run \\`qore login --portal ${portal.builtin ?? portal.apiOrigin}\\`.`\n}\n\nexport async function openSession(deps: Deps, portal: PortalRef, command: string, onRequest?: (l: string) => void) {\n const profile: ProfileRecord | undefined = (await deps.config.read()).profiles[portal.apiOrigin]\n if (!profile) throw new QoreError(\"QORE_NOT_LOGGED_IN\", `Not logged in to ${portal.apiOrigin}`, { hint: loginHint(portal) })\n const hash = profileHash(profile.apiOrigin, profile.issuer)\n const tokens = new TokenStore(deps.keychain, hash)\n if (!(await tokens.getRefresh())) throw new QoreError(\"QORE_NOT_LOGGED_IN\", `Not logged in to ${portal.apiOrigin}`, { hint: loginHint(portal) })\n const refresh = new RefreshCoordinator({ store: tokens, oidc: () => deps.oidcFor(profile.issuer), withLock: deps.withLock, lockName: hash, now: deps.now })\n const api = new QoreApiClient({\n apiOrigin: profile.apiOrigin, fetch: deps.fetch, token: (force) => refresh.accessToken({ force }),\n cliVersion: deps.version, command, platform: `${deps.platform} ${process.arch}; node ${process.versions.node}`, onRequest,\n })\n return { profile, api, tokens, refresh }\n}\n","import type { Command } from \"commander\"\nimport { fetchMeta, negotiate } from \"../../core/api/meta.js\"\nimport type { CliMe, CliMeta } from \"../../core/api/types.js\"\nimport { deviceLogin } from \"../../core/auth/login.js\"\nimport { TokenStore } from \"../../core/auth/tokenStore.js\"\nimport { profileHash, resolvePortal } from \"../../core/profiles.js\"\nimport { openSession } from \"../../core/session.js\"\nimport { requestLog, type CommandContext } from \"../program.js\"\nimport { renderJson } from \"../render.js\"\n\nexport function registerLogin(program: Command, ctx: CommandContext): void {\n program.command(\"login\").description(\"Log in with your Qore account\")\n .option(\"--no-browser\", \"only print the URL\")\n .action(async (cmd: { browser: boolean }) => {\n const { deps, io, signal } = ctx\n const g = ctx.opts()\n const cfg = await deps.config.read()\n const portal = resolvePortal(g.portal, cfg.defaultProfile)\n const meta: CliMeta = await fetchMeta(deps.fetch, portal.apiOrigin)\n const known = cfg.profiles[portal.apiOrigin]?.issuer\n const pinned = { ...portal, pinnedIssuer: portal.pinnedIssuer ?? known ?? null }\n if (!pinned.pinnedIssuer && portal.builtin === null) {\n io.err(`! Logging in to ${portal.apiOrigin}, identity provider ${meta.auth.issuer}`)\n }\n negotiate(meta, pinned, deps.version)\n const issuer = pinned.pinnedIssuer ?? meta.auth.issuer\n const hash = profileHash(portal.apiOrigin, issuer)\n const store = new TokenStore(deps.keychain, hash)\n const t = await deviceLogin({\n oidc: await deps.oidcFor(issuer), store, now: deps.now, signal,\n withLock: deps.withLock, lockName: hash,\n onCode: async (s, settled) => {\n const url = s.verificationUriComplete ?? s.verificationUri\n io.err(`! First copy your one-time code: ${s.userCode}`)\n if (io.interactive && cmd.browser) {\n try {\n await io.waitForEnter(` Press Enter to open ${url} (or open it yourself)`, AbortSignal.any([signal, settled]))\n } catch (e) {\n // Approved (or denied) in a browser the user opened themselves: nothing left to open.\n if (settled.aborted && !signal.aborted) return\n throw e\n }\n if (settled.aborted) return\n if (!(await io.openUrl(url))) io.err(` Open ${url} in a browser`)\n } else {\n io.err(` Open ${url} in a browser`)\n }\n },\n })\n await deps.config.update((c) => {\n c.profiles[portal.apiOrigin] = { ...c.profiles[portal.apiOrigin], apiOrigin: portal.apiOrigin, issuer,\n sub: t.sub, email: t.email, meta: { fetchedAt: deps.now().toISOString(), doc: meta } }\n if (g.portal || !c.defaultProfile) c.defaultProfile = portal.apiOrigin\n })\n const { api } = await openSession(deps, { ...portal, pinnedIssuer: issuer }, \"login\", requestLog(ctx))\n const me = await api.get<CliMe>(\"/api/cli/v1/me\")\n const prev = cfg.profiles[portal.apiOrigin]\n let active: { id: string; slug: string } | undefined =\n prev?.sub === t.sub && prev.activeTenant && me.tenants.some((x) => x.id === prev.activeTenant!.id)\n ? prev.activeTenant\n : undefined\n if (active) {\n // A previous session's active tenant is still valid for this sub: keep it, no re-selection.\n } else if (me.tenants.length === 0) {\n io.err(\"! Your account is not a developer in any organisation. Ask an admin to invite you as developer.\")\n } else if (me.tenants.length === 1) {\n active = { id: me.tenants[0]!.id, slug: me.tenants[0]!.slug }\n io.err(`✓ Using tenant ${me.tenants[0]!.name}`)\n } else if (io.interactive) {\n active = await io.select(\"Select a tenant\", me.tenants.map((x) => ({ name: `${x.name} ${x.role}`, value: { id: x.id, slug: x.slug } })))\n } else {\n io.err(`! You belong to ${me.tenants.length} tenants; choose one with \\`qore tenant use <slug>\\``)\n }\n await deps.config.update((c) => { c.profiles[portal.apiOrigin]!.activeTenant = active })\n const label = portal.builtin ?? portal.apiOrigin\n if (g.json) renderJson(io, { portal: label, email: me.email, activeTenant: active ?? null })\n else io.out(`✓ Logged in as ${me.email} (${label})`)\n })\n}\n","import type { Command } from \"commander\"\nimport { TokenStore } from \"../../core/auth/tokenStore.js\"\nimport { QoreError } from \"../../core/errors.js\"\nimport { profileHash, resolvePortal } from \"../../core/profiles.js\"\nimport type { CommandContext } from \"../program.js\"\nimport { renderJson } from \"../render.js\"\n\nexport function registerLogout(program: Command, ctx: CommandContext): void {\n program.command(\"logout\").description(\"End the CLI session\")\n .option(\"--all\", \"log out of every portal\")\n .action(async (cmd: { all?: boolean }) => {\n const { deps, io } = ctx\n const g = ctx.opts()\n const cfg = await deps.config.read()\n const targets = cmd.all ? Object.values(cfg.profiles)\n : [cfg.profiles[resolvePortal(g.portal, cfg.defaultProfile).apiOrigin]].filter((p) => p !== undefined)\n const done: string[] = []\n for (const p of targets) {\n const hash = profileHash(p.apiOrigin, p.issuer)\n const store = new TokenStore(deps.keychain, hash)\n const host = new URL(p.issuer).host\n // Read, revoke and clear under one lock, so a concurrent refresh cannot rotate the\n // RT between our read and the revoke (we would revoke a stale one) or resurrect it.\n await deps.withLock(hash, async () => {\n const rt = await store.getRefresh()\n if (rt) {\n try { await (await deps.oidcFor(p.issuer)).revoke(rt.rt) }\n catch (e) {\n const network = e instanceof QoreError && e.details?.reason !== undefined\n io.err(network\n ? `! Could not reach ${host}; the server session may persist until it expires.`\n : `! Could not revoke the session at ${host} (${e instanceof Error ? e.message : String(e)}); the server session may persist until it expires.`)\n }\n }\n await store.clear()\n })\n done.push(p.apiOrigin)\n }\n if (g.json) renderJson(io, { loggedOut: done })\n else if (done.length === 0) io.out(\"Not logged in\")\n else io.out(`✓ Logged out of ${done.map((o) => resolvePortal(o, undefined).builtin ?? o).join(\", \")}`)\n })\n}\n","import type { Command } from \"commander\"\nimport type { CliMe } from \"../../core/api/types.js\"\nimport { QoreError } from \"../../core/errors.js\"\nimport { resolvePortal } from \"../../core/profiles.js\"\nimport { openSession } from \"../../core/session.js\"\nimport { requestLog, type CommandContext } from \"../program.js\"\nimport { renderJson } from \"../render.js\"\n\nexport function registerTenant(program: Command, ctx: CommandContext): void {\n const tenant = program.command(\"tenant\").description(\"Manage the active tenant\")\n\n tenant.command(\"list\").description(\"List tenants you have access to\")\n .action(async () => {\n const { deps, io } = ctx\n const g = ctx.opts()\n const cfg = await deps.config.read()\n const portal = resolvePortal(g.portal, cfg.defaultProfile)\n const { profile, api } = await openSession(deps, portal, \"tenant list\", requestLog(ctx))\n const me = await api.get<CliMe>(\"/api/cli/v1/me\")\n const activeId = profile.activeTenant?.id\n if (g.json) {\n renderJson(io, { tenants: me.tenants.map((t) => ({ ...t, active: t.id === activeId })) })\n return\n }\n for (const t of me.tenants) {\n const mark = t.id === activeId ? \"*\" : \" \"\n io.out(`${mark} ${t.name} ${t.role}`)\n }\n })\n\n tenant.command(\"use\").description(\"Set the active tenant\").argument(\"[slug]\", \"tenant slug\")\n .action(async (slug: string | undefined) => {\n const { deps, io } = ctx\n const g = ctx.opts()\n const cfg = await deps.config.read()\n const portal = resolvePortal(g.portal, cfg.defaultProfile)\n const { api } = await openSession(deps, portal, \"tenant use\", requestLog(ctx))\n const me = await api.get<CliMe>(\"/api/cli/v1/me\")\n const candidates = me.tenants.map((t) => t.slug)\n let chosen: { id: string; slug: string }\n if (slug) {\n const found = me.tenants.find((t) => t.slug === slug)\n if (!found) throw new QoreError(\"QORE_RESOURCE_NOT_FOUND\", `No tenant \"${slug}\" for this account`, { candidates })\n chosen = { id: found.id, slug: found.slug }\n } else if (io.interactive) {\n chosen = await io.select(\"Select a tenant\", me.tenants.map((t) => ({ name: `${t.name} ${t.role}`, value: { id: t.id, slug: t.slug } })))\n } else {\n throw new QoreError(\"QORE_CONTEXT_REQUIRED\", \"Which tenant? Pass a slug or run interactively.\", { candidates })\n }\n await deps.config.update((c) => { c.profiles[portal.apiOrigin]!.activeTenant = chosen })\n if (g.json) renderJson(io, { activeTenant: chosen })\n else io.out(`✓ Using tenant ${chosen.slug}`)\n })\n}\n","import type { Command } from \"commander\"\nimport { fetchMeta } from \"../../core/api/meta.js\"\nimport { CancelledError } from \"../../core/errors.js\"\nimport { resolvePortal } from \"../../core/profiles.js\"\nimport type { CommandContext } from \"../program.js\"\nimport { renderJson } from \"../render.js\"\n\nexport function registerVersion(program: Command, ctx: CommandContext): void {\n program.command(\"version\").description(\"Show the CLI and portal version\")\n .action(async () => {\n const { deps, io } = ctx\n const g = ctx.opts()\n const cfg = await deps.config.read()\n const portal = resolvePortal(g.portal, cfg.defaultProfile)\n let portalInfo: { apiVersions: string[]; minCliVersion: string; latestCliVersion: string; capabilities: string[] } | null = null\n try {\n const meta = await fetchMeta(deps.fetch, portal.apiOrigin)\n portalInfo = { apiVersions: meta.apiVersions, minCliVersion: meta.minCliVersion, latestCliVersion: meta.latestCliVersion, capabilities: meta.capabilities }\n } catch (e) {\n // A cancel is not \"unreachable\": Ctrl+C still exits 130.\n if (e instanceof CancelledError) throw e\n /* portal unreachable; report null below */\n }\n if (g.json) {\n renderJson(io, { cli: deps.version, portal: portalInfo })\n return\n }\n io.out(`qore ${deps.version}`)\n const label = portal.builtin ?? portal.apiOrigin\n if (portalInfo) {\n io.out(`portal ${label}: api ${portalInfo.apiVersions.join(\",\")}, min ${portalInfo.minCliVersion}, latest ${portalInfo.latestCliVersion}`)\n } else {\n io.out(`portal ${label}: unreachable`)\n }\n })\n}\n","import type { Command } from \"commander\"\nimport type { CliMe } from \"../../core/api/types.js\"\nimport { resolvePortal } from \"../../core/profiles.js\"\nimport { openSession } from \"../../core/session.js\"\nimport { requestLog, type CommandContext } from \"../program.js\"\nimport { renderJson } from \"../render.js\"\n\nexport function registerWhoami(program: Command, ctx: CommandContext): void {\n program.command(\"whoami\").description(\"Show who you're logged in as\")\n .action(async () => {\n const { deps, io } = ctx\n const g = ctx.opts()\n const cfg = await deps.config.read()\n const portal = resolvePortal(g.portal, cfg.defaultProfile)\n const { profile, api } = await openSession(deps, portal, \"whoami\", requestLog(ctx))\n const me = await api.get<CliMe>(\"/api/cli/v1/me\")\n const activeTenant = profile.activeTenant\n if (activeTenant && !me.tenants.some((t) => t.id === activeTenant.id)) {\n io.err(`! You no longer have developer access to ${activeTenant.slug}`)\n }\n const label = portal.builtin ?? portal.apiOrigin\n if (g.json) {\n renderJson(io, { portal: label, activeTenant: activeTenant ?? null, me })\n return\n }\n io.out(`${me.email} (${label})`)\n for (const t of me.tenants) {\n const mark = activeTenant?.id === t.id ? \"*\" : \" \"\n io.out(`${mark} ${t.name} ${t.role}`)\n for (const a of t.apps) {\n io.out(` ${a.slug} ${a.access}`)\n for (const m of a.modules) {\n io.out(` ${m.slug} ${m.type} ${m.access}`)\n }\n }\n }\n })\n}\n","import type { Register } from \"../program.js\"\nimport { registerLogin } from \"./login.js\"\nimport { registerLogout } from \"./logout.js\"\nimport { registerTenant } from \"./tenant.js\"\nimport { registerVersion } from \"./version.js\"\nimport { registerWhoami } from \"./whoami.js\"\n\nexport const COMMANDS: Register[] = [registerLogin, registerLogout, registerWhoami, registerTenant, registerVersion]\n","import { compareVersions } from \"../core/api/meta.js\"\nimport type { Deps } from \"../core/deps.js\"\nimport type { Io } from \"./io.js\"\n\nconst REGISTRY_URL = \"https://registry.npmjs.org/@quatronic%2Fqore/latest\"\nconst DAY_MS = 24 * 60 * 60 * 1000\nconst DEFAULT_TIMEOUT_MS = 1500\n\nexport async function maybeNotifyUpdate(deps: Deps, io: Io, o: { json: boolean }, timeoutMs = DEFAULT_TIMEOUT_MS): Promise<void> {\n if (o.json || deps.env.CI || deps.env.QORE_NO_UPDATE_CHECK === \"1\" || !io.interactive) return\n const cfg = await deps.config.read()\n const last = cfg.updateCheck?.lastCheckedAt\n if (last && deps.now().getTime() - new Date(last).getTime() < DAY_MS) return\n const controller = new AbortController()\n const timer = setTimeout(() => controller.abort(), timeoutMs)\n let latest: string | undefined\n try {\n const res = await deps.fetch(REGISTRY_URL, { signal: controller.signal })\n if (res.ok) latest = ((await res.json()) as { version?: string }).version\n } catch { /* silent: an update check never affects the run */ }\n finally { clearTimeout(timer) }\n try {\n // Recorded after a failed, non-OK or timed-out check too, so an offline user does not\n // pay the timeout on every command; the last known latest version is kept then.\n await deps.config.update((c) => {\n c.updateCheck = { lastCheckedAt: deps.now().toISOString(), latest: latest ?? c.updateCheck?.latest ?? deps.version }\n })\n } catch { return }\n if (latest && compareVersions(latest, deps.version) > 0) {\n io.err(`A new qore is available: ${deps.version} → ${latest} npm i -g @quatronic/qore`)\n }\n}\n","import { mkdir, readFile, rename, writeFile, chmod } from \"node:fs/promises\"\nimport { join } from \"node:path\"\nimport { randomBytes } from \"node:crypto\"\nimport { QoreError } from \"./errors.js\"\n\nexport type ProfileRecord = {\n apiOrigin: string\n issuer: string\n sub?: string\n email?: string\n activeTenant?: { id: string; slug: string }\n meta?: { fetchedAt: string; doc: unknown }\n}\n\nexport type QoreConfig = {\n schemaVersion: 1\n defaultProfile?: string\n profiles: Record<string, ProfileRecord>\n updateCheck?: { lastCheckedAt: string; latest: string }\n}\n\nconst empty = (): QoreConfig => ({ schemaVersion: 1, profiles: {} })\n\nexport class ConfigStore {\n constructor(readonly dir: string) {}\n\n private get file() { return join(this.dir, \"config.json\") }\n\n async read(): Promise<QoreConfig> {\n let raw: string\n try {\n raw = await readFile(this.file, \"utf8\")\n } catch (e) {\n if ((e as NodeJS.ErrnoException).code === \"ENOENT\") return empty()\n throw e\n }\n try {\n const parsed = JSON.parse(raw) as QoreConfig\n if (parsed.schemaVersion !== 1 || typeof parsed.profiles !== \"object\") throw new Error(\"shape\")\n return parsed\n } catch (cause) {\n throw new QoreError(\"QORE_CONTEXT_INVALID\", `Qore config is malformed: ${this.file}`, {\n hint: \"Fix or delete the file, then run `qore login` again\", cause,\n })\n }\n }\n\n async update(fn: (c: QoreConfig) => QoreConfig | void): Promise<QoreConfig> {\n const current = await this.read()\n const next = fn(current) ?? current\n await mkdir(this.dir, { recursive: true, mode: 0o700 })\n const tmp = join(this.dir, `.config.${randomBytes(6).toString(\"hex\")}.tmp`)\n await writeFile(tmp, JSON.stringify(next, null, 2) + \"\\n\", { mode: 0o600 })\n await chmod(tmp, 0o600)\n await rename(tmp, this.file)\n return next\n }\n}\n","import { Entry } from \"@napi-rs/keyring\"\nimport { QoreError } from \"../core/errors.js\"\n\nexport interface Keychain {\n get(account: string): Promise<string | null>\n set(account: string, value: string): Promise<void>\n delete(account: string): Promise<void>\n}\n\nconst SERVICE = \"qore\"\nconst HINTS: Partial<Record<NodeJS.Platform, string>> = {\n linux: \"Install and unlock a Secret Service provider (gnome-keyring or KWallet); headless machines and containers have none.\",\n darwin: \"Unlock your login keychain in Keychain Access.\",\n win32: \"Windows Credential Manager must be available for your user.\",\n}\n\nexport function classifyKeychainError(e: unknown, platform: NodeJS.Platform): QoreError {\n const msg = e instanceof Error ? e.message : String(e)\n // keyring-rs Error::TooLong (\"… is longer than the platform limit of N chars\"): Windows\n // Credential Manager caps a credential blob (R18). Still UNAVAILABLE, but say what it is.\n if (/TooLong|longer than the platform limit/i.test(msg)) {\n return new QoreError(\"QORE_KEYCHAIN_UNAVAILABLE\", \"The session token is too large for the OS keychain\", {\n hint: platform === \"win32\"\n ? \"The token exceeds the Windows Credential Manager size limit. Report this to the Qore team.\"\n : \"The token exceeds the keychain's size limit. Report this to the Qore team.\",\n cause: e,\n })\n }\n if (/cancel|denied|errSecAuthFailed|user interaction/i.test(msg)) {\n return new QoreError(\"QORE_KEYCHAIN_DENIED\", \"Access to the OS keychain was denied\", {\n hint: \"Allow qore to use the keychain when your OS asks, then retry.\", cause: e,\n })\n }\n return new QoreError(\"QORE_KEYCHAIN_UNAVAILABLE\", \"No usable OS keychain\", {\n hint: HINTS[platform] ?? \"qore stores tokens only in the OS keychain.\", cause: e,\n })\n}\n\nexport class OsKeychain implements Keychain {\n constructor(private readonly platform: NodeJS.Platform = process.platform) {}\n\n private wrap<T>(fn: () => T): Promise<T> {\n try { return Promise.resolve(fn()) } catch (e) { return Promise.reject(classifyKeychainError(e, this.platform)) }\n }\n\n get(account: string) { return this.wrap(() => new Entry(SERVICE, account).getPassword() ?? null) }\n set(account: string, value: string) { return this.wrap(() => { new Entry(SERVICE, account).setPassword(value) }) }\n delete(account: string) {\n // deletePassword() returns false (rather than throwing) when there is no entry.\n return this.wrap(() => { new Entry(SERVICE, account).deletePassword() })\n }\n}\n","import { mkdir, writeFile } from \"node:fs/promises\"\nimport { join } from \"node:path\"\nimport lockfile from \"proper-lockfile\"\nimport { QoreError } from \"../core/errors.js\"\n\nexport type WithLock = <T>(name: string, fn: () => Promise<T>) => Promise<T>\n\nexport function fileLock(dir: string): WithLock {\n return async (name, fn) => {\n const locks = join(dir, \"locks\")\n await mkdir(locks, { recursive: true, mode: 0o700 })\n const target = join(locks, `${name}.lock`)\n await writeFile(target, \"\", { flag: \"a\" })\n let release: () => Promise<void>\n // proper-lockfile's default onCompromised throws from a timer (an uncaught crash). A\n // compromised lock (mtime update failed, or another process took it as stale) is only\n // recorded: the keychain writes under it are idempotent, and refresh re-reads the RT.\n let compromised: Error | undefined\n try {\n release = await lockfile.lock(target, {\n stale: 30_000,\n retries: { retries: 30, minTimeout: 100, maxTimeout: 1000, randomize: true },\n onCompromised: (err) => { compromised = err },\n })\n } catch (cause) {\n throw new QoreError(\"QORE_AUTH_BUSY\", \"Another qore process is refreshing the session\", { hint: \"Retry in a moment.\", cause })\n }\n try { return await fn() } finally {\n // After a compromise release() rejects (ERELEASED); that must not replace fn's outcome.\n await release().catch((e: unknown) => { if (!compromised) throw e })\n }\n }\n}\n","import { posix, win32 } from \"node:path\"\n\nexport function configDir(env: NodeJS.ProcessEnv, platform: NodeJS.Platform, home: string): string {\n if (platform === \"win32\") return win32.join(env.APPDATA ?? win32.join(home, \"AppData\", \"Roaming\"), \"qore\")\n // posix.join, not the host's join: the result is for the target platform, whatever the host\n // (tests run on Windows CI too).\n if (platform === \"darwin\") return posix.join(home, \"Library\", \"Application Support\", \"qore\")\n // XDG Base Directory spec: a relative $XDG_CONFIG_HOME is invalid and must be ignored.\n const xdg = env.XDG_CONFIG_HOME && posix.isAbsolute(env.XDG_CONFIG_HOME) ? env.XDG_CONFIG_HOME : undefined\n return posix.join(xdg ?? posix.join(home, \".config\"), \"qore\")\n}\n","declare const __QORE_VERSION__: string | undefined\n// tsup replaces __QORE_VERSION__ at build time; tests run from source and see \"0.0.0-dev\".\nexport const VERSION: string = typeof __QORE_VERSION__ === \"string\" ? __QORE_VERSION__ : \"0.0.0-dev\"\n"],"mappings":"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","names":["fetch","pc","io","json","argv","deps","io","json","pc","fetch","deps","deps","io","deps","io","deps","io","deps","io","deps","io","deps","io","dir","mkdir","writeFile","join","dir","join","mkdir","writeFile"]}
|
|
1
|
+
{"version":3,"sources":["../src/cli.ts","../src/cli/io.ts","../src/platform/browser.ts","../src/core/errors.ts","../src/cli/program.ts","../src/core/api/http.ts","../src/cli/render.ts","../src/cli/commands/env.ts","../src/core/context/repoConfig.ts","../src/core/api/meta.ts","../src/core/api/capabilities.ts","../src/core/context/resolver.ts","../src/core/auth/tokenStore.ts","../src/core/profiles.ts","../src/core/api/client.ts","../src/core/auth/refresh.ts","../src/core/session.ts","../src/core/context/cache.ts","../src/core/jsonFile.ts","../src/core/context/repoKey.ts","../src/core/context/repoRoot.ts","../src/core/env/fetch.ts","../src/core/env/merge.ts","../src/core/env/pull.ts","../src/cli/context.ts","../src/core/trust.ts","../src/cli/trustPrompt.ts","../src/core/auth/oidc.ts","../src/core/auth/login.ts","../src/cli/commands/login.ts","../src/cli/commands/logout.ts","../src/cli/commands/run.ts","../src/cli/format.ts","../src/cli/commands/status.ts","../src/cli/commands/tenant.ts","../src/cli/commands/version.ts","../src/cli/commands/whoami.ts","../src/cli/commands/index.ts","../src/cli/updateCheck.ts","../src/core/config.ts","../src/platform/git.ts","../src/platform/keychain.ts","../src/platform/lock.ts","../src/platform/paths.ts","../src/platform/spawn.ts","../src/version.ts"],"sourcesContent":["import { homedir } from \"node:os\"\nimport { EnvHttpProxyAgent, setGlobalDispatcher } from \"undici\"\nimport { isInteractive, processIo } from \"./cli/io.js\"\nimport { argvBeforeSeparator, run } from \"./cli/program.js\"\nimport { COMMANDS } from \"./cli/commands/index.js\"\nimport { childRunning } from \"./cli/commands/run.js\"\nimport { maybeNotifyUpdate } from \"./cli/updateCheck.js\"\nimport { abortableFetch } from \"./core/api/http.js\"\nimport { createOidc } from \"./core/auth/oidc.js\"\nimport { ConfigStore } from \"./core/config.js\"\nimport type { Deps } from \"./core/deps.js\"\nimport { systemGit } from \"./platform/git.js\"\nimport { OsKeychain } from \"./platform/keychain.js\"\nimport { fileLock } from \"./platform/lock.js\"\nimport { configDir } from \"./platform/paths.js\"\nimport { crossSpawner } from \"./platform/spawn.js\"\nimport { VERSION } from \"./version.js\"\n\nif (process.env.HTTPS_PROXY || process.env.https_proxy || process.env.HTTP_PROXY) setGlobalDispatcher(new EnvHttpProxyAgent())\n\nconst dir = configDir(process.env, process.platform, homedir())\nconst argv = process.argv.slice(2)\n// Ruling R12: a child's own --json/--no-input (after --, e.g. `qore run -- node --json`)\n// must never reach qore's own flag scanning.\nconst preSeparatorArgv = argvBeforeSeparator(argv)\nconst json = preSeparatorArgv.includes(\"--json\")\n// Ctrl+C: the first one aborts every in-flight request and prompt through `ac.signal`\n// (→ CancelledError → exit 130); a second one exits at once, whatever is still running —\n// except while `qore run`'s child is alive (ruling R3, spec §11.2): the terminal already\n// delivered this SIGINT to the whole foreground process group, so the child's own exit\n// (its code, or the signal `run` re-raises) is what decides qore's exit code, not a forced\n// exit(130) here.\nconst ac = new AbortController()\nprocess.on(\"SIGINT\", () => {\n if (ac.signal.aborted) {\n if (childRunning.current) return\n process.exit(130)\n }\n ac.abort()\n})\nconst fetch = abortableFetch(globalThis.fetch, ac.signal)\nconst deps: Deps = {\n fetch,\n keychain: new OsKeychain(),\n config: new ConfigStore(dir),\n withLock: fileLock(dir),\n now: () => new Date(),\n oidcFor: (issuer) => createOidc({ issuer, clientId: \"qore-cli\", fetch }),\n env: process.env,\n platform: process.platform,\n version: VERSION,\n cwd: process.cwd(),\n git: systemGit,\n spawn: crossSpawner,\n raise: (signal) => { process.removeAllListeners(signal); process.kill(process.pid, signal) },\n}\nconst io = processIo(isInteractive({ stdinTTY: Boolean(process.stdin.isTTY), stdoutTTY: Boolean(process.stdout.isTTY),\n json, noInput: preSeparatorArgv.includes(\"--no-input\"), env: process.env }))\nprocess.exitCode = await run(argv, deps, io, ac.signal, COMMANDS)\nif (!ac.signal.aborted) {\n try {\n await maybeNotifyUpdate(deps, io, { json })\n } catch {\n // an update check must never change the exit code\n }\n}\n","import { confirm, select } from \"@inquirer/prompts\"\nimport { createInterface } from \"node:readline\"\nimport { openBrowser } from \"../platform/browser.js\"\nimport { CancelledError } from \"../core/errors.js\"\n\nexport interface Io {\n out(s: string): void\n err(s: string): void\n interactive: boolean\n select<T>(msg: string, choices: { name: string; value: T; description?: string }[]): Promise<T>\n confirm(message: string): Promise<boolean>\n waitForEnter(msg: string, signal: AbortSignal): Promise<void>\n openUrl(url: string): Promise<boolean>\n}\n\nexport function isInteractive(o: { stdinTTY: boolean; stdoutTTY: boolean; json: boolean; noInput: boolean; env: NodeJS.ProcessEnv }): boolean {\n return o.stdinTTY && o.stdoutTTY && !o.json && !o.noInput && !o.env.CI\n}\n\nexport function processIo(interactive: boolean): Io {\n return {\n out: (s) => { process.stdout.write(s + \"\\n\") },\n err: (s) => { process.stderr.write(s + \"\\n\") },\n interactive,\n async select(message, choices) {\n try { return await select({ message, choices }) } catch (e) {\n if ((e as Error).name === \"ExitPromptError\") throw new CancelledError()\n throw e\n }\n },\n async confirm(message) {\n try { return await confirm({ message, default: false }) } catch (e) {\n if ((e as Error).name === \"ExitPromptError\") throw new CancelledError()\n throw e\n }\n },\n waitForEnter: createWaitForEnter(process.stdin, process.stderr),\n openUrl: openBrowser,\n }\n}\n\n/** Builds a `waitForEnter` bound to the given streams, so tests can drive it without a\n * real TTY. Readline puts a TTY's stdin in raw mode, which turns Ctrl+C into the\n * interface's own 'SIGINT' event rather than a process-level SIGINT (R16) — that must be\n * turned into a CancelledError itself, since `process.once(\"SIGINT\", …)` in cli.ts never\n * fires for it. `terminal: true` makes readline parse Ctrl+C the same way on any stream. */\nexport function createWaitForEnter(\n input: NodeJS.ReadableStream, output: NodeJS.WritableStream,\n): (message: string, signal: AbortSignal) => Promise<void> {\n return (message, signal) => new Promise((resolve, reject) => {\n const rl = createInterface({ input, output, terminal: true })\n const onAbort = () => { rl.close(); reject(new CancelledError()) }\n const done = () => { signal.removeEventListener(\"abort\", onAbort); rl.close(); resolve() }\n signal.addEventListener(\"abort\", onAbort, { once: true })\n rl.on(\"SIGINT\", () => { signal.removeEventListener(\"abort\", onAbort); rl.close(); reject(new CancelledError()) })\n rl.question(message, done)\n })\n}\n","import open from \"open\"\n\n/** Opens the URL; false when there is no display (SSH, container) or it fails. */\nexport async function openBrowser(url: string): Promise<boolean> {\n if (process.platform === \"linux\" && !process.env.DISPLAY && !process.env.WAYLAND_DISPLAY) return false\n try { await open(url); return true } catch { return false }\n}\n","export const EXIT = {\n QORE_INTERNAL: 1,\n QORE_KEYCHAIN_UNAVAILABLE: 1,\n QORE_KEYCHAIN_DENIED: 1,\n QORE_GIT_UNAVAILABLE: 1,\n QORE_CONTEXT_REQUIRED: 2,\n QORE_CONTEXT_INVALID: 2,\n QORE_CONTEXT_UNSUPPORTED: 2,\n QORE_APP_AMBIGUOUS: 2,\n QORE_NOT_LOGGED_IN: 4,\n QORE_SESSION_EXPIRED: 4,\n QORE_LOGIN_EXPIRED: 4,\n QORE_LOGIN_DENIED: 4,\n QORE_CLOCK_SKEW: 4,\n QORE_TENANT_ACCESS_LOST: 5,\n QORE_RESOURCE_NOT_FOUND: 5,\n QORE_ACCESS_DENIED: 5,\n QORE_NO_DEVELOPER_ACCESS: 5,\n QORE_AUTH_UNAVAILABLE: 6,\n QORE_AUTH_BUSY: 6,\n QORE_API_UNREACHABLE: 6,\n QORE_API_UNAVAILABLE: 6,\n QORE_INCOMPATIBLE_SERVER: 7,\n QORE_UNSUPPORTED_BY_SERVER: 7,\n QORE_UPGRADE_REQUIRED: 7,\n QORE_PORTAL_UNTRUSTED: 7,\n QORE_RATE_LIMITED: 8,\n} as const\n\nexport type QoreErrorCode = keyof typeof EXIT\n\n/** One element of `error.candidates`, the same shape under every code (--json is a\n * semver contract): what the user can pick from to resolve the error. `tenant` (a\n * tenant slug) accompanies module candidates, whose slugs are unique only per tenant. */\nexport type Candidate = {\n kind: \"module\" | \"tenant\" | \"app\"\n id?: string\n slug: string\n name?: string\n remote?: string\n tenant?: string\n}\n\ntype Opts = {\n hint?: string\n status?: number\n requestId?: string\n candidates?: Candidate[]\n serverCode?: string\n details?: Record<string, unknown>\n cause?: unknown\n}\n\nexport class QoreError extends Error {\n readonly code: QoreErrorCode\n readonly hint?: string\n readonly status?: number\n readonly requestId?: string\n readonly candidates?: Candidate[]\n readonly serverCode?: string\n readonly details?: Record<string, unknown>\n\n constructor(code: QoreErrorCode, message: string, opts: Opts = {}) {\n super(message, opts.cause === undefined ? undefined : { cause: opts.cause })\n this.name = \"QoreError\"\n this.code = code\n this.hint = opts.hint\n this.status = opts.status\n this.requestId = opts.requestId\n this.candidates = opts.candidates\n this.serverCode = opts.serverCode\n this.details = opts.details\n }\n}\n\nexport class CancelledError extends Error {\n constructor() {\n super(\"Cancelled\")\n this.name = \"CancelledError\"\n }\n}\n\nexport function exitCodeFor(err: unknown): number {\n if (err instanceof CancelledError || (err instanceof Error && err.name === \"CancelledError\")) return 130\n if (err instanceof QoreError) return EXIT[err.code]\n return 1\n}\n\nexport function toJsonError(err: unknown): Record<string, unknown> {\n if (!(err instanceof QoreError)) {\n return { code: \"QORE_INTERNAL\", message: err instanceof Error ? err.message : String(err) }\n }\n const out: Record<string, unknown> = { code: err.code, message: err.message }\n for (const k of [\"hint\", \"status\", \"requestId\", \"candidates\", \"serverCode\", \"details\"] as const) {\n if (err[k] !== undefined) out[k] = err[k]\n }\n return out\n}\n","import { Command, CommanderError } from \"commander\"\nimport type { Deps } from \"../core/deps.js\"\nimport { isAbortError } from \"../core/api/http.js\"\nimport { CancelledError, exitCodeFor } from \"../core/errors.js\"\nimport type { Io } from \"./io.js\"\nimport pc from \"picocolors\"\nimport { renderError } from \"./render.js\"\n\n/** The portion of argv before the first bare `--`. Everything from `--` on belongs to\n * a child command (e.g. `qore run -- node --json --no-input`), so no qore-side argv\n * scan — here or in cli.ts — may look past it (ruling R12): a child's own `--json` must\n * not switch qore into JSON mode, and a child's own `--no-input` must not disable\n * prompting. */\nexport function argvBeforeSeparator(argv: string[]): string[] {\n const i = argv.indexOf(\"--\")\n return i === -1 ? argv : argv.slice(0, i)\n}\n\n/** Detects --json before commander has parsed anything, so a parse error (thrown before\n * global opts exist) can still be rendered as JSON, and commander's own stderr line\n * can be suppressed in that mode. See ruling R12. */\nfunction jsonFromArgv(argv: string[]): boolean {\n return argvBeforeSeparator(argv).some((a) => a === \"--json\" || a.startsWith(\"--json=\"))\n}\n\nexport type GlobalOpts = { portal?: string; json?: boolean; input?: boolean; verbose?: boolean; color?: boolean }\n\nexport type CommandContext = { deps: Deps; io: Io; signal: AbortSignal; opts: () => GlobalOpts; setExitCode: (code: number) => void }\n\nexport type Register = (program: Command, ctx: CommandContext) => void\n\n/** `--verbose`: request lines (method, path, status, request id; never a token) on stderr. */\nexport function requestLog(ctx: CommandContext): ((line: string) => void) | undefined {\n return ctx.opts().verbose ? (line) => ctx.io.err(line) : undefined\n}\n\nexport function buildProgram(deps: Deps, io: Io, signal: AbortSignal, register: Register[], setExitCode: (code: number) => void): Command {\n const program = new Command(\"qore\")\n .description(\"Qore developer CLI\")\n .option(\"--portal <name|url>\", \"prod, staging, or a portal URL (default: the portal you last logged in to, else prod)\")\n .option(\"--json\", \"print exactly one JSON document on stdout\")\n .option(\"--no-input\", \"never prompt\")\n .option(\"--verbose\", \"log request lines (never secrets)\")\n .option(\"--no-color\", \"disable colours\")\n .exitOverride()\n .configureOutput({ writeOut: (s) => io.out(s.trimEnd()), writeErr: (s) => io.err(s.trimEnd()) })\n const ctx: CommandContext = { deps, io, signal, opts: () => program.opts<GlobalOpts>(), setExitCode }\n for (const r of register) r(program, ctx)\n return program\n}\n\nexport async function run(argv: string[], deps: Deps, io: Io, signal: AbortSignal, register: Register[]): Promise<number> {\n const json = jsonFromArgv(argv)\n // Commander may throw before global opts exist (e.g. an unknown option), and by default\n // writes its own message to stderr on the way there. In --json mode that would land\n // alongside our single JSON document, so suppress it here and render the error ourselves.\n const parseIo: Io = json ? { ...io, err: () => {} } : io\n const state: { exitCode?: number } = {}\n const program = buildProgram(deps, parseIo, signal, register, (code) => { state.exitCode = code })\n try {\n await program.parseAsync(argv, { from: \"user\" })\n return state.exitCode ?? 0\n } catch (caught) {\n // Once Ctrl+C has fired, any AbortError that escaped a mapping is that cancel.\n const e = signal.aborted && isAbortError(caught) ? new CancelledError() : caught\n if (e instanceof CommanderError) {\n if (e.exitCode === 0) return 0\n if (json) io.out(JSON.stringify({ ok: false, error: { code: \"QORE_CONTEXT_INVALID\", message: e.message } }))\n return 2\n }\n const opts = program.opts<GlobalOpts>()\n renderError(io, e, Boolean(opts.json), pc.isColorSupported && opts.color !== false)\n return exitCodeFor(e)\n }\n}\n","import { CancelledError, QoreError, type QoreErrorCode } from \"../errors.js\"\n\nexport type Fetch = (input: string | URL, init?: RequestInit) => Promise<Response>\n\n/** Every request also carries `signal` (the process's Ctrl+C signal), next to any signal\n * of the caller's own, so a cancel aborts whatever is in flight (spec §4). */\nexport function abortableFetch(fetch: Fetch, signal: AbortSignal): Fetch {\n return (input, init) => fetch(input, { ...init, signal: init?.signal ? AbortSignal.any([init.signal, signal]) : signal })\n}\n\nconst TLS = new Set([\"SELF_SIGNED_CERT_IN_CHAIN\", \"UNABLE_TO_GET_ISSUER_CERT_LOCALLY\",\n \"DEPTH_ZERO_SELF_SIGNED_CERT\", \"UNABLE_TO_VERIFY_LEAF_SIGNATURE\", \"CERT_HAS_EXPIRED\"])\n\nfunction causeCode(e: unknown): string | undefined {\n const c = (e as { cause?: { code?: unknown } })?.cause\n const code = c?.code ?? (e as { code?: unknown })?.code\n // DOMException carries a numeric legacy `code`; only errno-style strings are meaningful here.\n return typeof code === \"string\" ? code : undefined\n}\n\nexport function isAbortError(e: unknown): boolean {\n return (e as { name?: unknown } | null)?.name === \"AbortError\"\n}\n\n/** A failed fetch: a cancel (Ctrl+C aborted the request) or a network failure. */\nexport function fetchError(e: unknown, host: string): Error {\n return isAbortError(e) ? new CancelledError() : networkError(e, host)\n}\n\nexport function networkError(e: unknown, host: string): QoreError {\n const code = causeCode(e) ?? \"\"\n let reason = \"connect\"\n let hint = \"Check your network or VPN.\"\n if (code === \"ENOTFOUND\" || code === \"EAI_AGAIN\") {\n reason = \"dns\"; hint = `${host} could not be resolved. Check your network or VPN.`\n } else if (TLS.has(code)) {\n reason = \"tls\"\n hint = \"A proxy is re-signing TLS. Point NODE_EXTRA_CA_CERTS at your organisation's CA certificate.\"\n } else if (code.includes(\"TIMEOUT\") || code === \"ETIMEDOUT\") {\n reason = \"timeout\"\n } else if (!process.env.HTTPS_PROXY && !process.env.https_proxy) {\n hint = \"Check your network. Behind a corporate proxy, set HTTPS_PROXY.\"\n }\n return new QoreError(\"QORE_API_UNREACHABLE\", `Could not reach ${host}`, { hint, details: { reason, host, errno: code || undefined }, cause: e })\n}\n\nconst BY_SERVER_CODE: Record<string, QoreErrorCode> = {\n \"app.access.denied\": \"QORE_ACCESS_DENIED\",\n \"auth.scope.insufficient\": \"QORE_ACCESS_DENIED\",\n \"cli.upgrade_required\": \"QORE_UPGRADE_REQUIRED\",\n \"rate_limited\": \"QORE_RATE_LIMITED\",\n \"module.not_found\": \"QORE_RESOURCE_NOT_FOUND\",\n \"tenant.not_found\": \"QORE_RESOURCE_NOT_FOUND\",\n \"module.app_ambiguous\": \"QORE_APP_AMBIGUOUS\",\n}\n\nfunction byStatus(status: number): QoreErrorCode {\n if (status === 403) return \"QORE_ACCESS_DENIED\"\n if (status === 404) return \"QORE_RESOURCE_NOT_FOUND\"\n if (status === 426) return \"QORE_UPGRADE_REQUIRED\"\n if (status === 429) return \"QORE_RATE_LIMITED\"\n if (status === 502 || status === 503 || status === 504) return \"QORE_API_UNAVAILABLE\"\n return \"QORE_INTERNAL\"\n}\n\nexport async function problemToError(res: Response): Promise<QoreError> {\n let body: { code?: string; title?: string; detail?: unknown } = {}\n try { body = (await res.json()) as typeof body } catch { /* not JSON */ }\n const serverCode = body.code\n const code = (serverCode && BY_SERVER_CODE[serverCode]) || byStatus(res.status)\n const requestId = res.headers.get(\"x-request-id\") ?? undefined\n const details: Record<string, unknown> = {}\n if (body.detail && typeof body.detail === \"object\") Object.assign(details, body.detail)\n const detail = typeof body.detail === \"string\" && body.detail ? body.detail : undefined\n if (detail) details.detail = detail\n const retry = res.headers.get(\"retry-after\")\n if (retry && /^\\d+$/.test(retry)) details.retryAfter = Number(retry)\n const hint =\n code === \"QORE_UPGRADE_REQUIRED\" ? \"Run: npm i -g @quatronic/qore\"\n : code === \"QORE_RATE_LIMITED\" ? `Wait ${details.retryAfter ?? \"a moment\"} s and retry.`\n : code === \"QORE_API_UNAVAILABLE\" ? \"Qore is temporarily unavailable; retry in a minute.\"\n : code === \"QORE_APP_AMBIGUOUS\" ? \"Pass --app <slug>.\"\n : undefined\n const apps = (body.detail as { apps?: unknown } | undefined)?.apps\n const candidates = code === \"QORE_APP_AMBIGUOUS\" && Array.isArray(apps)\n ? (apps as { id?: string; slug: string; name?: string }[]).map((a) => ({ kind: \"app\" as const, id: a.id, slug: a.slug, name: a.name }))\n : undefined\n if (candidates) delete details.apps\n // portal-api falls back to the title \"HTTP error\"; a server code is no message either.\n // Then the string detail is the most useful message there is.\n const genericTitle = !body.title || body.title === \"HTTP error\" || body.title === serverCode\n const message = (genericTitle && detail) || body.title || `Request failed (${res.status})`\n return new QoreError(code, message, {\n status: res.status, requestId, serverCode, hint, candidates,\n details: Object.keys(details).length ? details : undefined,\n })\n}\n","import pc, { createColors } from \"picocolors\"\nimport { QoreError, toJsonError } from \"../core/errors.js\"\nimport type { Io } from \"./io.js\"\n\nexport function renderJson(io: Io, data: unknown): void {\n io.out(JSON.stringify({ ok: true, data }))\n}\n\nexport function renderError(io: Io, err: unknown, json: boolean, colorEnabled = pc.isColorSupported): void {\n if (json) { io.out(JSON.stringify({ ok: false, error: toJsonError(err) })); return }\n if (err instanceof Error && err.name === \"CancelledError\") { io.err(\"Cancelled\"); return }\n const c = createColors(colorEnabled)\n const e = err instanceof QoreError ? err : new QoreError(\"QORE_INTERNAL\", err instanceof Error ? err.message : String(err))\n io.err(c.red(`Error: ${e.message}`))\n if (e.hint) io.err(e.hint)\n io.err(c.dim(`Code: ${e.code}${e.requestId ? ` (request ${e.requestId})` : \"\"}`))\n}\n","import { randomBytes } from \"node:crypto\"\nimport { chmod, readFile, realpath, rename, unlink, writeFile } from \"node:fs/promises\"\nimport { basename, dirname, join, relative } from \"node:path\"\nimport type { Command } from \"commander\"\nimport { moduleDefaults, readRepoConfig } from \"../../core/context/repoConfig.js\"\nimport { QoreError } from \"../../core/errors.js\"\nimport { fetchLocalEnv } from \"../../core/env/fetch.js\"\nimport { parseEnv } from \"../../core/env/merge.js\"\nimport { planPull, resolveTarget, type PullPlan } from \"../../core/env/pull.js\"\nimport { appFor, contextJson, moduleContextFor } from \"../context.js\"\nimport type { CommandContext } from \"../program.js\"\nimport { renderJson } from \"../render.js\"\nimport { ensureTrusted } from \"../trustPrompt.js\"\n\n/** Ruling T10-I1: spec §11.1 (\"values masked\") plus T8 (\"qore never prints values\")\n * override the brief's SDK maskSecret rule — every value in the conflict prompt is\n * masked, showing only its length, never its content (even for a non-sensitive key). */\nconst maskLen = (v: string | undefined) => (v === undefined ? \"(unset)\" : `•••• (${v.length} chars)`)\n\nasync function readOrNull(p: string): Promise<string | null> {\n try { return await readFile(p, \"utf8\") } catch (e) {\n if ((e as NodeJS.ErrnoException).code === \"ENOENT\") return null\n throw e\n }\n}\n\n/** T10-WRITE + ruling T10-I2/I3: write via a temp file in the target's own directory,\n * created with \"wx\" (never follow a pre-existing path at the temp name) and mode 0600,\n * then rename over the target — never write through a symlink an attacker plants at the\n * target path after `resolveTarget` checked it. Cleaned up in a `finally`, which covers\n * every non-crash failure path (a kill between `writeFile` and `rename` is the one window\n * it cannot cover).\n *\n * The temp name is built to fall under the generated templates' own ignore patterns where\n * possible: next-base ignores `.env*.local`, so a `<name>.local` target gets a temp name\n * of `<name-without-.local>.qore-<hex>.local` (e.g. `.env.qore-ab12.local` for\n * `.env.local`), which still matches that pattern. A plain `.env` target has no such\n * pattern to fall under (node-backend-base ignores the literal `.env`, not `.env*`), so its\n * temp name is just `.env.qore-<hex>.tmp` — untracked-but-not-ignored is the accepted\n * residual risk for that crash window (M2). */\nasync function writeSecurely(target: string, text: string): Promise<void> {\n const base = basename(target)\n const tmpName = base.endsWith(\".local\")\n ? `${base.slice(0, -\".local\".length)}.qore-${randomBytes(6).toString(\"hex\")}.local`\n : `${base}.qore-${randomBytes(6).toString(\"hex\")}.tmp`\n const tmp = join(dirname(target), tmpName)\n try {\n await writeFile(tmp, text, { mode: 0o600, flag: \"wx\" })\n await chmod(tmp, 0o600)\n await rename(tmp, target)\n } finally {\n await unlink(tmp).catch(() => {})\n }\n}\n\ntype Flags = { module?: string; app?: string; target?: string; usePortal?: boolean; yes?: boolean }\n\nexport function registerEnv(program: Command, ctx: CommandContext): void {\n const env = program.command(\"env\").description(\"Local environment\")\n env.command(\"pull\").description(\"Write this module's local secrets into its env file\")\n .option(\"--module <slug|id>\", \"the module (default: from this repository's git remote)\")\n .option(\"--app <slug|id>\", \"the app, when the module is part of several\")\n .option(\"--target <path>\", \"env file to write (inside the repository)\")\n .option(\"--use-portal\", \"take the portal's value for keys that differ locally\")\n .option(\"--yes\", \"trust this repository without asking\")\n .action(async (f: Flags) => {\n const { deps, io } = ctx\n const g = ctx.opts()\n const mc = await moduleContextFor(ctx, f, \"env pull\")\n if (!mc.repoRoot) {\n throw new QoreError(\"QORE_CONTEXT_REQUIRED\", \"env pull writes into a module repository\", { hint: \"cd into the module's repository.\" })\n }\n const app = await appFor(ctx, mc, f.app)\n const cfg = await readRepoConfig(mc.repoRoot)\n const defaults = moduleDefaults(mc.module.type)\n // R11: --target resolves against the cwd; .qore.json's envFile resolves against the\n // repository root. Both must still land inside the repository.\n // Ruling T10-ORDER: target → trust → fetch, so --yes never saves trust for a pull\n // whose target is then rejected.\n const target = f.target\n ? await resolveTarget(mc.repoRoot, f.target, deps.cwd)\n : await resolveTarget(mc.repoRoot, cfg.envFile ?? defaults.envFile)\n await ensureTrusted(ctx, mc, app, { yes: f.yes })\n const existing = await readOrNull(target)\n const example = existing === null ? await readOrNull(join(dirname(target), \".env.example\")) : null\n const local = await fetchLocalEnv(deps, mc, app)\n const inputs = {\n existing, example, fetched: local.env, managed: local.managedKeys,\n localSecrets: cfg.localSecrets ?? defaults.localSecrets,\n defaultChoice: f.usePortal ? \"use-portal\" as const : \"keep\" as const,\n random: () => randomBytes(32).toString(\"hex\"),\n }\n let plan = planPull(inputs)\n if (plan.conflicts.length && io.interactive && !f.usePortal) {\n const current = parseEnv(existing ?? example ?? \"\")\n const choices: Record<string, \"keep\" | \"use-portal\"> = {}\n let bulk: \"keep\" | \"use-portal\" | undefined\n for (const key of plan.conflicts) {\n if (bulk) { choices[key] = bulk; continue }\n const pick = await io.select<\"keep\" | \"portal\" | \"all\" | \"skip\">(\n `${key} differs (local ${maskLen(current.get(key))}, portal ${maskLen(local.env[key])})`,\n [{ name: \"keep local\", value: \"keep\" }, { name: \"use portal\", value: \"portal\" },\n { name: \"use portal for all\", value: \"all\" }, { name: \"keep local for all\", value: \"skip\" }])\n if (pick === \"all\") bulk = \"use-portal\"\n if (pick === \"skip\") bulk = \"keep\"\n choices[key] = pick === \"portal\" || pick === \"all\" ? \"use-portal\" : \"keep\"\n }\n plan = planPull({ ...inputs, choices })\n }\n // M5: when nothing changed, skip the write (and its rename/mtime bump — Next's dev\n // server reloads env on mtime change) and only enforce the 0600 mode.\n if (existing !== null && plan.text === existing) {\n await chmod(target, 0o600)\n } else {\n await writeSecurely(target, plan.text)\n }\n // resolveTarget resolved through realpath (e.g. macOS's /var → /private/var), so the\n // relative path must be computed against the repo root's realpath too.\n const rel = relative(await realpath(mc.repoRoot), target)\n if (g.json) {\n const names: Omit<PullPlan, \"text\"> = {\n created: plan.created, seededFromExample: plan.seededFromExample, added: plan.added,\n updated: plan.updated, kept: plan.kept, replaced: plan.replaced, unchanged: plan.unchanged, generated: plan.generated,\n }\n renderJson(io, { context: contextJson(mc, app), target: rel, ...names })\n return\n }\n if (plan.kept.length && !io.interactive) {\n io.err(`! ${plan.kept.length} key(s) differ locally and were kept: ${plan.kept.join(\", \")} — --use-portal takes the portal's values`)\n }\n const parts = [\n plan.added.length && `${plan.added.length} added`,\n plan.updated.length && `${plan.updated.length} updated (managed)`,\n plan.replaced.length && `${plan.replaced.length} replaced`,\n plan.kept.length && `${plan.kept.length} kept (differs locally; --use-portal to overwrite)`,\n plan.generated.length && `${plan.generated.length} generated`,\n ].filter(Boolean)\n io.out(`✓ ${rel}${plan.seededFromExample ? \" (created from .env.example)\" : \"\"} — ${parts.length ? parts.join(\", \") : \"up to date\"}`)\n })\n}\n","import { readFile } from \"node:fs/promises\"\nimport { join } from \"node:path\"\nimport { QoreError } from \"../errors.js\"\n\nexport type RepoConfig = { envFile?: string; localSecrets?: string[] }\n\n// A field that would pick a resource or a server: refused so a repository cannot\n// steer secrets or tokens (spec §5.2, §10.1 T4/T5). Keep in step with schema/qore.schema.json.\nconst FORBIDDEN = [\"portal\", \"api\", \"apiOrigin\", \"issuer\", \"tenant\", \"tenantId\", \"app\", \"appId\", \"module\", \"moduleId\"]\nconst KEY = /^[A-Za-z_][A-Za-z0-9_]*$/\n\nconst invalid = (msg: string, details?: Record<string, unknown>) =>\n new QoreError(\"QORE_CONTEXT_INVALID\", `.qore.json: ${msg}`, { hint: \"Fix .qore.json in the repository root; see the $schema it names.\", details })\n\nexport function moduleDefaults(type: string): { envFile: string; localSecrets: string[] } {\n return type === \"frontend\"\n ? { envFile: \".env.local\", localSecrets: [\"SESSION_COOKIE_SECRET\"] }\n : { envFile: \".env\", localSecrets: [] }\n}\n\nexport async function readRepoConfig(root: string): Promise<RepoConfig> {\n let raw: string\n try { raw = await readFile(join(root, \".qore.json\"), \"utf8\") } catch (e) {\n if ((e as NodeJS.ErrnoException).code === \"ENOENT\") return {}\n throw e\n }\n let doc: Record<string, unknown>\n try { doc = JSON.parse(raw) as Record<string, unknown> } catch { throw invalid(\"not valid JSON\") }\n if (!doc || typeof doc !== \"object\" || Array.isArray(doc)) throw invalid(\"must be an object\")\n // M9: `??` would also default an explicit `null` to 1, silently accepting a value the\n // schema (`\"type\": \"integer\"`) rejects. Only a genuinely absent key gets the default.\n const v = doc.schemaVersion === undefined ? 1 : doc.schemaVersion\n if (!Number.isInteger(v) || (v as number) < 1) throw invalid(\"schemaVersion must be a positive integer\")\n if ((v as number) > 1) {\n throw new QoreError(\"QORE_CONTEXT_UNSUPPORTED\", `.qore.json schemaVersion ${v} is newer than this qore`, { hint: \"Run: npm i -g @quatronic/qore\" })\n }\n for (const f of FORBIDDEN) if (f in doc) throw invalid(`\"${f}\" is not allowed — .qore.json never selects a portal or a resource`, { field: f })\n const out: RepoConfig = {}\n if (doc.envFile !== undefined) {\n if (typeof doc.envFile !== \"string\" || !doc.envFile) throw invalid(\"envFile must be a non-empty string\")\n out.envFile = doc.envFile\n }\n if (doc.localSecrets !== undefined) {\n if (!Array.isArray(doc.localSecrets) || !doc.localSecrets.every((k) => typeof k === \"string\" && KEY.test(k))) {\n throw invalid(\"localSecrets must be a list of env key names\")\n }\n // M9: the schema declares `uniqueItems`; reject a duplicate rather than silently\n // deduplicating, for consistency with the schemaVersion fix above (reject, don't coerce).\n if (new Set(doc.localSecrets).size !== doc.localSecrets.length) throw invalid(\"localSecrets must not contain duplicates\")\n out.localSecrets = doc.localSecrets as string[]\n }\n return out\n}\n","import { QoreError } from \"../errors.js\"\nimport type { PortalRef } from \"../profiles.js\"\nimport { fetchError, problemToError, type Fetch } from \"./http.js\"\nimport type { CliMeta } from \"./types.js\"\n\nconst SUPPORTED = [\"v1\"] as const\nconst SEMVER = /^(\\d+)\\.(\\d+)\\.(\\d+)(?:-([0-9A-Za-z.-]+))?/\n\nexport function compareVersions(a: string, b: string): number {\n const pa = SEMVER.exec(a), pb = SEMVER.exec(b)\n if (!pa || !pb) return 0\n for (let i = 1; i <= 3; i++) {\n const d = Number(pa[i]) - Number(pb[i])\n if (d !== 0) return d\n }\n if (pa[4] && !pb[4]) return -1\n if (!pa[4] && pb[4]) return 1\n return 0\n}\n\nexport async function fetchMeta(fetch: Fetch, apiOrigin: string): Promise<CliMeta> {\n let res: Response\n try { res = await fetch(`${apiOrigin}/api/cli/meta`, { headers: { accept: \"application/json\" } }) }\n catch (e) { throw fetchError(e, new URL(apiOrigin).host) }\n if (res.status === 404) {\n // No CLI surface at all: a portal-api from before the CLI (or the wrong URL).\n throw new QoreError(\"QORE_INCOMPATIBLE_SERVER\", \"This portal does not support the Qore CLI yet\", {\n status: 404, requestId: res.headers.get(\"x-request-id\") ?? undefined,\n hint: `Check the portal URL (${apiOrigin}); if it is right, the portal must be upgraded before qore can use it.`,\n })\n }\n if (!res.ok) throw await problemToError(res)\n return (await res.json()) as CliMeta\n}\n\nexport function negotiate(meta: CliMeta, portal: PortalRef, cliVersion: string): { apiVersion: \"v1\" } {\n if (portal.pinnedIssuer && meta.auth.issuer !== portal.pinnedIssuer) {\n throw new QoreError(\"QORE_PORTAL_UNTRUSTED\", `${portal.apiOrigin} names an unexpected identity provider`, {\n details: { expected: portal.pinnedIssuer, got: meta.auth.issuer },\n hint: \"Refusing to log in. Check the portal URL and your network.\",\n })\n }\n const apiVersion = SUPPORTED.find((v) => meta.apiVersions.includes(v))\n if (!apiVersion) {\n throw new QoreError(\"QORE_INCOMPATIBLE_SERVER\", \"This portal speaks no API version this qore knows\", {\n details: { server: meta.apiVersions, client: [...SUPPORTED] }, hint: \"Run: npm i -g @quatronic/qore\",\n })\n }\n if (!cliVersion.endsWith(\"-dev\") && compareVersions(cliVersion, meta.minCliVersion) < 0) {\n throw new QoreError(\"QORE_UPGRADE_REQUIRED\", `qore ${cliVersion} is too old for this portal (needs ${meta.minCliVersion})`, {\n hint: \"Run: npm i -g @quatronic/qore\",\n })\n }\n return { apiVersion }\n}\n","import type { Deps } from \"../deps.js\"\nimport { QoreError } from \"../errors.js\"\nimport { fetchMeta } from \"./meta.js\"\nimport type { CliMeta } from \"./types.js\"\n\nconst TTL_MS = 3600_000\n\nfunction isMeta(doc: unknown): doc is CliMeta {\n return !!doc && typeof doc === \"object\" && Array.isArray((doc as CliMeta).capabilities)\n}\n\nasync function loadMeta(deps: Deps, apiOrigin: string, refresh: boolean): Promise<{ meta: CliMeta; cached: boolean }> {\n const cached = (await deps.config.read()).profiles[apiOrigin]?.meta\n if (!refresh && cached && isMeta(cached.doc) && deps.now().getTime() - new Date(cached.fetchedAt).getTime() < TTL_MS) {\n return { meta: cached.doc, cached: true }\n }\n const meta = await fetchMeta(deps.fetch, apiOrigin)\n await deps.config.update((c) => {\n const p = c.profiles[apiOrigin]\n if (p) p.meta = { fetchedAt: deps.now().toISOString(), doc: meta }\n })\n return { meta, cached: false }\n}\n\n/** Meta per profile, cached 1 h in the profile (spec §9.1). The issuer was pinned at\n * login; a refresh here only updates capabilities and versions. */\nexport async function metaFor(deps: Deps, apiOrigin: string): Promise<CliMeta> {\n return (await loadMeta(deps, apiOrigin, false)).meta\n}\n\n/** `requireCapability` against the profile's meta. A miss on *cached* meta refetches once\n * before failing: the cache may predate a portal upgrade, and \"try again once it has been\n * updated\" is wrong advice for an hour after it has been. */\nexport async function ensureCapability(deps: Deps, apiOrigin: string, capability: string): Promise<CliMeta> {\n const first = await loadMeta(deps, apiOrigin, false)\n let meta = first.meta\n if (!meta.capabilities.includes(capability) && first.cached) meta = (await loadMeta(deps, apiOrigin, true)).meta\n requireCapability(meta, capability, apiOrigin)\n return meta\n}\n\nexport function requireCapability(meta: CliMeta, capability: string, apiOrigin: string): void {\n if (meta.capabilities.includes(capability)) return\n throw new QoreError(\"QORE_UNSUPPORTED_BY_SERVER\", `This portal does not support ${capability} yet`, {\n hint: `The portal at ${apiOrigin} is older than this qore. Try again once it has been updated.`,\n details: { capability, portal: apiOrigin },\n })\n}\n","import { join } from \"node:path\"\nimport { ensureCapability } from \"../api/capabilities.js\"\nimport { TokenStore } from \"../auth/tokenStore.js\"\nimport type { CliMe, CliModuleDetail, CliRef, CliRepoResolve } from \"../api/types.js\"\nimport type { QoreConfig } from \"../config.js\"\nimport type { Deps } from \"../deps.js\"\nimport { CancelledError, QoreError, type Candidate, type QoreErrorCode } from \"../errors.js\"\nimport { BUILTIN_PORTALS, profileHash, resolvePortal, type PortalRef } from \"../profiles.js\"\nimport { openSession, type Session } from \"../session.js\"\nimport type { Remote } from \"../../platform/git.js\"\nimport { ResolutionCache } from \"./cache.js\"\nimport { repoKey } from \"./repoKey.js\"\nimport { findRepoRoot } from \"./repoRoot.js\"\n\nexport type ContextSource =\n | { kind: \"remote\"; remote: string; url: string }\n | { kind: \"flag\"; overrides?: string } // overrides = the remote whose derived module differs from --module\nexport type ModuleContext = { portal: PortalRef; session: Session; module: CliModuleDetail; source: ContextSource; repoRoot: string | null }\ntype Keyed = Remote & { key: string }\ntype Opts = {\n portal?: string\n module?: string\n choose?: string // module id picked from QORE_CONTEXT_REQUIRED's module candidates\n tenant?: string // tenant id picked from QORE_CONTEXT_REQUIRED's tenant candidates (--module <slug>)\n command: string\n onRequest?: (l: string) => void\n}\ntype Skipped = { profile: string; code: QoreErrorCode; message: string }\n\nconst UUID = /^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i\nconst HINT_FLAG = \"cd into a module repository, or pass --module <slug|id>.\"\nconst RESOLVE = \"/api/cli/v1/repos/resolve\"\n\n/** Errors that make one profile unusable for this walk without saying anything about the\n * repository: the portal is unreachable, or the profile has no usable token (spec §3, §14.2). */\nconst SKIPPABLE = new Set<QoreErrorCode>([\n \"QORE_API_UNREACHABLE\", \"QORE_API_UNAVAILABLE\", \"QORE_AUTH_UNAVAILABLE\",\n \"QORE_NOT_LOGGED_IN\", \"QORE_SESSION_EXPIRED\",\n])\n\nconst label = (p: PortalRef) => p.builtin ?? p.apiOrigin\n\n/** origin first, then upstream, then the rest in git order. */\nfunction byPreference(remotes: Keyed[]): Keyed[] {\n const rank = (r: Keyed) => (r.name === \"origin\" ? 0 : r.name === \"upstream\" ? 1 : 2)\n return [...remotes].sort((a, b) => rank(a) - rank(b)) // stable: git order within a rank\n}\nconst preferred = (remotes: Keyed[]): Keyed => byPreference(remotes)[0]!\n\n/** null outside a repository. A failing `git remote` (a broken or half-initialised\n * repository) counts as \"no remotes\" so it ends in QORE_CONTEXT_REQUIRED rather than\n * QORE_INTERNAL; git missing from PATH stays QORE_GIT_UNAVAILABLE. */\nasync function repoRemotes(deps: Deps): Promise<{ root: string; keyed: Keyed[]; gitError?: QoreError } | null> {\n const root = await findRepoRoot(deps.cwd)\n if (!root) return null\n let remotes: Remote[]\n try {\n remotes = await deps.git.remotes(root)\n } catch (e) {\n if (e instanceof QoreError && e.code !== \"QORE_GIT_UNAVAILABLE\") return { root, keyed: [], gitError: e }\n throw e\n }\n const keyed = remotes.map((r) => ({ ...r, key: repoKey(r.url) })).filter((r): r is Keyed => r.key !== null)\n return { root, keyed }\n}\n\nfunction detail(session: Session, id: string): Promise<CliModuleDetail> {\n return session.api.get<CliModuleDetail>(`/api/cli/v1/modules/${encodeURIComponent(id)}`)\n}\n\n/** Spec §5.3: with --module inside a repository, the remote's own module is derived too\n * (cache first, else one repos/resolve on the same profile) so the context line can say\n * \"--module, overrides <remote>\". Best effort: any failure means \"nothing derived\". */\nasync function flagOverrides(deps: Deps, session: Session, portal: PortalRef, cache: ResolutionCache, moduleId: string) {\n try {\n const keyed = (await repoRemotes(deps))?.keyed ?? []\n const derived = new Map<string, Set<string>>()\n const uncached: string[] = []\n for (const key of new Set(keyed.map((r) => r.key))) {\n const id = await cache.get(portal.apiOrigin, key)\n if (id) derived.set(key, new Set([id]))\n else uncached.push(key)\n }\n if (uncached.length > 0) {\n try {\n const { matches } = await session.api.post<CliRepoResolve>(RESOLVE, { repoKeys: uncached })\n for (const m of matches) derived.set(m.repoKey, (derived.get(m.repoKey) ?? new Set()).add(m.module.id))\n const ids = new Set(matches.map((m) => m.module.id))\n if (ids.size === 1) for (const m of matches) await cache.put(portal.apiOrigin, m.repoKey, m.module.id)\n } catch (e) { if (e instanceof CancelledError) throw e /* else best effort */ }\n }\n return byPreference(keyed).find((r) => [...(derived.get(r.key) ?? [])].some((id) => id !== moduleId))?.name\n } catch (e) {\n if (e instanceof CancelledError) throw e // Ctrl+C is never \"best effort\"\n return undefined\n }\n}\n\nasync function byFlag(deps: Deps, o: Opts, cache: ResolutionCache): Promise<ModuleContext> {\n const cfg = await deps.config.read()\n const portal = resolvePortal(o.portal, cfg.defaultProfile)\n const session = await openSession(deps, portal, o.command, o.onRequest)\n await ensureCapability(deps, portal.apiOrigin, \"repo.resolve\")\n let id = o.module!\n if (!UUID.test(id)) {\n let tenantId = o.tenant ?? session.profile.activeTenant?.id\n if (!tenantId) {\n const me = await session.api.get<CliMe>(\"/api/cli/v1/me\")\n // /me lists only developer (non end_user) memberships.\n if (me.tenants.length === 0) {\n throw new QoreError(\"QORE_NO_DEVELOPER_ACCESS\", \"Your account is not a developer in any organisation\", {\n hint: \"Ask an admin to invite you as a developer.\",\n })\n }\n if (me.tenants.length > 1) {\n const candidates: Candidate[] = me.tenants.map((t) => ({ kind: \"tenant\", id: t.id, slug: t.slug, name: t.name }))\n throw new QoreError(\"QORE_CONTEXT_REQUIRED\", `Which tenant is \"${id}\" in?`, {\n hint: \"Run `qore tenant use <slug>`, or pass the module id.\", candidates,\n })\n }\n tenantId = me.tenants[0]!.id\n }\n id = (await session.api.get<{ id: string }>(\n `/api/cli/v1/tenants/${encodeURIComponent(tenantId)}/modules/resolve?slug=${encodeURIComponent(id)}`)).id\n }\n const module = await detail(session, id)\n const overrides = await flagOverrides(deps, session, portal, cache, module.id)\n const repoRoot = await findRepoRoot(deps.cwd)\n return { portal, session, module, source: overrides ? { kind: \"flag\", overrides } : { kind: \"flag\" }, repoRoot }\n}\n\nfunction profileOrder(cfg: QoreConfig, cachedOrigins: string[], portalArg?: string): PortalRef[] {\n if (portalArg) return [resolvePortal(portalArg, cfg.defaultProfile)]\n const rank = (o: string) => (o === BUILTIN_PORTALS.prod.apiOrigin ? 0 : o === BUILTIN_PORTALS.staging.apiOrigin ? 1 : 2)\n const rest = Object.keys(cfg.profiles).sort((a, b) => rank(a) - rank(b) || a.localeCompare(b))\n // Cached origins are filtered to known profiles *before* parsing: a garbage origin in the\n // cache file must not become QORE_CONTEXT_INVALID (a malformed cache is an empty cache).\n const cached = cachedOrigins.filter((c) => cfg.profiles[c])\n const origins = [...cached, resolvePortal(undefined, cfg.defaultProfile).apiOrigin, ...rest]\n return [...new Set(origins)].filter((c) => cfg.profiles[c]).map((c) => resolvePortal(c, undefined))\n}\n\n/** Merge extra `details` onto a QoreError, keeping its other fields (status, requestId,\n * candidates, serverCode) and chaining the original as `cause`. An explicit `hint`\n * replaces the original's; omitted, the original's hint carries over. Shared with\n * `core/env/fetch.ts` so both callers wrap an upstream error the same way. */\nexport function withDetails(e: QoreError, extra: Record<string, unknown>, hint?: string): QoreError {\n return new QoreError(e.code, e.message, {\n hint: hint ?? e.hint, status: e.status, requestId: e.requestId, candidates: e.candidates, serverCode: e.serverCode,\n details: { ...e.details, ...extra }, cause: e,\n })\n}\n\n/** One profile of the walk: the module, null for \"no match here\", or a throw. */\nasync function onProfile(deps: Deps, o: Opts, cache: ResolutionCache, portal: PortalRef, keyed: Keyed[], keys: string[],\n repoRoot: string, unsupported: (e: QoreError) => void): Promise<ModuleContext | null> {\n const session = await openSession(deps, portal, o.command, o.onRequest)\n try {\n await ensureCapability(deps, portal.apiOrigin, \"repo.resolve\")\n } catch (e) {\n // A transport failure is a skippable profile (rethrown to the walk), not \"unsupported\".\n if (!(e instanceof QoreError) || e.code !== \"QORE_UNSUPPORTED_BY_SERVER\") throw e\n unsupported(e)\n return null\n }\n\n // The cache may answer only when it cannot contradict spec §5.2: every keyed remote is\n // cached to one and the same module, or not cached at all. Remotes cached to different\n // modules go to repos/resolve, which decides (and asks when several match).\n const hits: { remote: Keyed; id: string }[] = []\n for (const r of byPreference(keyed)) {\n const id = await cache.get(portal.apiOrigin, r.key)\n if (id) hits.push({ remote: r, id })\n }\n if (hits.length > 0 && hits.every((h) => h.id === hits[0]!.id)) {\n const { remote: r, id } = hits[0]!\n try {\n return { portal, session, module: await detail(session, id), source: { kind: \"remote\", remote: r.name, url: r.url }, repoRoot }\n } catch (e) {\n if (!(e instanceof QoreError) || e.code !== \"QORE_RESOURCE_NOT_FOUND\") throw e\n for (const h of hits) await cache.drop(portal.apiOrigin, h.remote.key)\n }\n }\n\n const { matches } = await session.api.post<CliRepoResolve>(RESOLVE, { repoKeys: keys })\n const ids = [...new Set(matches.map((m) => m.module.id))]\n if (ids.length === 0) return null\n let id = ids[0]!\n if (ids.length > 1) {\n if (o.choose && ids.includes(o.choose)) id = o.choose\n else {\n const candidates: Candidate[] = ids.map((mid) => {\n const own = matches.filter((m) => m.module.id === mid)\n const m = own[0]!\n const remote = preferred(keyed.filter((r) => own.some((x) => x.repoKey === r.key))).name\n return { kind: \"module\", id: m.module.id, slug: m.module.slug, name: m.module.name, remote, tenant: m.tenant.slug }\n })\n throw new QoreError(\"QORE_CONTEXT_REQUIRED\", \"This repository's remotes match several modules\", {\n hint: \"Pass --module <slug|id>.\", candidates,\n })\n }\n }\n const matchedKeys = new Set(matches.filter((m) => m.module.id === id).map((m) => m.repoKey))\n // Only an unambiguous match is cached (spec §5.2): a pick among several must be asked again.\n if (ids.length === 1) for (const k of matchedKeys) await cache.put(portal.apiOrigin, k, id)\n const remote = preferred(keyed.filter((r) => matchedKeys.has(r.key)))\n return { portal, session, module: await detail(session, id), source: { kind: \"remote\", remote: remote.name, url: remote.url }, repoRoot }\n}\n\nasync function anyLoggedIn(deps: Deps, cfg: QoreConfig): Promise<boolean> {\n for (const p of Object.values(cfg.profiles)) {\n if (await new TokenStore(deps.keychain, profileHash(p.apiOrigin, p.issuer)).getRefresh()) return true\n }\n return false\n}\n\nexport async function resolveModuleContext(deps: Deps, o: Opts): Promise<ModuleContext> {\n const cache = new ResolutionCache(join(deps.config.dir, \"cache\"), deps.now)\n if (o.module) return byFlag(deps, o, cache)\n\n // Login before repository: a logged-out user cannot pass --module either, so\n // \"log in\" is the more useful first answer (pinned by the E2E test in Task 13).\n const cfg = await deps.config.read()\n const first = resolvePortal(o.portal, cfg.defaultProfile)\n // Based on tokens, not rows: `qore logout` clears the keychain but keeps the profile row.\n if (o.portal || !(await anyLoggedIn(deps, cfg))) {\n await openSession(deps, first, o.command) // throws QORE_NOT_LOGGED_IN with the right hint\n }\n\n const repo = await repoRemotes(deps)\n if (repo === null) throw new QoreError(\"QORE_CONTEXT_REQUIRED\", \"Not inside a module repository\", { hint: HINT_FLAG })\n const { root, keyed, gitError } = repo\n if (keyed.length === 0) {\n // git's own last stderr line (e.g. \"detected dubious ownership\") says why there are\n // no remotes; without it the message would claim the opposite of the truth (§14.1).\n const said = gitError?.hint\n throw new QoreError(\"QORE_CONTEXT_REQUIRED\", \"This repository has no remote Qore can match\", {\n hint: said ? `${HINT_FLAG} git said: ${said}` : HINT_FLAG,\n details: gitError ? { git: said ?? gitError.message } : undefined,\n cause: gitError,\n })\n }\n const keys = [...new Set(keyed.map((r) => r.key))]\n\n const tried: string[] = [] // every profile walked, in order\n const answered: string[] = [] // profiles whose repos/resolve answered \"no match\"\n const skipped: Skipped[] = []\n const skipErrors: QoreError[] = []\n let unsupported: QoreError | undefined\n for (const portal of profileOrder(cfg, await cache.originsFor(keys), o.portal)) {\n tried.push(label(portal))\n let capabilityMissing = false\n try {\n const mc = await onProfile(deps, o, cache, portal, keyed, keys, root, (e) => {\n capabilityMissing = true\n unsupported ??= e\n skipped.push({ profile: label(portal), code: e.code, message: e.message })\n })\n if (mc) return mc\n if (!capabilityMissing) answered.push(label(portal))\n } catch (e) {\n if (!(e instanceof QoreError) || !SKIPPABLE.has(e.code)) throw e\n skipped.push({ profile: label(portal), code: e.code, message: e.message })\n skipErrors.push(e)\n }\n }\n\n const details: Record<string, unknown> = { triedProfiles: tried }\n if (skipped.length > 0) details.skippedProfiles = skipped\n if (answered.length === 0) {\n // No profile could say anything about this repository: its own failure is the answer\n // (unreachable → QORE_API_UNREACHABLE, no token → QORE_NOT_LOGGED_IN, too old →\n // QORE_UNSUPPORTED_BY_SERVER), not \"no module selected\".\n const cause = skipErrors[0] ?? unsupported\n if (cause) throw withDetails(cause, details)\n }\n const unchecked = skipped.length ? ` ${skipped.map((s) => s.profile).join(\", \")} could not be checked (${skipped.map((s) => s.code).join(\", \")}).` : \"\"\n // A staging row without a usable token needs the same remedy as no staging row at all.\n const stagingLoggedIn = Boolean(cfg.profiles[BUILTIN_PORTALS.staging.apiOrigin])\n && !skipped.some((s) => s.profile === \"staging\" && (s.code === \"QORE_NOT_LOGGED_IN\" || s.code === \"QORE_SESSION_EXPIRED\"))\n throw new QoreError(\"QORE_CONTEXT_REQUIRED\", \"No module selected\", {\n hint: `This repository's remotes match no module you can access on ${answered.join(\", \")}; pass --module <slug|id>.`\n + unchecked\n + (stagingLoggedIn ? \"\" : \" If it is a staging repository, run `qore login --portal staging`.\"),\n details,\n })\n}\n\nconst appCandidates = (apps: CliRef[]): Candidate[] => apps.map((a) => ({ kind: \"app\", id: a.id, slug: a.slug, name: a.name }))\n\nexport function pickApp(mc: Pick<ModuleContext, \"module\">, app?: string): CliRef {\n const apps = mc.module.apps\n if (app) {\n const found = apps.find((a) => a.id === app || a.slug === app)\n if (!found) {\n throw new QoreError(\"QORE_RESOURCE_NOT_FOUND\", `${mc.module.slug} is not part of an app \"${app}\" you can read`, {\n candidates: appCandidates(apps),\n })\n }\n return found\n }\n if (apps.length === 1) return apps[0]!\n if (apps.length === 0) throw new QoreError(\"QORE_RESOURCE_NOT_FOUND\", `${mc.module.slug} is not part of an app you can read`)\n throw new QoreError(\"QORE_APP_AMBIGUOUS\", `${mc.module.slug} is part of several apps`, { hint: \"Pass --app <slug>.\", candidates: appCandidates(apps) })\n}\n","import type { Keychain } from \"../../platform/keychain.js\"\n\nexport type StoredRefresh = { rt: string; sub: string; scope: string; obtainedAt: string }\nexport type StoredAccess = { at: string; expiresAt: string }\n\nexport class TokenStore {\n constructor(private readonly kc: Keychain, private readonly hash: string) {}\n\n private async read<T>(suffix: string): Promise<T | null> {\n const raw = await this.kc.get(`${this.hash}:${suffix}`)\n if (raw === null) return null\n try { return JSON.parse(raw) as T } catch { return null }\n }\n\n getRefresh() { return this.read<StoredRefresh>(\"refresh\") }\n getAccess() { return this.read<StoredAccess>(\"access\") }\n setRefresh(v: StoredRefresh) { return this.kc.set(`${this.hash}:refresh`, JSON.stringify(v)) }\n setAccess(v: StoredAccess) { return this.kc.set(`${this.hash}:access`, JSON.stringify(v)) }\n async clear() {\n await this.kc.delete(`${this.hash}:access`)\n await this.kc.delete(`${this.hash}:refresh`)\n }\n}\n","import { createHash } from \"node:crypto\"\nimport { QoreError } from \"./errors.js\"\n\nexport type PortalRef = { apiOrigin: string; pinnedIssuer: string | null; builtin: \"prod\" | \"staging\" | null }\n\nexport const BUILTIN_PORTALS = {\n prod: {\n apiOrigin: \"https://api.quatronic.app\",\n pinnedIssuer: \"https://auth.quatronic.app/realms/platform-prod\",\n },\n staging: {\n apiOrigin: \"https://p01--portal-api-staging--hcywmtb2vksv.code.run\",\n pinnedIssuer: \"https://auth-staging.quatronic.app/realms/platform-staging\",\n },\n} as const satisfies Record<string, { apiOrigin: string; pinnedIssuer: string | null }>\n\nfunction builtinFor(origin: string): PortalRef | null {\n for (const [name, p] of Object.entries(BUILTIN_PORTALS)) {\n if (p.apiOrigin === origin) return { ...p, builtin: name as \"prod\" | \"staging\" }\n }\n return null\n}\n\nfunction toOrigin(raw: string): string {\n let url: URL\n try { url = new URL(raw) } catch {\n throw new QoreError(\"QORE_CONTEXT_INVALID\", `Not a portal name or URL: ${raw}`, {\n hint: \"Use --portal prod, --portal staging or --portal https://…\",\n })\n }\n const loopback = url.hostname === \"localhost\" || url.hostname === \"127.0.0.1\"\n if (url.protocol !== \"https:\" && !(url.protocol === \"http:\" && loopback)) {\n throw new QoreError(\"QORE_CONTEXT_INVALID\", \"A portal URL must use https (http only for localhost)\")\n }\n return url.origin.toLowerCase()\n}\n\nexport function resolvePortal(arg: string | undefined, defaultProfile: string | undefined): PortalRef {\n const chosen = arg ?? defaultProfile\n if (chosen === undefined || chosen === \"prod\") return { ...BUILTIN_PORTALS.prod, builtin: \"prod\" }\n if (chosen === \"staging\") return { ...BUILTIN_PORTALS.staging, builtin: \"staging\" }\n const origin = toOrigin(chosen)\n return builtinFor(origin) ?? { apiOrigin: origin, pinnedIssuer: null, builtin: null }\n}\n\nexport function profileHash(apiOrigin: string, issuer: string): string {\n return createHash(\"sha256\").update(`${apiOrigin}|${issuer}`).digest(\"hex\").slice(0, 16)\n}\n","import { QoreError } from \"../errors.js\"\nimport { fetchError, problemToError, type Fetch } from \"./http.js\"\n\nexport class QoreApiClient {\n constructor(private readonly o: {\n apiOrigin: string; fetch: Fetch; token: (force: boolean) => Promise<string>\n cliVersion: string; command: string; platform: string; onRequest?: (line: string) => void\n }) {}\n\n private async once(method: \"GET\" | \"POST\", path: string, body: unknown, force: boolean): Promise<Response> {\n const token = await this.o.token(force)\n const headers: Record<string, string> = {\n authorization: `Bearer ${token}`,\n accept: \"application/json\",\n \"qore-cli-version\": this.o.cliVersion,\n \"qore-command\": this.o.command,\n \"user-agent\": `qore/${this.o.cliVersion} (${this.o.platform})`,\n }\n if (body !== undefined) headers[\"content-type\"] = \"application/json\"\n let res: Response\n try {\n res = await this.o.fetch(`${this.o.apiOrigin}${path}`, {\n method, headers, body: body === undefined ? undefined : JSON.stringify(body),\n })\n } catch (e) { throw fetchError(e, new URL(this.o.apiOrigin).host) }\n const rid = res.headers.get(\"x-request-id\")\n this.o.onRequest?.(`${method} ${path} → ${res.status}${rid ? ` (${rid})` : \"\"}`)\n return res\n }\n\n private async request<T>(method: \"GET\" | \"POST\", path: string, body?: unknown): Promise<T> {\n let res = await this.once(method, path, body, false)\n if (res.status === 401) {\n res = await this.once(method, path, body, true)\n if (res.status === 401) {\n throw new QoreError(\"QORE_SESSION_EXPIRED\", \"The portal no longer accepts your session\", {\n hint: \"Run `qore login`.\", status: 401, requestId: res.headers.get(\"x-request-id\") ?? undefined,\n })\n }\n }\n if (!res.ok) throw await problemToError(res)\n return (await res.json()) as T\n }\n\n get<T>(path: string): Promise<T> { return this.request<T>(\"GET\", path) }\n post<T>(path: string, body: unknown): Promise<T> { return this.request<T>(\"POST\", path, body) }\n}\n","import { QoreError } from \"../errors.js\"\nimport type { WithLock } from \"../../platform/lock.js\"\nimport type { Oidc, TokenSet } from \"./oidc.js\"\nimport type { TokenStore } from \"./tokenStore.js\"\n\nconst SKEW_MS = 60_000\n\nexport class RefreshCoordinator {\n constructor(private readonly o: {\n store: TokenStore; oidc: () => Promise<Oidc>; withLock: WithLock; lockName: string; now: () => Date\n }) {}\n\n private fresh(expiresAt: string): boolean {\n return new Date(expiresAt).getTime() - this.o.now().getTime() > SKEW_MS\n }\n\n private async rotate(scope?: string): Promise<TokenSet> {\n let stored = await this.o.store.getRefresh()\n if (!stored) throw new QoreError(\"QORE_NOT_LOGGED_IN\", \"Not logged in\", { hint: \"Run `qore login`.\" })\n let t: TokenSet\n for (let attempt = 0; ; attempt++) {\n try {\n t = await (await this.o.oidc()).refresh(stored.rt, scope)\n break\n } catch (e) {\n if (!(e instanceof QoreError && e.code === \"QORE_SESSION_EXPIRED\")) throw e\n // Only the RT we presented was rejected. Another process may have rotated it\n // meanwhile (a stolen stale lock, a second config dir, a lost response): then the\n // stored RT is newer, so retry once with it instead of logging the user out.\n const now = await this.o.store.getRefresh()\n if (now && now.rt !== stored.rt) {\n if (attempt === 0) { stored = now; continue }\n throw e\n }\n await this.o.store.clear()\n throw e\n }\n }\n // Store the scope the token response reports: after a downscoped refresh the rotated RT\n // may carry only the narrowed scope, so never record the old full scope for it. An empty\n // response scope means \"as requested\" (RFC 6749 §5.1).\n await this.o.store.setRefresh({ rt: t.refreshToken, sub: t.sub, scope: t.scope || (scope ?? stored.scope), obtainedAt: this.o.now().toISOString() })\n return t\n }\n\n async accessToken(opts: { force?: boolean } = {}): Promise<string> {\n const seen = await this.o.store.getAccess()\n if (!opts.force && seen && this.fresh(seen.expiresAt)) return seen.at\n return this.o.withLock(this.o.lockName, async () => {\n const again = await this.o.store.getAccess()\n if (again && again.at !== seen?.at && this.fresh(again.expiresAt)) return again.at\n const t = await this.rotate()\n await this.o.store.setAccess({ at: t.accessToken, expiresAt: new Date(this.o.now().getTime() + t.expiresIn * 1000).toISOString() })\n return t.accessToken\n })\n }\n\n /** A token carrying only `scopes`, held in memory by the caller (qore mcp). */\n async downscoped(scopes: string[]): Promise<string> {\n return this.o.withLock(this.o.lockName, async () => (await this.rotate(scopes.join(\" \"))).accessToken)\n }\n}\n","import { QoreApiClient } from \"./api/client.js\"\nimport { RefreshCoordinator } from \"./auth/refresh.js\"\nimport { TokenStore } from \"./auth/tokenStore.js\"\nimport type { ProfileRecord } from \"./config.js\"\nimport type { Deps } from \"./deps.js\"\nimport { QoreError } from \"./errors.js\"\nimport { profileHash, type PortalRef } from \"./profiles.js\"\n\nexport function loginHint(portal: PortalRef): string {\n return portal.builtin === \"prod\" ? \"Run `qore login`.\" : `Run \\`qore login --portal ${portal.builtin ?? portal.apiOrigin}\\`.`\n}\n\nexport async function openSession(deps: Deps, portal: PortalRef, command: string, onRequest?: (l: string) => void) {\n const profile: ProfileRecord | undefined = (await deps.config.read()).profiles[portal.apiOrigin]\n if (!profile) throw new QoreError(\"QORE_NOT_LOGGED_IN\", `Not logged in to ${portal.apiOrigin}`, { hint: loginHint(portal) })\n const hash = profileHash(profile.apiOrigin, profile.issuer)\n const tokens = new TokenStore(deps.keychain, hash)\n if (!(await tokens.getRefresh())) throw new QoreError(\"QORE_NOT_LOGGED_IN\", `Not logged in to ${portal.apiOrigin}`, { hint: loginHint(portal) })\n const refresh = new RefreshCoordinator({ store: tokens, oidc: () => deps.oidcFor(profile.issuer), withLock: deps.withLock, lockName: hash, now: deps.now })\n const api = new QoreApiClient({\n apiOrigin: profile.apiOrigin, fetch: deps.fetch, token: (force) => refresh.accessToken({ force }),\n cliVersion: deps.version, command, platform: `${deps.platform} ${process.arch}; node ${process.versions.node}`, onRequest,\n })\n return { profile, api, tokens, refresh }\n}\n\nexport type Session = Awaited<ReturnType<typeof openSession>>\n","import { join } from \"node:path\"\nimport { readJson, writeJsonAtomic } from \"../jsonFile.js\"\n\ntype Entry = { moduleId: string; resolvedAt: string }\ntype CacheFile = { schemaVersion: 1; entries: Record<string, Entry> }\nconst TTL_MS = 24 * 3600_000\n\n/** Speed and offline display only — every command still sends the moduleId to the\n * server, which authorizes it afresh (spec §5.2). */\nexport class ResolutionCache {\n constructor(private readonly dir: string, private readonly now: () => Date) {}\n\n private async load(): Promise<CacheFile> {\n try {\n const f = await readJson<CacheFile>(join(this.dir, \"repos.json\"))\n if (f && f.schemaVersion === 1 && typeof f.entries === \"object\" && f.entries) return f\n } catch { /* a malformed cache is an empty cache */ }\n return { schemaVersion: 1, entries: {} }\n }\n\n private fresh(e: Entry | undefined): e is Entry {\n return !!e && this.now().getTime() - new Date(e.resolvedAt).getTime() < TTL_MS\n }\n\n async get(origin: string, key: string): Promise<string | null> {\n const e = (await this.load()).entries[`${origin}|${key}`]\n return this.fresh(e) ? e.moduleId : null\n }\n\n /** Never throws: a read-only config dir, a full disk or a Windows EPERM on rename\n * (another qore holding the file) must not fail a command that already resolved. */\n async put(origin: string, key: string, moduleId: string): Promise<void> {\n const f = await this.load()\n f.entries[`${origin}|${key}`] = { moduleId, resolvedAt: this.now().toISOString() }\n for (const [k, e] of Object.entries(f.entries)) if (!this.fresh(e)) delete f.entries[k]\n await this.save(f)\n }\n\n /** Never throws, like `put`. */\n async drop(origin: string, key: string): Promise<void> {\n const f = await this.load()\n if (!(`${origin}|${key}` in f.entries)) return\n delete f.entries[`${origin}|${key}`]\n await this.save(f)\n }\n\n private async save(f: CacheFile): Promise<void> {\n try { await writeJsonAtomic(this.dir, \"repos.json\", f) } catch { /* cache only */ }\n }\n\n async originsFor(keys: string[]): Promise<string[]> {\n const f = await this.load()\n const hits: { origin: string; at: number }[] = []\n for (const [k, e] of Object.entries(f.entries)) {\n const sep = k.lastIndexOf(\"|\")\n if (keys.includes(k.slice(sep + 1)) && this.fresh(e)) hits.push({ origin: k.slice(0, sep), at: new Date(e.resolvedAt).getTime() })\n }\n hits.sort((a, b) => b.at - a.at)\n return [...new Set(hits.map((h) => h.origin))]\n }\n}\n","import { chmod, mkdir, readFile, rename, writeFile } from \"node:fs/promises\"\nimport { join } from \"node:path\"\nimport { randomBytes } from \"node:crypto\"\n\nexport async function readJson<T>(file: string): Promise<T | null> {\n let raw: string\n try { raw = await readFile(file, \"utf8\") } catch (e) {\n if ((e as NodeJS.ErrnoException).code === \"ENOENT\") return null\n throw e\n }\n return JSON.parse(raw) as T\n}\n\nexport async function writeJsonAtomic(dir: string, name: string, data: unknown): Promise<void> {\n await mkdir(dir, { recursive: true, mode: 0o700 })\n const tmp = join(dir, `.${name}.${randomBytes(6).toString(\"hex\")}.tmp`)\n await writeFile(tmp, JSON.stringify(data, null, 2) + \"\\n\", { mode: 0o600 })\n await chmod(tmp, 0o600)\n await rename(tmp, join(dir, name))\n}\n","/** `host/owner/repo`, lowercase — the same normalisation portal-api applies\n * (QDC `services/cli_repo_key.py`), pinned by a shared parity table. */\n\n// scp-like git syntax: [user@]host:path, path not starting with \"/\".\nconst SCP = /^(?:[^@/]+@)?([^:/]+):([^/].*)$/\nconst SCHEMES = new Set([\"https:\", \"http:\", \"ssh:\", \"git:\"])\n// Dot segments, also percent-encoded: WHATWG URL resolves these and Python's urlsplit\n// does not, so the two sides would disagree. Neither is a realistic remote: reject.\nconst DOT_SEGMENTS = new Set([\".\", \"..\", \"%2e\", \"%2e%2e\", \".%2e\", \"%2e.\"])\nconst hasDotSegment = (pieces: string[]) => pieces.some((p) => DOT_SEGMENTS.has(p.toLowerCase()))\n\nexport function repoKey(url: string): string | null {\n let raw = url.trim()\n if (raw.startsWith(\"git+\")) raw = raw.slice(4)\n // A backslash is a separator to WHATWG but a literal to urlsplit: reject it outright.\n if (!raw || raw.includes(\"\\\\\")) return null\n let host: string\n let path: string\n if (raw.includes(\"://\")) {\n if (hasDotSegment(raw.slice(raw.indexOf(\"://\") + 3).split(\"/\").slice(1))) return null\n let u: URL\n try { u = new URL(raw) } catch { return null }\n if (!SCHEMES.has(u.protocol.toLowerCase())) return null\n // WHATWG leaves non-special hosts (ssh:, git:) in their original case.\n host = u.hostname\n path = u.pathname\n } else {\n const m = SCP.exec(raw)\n if (!m) return null\n host = m[1]!\n path = m[2]!\n }\n const segments = path.split(\"/\").filter(Boolean)\n if (!host || segments.length !== 2 || hasDotSegment(segments)) return null\n const owner = segments[0]!\n let repo = segments[1]!\n if (repo.toLowerCase().endsWith(\".git\")) repo = repo.slice(0, -4)\n if (!repo) return null\n return `${host.toLowerCase()}/${owner.toLowerCase()}/${repo.toLowerCase()}`\n}\n","import { stat } from \"node:fs/promises\"\nimport { dirname, join, resolve } from \"node:path\"\n\n/** The first directory upwards that holds `.git` — a directory, or a file in a\n * worktree or submodule (spec §5.2 step 1, §15). */\nexport async function findRepoRoot(start: string): Promise<string | null> {\n let dir = resolve(start)\n for (;;) {\n try {\n await stat(join(dir, \".git\"))\n return dir\n } catch { /* not here (or unreadable): keep walking up */ }\n const up = dirname(dir)\n if (up === dir) return null\n dir = up\n }\n}\n","import { ensureCapability } from \"../api/capabilities.js\"\nimport type { CliLocalEnv, CliRef } from \"../api/types.js\"\nimport { withDetails } from \"../context/resolver.js\"\nimport type { ModuleContext } from \"../context/resolver.js\"\nimport type { Deps } from \"../deps.js\"\nimport { QoreError } from \"../errors.js\"\n\nexport async function fetchLocalEnv(deps: Deps, mc: ModuleContext, app: CliRef): Promise<CliLocalEnv> {\n await ensureCapability(deps, mc.portal.apiOrigin, \"module.local-env\")\n try {\n return await mc.session.api.get<CliLocalEnv>(\n `/api/cli/v1/modules/${encodeURIComponent(mc.module.id)}/local-env?app_id=${encodeURIComponent(app.id)}`)\n } catch (e) {\n if (!(e instanceof QoreError) || e.code !== \"QORE_ACCESS_DENIED\") throw e\n if (e.serverCode === \"app.access.denied\") {\n throw withDetails(e, { required: \"write\", have: mc.module.access },\n `You have ${mc.module.access} on ${mc.module.slug}; local secrets need write. Ask a maintainer of the app's dev team for write access.`)\n }\n // C13: a token minted before qore:local-env existed as a scope.\n if (e.serverCode === \"auth.scope.insufficient\") throw withDetails(e, {}, \"Run `qore login` again.\")\n throw e\n }\n}\n","/** .env merge semantics, ported behaviour-identically from qdc-sdk\n * packages/sdk/src/cli/setup-env-core.ts (spec §11.1). Keep the two in step until\n * the SDK's copy is removed in migration phase 2. */\n\n/** Parse `.env` text into an ordered Map<key,value>. Comments and blank lines\n * are not represented (preserved separately by renderEnv). */\nexport function parseEnv(contents: string): Map<string, string> {\n const map = new Map<string, string>()\n for (const line of contents.split(\"\\n\")) {\n const m = line.replace(/\\r$/, \"\").match(/^([A-Za-z_][A-Za-z0-9_]*)=(.*)$/)\n if (m?.[1] !== undefined && m[2] !== undefined) map.set(m[1], m[2])\n }\n return map\n}\n\n/** Does `key` match one of the portal's managed-key patterns? Exact match, or\n * the single wildcard form `PREFIX_*` used for CONN_*. */\nexport function isManagedKey(key: string, managed: string[]): boolean {\n for (const pattern of managed) {\n if (pattern.endsWith(\"*\")) {\n if (key.startsWith(pattern.slice(0, -1))) return true\n } else if (key === pattern) return true\n }\n return false\n}\n\nexport function planEnvUpdate({\n current,\n fetched,\n choices = {},\n defaultChoice = \"keep\",\n managed = [],\n}: {\n current: Map<string, string>\n fetched: Record<string, string>\n choices?: Record<string, \"keep\" | \"use-portal\">\n defaultChoice?: \"keep\" | \"use-portal\"\n managed?: string[]\n}): {\n merged: Map<string, string>\n conflicts: string[]\n added: string[]\n unchanged: string[]\n overwritten: string[]\n} {\n const merged = new Map(current)\n const conflicts: string[] = []\n const added: string[] = []\n const unchanged: string[] = []\n const overwritten: string[] = []\n\n for (const [key, portalValue] of Object.entries(fetched)) {\n const hasLocal = current.has(key)\n const localValue = current.get(key)\n const localEmpty = !hasLocal || localValue === \"\" || localValue === '\"\"' || localValue === \"''\"\n\n if (localEmpty) {\n merged.set(key, portalValue)\n added.push(key)\n continue\n }\n if (localValue === portalValue) {\n unchanged.push(key)\n continue\n }\n // The portal owns this key: take its value without asking. Anything the\n // developer needs to override permanently belongs in the portal as a\n // `local` secret, not in a hand-edited .env.local.\n if (isManagedKey(key, managed)) {\n merged.set(key, portalValue)\n overwritten.push(key)\n continue\n }\n conflicts.push(key)\n const choice = choices[key] ?? defaultChoice\n merged.set(key, choice === \"use-portal\" ? portalValue : localValue!)\n }\n\n return { merged, conflicts, added, unchanged, overwritten }\n}\n\n/** Render the merged Map back to `.env` text, preserving original comments,\n * blank lines, and key order. New keys are appended at the end. */\nexport function renderEnv(original: string, merged: Map<string, string>): string {\n const seen = new Set<string>()\n const lines = original.split(\"\\n\")\n const out = lines.map((line) => {\n const m = line.replace(/\\r$/, \"\").match(/^([A-Za-z_][A-Za-z0-9_]*)=(.*)$/)\n if (!m?.[1]) return line\n const key: string = m[1]\n if (!merged.has(key)) return line\n seen.add(key)\n return `${key}=${merged.get(key) ?? \"\"}`\n })\n\n const appended: string[] = []\n for (const [key, value] of merged) {\n if (!seen.has(key)) appended.push(`${key}=${value}`)\n }\n\n let text = out.join(\"\\n\")\n if (appended.length) {\n if (text.length && !text.endsWith(\"\\n\")) text += \"\\n\"\n text += appended.join(\"\\n\") + \"\\n\"\n }\n return text\n}\n","import { lstat, realpath } from \"node:fs/promises\"\nimport { basename, dirname, isAbsolute, relative, resolve, sep } from \"node:path\"\nimport { QoreError } from \"../errors.js\"\nimport { parseEnv, planEnvUpdate, renderEnv } from \"./merge.js\"\n\nconst outside = (target: string) => new QoreError(\"QORE_CONTEXT_INVALID\", `The env file must be inside the repository (got ${target})`, {\n hint: \"Use a path inside the repository for --target or .qore.json envFile.\",\n})\n\nconst symlinked = (target: string) => new QoreError(\"QORE_CONTEXT_INVALID\", `The env file target must not be a symlink (got ${target})`, {\n hint: \"Use a path inside the repository for --target or .qore.json envFile.\",\n})\n\nfunction inside(root: string, p: string): boolean {\n const rel = relative(root, p)\n return rel !== \"\" && rel !== \"..\" && !rel.startsWith(\"..\" + sep) && !isAbsolute(rel)\n}\n\n/** Spec §11.1 step 3, carried over from qdc-setup-env — plus a realpath check, so a\n * symlinked directory cannot carry the write out of the repository (review focus 1).\n *\n * `base` is where `target` is resolved from: the cwd for `--target`, the repository root\n * for `.qore.json`'s `envFile` (ruling R11) — both must still land inside `root`. Both sides\n * are compared by realpath(root) so macOS's /var → /private/var symlink cannot make an\n * in-repo path look external (ruling B5). */\nexport async function resolveTarget(root: string, target: string, base: string = root): Promise<string> {\n const realRoot = await realpath(root)\n const realBase = base === root ? realRoot : await realpath(base)\n const abs = resolve(realBase, target)\n // I2: `abs` is not yet realpath'd, so an absolute target spelled through a symlinked\n // directory (e.g. a repo under macOS /var, whose realpath is /private/var) would be\n // falsely rejected here even though it lands inside the repository. Containment is\n // enforced for real below, once the path is realpath'd (`final`, `realFinal`). This is\n // only a cheap pre-filter for the common relative-escape case (`../../etc/passwd`),\n // where realpath'ing an already-inside `abs` is pointless work to skip.\n if (!isAbsolute(target) && !inside(realRoot, abs)) throw outside(target)\n let parent: string\n try { parent = await realpath(dirname(abs)) } catch (e) {\n if ((e as NodeJS.ErrnoException).code !== \"ENOENT\") throw e\n throw new QoreError(\"QORE_CONTEXT_INVALID\", `The directory for ${target} does not exist`, {\n hint: \"Create the parent directory, or point --target / .qore.json envFile at an existing one.\",\n })\n }\n const final = resolve(parent, basename(abs))\n if (!inside(realRoot, final)) throw outside(target)\n\n // Review focus 1: an existing final path component that is itself a symlink is refused\n // outright — its target is never trusted, in or out of the repo — and if somehow not a\n // symlink but its realpath still escapes, that is refused too.\n try {\n const st = await lstat(final)\n if (st.isSymbolicLink()) throw symlinked(target)\n const realFinal = await realpath(final)\n if (!inside(realRoot, realFinal)) throw outside(target)\n } catch (e) {\n if (e instanceof QoreError) throw e\n if ((e as NodeJS.ErrnoException).code !== \"ENOENT\") throw e\n }\n\n return final\n}\n\nexport type PullPlan = {\n text: string; created: boolean; seededFromExample: boolean\n added: string[]; updated: string[]; kept: string[]; replaced: string[]; unchanged: string[]; generated: string[]\n}\n\nexport function planPull(o: {\n existing: string | null; example: string | null; fetched: Record<string, string>; managed: string[]\n localSecrets: string[]; choices?: Record<string, \"keep\" | \"use-portal\">; defaultChoice: \"keep\" | \"use-portal\"; random: () => string\n}): PullPlan & { conflicts: string[] } {\n const original = o.existing ?? o.example ?? \"\"\n const current = parseEnv(original)\n const r = planEnvUpdate({ current, fetched: o.fetched, choices: o.choices ?? {}, defaultChoice: o.defaultChoice, managed: o.managed })\n const choiceOf = (k: string) => o.choices?.[k] ?? o.defaultChoice\n const generated: string[] = []\n for (const key of o.localSecrets) {\n const v = r.merged.get(key)\n if (v === undefined || v === \"\" || v === '\"\"' || v === \"''\") { r.merged.set(key, o.random()); generated.push(key) }\n }\n return {\n text: renderEnv(original, r.merged),\n created: o.existing === null,\n seededFromExample: o.existing === null && o.example !== null,\n added: r.added, updated: r.overwritten, unchanged: r.unchanged, conflicts: r.conflicts,\n kept: r.conflicts.filter((k) => choiceOf(k) === \"keep\"),\n replaced: r.conflicts.filter((k) => choiceOf(k) === \"use-portal\"),\n generated,\n }\n}\n","import type { CliRef } from \"../core/api/types.js\"\nimport { QoreError, type Candidate } from \"../core/errors.js\"\nimport { pickApp, resolveModuleContext, type ModuleContext } from \"../core/context/resolver.js\"\nimport type { CommandContext } from \"./program.js\"\n\nconst allOfKind = (c: Candidate[] | undefined, kind: Candidate[\"kind\"]): c is (Candidate & { id: string })[] =>\n !!c && c.length > 0 && c.every((x) => x.kind === kind && typeof x.id === \"string\")\n\nexport async function moduleContextFor(ctx: CommandContext, flags: { module?: string }, command: string): Promise<ModuleContext> {\n const g = ctx.opts()\n const onRequest = g.verbose ? (l: string) => ctx.io.err(l) : undefined\n const base = { portal: g.portal, module: flags.module, command, onRequest }\n try {\n return await resolveModuleContext(ctx.deps, base)\n } catch (e) {\n if (!(e instanceof QoreError) || e.code !== \"QORE_CONTEXT_REQUIRED\" || !ctx.io.interactive) throw e\n // core/ never prompts (R5): it names the candidates, and only here do they become a picker.\n if (allOfKind(e.candidates, \"module\")) {\n const choose = await ctx.io.select(\"Select a module\",\n e.candidates.map((c) => ({ name: `${c.tenant ? `${c.tenant} / ` : \"\"}${c.slug} (${c.remote})`, value: c.id })))\n return resolveModuleContext(ctx.deps, { ...base, choose })\n }\n if (allOfKind(e.candidates, \"tenant\")) {\n const tenant = await ctx.io.select(\"Select a tenant\", e.candidates.map((c) => ({ name: c.name ?? c.slug, value: c.id })))\n return resolveModuleContext(ctx.deps, { ...base, tenant })\n }\n throw e\n }\n}\n\nexport async function appFor(ctx: CommandContext, mc: ModuleContext, app?: string): Promise<CliRef> {\n try {\n return pickApp(mc, app)\n } catch (e) {\n if (!(e instanceof QoreError) || e.code !== \"QORE_APP_AMBIGUOUS\" || !ctx.io.interactive) throw e\n const id = await ctx.io.select(\"Select an app\", mc.module.apps.map((a) => ({ name: a.name, value: a.id })))\n return pickApp(mc, id)\n }\n}\n\nfunction sourceText(mc: ModuleContext): string {\n if (mc.source.kind === \"remote\") return mc.source.remote\n return mc.source.overrides ? `--module, overrides ${mc.source.overrides}` : \"--module\"\n}\n\nexport function contextLine(mc: ModuleContext, app?: CliRef): string {\n const parts = [mc.module.tenant.name, ...(app ? [app.name] : []), mc.module.slug]\n return `→ ${parts.join(\" / \")} (${sourceText(mc)})`\n}\n\nexport function contextJson(mc: ModuleContext, app?: CliRef) {\n const { id, slug, name, type, access } = mc.module\n return {\n portal: mc.portal.builtin ?? mc.portal.apiOrigin,\n tenant: mc.module.tenant,\n app: app ?? null,\n module: { id, slug, name, type, access },\n source: mc.source.kind === \"remote\" ? mc.source.remote : \"--module\",\n ...(mc.source.kind === \"flag\" && mc.source.overrides ? { overrides: mc.source.overrides } : {}),\n }\n}\n","import { realpath } from \"node:fs/promises\"\nimport type { Deps } from \"./deps.js\"\n\n/** Spec §5.4: a safety interlock, not authorization — the server still authorizes. */\nexport function trustKey(root: string, platform: NodeJS.Platform): string {\n return platform === \"win32\" ? root.toLowerCase() : root\n}\n\nasync function keyOf(deps: Deps, root: string): Promise<string> {\n let real = root\n try {\n real = await realpath(root)\n } catch (e) {\n if ((e as NodeJS.ErrnoException).code !== \"ENOENT\") throw e\n // a vanished dir keeps its literal path\n }\n return trustKey(real, deps.platform)\n}\n\nexport async function isTrusted(deps: Deps, root: string, moduleId: string): Promise<boolean> {\n const cfg = await deps.config.read()\n return (cfg.trustedRepos?.[await keyOf(deps, root)] ?? []).includes(moduleId)\n}\n\nexport async function trust(deps: Deps, root: string, moduleId: string): Promise<void> {\n const key = await keyOf(deps, root)\n await deps.config.update((c) => {\n const repos = (c.trustedRepos ??= {})\n const list = new Set(repos[key] ?? [])\n list.add(moduleId)\n repos[key] = [...list]\n })\n}\n","import type { CliRef } from \"../core/api/types.js\"\nimport { repoKey } from \"../core/context/repoKey.js\"\nimport type { ModuleContext } from \"../core/context/resolver.js\"\nimport { CancelledError, QoreError } from \"../core/errors.js\"\nimport { isTrusted, trust } from \"../core/trust.js\"\nimport { contextLine } from \"./context.js\"\nimport type { CommandContext } from \"./program.js\"\n\n/** Task 10: the trust interlock (spec §5.4) as a first-use prompt. Trust is a safety\n * interlock, not authorization — the server still authorizes every fetch.\n *\n * Ruling C8: the context line prints exactly once, here — before the trust prompt, and\n * also before the untrusted non-TTY error — so the caller (env.ts) must not print it\n * again after calling this. */\nexport async function ensureTrusted(ctx: CommandContext, mc: ModuleContext, app: CliRef, o: { yes?: boolean }): Promise<void> {\n const root = mc.repoRoot ?? ctx.deps.cwd\n if (!ctx.opts().json) ctx.io.err(contextLine(mc, app))\n if (await isTrusted(ctx.deps, root, mc.module.id)) return\n if (o.yes) { await trust(ctx.deps, root, mc.module.id); return }\n if (!ctx.io.interactive) {\n throw new QoreError(\"QORE_CONTEXT_REQUIRED\", `This repository is not trusted for ${mc.module.slug} yet`, {\n hint: \"Run interactively once, or pass --yes.\", details: { reason: \"untrusted\", repository: root },\n })\n }\n if (mc.source.kind === \"remote\") {\n // I1: never print the raw remote URL — it may embed credentials (e.g. an\n // https x-access-token PAT). Print the normalised repo key instead.\n const key = repoKey(mc.source.url)\n ctx.io.err(` from remote ${mc.source.remote}: ${key ?? \"(unparsable remote URL)\"}`)\n }\n if (!(await ctx.io.confirm(\"Pull local secrets for this module into this repository?\"))) throw new CancelledError()\n await trust(ctx.deps, root, mc.module.id)\n}\n","import * as oc from \"openid-client\"\nimport { CancelledError, QoreError } from \"../errors.js\"\nimport type { Fetch } from \"../api/http.js\"\nimport { isAbortError, networkError } from \"../api/http.js\"\n\nexport type DeviceStart = { userCode: string; verificationUri: string; verificationUriComplete?: string; expiresIn: number; handle: unknown }\nexport type TokenSet = { accessToken: string; refreshToken: string; expiresIn: number; scope: string; sub: string; email?: string }\n\nexport interface Oidc {\n startDevice(scope: string): Promise<DeviceStart>\n pollDevice(start: DeviceStart, signal: AbortSignal): Promise<TokenSet>\n refresh(rt: string, scope?: string): Promise<TokenSet>\n revoke(rt: string): Promise<void>\n}\n\nexport const LOGIN_SCOPE = \"openid profile email offline_access qore:read qore:local-env\"\n\nfunction decodeSub(accessToken: string): { sub: string; email?: string } {\n const part = accessToken.split(\".\")[1] ?? \"\"\n const claims = JSON.parse(Buffer.from(part, \"base64url\").toString(\"utf8\")) as { sub: string; email?: string }\n return { sub: claims.sub, email: claims.email }\n}\n\nfunction toTokenSet(t: oc.TokenEndpointResponse, fallbackRt?: string): TokenSet {\n const rt = t.refresh_token ?? fallbackRt\n if (!rt) throw new QoreError(\"QORE_INTERNAL\", \"Keycloak returned no refresh token\")\n return { accessToken: t.access_token, refreshToken: rt, expiresIn: t.expires_in ?? 600,\n scope: t.scope ?? \"\", ...decodeSub(t.access_token) }\n}\n\n/** Keycloak unreachable is QORE_AUTH_UNAVAILABLE (spec §7, §14; R19), not the portal's\n * QORE_API_UNREACHABLE — with the same network diagnosis (hint, reason, host). */\nfunction unreachable(e: unknown, host: string): QoreError {\n const n = networkError(e, host)\n return new QoreError(\"QORE_AUTH_UNAVAILABLE\", n.message, { hint: n.hint, details: n.details, cause: e })\n}\n\nexport function mapOidcError(e: unknown, host: string): Error {\n if (e instanceof QoreError || e instanceof CancelledError) return e\n // Ctrl+C aborts the request's signal; openid-client wraps that DOMException as\n // ClientError { code: \"OAUTH_ABORT\", cause }.\n if (isAbortError(e) || (e as { code?: unknown })?.code === \"OAUTH_ABORT\" || isAbortError((e as { cause?: unknown })?.cause)) {\n return new CancelledError()\n }\n const err = (e as { error?: string }).error\n if (err === \"access_denied\") return new QoreError(\"QORE_LOGIN_DENIED\", \"The login was denied in the browser\")\n if (err === \"expired_token\") return new QoreError(\"QORE_LOGIN_EXPIRED\", \"The login code expired\", { hint: \"Run `qore login` again.\" })\n if (err === \"invalid_grant\") return new QoreError(\"QORE_SESSION_EXPIRED\", \"Your session has ended\", { hint: \"Run `qore login`.\" })\n const status = (e as { status?: number }).status\n if (status && status >= 500) return new QoreError(\"QORE_AUTH_UNAVAILABLE\", \"Keycloak is unavailable\", { cause: e })\n if (e instanceof TypeError) return unreachable(e, host)\n // openid-client sometimes wraps the raw fetch TypeError (DNS/TLS/connect/timeout) one\n // level deep, e.g. `new ClientError(\"something went wrong\", { cause: err })`.\n const cause = (e as { cause?: unknown })?.cause\n if (cause instanceof TypeError) return unreachable(cause, host)\n return new QoreError(\"QORE_AUTH_UNAVAILABLE\", \"Login failed\", { cause: e })\n}\n\nexport async function createOidc(opts: { issuer: string; clientId: string; fetch: Fetch }): Promise<Oidc> {\n const host = new URL(opts.issuer).host\n const execute = new URL(opts.issuer).protocol === \"http:\" ? [oc.allowInsecureRequests] : []\n let config: oc.Configuration\n try {\n config = await oc.discovery(new URL(opts.issuer), opts.clientId, undefined, oc.None(), {\n execute, [oc.customFetch]: opts.fetch as unknown as oc.CustomFetch,\n })\n } catch (e) { throw mapOidcError(e, host) }\n\n return {\n async startDevice(scope) {\n try {\n const r = await oc.initiateDeviceAuthorization(config, { scope })\n return { userCode: r.user_code, verificationUri: r.verification_uri,\n verificationUriComplete: r.verification_uri_complete, expiresIn: r.expires_in, handle: r }\n } catch (e) { throw mapOidcError(e, host) }\n },\n async pollDevice(start, signal) {\n try {\n const t = await oc.pollDeviceAuthorizationGrant(config, start.handle as oc.DeviceAuthorizationResponse, undefined, { signal })\n return toTokenSet(t)\n } catch (e) { throw mapOidcError(e, host) }\n },\n async refresh(rt, scope) {\n try {\n const t = await oc.refreshTokenGrant(config, rt, scope ? { scope } : undefined)\n return toTokenSet(t, rt)\n } catch (e) { throw mapOidcError(e, host) }\n },\n async revoke(rt) {\n try { await oc.tokenRevocation(config, rt, { token_type_hint: \"refresh_token\" }) }\n catch (e) { throw mapOidcError(e, host) }\n },\n }\n}\n","import type { WithLock } from \"../../platform/lock.js\"\nimport type { DeviceStart, Oidc, TokenSet } from \"./oidc.js\"\nimport { LOGIN_SCOPE } from \"./oidc.js\"\nimport type { TokenStore } from \"./tokenStore.js\"\n\nexport async function deviceLogin(opts: {\n oidc: Oidc\n store: TokenStore\n now: () => Date\n /** Shows the code. Polling already runs meanwhile; `settled` aborts once it succeeds or\n * fails, so a prompt waiting on the user (who may have opened the URL themselves) can end. */\n onCode: (s: DeviceStart, settled: AbortSignal) => void | Promise<void>\n signal: AbortSignal\n withLock?: WithLock\n lockName?: string\n}): Promise<TokenSet> {\n // Probe the keychain first: an unusable or denied keychain must fail before the user\n // approves anything in the browser (Review Focus #4), not after.\n await opts.store.getRefresh()\n const start = await opts.oidc.startDevice(LOGIN_SCOPE)\n const stopPoll = new AbortController()\n const settled = new AbortController()\n const poll = opts.oidc.pollDevice(start, AbortSignal.any([opts.signal, stopPoll.signal]))\n .finally(() => settled.abort())\n // Awaited below; this only keeps a poll that fails while onCode runs from counting as unhandled.\n poll.catch(() => {})\n try {\n await opts.onCode(start, settled.signal)\n } catch (e) {\n stopPoll.abort()\n // Approved just before onCode failed: that session is never stored, so end it server-side.\n const late = await poll.catch(() => null)\n if (late) await opts.oidc.revoke(late.refreshToken).catch(() => {})\n throw e\n }\n const t = await poll\n const at = opts.now()\n const write = async () => {\n // Refresh first: a crash between the two writes then leaves a usable session.\n await opts.store.setRefresh({ rt: t.refreshToken, sub: t.sub, scope: t.scope, obtainedAt: at.toISOString() })\n await opts.store.setAccess({ at: t.accessToken, expiresAt: new Date(at.getTime() + t.expiresIn * 1000).toISOString() })\n }\n try {\n if (opts.withLock && opts.lockName) await opts.withLock(opts.lockName, write)\n else await write()\n } catch (e) {\n // The new session cannot be kept: end it server-side and drop any half-written entry.\n // Both best-effort; the original (keychain) error is what the user needs to see.\n await opts.oidc.revoke(t.refreshToken).catch(() => {})\n await opts.store.clear().catch(() => {})\n throw e\n }\n return t\n}\n","import type { Command } from \"commander\"\nimport { fetchMeta, negotiate } from \"../../core/api/meta.js\"\nimport type { CliMe, CliMeta } from \"../../core/api/types.js\"\nimport { deviceLogin } from \"../../core/auth/login.js\"\nimport { TokenStore } from \"../../core/auth/tokenStore.js\"\nimport { profileHash, resolvePortal } from \"../../core/profiles.js\"\nimport { openSession } from \"../../core/session.js\"\nimport { requestLog, type CommandContext } from \"../program.js\"\nimport { renderJson } from \"../render.js\"\n\nexport function registerLogin(program: Command, ctx: CommandContext): void {\n program.command(\"login\").description(\"Log in with your Qore account\")\n .option(\"--no-browser\", \"only print the URL\")\n .action(async (cmd: { browser: boolean }) => {\n const { deps, io, signal } = ctx\n const g = ctx.opts()\n const cfg = await deps.config.read()\n const portal = resolvePortal(g.portal, cfg.defaultProfile)\n const meta: CliMeta = await fetchMeta(deps.fetch, portal.apiOrigin)\n const known = cfg.profiles[portal.apiOrigin]?.issuer\n const pinned = { ...portal, pinnedIssuer: portal.pinnedIssuer ?? known ?? null }\n if (!pinned.pinnedIssuer && portal.builtin === null) {\n io.err(`! Logging in to ${portal.apiOrigin}, identity provider ${meta.auth.issuer}`)\n }\n negotiate(meta, pinned, deps.version)\n const issuer = pinned.pinnedIssuer ?? meta.auth.issuer\n const hash = profileHash(portal.apiOrigin, issuer)\n const store = new TokenStore(deps.keychain, hash)\n const t = await deviceLogin({\n oidc: await deps.oidcFor(issuer), store, now: deps.now, signal,\n withLock: deps.withLock, lockName: hash,\n onCode: async (s, settled) => {\n const url = s.verificationUriComplete ?? s.verificationUri\n io.err(`! First copy your one-time code: ${s.userCode}`)\n if (io.interactive && cmd.browser) {\n try {\n await io.waitForEnter(` Press Enter to open ${url} (or open it yourself)`, AbortSignal.any([signal, settled]))\n } catch (e) {\n // Approved (or denied) in a browser the user opened themselves: nothing left to open.\n if (settled.aborted && !signal.aborted) return\n throw e\n }\n if (settled.aborted) return\n if (!(await io.openUrl(url))) io.err(` Open ${url} in a browser`)\n } else {\n io.err(` Open ${url} in a browser`)\n }\n },\n })\n await deps.config.update((c) => {\n c.profiles[portal.apiOrigin] = { ...c.profiles[portal.apiOrigin], apiOrigin: portal.apiOrigin, issuer,\n sub: t.sub, email: t.email, meta: { fetchedAt: deps.now().toISOString(), doc: meta } }\n if (g.portal || !c.defaultProfile) c.defaultProfile = portal.apiOrigin\n })\n const { api } = await openSession(deps, { ...portal, pinnedIssuer: issuer }, \"login\", requestLog(ctx))\n const me = await api.get<CliMe>(\"/api/cli/v1/me\")\n const prev = cfg.profiles[portal.apiOrigin]\n let active: { id: string; slug: string } | undefined =\n prev?.sub === t.sub && prev.activeTenant && me.tenants.some((x) => x.id === prev.activeTenant!.id)\n ? prev.activeTenant\n : undefined\n if (active) {\n // A previous session's active tenant is still valid for this sub: keep it, no re-selection.\n } else if (me.tenants.length === 0) {\n io.err(\"! Your account is not a developer in any organisation. Ask an admin to invite you as developer.\")\n } else if (me.tenants.length === 1) {\n active = { id: me.tenants[0]!.id, slug: me.tenants[0]!.slug }\n io.err(`✓ Using tenant ${me.tenants[0]!.name}`)\n } else if (io.interactive) {\n active = await io.select(\"Select a tenant\", me.tenants.map((x) => ({ name: `${x.name} ${x.role}`, value: { id: x.id, slug: x.slug } })))\n } else {\n io.err(`! You belong to ${me.tenants.length} tenants; choose one with \\`qore tenant use <slug>\\``)\n }\n await deps.config.update((c) => { c.profiles[portal.apiOrigin]!.activeTenant = active })\n const label = portal.builtin ?? portal.apiOrigin\n if (g.json) renderJson(io, { portal: label, email: me.email, activeTenant: active ?? null })\n else io.out(`✓ Logged in as ${me.email} (${label})`)\n })\n}\n","import type { Command } from \"commander\"\nimport { TokenStore } from \"../../core/auth/tokenStore.js\"\nimport { QoreError } from \"../../core/errors.js\"\nimport { profileHash, resolvePortal } from \"../../core/profiles.js\"\nimport type { CommandContext } from \"../program.js\"\nimport { renderJson } from \"../render.js\"\n\nexport function registerLogout(program: Command, ctx: CommandContext): void {\n program.command(\"logout\").description(\"End the CLI session\")\n .option(\"--all\", \"log out of every portal\")\n .action(async (cmd: { all?: boolean }) => {\n const { deps, io } = ctx\n const g = ctx.opts()\n const cfg = await deps.config.read()\n const targets = cmd.all ? Object.values(cfg.profiles)\n : [cfg.profiles[resolvePortal(g.portal, cfg.defaultProfile).apiOrigin]].filter((p) => p !== undefined)\n const done: string[] = []\n for (const p of targets) {\n const hash = profileHash(p.apiOrigin, p.issuer)\n const store = new TokenStore(deps.keychain, hash)\n const host = new URL(p.issuer).host\n // Read, revoke and clear under one lock, so a concurrent refresh cannot rotate the\n // RT between our read and the revoke (we would revoke a stale one) or resurrect it.\n await deps.withLock(hash, async () => {\n const rt = await store.getRefresh()\n if (rt) {\n try { await (await deps.oidcFor(p.issuer)).revoke(rt.rt) }\n catch (e) {\n const network = e instanceof QoreError && e.details?.reason !== undefined\n io.err(network\n ? `! Could not reach ${host}; the server session may persist until it expires.`\n : `! Could not revoke the session at ${host} (${e instanceof Error ? e.message : String(e)}); the server session may persist until it expires.`)\n }\n }\n await store.clear()\n })\n done.push(p.apiOrigin)\n }\n if (g.json) renderJson(io, { loggedOut: done })\n else if (done.length === 0) io.out(\"Not logged in\")\n else io.out(`✓ Logged out of ${done.map((o) => resolvePortal(o, undefined).builtin ?? o).join(\", \")}`)\n })\n}\n","import { constants } from \"node:os\"\nimport type { Command } from \"commander\"\nimport { QoreError } from \"../../core/errors.js\"\nimport { fetchLocalEnv } from \"../../core/env/fetch.js\"\nimport { appFor, moduleContextFor } from \"../context.js\"\nimport type { CommandContext } from \"../program.js\"\nimport { ensureTrusted } from \"../trustPrompt.js\"\n\n/** Ruling R3: while the child runs, cli.ts's own SIGINT handler must not force `exit(130)`\n * — the terminal already delivers Ctrl+C to the whole foreground process group (see\n * platform/spawn.ts), so the child's own exit (code or re-raised signal) is what decides\n * qore's exit code. This flag is the narrow hook cli.ts checks; it brackets exactly the\n * `deps.spawn.run` call, nothing more. */\nexport const childRunning = { current: false }\n\nexport function registerRun(program: Command, ctx: CommandContext): void {\n program\n .command(\"run\")\n .description(\"Run a command with this module's local secrets in its environment\")\n .option(\"--module <slug|id>\", \"the module (default: from this repository's git remote)\")\n .option(\"--app <slug|id>\", \"the app, when the module is part of several\")\n .option(\"--yes\", \"trust this repository without asking\")\n .argument(\"<command>\", \"the command to run (after --)\")\n .argument(\"[args...]\", \"its arguments, passed verbatim\")\n .action(async (cmd: string, args: string[], f: { module?: string; app?: string; yes?: boolean }) => {\n const { deps } = ctx\n if (ctx.opts().json) {\n throw new QoreError(\"QORE_CONTEXT_INVALID\", \"run has no --json output\", {\n hint: \"Drop --json; the child's own output passes through.\",\n })\n }\n const mc = await moduleContextFor(ctx, f, \"run\")\n const app = await appFor(ctx, mc, f.app)\n // C8: ensureTrusted prints the context line exactly once — do not print it again here.\n await ensureTrusted(ctx, mc, app, { yes: f.yes })\n const local = await fetchLocalEnv(deps, mc, app) // fetched on every run, never cached (§11.2)\n childRunning.current = true\n let exit\n try {\n exit = await deps.spawn.run(cmd, args, { ...deps.env, ...local.env })\n } finally {\n childRunning.current = false\n }\n if (exit.signal) {\n deps.raise(exit.signal)\n ctx.setExitCode(128 + (constants.signals[exit.signal] ?? 0))\n return\n }\n ctx.setExitCode(exit.code ?? 1)\n })\n}\n","import type { CliHealth } from \"../core/api/types.js\"\n\nexport function ago(iso: string | null, now: Date): string {\n if (!iso) return \"–\"\n const s = Math.max(0, Math.round((now.getTime() - new Date(iso).getTime()) / 1000))\n if (s < 60) return \"just now\"\n if (s < 3600) return `${Math.floor(s / 60)}m ago`\n if (s < 86400) return `${Math.floor(s / 3600)}h ago`\n return `${Math.floor(s / 86400)}d ago`\n}\n\nconst pct = (f: number) => String(Number((f * 100).toFixed(2)))\n\nexport function uptime(h: CliHealth | null): string {\n if (!h) return \"–\"\n const kind = h.cause && h.kind !== \"up\" ? `${h.kind}: ${h.cause}` : h.kind\n return h.uptime24h === null ? kind : `${kind} (${pct(h.uptime24h)}% 24h)`\n}\n\nexport function table(rows: string[][]): string[] {\n const widths = rows[0]!.map((_, i) => Math.max(...rows.map((r) => (r[i] ?? \"\").length)))\n return rows.map((r) => \" \" + r.map((c, i) => (i === r.length - 1 ? c : c.padEnd(widths[i]!))).join(\" \"))\n}\n","import type { Command } from \"commander\"\nimport { ensureCapability } from \"../../core/api/capabilities.js\"\nimport type { CliModuleStatus } from \"../../core/api/types.js\"\nimport { appFor, contextJson, contextLine, moduleContextFor } from \"../context.js\"\nimport { ago, table, uptime } from \"../format.js\"\nimport type { CommandContext } from \"../program.js\"\nimport { renderJson } from \"../render.js\"\n\nexport function registerStatus(program: Command, ctx: CommandContext): void {\n program.command(\"status\").description(\"Deployment and health per environment for this module\")\n .option(\"--module <slug|id>\", \"the module (default: from this repository's git remote)\")\n .option(\"--app <slug|id>\", \"the app, when the module is part of several\")\n .action(async (flags: { module?: string; app?: string }) => {\n const { deps, io } = ctx\n const g = ctx.opts()\n const mc = await moduleContextFor(ctx, flags, \"status\")\n await ensureCapability(deps, mc.portal.apiOrigin, \"module.status\")\n const app = await appFor(ctx, mc, flags.app)\n if (!g.json) io.err(contextLine(mc, app))\n const st = await mc.session.api.get<CliModuleStatus>(\n `/api/cli/v1/modules/${encodeURIComponent(mc.module.id)}/status?app_id=${encodeURIComponent(app.id)}`)\n if (g.json) { renderJson(io, { context: contextJson(mc, app), environments: st.environments }); return }\n if (st.environments.length === 0) { io.out(\"No environments yet.\"); return }\n const now = deps.now()\n const rows = [[\"ENV\", \"DEPLOY\", \"COMMIT\", \"DEPLOYED\", \"APP HEALTH\"],\n ...st.environments.map((e) => [e.name, e.paused ? \"paused\" : e.status, e.commit?.sha ?? \"–\",\n ago(e.commit?.deployedAt ?? null, now), uptime(e.health)])]\n for (const line of table(rows)) io.out(line)\n })\n}\n","import type { Command } from \"commander\"\nimport type { CliMe } from \"../../core/api/types.js\"\nimport { QoreError, type Candidate } from \"../../core/errors.js\"\nimport { resolvePortal } from \"../../core/profiles.js\"\nimport { openSession } from \"../../core/session.js\"\nimport { requestLog, type CommandContext } from \"../program.js\"\nimport { renderJson } from \"../render.js\"\n\nexport function registerTenant(program: Command, ctx: CommandContext): void {\n const tenant = program.command(\"tenant\").description(\"Manage the active tenant\")\n\n tenant.command(\"list\").description(\"List tenants you have access to\")\n .action(async () => {\n const { deps, io } = ctx\n const g = ctx.opts()\n const cfg = await deps.config.read()\n const portal = resolvePortal(g.portal, cfg.defaultProfile)\n const { profile, api } = await openSession(deps, portal, \"tenant list\", requestLog(ctx))\n const me = await api.get<CliMe>(\"/api/cli/v1/me\")\n const activeId = profile.activeTenant?.id\n if (g.json) {\n renderJson(io, { tenants: me.tenants.map((t) => ({ ...t, active: t.id === activeId })) })\n return\n }\n for (const t of me.tenants) {\n const mark = t.id === activeId ? \"*\" : \" \"\n io.out(`${mark} ${t.name} ${t.role}`)\n }\n })\n\n tenant.command(\"use\").description(\"Set the active tenant\").argument(\"[slug]\", \"tenant slug\")\n .action(async (slug: string | undefined) => {\n const { deps, io } = ctx\n const g = ctx.opts()\n const cfg = await deps.config.read()\n const portal = resolvePortal(g.portal, cfg.defaultProfile)\n const { api } = await openSession(deps, portal, \"tenant use\", requestLog(ctx))\n const me = await api.get<CliMe>(\"/api/cli/v1/me\")\n const candidates: Candidate[] = me.tenants.map((t) => ({ kind: \"tenant\", id: t.id, slug: t.slug, name: t.name }))\n let chosen: { id: string; slug: string }\n if (slug) {\n const found = me.tenants.find((t) => t.slug === slug)\n if (!found) throw new QoreError(\"QORE_RESOURCE_NOT_FOUND\", `No tenant \"${slug}\" for this account`, { candidates })\n chosen = { id: found.id, slug: found.slug }\n } else if (io.interactive) {\n chosen = await io.select(\"Select a tenant\", me.tenants.map((t) => ({ name: `${t.name} ${t.role}`, value: { id: t.id, slug: t.slug } })))\n } else {\n throw new QoreError(\"QORE_CONTEXT_REQUIRED\", \"Which tenant? Pass a slug or run interactively.\", { candidates })\n }\n await deps.config.update((c) => { c.profiles[portal.apiOrigin]!.activeTenant = chosen })\n if (g.json) renderJson(io, { activeTenant: chosen })\n else io.out(`✓ Using tenant ${chosen.slug}`)\n })\n}\n","import type { Command } from \"commander\"\nimport { fetchMeta } from \"../../core/api/meta.js\"\nimport { CancelledError } from \"../../core/errors.js\"\nimport { resolvePortal } from \"../../core/profiles.js\"\nimport type { CommandContext } from \"../program.js\"\nimport { renderJson } from \"../render.js\"\n\nexport function registerVersion(program: Command, ctx: CommandContext): void {\n program.command(\"version\").description(\"Show the CLI and portal version\")\n .action(async () => {\n const { deps, io } = ctx\n const g = ctx.opts()\n const cfg = await deps.config.read()\n const portal = resolvePortal(g.portal, cfg.defaultProfile)\n let portalInfo: { apiVersions: string[]; minCliVersion: string; latestCliVersion: string; capabilities: string[] } | null = null\n try {\n const meta = await fetchMeta(deps.fetch, portal.apiOrigin)\n portalInfo = { apiVersions: meta.apiVersions, minCliVersion: meta.minCliVersion, latestCliVersion: meta.latestCliVersion, capabilities: meta.capabilities }\n } catch (e) {\n // A cancel is not \"unreachable\": Ctrl+C still exits 130.\n if (e instanceof CancelledError) throw e\n /* portal unreachable; report null below */\n }\n if (g.json) {\n renderJson(io, { cli: deps.version, portal: portalInfo })\n return\n }\n io.out(`qore ${deps.version}`)\n const label = portal.builtin ?? portal.apiOrigin\n if (portalInfo) {\n io.out(`portal ${label}: api ${portalInfo.apiVersions.join(\",\")}, min ${portalInfo.minCliVersion}, latest ${portalInfo.latestCliVersion}`)\n } else {\n io.out(`portal ${label}: unreachable`)\n }\n })\n}\n","import type { Command } from \"commander\"\nimport type { CliMe } from \"../../core/api/types.js\"\nimport { resolvePortal } from \"../../core/profiles.js\"\nimport { openSession } from \"../../core/session.js\"\nimport { requestLog, type CommandContext } from \"../program.js\"\nimport { renderJson } from \"../render.js\"\n\nexport function registerWhoami(program: Command, ctx: CommandContext): void {\n program.command(\"whoami\").description(\"Show who you're logged in as\")\n .action(async () => {\n const { deps, io } = ctx\n const g = ctx.opts()\n const cfg = await deps.config.read()\n const portal = resolvePortal(g.portal, cfg.defaultProfile)\n const { profile, api } = await openSession(deps, portal, \"whoami\", requestLog(ctx))\n const me = await api.get<CliMe>(\"/api/cli/v1/me\")\n const activeTenant = profile.activeTenant\n if (activeTenant && !me.tenants.some((t) => t.id === activeTenant.id)) {\n io.err(`! You no longer have developer access to ${activeTenant.slug}`)\n }\n const label = portal.builtin ?? portal.apiOrigin\n if (g.json) {\n renderJson(io, { portal: label, activeTenant: activeTenant ?? null, me })\n return\n }\n io.out(`${me.email} (${label})`)\n for (const t of me.tenants) {\n const mark = activeTenant?.id === t.id ? \"*\" : \" \"\n io.out(`${mark} ${t.name} ${t.role}`)\n for (const a of t.apps) {\n io.out(` ${a.slug} ${a.access}`)\n for (const m of a.modules) {\n io.out(` ${m.slug} ${m.type} ${m.access}`)\n }\n }\n }\n })\n}\n","import type { Register } from \"../program.js\"\nimport { registerEnv } from \"./env.js\"\nimport { registerLogin } from \"./login.js\"\nimport { registerLogout } from \"./logout.js\"\nimport { registerRun } from \"./run.js\"\nimport { registerStatus } from \"./status.js\"\nimport { registerTenant } from \"./tenant.js\"\nimport { registerVersion } from \"./version.js\"\nimport { registerWhoami } from \"./whoami.js\"\n\nexport const COMMANDS: Register[] = [\n registerLogin, registerLogout, registerWhoami, registerTenant, registerStatus, registerEnv, registerRun, registerVersion,\n]\n","import { compareVersions } from \"../core/api/meta.js\"\nimport type { Deps } from \"../core/deps.js\"\nimport type { Io } from \"./io.js\"\n\nconst REGISTRY_URL = \"https://registry.npmjs.org/@quatronic%2Fqore/latest\"\nconst DAY_MS = 24 * 60 * 60 * 1000\nconst DEFAULT_TIMEOUT_MS = 1500\n\nexport async function maybeNotifyUpdate(deps: Deps, io: Io, o: { json: boolean }, timeoutMs = DEFAULT_TIMEOUT_MS): Promise<void> {\n if (o.json || deps.env.CI || deps.env.QORE_NO_UPDATE_CHECK === \"1\" || !io.interactive) return\n const cfg = await deps.config.read()\n const last = cfg.updateCheck?.lastCheckedAt\n if (last && deps.now().getTime() - new Date(last).getTime() < DAY_MS) return\n const controller = new AbortController()\n const timer = setTimeout(() => controller.abort(), timeoutMs)\n let latest: string | undefined\n try {\n const res = await deps.fetch(REGISTRY_URL, { signal: controller.signal })\n if (res.ok) latest = ((await res.json()) as { version?: string }).version\n } catch { /* silent: an update check never affects the run */ }\n finally { clearTimeout(timer) }\n try {\n // Recorded after a failed, non-OK or timed-out check too, so an offline user does not\n // pay the timeout on every command; the last known latest version is kept then.\n await deps.config.update((c) => {\n c.updateCheck = { lastCheckedAt: deps.now().toISOString(), latest: latest ?? c.updateCheck?.latest ?? deps.version }\n })\n } catch { return }\n if (latest && compareVersions(latest, deps.version) > 0) {\n io.err(`A new qore is available: ${deps.version} → ${latest} npm i -g @quatronic/qore`)\n }\n}\n","import { readFile } from \"node:fs/promises\"\nimport { join } from \"node:path\"\nimport { QoreError } from \"./errors.js\"\nimport { writeJsonAtomic } from \"./jsonFile.js\"\n\nexport type ProfileRecord = {\n apiOrigin: string\n issuer: string\n sub?: string\n email?: string\n activeTenant?: { id: string; slug: string }\n meta?: { fetchedAt: string; doc: unknown }\n}\n\nexport type QoreConfig = {\n schemaVersion: 1\n defaultProfile?: string\n profiles: Record<string, ProfileRecord>\n updateCheck?: { lastCheckedAt: string; latest: string }\n trustedRepos?: Record<string, string[]>\n}\n\nconst empty = (): QoreConfig => ({ schemaVersion: 1, profiles: {} })\n\nexport class ConfigStore {\n constructor(readonly dir: string) {}\n\n private get file() { return join(this.dir, \"config.json\") }\n\n async read(): Promise<QoreConfig> {\n let raw: string\n try {\n raw = await readFile(this.file, \"utf8\")\n } catch (e) {\n if ((e as NodeJS.ErrnoException).code === \"ENOENT\") return empty()\n throw e\n }\n try {\n const parsed = JSON.parse(raw) as QoreConfig\n if (parsed.schemaVersion !== 1 || typeof parsed.profiles !== \"object\") throw new Error(\"shape\")\n return parsed\n } catch (cause) {\n throw new QoreError(\"QORE_CONTEXT_INVALID\", `Qore config is malformed: ${this.file}`, {\n hint: \"Fix or delete the file, then run `qore login` again\", cause,\n })\n }\n }\n\n async update(fn: (c: QoreConfig) => QoreConfig | void): Promise<QoreConfig> {\n const current = await this.read()\n const next = fn(current) ?? current\n await writeJsonAtomic(this.dir, \"config.json\", next)\n return next\n }\n}\n","import { execFile, type ExecFileOptions } from \"node:child_process\"\nimport { homedir } from \"node:os\"\nimport { QoreError } from \"../core/errors.js\"\n\nexport type Remote = { name: string; url: string }\nexport interface Git { remotes(repoRoot: string): Promise<Remote[]> }\n\nexport function parseRemotes(stdout: string): Remote[] {\n const seen = new Set<string>()\n const out: Remote[] = []\n for (const line of stdout.split(/\\r?\\n/)) {\n const m = /^(\\S+)\\t(.+) \\(fetch\\)$/.exec(line)\n if (!m || seen.has(m[1]!)) continue\n seen.add(m[1]!)\n out.push({ name: m[1]!, url: m[2]! })\n }\n return out\n}\n\n/** Options for every git child. `cwd` is pinned to the home directory because on\n * Windows a bare \"git\" is looked up in the child's cwd before PATH: running from a\n * cloned repo would execute a git.exe planted at its top level. `-C <root>` only\n * steers git after it has started, so the repo stays the directory git works in. */\nexport function gitExecOptions(): ExecFileOptions {\n return { cwd: homedir(), env: { ...process.env, LC_ALL: \"C\" }, windowsHide: true }\n}\n\n/** `git -C <root> remote -v` — argv only, never a shell; LC_ALL=C for stable output.\n * Reading through git (not .git/config) means insteadOf rewrites and worktrees\n * behave exactly as git sees them (spec §2). */\nexport const systemGit: Git = {\n remotes(repoRoot) {\n return new Promise((resolve, reject) => {\n execFile(\"git\", [\"-C\", repoRoot, \"remote\", \"-v\"], gitExecOptions(),\n (err, stdout, stderr) => {\n if (err) {\n if ((err as NodeJS.ErrnoException).code === \"ENOENT\") {\n reject(new QoreError(\"QORE_GIT_UNAVAILABLE\", \"git is not installed or not on PATH\", {\n hint: \"Install git (https://git-scm.com/downloads) and open a new terminal.\" }))\n return\n }\n const last = String(stderr).trim().split(/\\r?\\n/).pop() ?? \"\"\n reject(new QoreError(\"QORE_INTERNAL\", `git remote -v failed in ${repoRoot}`, {\n hint: last || undefined, details: { command: \"git remote -v\", cwd: repoRoot }, cause: err }))\n return\n }\n resolve(parseRemotes(String(stdout)))\n })\n })\n },\n}\n","import { Entry } from \"@napi-rs/keyring\"\nimport { QoreError } from \"../core/errors.js\"\n\nexport interface Keychain {\n get(account: string): Promise<string | null>\n set(account: string, value: string): Promise<void>\n delete(account: string): Promise<void>\n}\n\nconst SERVICE = \"qore\"\nconst HINTS: Partial<Record<NodeJS.Platform, string>> = {\n linux: \"Install and unlock a Secret Service provider (gnome-keyring or KWallet); headless machines and containers have none.\",\n darwin: \"Unlock your login keychain in Keychain Access.\",\n win32: \"Windows Credential Manager must be available for your user.\",\n}\n\nexport function classifyKeychainError(e: unknown, platform: NodeJS.Platform): QoreError {\n const msg = e instanceof Error ? e.message : String(e)\n // keyring-rs Error::TooLong (\"… is longer than the platform limit of N chars\"): Windows\n // Credential Manager caps a credential blob (R18). Still UNAVAILABLE, but say what it is.\n if (/TooLong|longer than the platform limit/i.test(msg)) {\n return new QoreError(\"QORE_KEYCHAIN_UNAVAILABLE\", \"The session token is too large for the OS keychain\", {\n hint: platform === \"win32\"\n ? \"The token exceeds the Windows Credential Manager size limit. Report this to the Qore team.\"\n : \"The token exceeds the keychain's size limit. Report this to the Qore team.\",\n cause: e,\n })\n }\n if (/cancel|denied|errSecAuthFailed|user interaction/i.test(msg)) {\n return new QoreError(\"QORE_KEYCHAIN_DENIED\", \"Access to the OS keychain was denied\", {\n hint: \"Allow qore to use the keychain when your OS asks, then retry.\", cause: e,\n })\n }\n return new QoreError(\"QORE_KEYCHAIN_UNAVAILABLE\", \"No usable OS keychain\", {\n hint: HINTS[platform] ?? \"qore stores tokens only in the OS keychain.\", cause: e,\n })\n}\n\nexport class OsKeychain implements Keychain {\n constructor(private readonly platform: NodeJS.Platform = process.platform) {}\n\n private wrap<T>(fn: () => T): Promise<T> {\n try { return Promise.resolve(fn()) } catch (e) { return Promise.reject(classifyKeychainError(e, this.platform)) }\n }\n\n get(account: string) { return this.wrap(() => new Entry(SERVICE, account).getPassword() ?? null) }\n set(account: string, value: string) { return this.wrap(() => { new Entry(SERVICE, account).setPassword(value) }) }\n delete(account: string) {\n // deletePassword() returns false (rather than throwing) when there is no entry.\n return this.wrap(() => { new Entry(SERVICE, account).deletePassword() })\n }\n}\n","import { mkdir, writeFile } from \"node:fs/promises\"\nimport { join } from \"node:path\"\nimport lockfile from \"proper-lockfile\"\nimport { QoreError } from \"../core/errors.js\"\n\nexport type WithLock = <T>(name: string, fn: () => Promise<T>) => Promise<T>\n\nexport function fileLock(dir: string): WithLock {\n return async (name, fn) => {\n const locks = join(dir, \"locks\")\n await mkdir(locks, { recursive: true, mode: 0o700 })\n const target = join(locks, `${name}.lock`)\n await writeFile(target, \"\", { flag: \"a\" })\n let release: () => Promise<void>\n // proper-lockfile's default onCompromised throws from a timer (an uncaught crash). A\n // compromised lock (mtime update failed, or another process took it as stale) is only\n // recorded: the keychain writes under it are idempotent, and refresh re-reads the RT.\n let compromised: Error | undefined\n try {\n release = await lockfile.lock(target, {\n stale: 30_000,\n retries: { retries: 30, minTimeout: 100, maxTimeout: 1000, randomize: true },\n onCompromised: (err) => { compromised = err },\n })\n } catch (cause) {\n throw new QoreError(\"QORE_AUTH_BUSY\", \"Another qore process is refreshing the session\", { hint: \"Retry in a moment.\", cause })\n }\n try { return await fn() } finally {\n // After a compromise release() rejects (ERELEASED); that must not replace fn's outcome.\n await release().catch((e: unknown) => { if (!compromised) throw e })\n }\n }\n}\n","import { posix, win32 } from \"node:path\"\n\nexport function configDir(env: NodeJS.ProcessEnv, platform: NodeJS.Platform, home: string): string {\n if (platform === \"win32\") return win32.join(env.APPDATA ?? win32.join(home, \"AppData\", \"Roaming\"), \"qore\")\n // posix.join, not the host's join: the result is for the target platform, whatever the host\n // (tests run on Windows CI too).\n if (platform === \"darwin\") return posix.join(home, \"Library\", \"Application Support\", \"qore\")\n // XDG Base Directory spec: a relative $XDG_CONFIG_HOME is invalid and must be ignored.\n const xdg = env.XDG_CONFIG_HOME && posix.isAbsolute(env.XDG_CONFIG_HOME) ? env.XDG_CONFIG_HOME : undefined\n return posix.join(xdg ?? posix.join(home, \".config\"), \"qore\")\n}\n","import spawn from \"cross-spawn\"\nimport type { ChildProcess } from \"node:child_process\"\nimport { QoreError } from \"../core/errors.js\"\n\nexport type ChildExit = { code: number | null; signal: NodeJS.Signals | null }\nexport interface Spawner { run(cmd: string, args: string[], env: NodeJS.ProcessEnv): Promise<ChildExit> }\n\n/** Which signals `crossSpawner` ignores (left to the terminal's own process-group\n * delivery) vs. forwards to the child, per platform. Exported so tests can derive\n * the expected lists for the platform they run on instead of hard-coding POSIX's. */\nexport function signalsFor(platform: NodeJS.Platform): { ignore: NodeJS.Signals[]; forward: NodeJS.Signals[] } {\n return platform === \"win32\"\n ? { ignore: [\"SIGINT\", \"SIGBREAK\"], forward: [] }\n : { ignore: [\"SIGINT\", \"SIGQUIT\"], forward: [\"SIGTERM\", \"SIGHUP\"] }\n}\n\nconst { ignore: IGNORE, forward: FORWARD } = signalsFor(process.platform)\n\n/** The slice of `process` that `crossSpawner` touches: signal handler registration.\n * Injectable so tests can drive signal ignore/forward behaviour with a fake child and\n * a fake signal source, without sending real signals to the test runner's own process. */\nexport interface ProcessSignals {\n on(signal: NodeJS.Signals, listener: () => void): void\n off(signal: NodeJS.Signals, listener: () => void): void\n}\n\ntype SpawnFn = (cmd: string, args: string[], opts: { stdio: \"inherit\"; shell: false; env: NodeJS.ProcessEnv; windowsHide: true }) => ChildProcess\n\n/** Spec §11.2. The terminal delivers Ctrl+C / Ctrl+\\ to the whole foreground process\n * group, so forwarding them would double-signal the child: the parent only ignores\n * them and waits. SIGTERM/SIGHUP come to the parent alone and are passed on. */\nexport function makeSpawner(spawnFn: SpawnFn, proc: ProcessSignals): Spawner {\n return {\n run(cmd, args, env) {\n return new Promise((resolve, reject) => {\n let child: ChildProcess\n try {\n child = spawnFn(cmd, args, { stdio: \"inherit\", shell: false, env, windowsHide: true })\n } catch (e) {\n // Node validates `options.env` synchronously (e.g. ERR_INVALID_ARG_VALUE for a\n // NUL byte in a value) and embeds the offending value in its message — never\n // pass that message through, only the error code, same as the \"error\" path below.\n reject(new QoreError(\"QORE_INTERNAL\", `Could not start ${cmd}: ${(e as NodeJS.ErrnoException).code ?? \"error\"}`))\n return\n }\n const ignore = () => {}\n const forwarders = FORWARD.map((sig) => [sig, () => { child.kill(sig) }] as const)\n for (const sig of IGNORE) proc.on(sig, ignore)\n for (const [sig, fn] of forwarders) proc.on(sig, fn)\n const cleanup = () => {\n for (const sig of IGNORE) proc.off(sig, ignore)\n for (const [sig, fn] of forwarders) proc.off(sig, fn)\n }\n child.once(\"error\", (e: NodeJS.ErrnoException) => {\n cleanup()\n reject(e.code === \"ENOENT\"\n ? new QoreError(\"QORE_INTERNAL\", `Command not found: ${cmd}`, { hint: \"Check the command after --; it runs without a shell.\" })\n : new QoreError(\"QORE_INTERNAL\", `Could not start ${cmd}: ${e.code ?? \"error\"}`))\n })\n child.once(\"exit\", (code, signal) => { cleanup(); resolve({ code, signal }) })\n })\n },\n }\n}\n\nexport const crossSpawner: Spawner = makeSpawner(spawn, process)\n","declare const __QORE_VERSION__: string | undefined\n// tsup replaces __QORE_VERSION__ at build time; tests run from source and see \"0.0.0-dev\".\nexport const VERSION: string = typeof __QORE_VERSION__ === \"string\" ? __QORE_VERSION__ : \"0.0.0-dev\"\n"],"mappings":"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","names":["homedir","resolve","fetch","detail","pc","io","json","argv","deps","io","json","pc","randomBytes","chmod","readFile","realpath","rename","writeFile","basename","dirname","join","relative","fetch","deps","deps","join","deps","join","readFile","join","dir","TTL_MS","dir","join","sep","join","dir","deps","id","m","remote","join","deps","dirname","resolve","resolve","dirname","realpath","deps","readFile","basename","randomBytes","join","dirname","writeFile","chmod","rename","deps","io","relative","realpath","deps","io","label","deps","io","deps","deps","io","deps","io","deps","io","label","deps","io","label","deps","io","readFile","join","dir","join","readFile","resolve","mkdir","writeFile","join","dir","join","mkdir","writeFile","resolve","homedir"]}
|