#!/usr/bin/env -S node --no-warnings=DEP0040 const require = (await import('node:module')).createRequire(import.meta.url); const __chunk_filename = (await import('node:url')).fileURLToPath(import.meta.url); const __chunk_dirname = (await import('node:path')).dirname(__chunk_filename); import { BuiltinCommandLoader, CommandService, ConsolePatcher, DEFAULT_THEME, ExtensionManager, FileCommandLoader, INSTALL_WARNING_MESSAGE, McpPromptLoader, McpServerEnablementManager, RELAUNCH_EXIT_CODE, RESUME_LATEST, SessionError, SessionSelector, SettingScope, USER_SETTINGS_PATH, appEvents, canLoadServer, checkForAllExtensionUpdates, checkForExtensionUpdate, cleanupCheckpoints, cleanupExpiredSessions, cleanupToolOutputFiles, configureAllExtensions, configureExtension, configureSpecificSetting, disableSkill, enableSkill, execa, formatRelativeTime, getExtensionManager, getThemeTypeFromBackgroundColor, handleAtCommand, inferInstallMetadata, initializeApp, installSkill, isAlternateBufferEnabled, isFolderTrustEnabled, isSlashCommand, isWorkspaceTrusted, isWorktreeEnabled, linkSkill, loadSettings, loadTrustedFolders, normalizeServerId, parseSlashCommand, pickDefaultThemeName, promptForConsentNonInteractive, promptForSetting, registerCleanup, registerSyncCleanup, registerTelemetryConfig, renderSkillActionFeedback, requestConsentNonInteractive, require_semver, require_source, runExitCleanup, runSyncCleanup, saveModelChange, setupSignalHandlers, skillsConsentString, terminalCapabilityManager, themeManager, uninstallSkill, updateAllUpdatableExtensions, updateExtension, validateAuthMethod } from "./chunk-UNM3DGTG.js"; import { AuthType, ChatRecordingService, Client, Config, CoreToolCallStatus, ExitCodes, FileDiscoveryService, FolderTrustDiscoveryService, GeminiEventType, IntegrityStatus, JsonFormatter, JsonStreamEventType, LlmRole, Logger, MCPServerConfig, MCPServerStatus, OutputFormat, PolicyIntegrityManager, ROOT_SCHEDULER_ID, ReadManyFilesTool, Scheduler, SessionEndReason, SessionStartSource, ShellExecutionService, StreamEventType, StreamJsonFormatter, ToolCallEvent, UserPromptEvent, ValidationCancelledError, ValidationRequiredError, WarningPriority, addMemory, applyAdminAllowlist, applyRequiredServers, clearCachedCredentialFile, convertSessionToClientHistory, convertToFunctionResponse, createPolicyEngineConfig, createPolicyUpdater, createTransport, createWorkingStdio, createWorktreeService, detectIdeFromEnv, external_exports as external_exports2, generateSummary, getAdminBlockedMcpServersMessage, getAdminErrorMessage, getAuthTypeFromEnv, getCheckpointInfoList, getCompatibilityWarnings, getErrorStatus, getOauthClient, getPackageJson, getProjectRootForWorktree, getPty, getRealPath, getToolCallDataSchema, getVersion, isGeminiWorktree, isHeadlessMode, isWithinRoot, listExtensions, listMemoryFiles, logToolCall, logUserPrompt, parseAndFormatApiError, partListUnionToString, patchStdio, performInit, performRestore, promptIdContext, recordToolCallInteractions, refreshMemory, require_shell_quote, require_strip_json_comments, resolveTelemetrySettings, sessionId, shouldEnterAlternateScreen, showMemory, startupProfiler, stripAnsi, uiTelemetryService, writeToStderr, writeToStdout } from "./chunk-QVTX2M5J.js"; import { ASK_USER_TOOL_NAME, ApprovalMode, CoreEvent, DEFAULT_FILE_FILTERING_OPTIONS, DEFAULT_GEMINI_EMBEDDING_MODEL, DEFAULT_GEMINI_FLASH_LITE_MODEL, DEFAULT_GEMINI_FLASH_MODEL, DEFAULT_GEMINI_MODEL, DEFAULT_GEMINI_MODEL_AUTO, DEFAULT_MEMORY_FILE_FILTERING_OPTIONS, DiscoveredMCPTool, FatalCancellationError, FatalConfigError, FatalError, FatalInputError, FatalSandboxError, FatalToolExecutionError, FatalTurnLimitedError, GEMINI_DIR, GEMINI_MODEL_ALIAS_AUTO, Kind, PREVIEW_GEMINI_3_1_CUSTOM_TOOLS_MODEL, PREVIEW_GEMINI_3_1_MODEL, PREVIEW_GEMINI_FLASH_MODEL, PREVIEW_GEMINI_MODEL, PREVIEW_GEMINI_MODEL_AUTO, REFERENCE_CONTENT_START, Storage, ToolConfirmationOutcome, ToolErrorType, coreEvents, debugLogger, external_exports, getCurrentGeminiMdFilename, getDisplayString, getErrorMessage, homedir, isFatalToolError, isNodeError, loadServerHierarchicalMemory, resolveModel, resolveToRealPath, setGeminiMdFilename } from "./chunk-S2IQOR7T.js"; import "./chunk-664ZODQF.js"; import "./chunk-RJTRUG2J.js"; import "./chunk-IUUIT4SU.js"; import { __commonJS, __require, __toESM } from "./chunk-34MYV7JD.js"; // node_modules/command-exists/lib/command-exists.js var require_command_exists = __commonJS({ "node_modules/command-exists/lib/command-exists.js"(exports, module) { "use strict"; var exec2 = __require("child_process").exec; var execSync2 = __require("child_process").execSync; var fs11 = __require("fs"); var path14 = __require("path"); var access2 = fs11.access; var accessSync = fs11.accessSync; var constants = fs11.constants || fs11; var isUsingWindows = process.platform == "win32"; var fileNotExists = function(commandName, callback) { access2( commandName, constants.F_OK, function(err) { callback(!err); } ); }; var fileNotExistsSync = function(commandName) { try { accessSync(commandName, constants.F_OK); return false; } catch (e) { return true; } }; var localExecutable = function(commandName, callback) { access2( commandName, constants.F_OK | constants.X_OK, function(err) { callback(null, !err); } ); }; var localExecutableSync = function(commandName) { try { accessSync(commandName, constants.F_OK | constants.X_OK); return true; } catch (e) { return false; } }; var commandExistsUnix = function(commandName, cleanedCommandName, callback) { fileNotExists(commandName, function(isFile) { if (!isFile) { var child = exec2( "command -v " + cleanedCommandName + " 2>/dev/null && { echo >&1 " + cleanedCommandName + "; exit 0; }", function(error, stdout, stderr) { callback(null, !!stdout); } ); return; } localExecutable(commandName, callback); }); }; var commandExistsWindows = function(commandName, cleanedCommandName, callback) { if (!/^(?!(?:.*\s|.*\.|\W+)$)(?:[a-zA-Z]:)?(?:(?:[^<>:"\|\?\*\n])+(?:\/\/|\/|\\\\|\\)?)+$/m.test(commandName)) { callback(null, false); return; } var child = exec2( "where " + cleanedCommandName, function(error) { if (error !== null) { callback(null, false); } else { callback(null, true); } } ); }; var commandExistsUnixSync = function(commandName, cleanedCommandName) { if (fileNotExistsSync(commandName)) { try { var stdout = execSync2( "command -v " + cleanedCommandName + " 2>/dev/null && { echo >&1 " + cleanedCommandName + "; exit 0; }" ); return !!stdout; } catch (error) { return false; } } return localExecutableSync(commandName); }; var commandExistsWindowsSync = function(commandName, cleanedCommandName, callback) { if (!/^(?!(?:.*\s|.*\.|\W+)$)(?:[a-zA-Z]:)?(?:(?:[^<>:"\|\?\*\n])+(?:\/\/|\/|\\\\|\\)?)+$/m.test(commandName)) { return false; } try { var stdout = execSync2("where " + cleanedCommandName, { stdio: [] }); return !!stdout; } catch (error) { return false; } }; var cleanInput = function(s) { if (/[^A-Za-z0-9_\/:=-]/.test(s)) { s = "'" + s.replace(/'/g, "'\\''") + "'"; s = s.replace(/^(?:'')+/g, "").replace(/\\'''/g, "\\'"); } return s; }; if (isUsingWindows) { cleanInput = function(s) { var isPathName = /[\\]/.test(s); if (isPathName) { var dirname4 = '"' + path14.dirname(s) + '"'; var basename4 = '"' + path14.basename(s) + '"'; return dirname4 + ":" + basename4; } return '"' + s + '"'; }; } module.exports = function commandExists2(commandName, callback) { var cleanedCommandName = cleanInput(commandName); if (!callback && typeof Promise !== "undefined") { return new Promise(function(resolve9, reject) { commandExists2(commandName, function(error, output) { if (output) { resolve9(commandName); } else { reject(error); } }); }); } if (isUsingWindows) { commandExistsWindows(commandName, cleanedCommandName, callback); } else { commandExistsUnix(commandName, cleanedCommandName, callback); } }; module.exports.sync = function(commandName) { var cleanedCommandName = cleanInput(commandName); if (isUsingWindows) { return commandExistsWindowsSync(commandName, cleanedCommandName); } else { return commandExistsUnixSync(commandName, cleanedCommandName); } }; } }); // node_modules/command-exists/index.js var require_command_exists2 = __commonJS({ "node_modules/command-exists/index.js"(exports, module) { module.exports = require_command_exists(); } }); // node_modules/yargs/lib/platform-shims/esm.mjs import { notStrictEqual, strictEqual } from "assert"; // node_modules/cliui/build/lib/index.js var align = { right: alignRight, center: alignCenter }; var top = 0; var right = 1; var bottom = 2; var left = 3; var UI = class { constructor(opts) { var _a2; this.width = opts.width; this.wrap = (_a2 = opts.wrap) !== null && _a2 !== void 0 ? _a2 : true; this.rows = []; } span(...args) { const cols = this.div(...args); cols.span = true; } resetOutput() { this.rows = []; } div(...args) { if (args.length === 0) { this.div(""); } if (this.wrap && this.shouldApplyLayoutDSL(...args) && typeof args[0] === "string") { return this.applyLayoutDSL(args[0]); } const cols = args.map((arg) => { if (typeof arg === "string") { return this.colFromString(arg); } return arg; }); this.rows.push(cols); return cols; } shouldApplyLayoutDSL(...args) { return args.length === 1 && typeof args[0] === "string" && /[\t\n]/.test(args[0]); } applyLayoutDSL(str) { const rows = str.split("\n").map((row) => row.split(" ")); let leftColumnWidth = 0; rows.forEach((columns) => { if (columns.length > 1 && mixin.stringWidth(columns[0]) > leftColumnWidth) { leftColumnWidth = Math.min(Math.floor(this.width * 0.5), mixin.stringWidth(columns[0])); } }); rows.forEach((columns) => { this.div(...columns.map((r, i) => { return { text: r.trim(), padding: this.measurePadding(r), width: i === 0 && columns.length > 1 ? leftColumnWidth : void 0 }; })); }); return this.rows[this.rows.length - 1]; } colFromString(text) { return { text, padding: this.measurePadding(text) }; } measurePadding(str) { const noAnsi = mixin.stripAnsi(str); return [0, noAnsi.match(/\s*$/)[0].length, 0, noAnsi.match(/^\s*/)[0].length]; } toString() { const lines = []; this.rows.forEach((row) => { this.rowToString(row, lines); }); return lines.filter((line) => !line.hidden).map((line) => line.text).join("\n"); } rowToString(row, lines) { this.rasterize(row).forEach((rrow, r) => { let str = ""; rrow.forEach((col, c) => { const { width } = row[c]; const wrapWidth = this.negatePadding(row[c]); let ts = col; if (wrapWidth > mixin.stringWidth(col)) { ts += " ".repeat(wrapWidth - mixin.stringWidth(col)); } if (row[c].align && row[c].align !== "left" && this.wrap) { const fn = align[row[c].align]; ts = fn(ts, wrapWidth); if (mixin.stringWidth(ts) < wrapWidth) { ts += " ".repeat((width || 0) - mixin.stringWidth(ts) - 1); } } const padding = row[c].padding || [0, 0, 0, 0]; if (padding[left]) { str += " ".repeat(padding[left]); } str += addBorder(row[c], ts, "| "); str += ts; str += addBorder(row[c], ts, " |"); if (padding[right]) { str += " ".repeat(padding[right]); } if (r === 0 && lines.length > 0) { str = this.renderInline(str, lines[lines.length - 1]); } }); lines.push({ text: str.replace(/ +$/, ""), span: row.span }); }); return lines; } // if the full 'source' can render in // the target line, do so. renderInline(source, previousLine) { const match = source.match(/^ */); const leadingWhitespace = match ? match[0].length : 0; const target = previousLine.text; const targetTextWidth = mixin.stringWidth(target.trimRight()); if (!previousLine.span) { return source; } if (!this.wrap) { previousLine.hidden = true; return target + source; } if (leadingWhitespace < targetTextWidth) { return source; } previousLine.hidden = true; return target.trimRight() + " ".repeat(leadingWhitespace - targetTextWidth) + source.trimLeft(); } rasterize(row) { const rrows = []; const widths = this.columnWidths(row); let wrapped; row.forEach((col, c) => { col.width = widths[c]; if (this.wrap) { wrapped = mixin.wrap(col.text, this.negatePadding(col), { hard: true }).split("\n"); } else { wrapped = col.text.split("\n"); } if (col.border) { wrapped.unshift("." + "-".repeat(this.negatePadding(col) + 2) + "."); wrapped.push("'" + "-".repeat(this.negatePadding(col) + 2) + "'"); } if (col.padding) { wrapped.unshift(...new Array(col.padding[top] || 0).fill("")); wrapped.push(...new Array(col.padding[bottom] || 0).fill("")); } wrapped.forEach((str, r) => { if (!rrows[r]) { rrows.push([]); } const rrow = rrows[r]; for (let i = 0; i < c; i++) { if (rrow[i] === void 0) { rrow.push(""); } } rrow.push(str); }); }); return rrows; } negatePadding(col) { let wrapWidth = col.width || 0; if (col.padding) { wrapWidth -= (col.padding[left] || 0) + (col.padding[right] || 0); } if (col.border) { wrapWidth -= 4; } return wrapWidth; } columnWidths(row) { if (!this.wrap) { return row.map((col) => { return col.width || mixin.stringWidth(col.text); }); } let unset = row.length; let remainingWidth = this.width; const widths = row.map((col) => { if (col.width) { unset--; remainingWidth -= col.width; return col.width; } return void 0; }); const unsetWidth = unset ? Math.floor(remainingWidth / unset) : 0; return widths.map((w, i) => { if (w === void 0) { return Math.max(unsetWidth, _minWidth(row[i])); } return w; }); } }; function addBorder(col, ts, style) { if (col.border) { if (/[.']-+[.']/.test(ts)) { return ""; } if (ts.trim().length !== 0) { return style; } return " "; } return ""; } function _minWidth(col) { const padding = col.padding || []; const minWidth = 1 + (padding[left] || 0) + (padding[right] || 0); if (col.border) { return minWidth + 4; } return minWidth; } function getWindowWidth() { if (typeof process === "object" && process.stdout && process.stdout.columns) { return process.stdout.columns; } return 80; } function alignRight(str, width) { str = str.trim(); const strWidth = mixin.stringWidth(str); if (strWidth < width) { return " ".repeat(width - strWidth) + str; } return str; } function alignCenter(str, width) { str = str.trim(); const strWidth = mixin.stringWidth(str); if (strWidth >= width) { return str; } return " ".repeat(width - strWidth >> 1) + str; } var mixin; function cliui(opts, _mixin) { mixin = _mixin; return new UI({ width: (opts === null || opts === void 0 ? void 0 : opts.width) || getWindowWidth(), wrap: opts === null || opts === void 0 ? void 0 : opts.wrap }); } // node_modules/cliui/build/lib/string-utils.js var ansi = new RegExp("\x1B(?:\\[(?:\\d+[ABCDEFGJKSTm]|\\d+;\\d+[Hfm]|\\d+;\\d+;\\d+m|6n|s|u|\\?25[lh])|\\w)", "g"); function stripAnsi2(str) { return str.replace(ansi, ""); } function wrap(str, width) { const [start, end] = str.match(ansi) || ["", ""]; str = stripAnsi2(str); let wrapped = ""; for (let i = 0; i < str.length; i++) { if (i !== 0 && i % width === 0) { wrapped += "\n"; } wrapped += str.charAt(i); } if (start && end) { wrapped = `${start}${wrapped}${end}`; } return wrapped; } // node_modules/cliui/index.mjs function ui(opts) { return cliui(opts, { stringWidth: (str) => { return [...str].length; }, stripAnsi: stripAnsi2, wrap }); } // node_modules/escalade/sync/index.mjs import { dirname, resolve } from "path"; import { readdirSync, statSync } from "fs"; function sync_default(start, callback) { let dir = resolve(".", start); let tmp, stats = statSync(dir); if (!stats.isDirectory()) { dir = dirname(dir); } while (true) { tmp = callback(dir, readdirSync(dir)); if (tmp) return resolve(dir, tmp); dir = dirname(tmp = dir); if (tmp === dir) break; } } // node_modules/yargs/lib/platform-shims/esm.mjs import { inspect } from "util"; import { readFileSync as readFileSync3 } from "fs"; import { fileURLToPath } from "url"; // node_modules/yargs-parser/build/lib/index.js import { format } from "util"; import { normalize, resolve as resolve2 } from "path"; // node_modules/yargs-parser/build/lib/string-utils.js function camelCase(str) { const isCamelCase = str !== str.toLowerCase() && str !== str.toUpperCase(); if (!isCamelCase) { str = str.toLowerCase(); } if (str.indexOf("-") === -1 && str.indexOf("_") === -1) { return str; } else { let camelcase = ""; let nextChrUpper = false; const leadingHyphens = str.match(/^-+/); for (let i = leadingHyphens ? leadingHyphens[0].length : 0; i < str.length; i++) { let chr = str.charAt(i); if (nextChrUpper) { nextChrUpper = false; chr = chr.toUpperCase(); } if (i !== 0 && (chr === "-" || chr === "_")) { nextChrUpper = true; } else if (chr !== "-" && chr !== "_") { camelcase += chr; } } return camelcase; } } function decamelize(str, joinString) { const lowercase = str.toLowerCase(); joinString = joinString || "-"; let notCamelcase = ""; for (let i = 0; i < str.length; i++) { const chrLower = lowercase.charAt(i); const chrString = str.charAt(i); if (chrLower !== chrString && i > 0) { notCamelcase += `${joinString}${lowercase.charAt(i)}`; } else { notCamelcase += chrString; } } return notCamelcase; } function looksLikeNumber(x) { if (x === null || x === void 0) return false; if (typeof x === "number") return true; if (/^0x[0-9a-f]+$/i.test(x)) return true; if (/^0[^.]/.test(x)) return false; return /^[-]?(?:\d+(?:\.\d*)?|\.\d+)(e[-+]?\d+)?$/.test(x); } // node_modules/yargs-parser/build/lib/tokenize-arg-string.js function tokenizeArgString(argString) { if (Array.isArray(argString)) { return argString.map((e) => typeof e !== "string" ? e + "" : e); } argString = argString.trim(); let i = 0; let prevC = null; let c = null; let opening = null; const args = []; for (let ii = 0; ii < argString.length; ii++) { prevC = c; c = argString.charAt(ii); if (c === " " && !opening) { if (!(prevC === " ")) { i++; } continue; } if (c === opening) { opening = null; } else if ((c === "'" || c === '"') && !opening) { opening = c; } if (!args[i]) args[i] = ""; args[i] += c; } return args; } // node_modules/yargs-parser/build/lib/yargs-parser-types.js var DefaultValuesForTypeKey; (function(DefaultValuesForTypeKey2) { DefaultValuesForTypeKey2["BOOLEAN"] = "boolean"; DefaultValuesForTypeKey2["STRING"] = "string"; DefaultValuesForTypeKey2["NUMBER"] = "number"; DefaultValuesForTypeKey2["ARRAY"] = "array"; })(DefaultValuesForTypeKey || (DefaultValuesForTypeKey = {})); // node_modules/yargs-parser/build/lib/yargs-parser.js var mixin2; var YargsParser = class { constructor(_mixin) { mixin2 = _mixin; } parse(argsInput, options) { const opts = Object.assign({ alias: void 0, array: void 0, boolean: void 0, config: void 0, configObjects: void 0, configuration: void 0, coerce: void 0, count: void 0, default: void 0, envPrefix: void 0, narg: void 0, normalize: void 0, string: void 0, number: void 0, __: void 0, key: void 0 }, options); const args = tokenizeArgString(argsInput); const inputIsString = typeof argsInput === "string"; const aliases = combineAliases(Object.assign(/* @__PURE__ */ Object.create(null), opts.alias)); const configuration = Object.assign({ "boolean-negation": true, "camel-case-expansion": true, "combine-arrays": false, "dot-notation": true, "duplicate-arguments-array": true, "flatten-duplicate-arrays": true, "greedy-arrays": true, "halt-at-non-option": false, "nargs-eats-options": false, "negation-prefix": "no-", "parse-numbers": true, "parse-positional-numbers": true, "populate--": false, "set-placeholder-key": false, "short-option-groups": true, "strip-aliased": false, "strip-dashed": false, "unknown-options-as-args": false }, opts.configuration); const defaults = Object.assign(/* @__PURE__ */ Object.create(null), opts.default); const configObjects = opts.configObjects || []; const envPrefix = opts.envPrefix; const notFlagsOption = configuration["populate--"]; const notFlagsArgv = notFlagsOption ? "--" : "_"; const newAliases = /* @__PURE__ */ Object.create(null); const defaulted = /* @__PURE__ */ Object.create(null); const __ = opts.__ || mixin2.format; const flags = { aliases: /* @__PURE__ */ Object.create(null), arrays: /* @__PURE__ */ Object.create(null), bools: /* @__PURE__ */ Object.create(null), strings: /* @__PURE__ */ Object.create(null), numbers: /* @__PURE__ */ Object.create(null), counts: /* @__PURE__ */ Object.create(null), normalize: /* @__PURE__ */ Object.create(null), configs: /* @__PURE__ */ Object.create(null), nargs: /* @__PURE__ */ Object.create(null), coercions: /* @__PURE__ */ Object.create(null), keys: [] }; const negative = /^-([0-9]+(\.[0-9]+)?|\.[0-9]+)$/; const negatedBoolean = new RegExp("^--" + configuration["negation-prefix"] + "(.+)"); [].concat(opts.array || []).filter(Boolean).forEach(function(opt) { const key = typeof opt === "object" ? opt.key : opt; const assignment = Object.keys(opt).map(function(key2) { const arrayFlagKeys = { boolean: "bools", string: "strings", number: "numbers" }; return arrayFlagKeys[key2]; }).filter(Boolean).pop(); if (assignment) { flags[assignment][key] = true; } flags.arrays[key] = true; flags.keys.push(key); }); [].concat(opts.boolean || []).filter(Boolean).forEach(function(key) { flags.bools[key] = true; flags.keys.push(key); }); [].concat(opts.string || []).filter(Boolean).forEach(function(key) { flags.strings[key] = true; flags.keys.push(key); }); [].concat(opts.number || []).filter(Boolean).forEach(function(key) { flags.numbers[key] = true; flags.keys.push(key); }); [].concat(opts.count || []).filter(Boolean).forEach(function(key) { flags.counts[key] = true; flags.keys.push(key); }); [].concat(opts.normalize || []).filter(Boolean).forEach(function(key) { flags.normalize[key] = true; flags.keys.push(key); }); if (typeof opts.narg === "object") { Object.entries(opts.narg).forEach(([key, value]) => { if (typeof value === "number") { flags.nargs[key] = value; flags.keys.push(key); } }); } if (typeof opts.coerce === "object") { Object.entries(opts.coerce).forEach(([key, value]) => { if (typeof value === "function") { flags.coercions[key] = value; flags.keys.push(key); } }); } if (typeof opts.config !== "undefined") { if (Array.isArray(opts.config) || typeof opts.config === "string") { ; [].concat(opts.config).filter(Boolean).forEach(function(key) { flags.configs[key] = true; }); } else if (typeof opts.config === "object") { Object.entries(opts.config).forEach(([key, value]) => { if (typeof value === "boolean" || typeof value === "function") { flags.configs[key] = value; } }); } } extendAliases(opts.key, aliases, opts.default, flags.arrays); Object.keys(defaults).forEach(function(key) { (flags.aliases[key] || []).forEach(function(alias) { defaults[alias] = defaults[key]; }); }); let error = null; checkConfiguration(); let notFlags = []; const argv = Object.assign(/* @__PURE__ */ Object.create(null), { _: [] }); const argvReturn = {}; for (let i = 0; i < args.length; i++) { const arg = args[i]; const truncatedArg = arg.replace(/^-{3,}/, "---"); let broken; let key; let letters; let m; let next; let value; if (arg !== "--" && /^-/.test(arg) && isUnknownOptionAsArg(arg)) { pushPositional(arg); } else if (truncatedArg.match(/^---+(=|$)/)) { pushPositional(arg); continue; } else if (arg.match(/^--.+=/) || !configuration["short-option-groups"] && arg.match(/^-.+=/)) { m = arg.match(/^--?([^=]+)=([\s\S]*)$/); if (m !== null && Array.isArray(m) && m.length >= 3) { if (checkAllAliases(m[1], flags.arrays)) { i = eatArray(i, m[1], args, m[2]); } else if (checkAllAliases(m[1], flags.nargs) !== false) { i = eatNargs(i, m[1], args, m[2]); } else { setArg(m[1], m[2], true); } } } else if (arg.match(negatedBoolean) && configuration["boolean-negation"]) { m = arg.match(negatedBoolean); if (m !== null && Array.isArray(m) && m.length >= 2) { key = m[1]; setArg(key, checkAllAliases(key, flags.arrays) ? [false] : false); } } else if (arg.match(/^--.+/) || !configuration["short-option-groups"] && arg.match(/^-[^-]+/)) { m = arg.match(/^--?(.+)/); if (m !== null && Array.isArray(m) && m.length >= 2) { key = m[1]; if (checkAllAliases(key, flags.arrays)) { i = eatArray(i, key, args); } else if (checkAllAliases(key, flags.nargs) !== false) { i = eatNargs(i, key, args); } else { next = args[i + 1]; if (next !== void 0 && (!next.match(/^-/) || next.match(negative)) && !checkAllAliases(key, flags.bools) && !checkAllAliases(key, flags.counts)) { setArg(key, next); i++; } else if (/^(true|false)$/.test(next)) { setArg(key, next); i++; } else { setArg(key, defaultValue(key)); } } } } else if (arg.match(/^-.\..+=/)) { m = arg.match(/^-([^=]+)=([\s\S]*)$/); if (m !== null && Array.isArray(m) && m.length >= 3) { setArg(m[1], m[2]); } } else if (arg.match(/^-.\..+/) && !arg.match(negative)) { next = args[i + 1]; m = arg.match(/^-(.\..+)/); if (m !== null && Array.isArray(m) && m.length >= 2) { key = m[1]; if (next !== void 0 && !next.match(/^-/) && !checkAllAliases(key, flags.bools) && !checkAllAliases(key, flags.counts)) { setArg(key, next); i++; } else { setArg(key, defaultValue(key)); } } } else if (arg.match(/^-[^-]+/) && !arg.match(negative)) { letters = arg.slice(1, -1).split(""); broken = false; for (let j = 0; j < letters.length; j++) { next = arg.slice(j + 2); if (letters[j + 1] && letters[j + 1] === "=") { value = arg.slice(j + 3); key = letters[j]; if (checkAllAliases(key, flags.arrays)) { i = eatArray(i, key, args, value); } else if (checkAllAliases(key, flags.nargs) !== false) { i = eatNargs(i, key, args, value); } else { setArg(key, value); } broken = true; break; } if (next === "-") { setArg(letters[j], next); continue; } if (/[A-Za-z]/.test(letters[j]) && /^-?\d+(\.\d*)?(e-?\d+)?$/.test(next) && checkAllAliases(next, flags.bools) === false) { setArg(letters[j], next); broken = true; break; } if (letters[j + 1] && letters[j + 1].match(/\W/)) { setArg(letters[j], next); broken = true; break; } else { setArg(letters[j], defaultValue(letters[j])); } } key = arg.slice(-1)[0]; if (!broken && key !== "-") { if (checkAllAliases(key, flags.arrays)) { i = eatArray(i, key, args); } else if (checkAllAliases(key, flags.nargs) !== false) { i = eatNargs(i, key, args); } else { next = args[i + 1]; if (next !== void 0 && (!/^(-|--)[^-]/.test(next) || next.match(negative)) && !checkAllAliases(key, flags.bools) && !checkAllAliases(key, flags.counts)) { setArg(key, next); i++; } else if (/^(true|false)$/.test(next)) { setArg(key, next); i++; } else { setArg(key, defaultValue(key)); } } } } else if (arg.match(/^-[0-9]$/) && arg.match(negative) && checkAllAliases(arg.slice(1), flags.bools)) { key = arg.slice(1); setArg(key, defaultValue(key)); } else if (arg === "--") { notFlags = args.slice(i + 1); break; } else if (configuration["halt-at-non-option"]) { notFlags = args.slice(i); break; } else { pushPositional(arg); } } applyEnvVars(argv, true); applyEnvVars(argv, false); setConfig(argv); setConfigObjects(); applyDefaultsAndAliases(argv, flags.aliases, defaults, true); applyCoercions(argv); if (configuration["set-placeholder-key"]) setPlaceholderKeys(argv); Object.keys(flags.counts).forEach(function(key) { if (!hasKey(argv, key.split("."))) setArg(key, 0); }); if (notFlagsOption && notFlags.length) argv[notFlagsArgv] = []; notFlags.forEach(function(key) { argv[notFlagsArgv].push(key); }); if (configuration["camel-case-expansion"] && configuration["strip-dashed"]) { Object.keys(argv).filter((key) => key !== "--" && key.includes("-")).forEach((key) => { delete argv[key]; }); } if (configuration["strip-aliased"]) { ; [].concat(...Object.keys(aliases).map((k) => aliases[k])).forEach((alias) => { if (configuration["camel-case-expansion"] && alias.includes("-")) { delete argv[alias.split(".").map((prop) => camelCase(prop)).join(".")]; } delete argv[alias]; }); } function pushPositional(arg) { const maybeCoercedNumber = maybeCoerceNumber("_", arg); if (typeof maybeCoercedNumber === "string" || typeof maybeCoercedNumber === "number") { argv._.push(maybeCoercedNumber); } } function eatNargs(i, key, args2, argAfterEqualSign) { let ii; let toEat = checkAllAliases(key, flags.nargs); toEat = typeof toEat !== "number" || isNaN(toEat) ? 1 : toEat; if (toEat === 0) { if (!isUndefined(argAfterEqualSign)) { error = Error(__("Argument unexpected for: %s", key)); } setArg(key, defaultValue(key)); return i; } let available = isUndefined(argAfterEqualSign) ? 0 : 1; if (configuration["nargs-eats-options"]) { if (args2.length - (i + 1) + available < toEat) { error = Error(__("Not enough arguments following: %s", key)); } available = toEat; } else { for (ii = i + 1; ii < args2.length; ii++) { if (!args2[ii].match(/^-[^0-9]/) || args2[ii].match(negative) || isUnknownOptionAsArg(args2[ii])) available++; else break; } if (available < toEat) error = Error(__("Not enough arguments following: %s", key)); } let consumed = Math.min(available, toEat); if (!isUndefined(argAfterEqualSign) && consumed > 0) { setArg(key, argAfterEqualSign); consumed--; } for (ii = i + 1; ii < consumed + i + 1; ii++) { setArg(key, args2[ii]); } return i + consumed; } function eatArray(i, key, args2, argAfterEqualSign) { let argsToSet = []; let next = argAfterEqualSign || args2[i + 1]; const nargsCount = checkAllAliases(key, flags.nargs); if (checkAllAliases(key, flags.bools) && !/^(true|false)$/.test(next)) { argsToSet.push(true); } else if (isUndefined(next) || isUndefined(argAfterEqualSign) && /^-/.test(next) && !negative.test(next) && !isUnknownOptionAsArg(next)) { if (defaults[key] !== void 0) { const defVal = defaults[key]; argsToSet = Array.isArray(defVal) ? defVal : [defVal]; } } else { if (!isUndefined(argAfterEqualSign)) { argsToSet.push(processValue(key, argAfterEqualSign, true)); } for (let ii = i + 1; ii < args2.length; ii++) { if (!configuration["greedy-arrays"] && argsToSet.length > 0 || nargsCount && typeof nargsCount === "number" && argsToSet.length >= nargsCount) break; next = args2[ii]; if (/^-/.test(next) && !negative.test(next) && !isUnknownOptionAsArg(next)) break; i = ii; argsToSet.push(processValue(key, next, inputIsString)); } } if (typeof nargsCount === "number" && (nargsCount && argsToSet.length < nargsCount || isNaN(nargsCount) && argsToSet.length === 0)) { error = Error(__("Not enough arguments following: %s", key)); } setArg(key, argsToSet); return i; } function setArg(key, val, shouldStripQuotes = inputIsString) { if (/-/.test(key) && configuration["camel-case-expansion"]) { const alias = key.split(".").map(function(prop) { return camelCase(prop); }).join("."); addNewAlias(key, alias); } const value = processValue(key, val, shouldStripQuotes); const splitKey = key.split("."); setKey(argv, splitKey, value); if (flags.aliases[key]) { flags.aliases[key].forEach(function(x) { const keyProperties = x.split("."); setKey(argv, keyProperties, value); }); } if (splitKey.length > 1 && configuration["dot-notation"]) { ; (flags.aliases[splitKey[0]] || []).forEach(function(x) { let keyProperties = x.split("."); const a = [].concat(splitKey); a.shift(); keyProperties = keyProperties.concat(a); if (!(flags.aliases[key] || []).includes(keyProperties.join("."))) { setKey(argv, keyProperties, value); } }); } if (checkAllAliases(key, flags.normalize) && !checkAllAliases(key, flags.arrays)) { const keys = [key].concat(flags.aliases[key] || []); keys.forEach(function(key2) { Object.defineProperty(argvReturn, key2, { enumerable: true, get() { return val; }, set(value2) { val = typeof value2 === "string" ? mixin2.normalize(value2) : value2; } }); }); } } function addNewAlias(key, alias) { if (!(flags.aliases[key] && flags.aliases[key].length)) { flags.aliases[key] = [alias]; newAliases[alias] = true; } if (!(flags.aliases[alias] && flags.aliases[alias].length)) { addNewAlias(alias, key); } } function processValue(key, val, shouldStripQuotes) { if (shouldStripQuotes) { val = stripQuotes(val); } if (checkAllAliases(key, flags.bools) || checkAllAliases(key, flags.counts)) { if (typeof val === "string") val = val === "true"; } let value = Array.isArray(val) ? val.map(function(v) { return maybeCoerceNumber(key, v); }) : maybeCoerceNumber(key, val); if (checkAllAliases(key, flags.counts) && (isUndefined(value) || typeof value === "boolean")) { value = increment(); } if (checkAllAliases(key, flags.normalize) && checkAllAliases(key, flags.arrays)) { if (Array.isArray(val)) value = val.map((val2) => { return mixin2.normalize(val2); }); else value = mixin2.normalize(val); } return value; } function maybeCoerceNumber(key, value) { if (!configuration["parse-positional-numbers"] && key === "_") return value; if (!checkAllAliases(key, flags.strings) && !checkAllAliases(key, flags.bools) && !Array.isArray(value)) { const shouldCoerceNumber = looksLikeNumber(value) && configuration["parse-numbers"] && Number.isSafeInteger(Math.floor(parseFloat(`${value}`))); if (shouldCoerceNumber || !isUndefined(value) && checkAllAliases(key, flags.numbers)) { value = Number(value); } } return value; } function setConfig(argv2) { const configLookup = /* @__PURE__ */ Object.create(null); applyDefaultsAndAliases(configLookup, flags.aliases, defaults); Object.keys(flags.configs).forEach(function(configKey) { const configPath = argv2[configKey] || configLookup[configKey]; if (configPath) { try { let config = null; const resolvedConfigPath = mixin2.resolve(mixin2.cwd(), configPath); const resolveConfig = flags.configs[configKey]; if (typeof resolveConfig === "function") { try { config = resolveConfig(resolvedConfigPath); } catch (e) { config = e; } if (config instanceof Error) { error = config; return; } } else { config = mixin2.require(resolvedConfigPath); } setConfigObject(config); } catch (ex) { if (ex.name === "PermissionDenied") error = ex; else if (argv2[configKey]) error = Error(__("Invalid JSON config file: %s", configPath)); } } }); } function setConfigObject(config, prev) { Object.keys(config).forEach(function(key) { const value = config[key]; const fullKey = prev ? prev + "." + key : key; if (typeof value === "object" && value !== null && !Array.isArray(value) && configuration["dot-notation"]) { setConfigObject(value, fullKey); } else { if (!hasKey(argv, fullKey.split(".")) || checkAllAliases(fullKey, flags.arrays) && configuration["combine-arrays"]) { setArg(fullKey, value); } } }); } function setConfigObjects() { if (typeof configObjects !== "undefined") { configObjects.forEach(function(configObject) { setConfigObject(configObject); }); } } function applyEnvVars(argv2, configOnly) { if (typeof envPrefix === "undefined") return; const prefix = typeof envPrefix === "string" ? envPrefix : ""; const env2 = mixin2.env(); Object.keys(env2).forEach(function(envVar) { if (prefix === "" || envVar.lastIndexOf(prefix, 0) === 0) { const keys = envVar.split("__").map(function(key, i) { if (i === 0) { key = key.substring(prefix.length); } return camelCase(key); }); if ((configOnly && flags.configs[keys.join(".")] || !configOnly) && !hasKey(argv2, keys)) { setArg(keys.join("."), env2[envVar]); } } }); } function applyCoercions(argv2) { let coerce; const applied = /* @__PURE__ */ new Set(); Object.keys(argv2).forEach(function(key) { if (!applied.has(key)) { coerce = checkAllAliases(key, flags.coercions); if (typeof coerce === "function") { try { const value = maybeCoerceNumber(key, coerce(argv2[key])); [].concat(flags.aliases[key] || [], key).forEach((ali) => { applied.add(ali); argv2[ali] = value; }); } catch (err) { error = err; } } } }); } function setPlaceholderKeys(argv2) { flags.keys.forEach((key) => { if (~key.indexOf(".")) return; if (typeof argv2[key] === "undefined") argv2[key] = void 0; }); return argv2; } function applyDefaultsAndAliases(obj, aliases2, defaults2, canLog = false) { Object.keys(defaults2).forEach(function(key) { if (!hasKey(obj, key.split("."))) { setKey(obj, key.split("."), defaults2[key]); if (canLog) defaulted[key] = true; (aliases2[key] || []).forEach(function(x) { if (hasKey(obj, x.split("."))) return; setKey(obj, x.split("."), defaults2[key]); }); } }); } function hasKey(obj, keys) { let o = obj; if (!configuration["dot-notation"]) keys = [keys.join(".")]; keys.slice(0, -1).forEach(function(key2) { o = o[key2] || {}; }); const key = keys[keys.length - 1]; if (typeof o !== "object") return false; else return key in o; } function setKey(obj, keys, value) { let o = obj; if (!configuration["dot-notation"]) keys = [keys.join(".")]; keys.slice(0, -1).forEach(function(key2) { key2 = sanitizeKey(key2); if (typeof o === "object" && o[key2] === void 0) { o[key2] = {}; } if (typeof o[key2] !== "object" || Array.isArray(o[key2])) { if (Array.isArray(o[key2])) { o[key2].push({}); } else { o[key2] = [o[key2], {}]; } o = o[key2][o[key2].length - 1]; } else { o = o[key2]; } }); const key = sanitizeKey(keys[keys.length - 1]); const isTypeArray = checkAllAliases(keys.join("."), flags.arrays); const isValueArray = Array.isArray(value); let duplicate = configuration["duplicate-arguments-array"]; if (!duplicate && checkAllAliases(key, flags.nargs)) { duplicate = true; if (!isUndefined(o[key]) && flags.nargs[key] === 1 || Array.isArray(o[key]) && o[key].length === flags.nargs[key]) { o[key] = void 0; } } if (value === increment()) { o[key] = increment(o[key]); } else if (Array.isArray(o[key])) { if (duplicate && isTypeArray && isValueArray) { o[key] = configuration["flatten-duplicate-arrays"] ? o[key].concat(value) : (Array.isArray(o[key][0]) ? o[key] : [o[key]]).concat([value]); } else if (!duplicate && Boolean(isTypeArray) === Boolean(isValueArray)) { o[key] = value; } else { o[key] = o[key].concat([value]); } } else if (o[key] === void 0 && isTypeArray) { o[key] = isValueArray ? value : [value]; } else if (duplicate && !(o[key] === void 0 || checkAllAliases(key, flags.counts) || checkAllAliases(key, flags.bools))) { o[key] = [o[key], value]; } else { o[key] = value; } } function extendAliases(...args2) { args2.forEach(function(obj) { Object.keys(obj || {}).forEach(function(key) { if (flags.aliases[key]) return; flags.aliases[key] = [].concat(aliases[key] || []); flags.aliases[key].concat(key).forEach(function(x) { if (/-/.test(x) && configuration["camel-case-expansion"]) { const c = camelCase(x); if (c !== key && flags.aliases[key].indexOf(c) === -1) { flags.aliases[key].push(c); newAliases[c] = true; } } }); flags.aliases[key].concat(key).forEach(function(x) { if (x.length > 1 && /[A-Z]/.test(x) && configuration["camel-case-expansion"]) { const c = decamelize(x, "-"); if (c !== key && flags.aliases[key].indexOf(c) === -1) { flags.aliases[key].push(c); newAliases[c] = true; } } }); flags.aliases[key].forEach(function(x) { flags.aliases[x] = [key].concat(flags.aliases[key].filter(function(y) { return x !== y; })); }); }); }); } function checkAllAliases(key, flag) { const toCheck = [].concat(flags.aliases[key] || [], key); const keys = Object.keys(flag); const setAlias = toCheck.find((key2) => keys.includes(key2)); return setAlias ? flag[setAlias] : false; } function hasAnyFlag(key) { const flagsKeys = Object.keys(flags); const toCheck = [].concat(flagsKeys.map((k) => flags[k])); return toCheck.some(function(flag) { return Array.isArray(flag) ? flag.includes(key) : flag[key]; }); } function hasFlagsMatching(arg, ...patterns) { const toCheck = [].concat(...patterns); return toCheck.some(function(pattern) { const match = arg.match(pattern); return match && hasAnyFlag(match[1]); }); } function hasAllShortFlags(arg) { if (arg.match(negative) || !arg.match(/^-[^-]+/)) { return false; } let hasAllFlags = true; let next; const letters = arg.slice(1).split(""); for (let j = 0; j < letters.length; j++) { next = arg.slice(j + 2); if (!hasAnyFlag(letters[j])) { hasAllFlags = false; break; } if (letters[j + 1] && letters[j + 1] === "=" || next === "-" || /[A-Za-z]/.test(letters[j]) && /^-?\d+(\.\d*)?(e-?\d+)?$/.test(next) || letters[j + 1] && letters[j + 1].match(/\W/)) { break; } } return hasAllFlags; } function isUnknownOptionAsArg(arg) { return configuration["unknown-options-as-args"] && isUnknownOption(arg); } function isUnknownOption(arg) { arg = arg.replace(/^-{3,}/, "--"); if (arg.match(negative)) { return false; } if (hasAllShortFlags(arg)) { return false; } const flagWithEquals = /^-+([^=]+?)=[\s\S]*$/; const normalFlag = /^-+([^=]+?)$/; const flagEndingInHyphen = /^-+([^=]+?)-$/; const flagEndingInDigits = /^-+([^=]+?\d+)$/; const flagEndingInNonWordCharacters = /^-+([^=]+?)\W+.*$/; return !hasFlagsMatching(arg, flagWithEquals, negatedBoolean, normalFlag, flagEndingInHyphen, flagEndingInDigits, flagEndingInNonWordCharacters); } function defaultValue(key) { if (!checkAllAliases(key, flags.bools) && !checkAllAliases(key, flags.counts) && `${key}` in defaults) { return defaults[key]; } else { return defaultForType(guessType2(key)); } } function defaultForType(type) { const def = { [DefaultValuesForTypeKey.BOOLEAN]: true, [DefaultValuesForTypeKey.STRING]: "", [DefaultValuesForTypeKey.NUMBER]: void 0, [DefaultValuesForTypeKey.ARRAY]: [] }; return def[type]; } function guessType2(key) { let type = DefaultValuesForTypeKey.BOOLEAN; if (checkAllAliases(key, flags.strings)) type = DefaultValuesForTypeKey.STRING; else if (checkAllAliases(key, flags.numbers)) type = DefaultValuesForTypeKey.NUMBER; else if (checkAllAliases(key, flags.bools)) type = DefaultValuesForTypeKey.BOOLEAN; else if (checkAllAliases(key, flags.arrays)) type = DefaultValuesForTypeKey.ARRAY; return type; } function isUndefined(num) { return num === void 0; } function checkConfiguration() { Object.keys(flags.counts).find((key) => { if (checkAllAliases(key, flags.arrays)) { error = Error(__("Invalid configuration: %s, opts.count excludes opts.array.", key)); return true; } else if (checkAllAliases(key, flags.nargs)) { error = Error(__("Invalid configuration: %s, opts.count excludes opts.narg.", key)); return true; } return false; }); } return { aliases: Object.assign({}, flags.aliases), argv: Object.assign(argvReturn, argv), configuration, defaulted: Object.assign({}, defaulted), error, newAliases: Object.assign({}, newAliases) }; } }; function combineAliases(aliases) { const aliasArrays = []; const combined = /* @__PURE__ */ Object.create(null); let change = true; Object.keys(aliases).forEach(function(key) { aliasArrays.push([].concat(aliases[key], key)); }); while (change) { change = false; for (let i = 0; i < aliasArrays.length; i++) { for (let ii = i + 1; ii < aliasArrays.length; ii++) { const intersect = aliasArrays[i].filter(function(v) { return aliasArrays[ii].indexOf(v) !== -1; }); if (intersect.length) { aliasArrays[i] = aliasArrays[i].concat(aliasArrays[ii]); aliasArrays.splice(ii, 1); change = true; break; } } } } aliasArrays.forEach(function(aliasArray) { aliasArray = aliasArray.filter(function(v, i, self) { return self.indexOf(v) === i; }); const lastAlias = aliasArray.pop(); if (lastAlias !== void 0 && typeof lastAlias === "string") { combined[lastAlias] = aliasArray; } }); return combined; } function increment(orig) { return orig !== void 0 ? orig + 1 : 1; } function sanitizeKey(key) { if (key === "__proto__") return "___proto___"; return key; } function stripQuotes(val) { return typeof val === "string" && (val[0] === "'" || val[0] === '"') && val[val.length - 1] === val[0] ? val.substring(1, val.length - 1) : val; } // node_modules/yargs-parser/build/lib/index.js import { readFileSync } from "fs"; var _a; var _b; var _c; var minNodeVersion = process && process.env && process.env.YARGS_MIN_NODE_VERSION ? Number(process.env.YARGS_MIN_NODE_VERSION) : 12; var nodeVersion = (_b = (_a = process === null || process === void 0 ? void 0 : process.versions) === null || _a === void 0 ? void 0 : _a.node) !== null && _b !== void 0 ? _b : (_c = process === null || process === void 0 ? void 0 : process.version) === null || _c === void 0 ? void 0 : _c.slice(1); if (nodeVersion) { const major = Number(nodeVersion.match(/^([^.]+)/)[1]); if (major < minNodeVersion) { throw Error(`yargs parser supports a minimum Node.js version of ${minNodeVersion}. Read our version support policy: https://github.com/yargs/yargs-parser#supported-nodejs-versions`); } } var env = process ? process.env : {}; var parser = new YargsParser({ cwd: process.cwd, env: () => { return env; }, format, normalize, resolve: resolve2, // TODO: figure out a way to combine ESM and CJS coverage, such that // we can exercise all the lines below: require: (path14) => { if (typeof __require !== "undefined") { return __require(path14); } else if (path14.match(/\.json$/)) { return JSON.parse(readFileSync(path14, "utf8")); } else { throw Error("only .json config files are supported in ESM"); } } }); var yargsParser = function Parser(args, opts) { const result = parser.parse(args.slice(), opts); return result.argv; }; yargsParser.detailed = function(args, opts) { return parser.parse(args.slice(), opts); }; yargsParser.camelCase = camelCase; yargsParser.decamelize = decamelize; yargsParser.looksLikeNumber = looksLikeNumber; var lib_default = yargsParser; // node_modules/yargs/lib/platform-shims/esm.mjs import { basename, dirname as dirname2, extname, relative, resolve as resolve4 } from "path"; // node_modules/yargs/build/lib/utils/process-argv.js function getProcessArgvBinIndex() { if (isBundledElectronApp()) return 0; return 1; } function isBundledElectronApp() { return isElectronApp() && !process.defaultApp; } function isElectronApp() { return !!process.versions.electron; } function hideBin(argv) { return argv.slice(getProcessArgvBinIndex() + 1); } function getProcessArgvBin() { return process.argv[getProcessArgvBinIndex()]; } // node_modules/yargs/build/lib/yerror.js var YError = class _YError extends Error { constructor(msg) { super(msg || "yargs error"); this.name = "YError"; if (Error.captureStackTrace) { Error.captureStackTrace(this, _YError); } } }; // node_modules/y18n/build/lib/platform-shims/node.js import { readFileSync as readFileSync2, statSync as statSync2, writeFile } from "fs"; import { format as format2 } from "util"; import { resolve as resolve3 } from "path"; var node_default = { fs: { readFileSync: readFileSync2, writeFile }, format: format2, resolve: resolve3, exists: (file) => { try { return statSync2(file).isFile(); } catch (err) { return false; } } }; // node_modules/y18n/build/lib/index.js var shim; var Y18N = class { constructor(opts) { opts = opts || {}; this.directory = opts.directory || "./locales"; this.updateFiles = typeof opts.updateFiles === "boolean" ? opts.updateFiles : true; this.locale = opts.locale || "en"; this.fallbackToLanguage = typeof opts.fallbackToLanguage === "boolean" ? opts.fallbackToLanguage : true; this.cache = /* @__PURE__ */ Object.create(null); this.writeQueue = []; } __(...args) { if (typeof arguments[0] !== "string") { return this._taggedLiteral(arguments[0], ...arguments); } const str = args.shift(); let cb = function() { }; if (typeof args[args.length - 1] === "function") cb = args.pop(); cb = cb || function() { }; if (!this.cache[this.locale]) this._readLocaleFile(); if (!this.cache[this.locale][str] && this.updateFiles) { this.cache[this.locale][str] = str; this._enqueueWrite({ directory: this.directory, locale: this.locale, cb }); } else { cb(); } return shim.format.apply(shim.format, [this.cache[this.locale][str] || str].concat(args)); } __n() { const args = Array.prototype.slice.call(arguments); const singular = args.shift(); const plural = args.shift(); const quantity = args.shift(); let cb = function() { }; if (typeof args[args.length - 1] === "function") cb = args.pop(); if (!this.cache[this.locale]) this._readLocaleFile(); let str = quantity === 1 ? singular : plural; if (this.cache[this.locale][singular]) { const entry = this.cache[this.locale][singular]; str = entry[quantity === 1 ? "one" : "other"]; } if (!this.cache[this.locale][singular] && this.updateFiles) { this.cache[this.locale][singular] = { one: singular, other: plural }; this._enqueueWrite({ directory: this.directory, locale: this.locale, cb }); } else { cb(); } const values = [str]; if (~str.indexOf("%d")) values.push(quantity); return shim.format.apply(shim.format, values.concat(args)); } setLocale(locale) { this.locale = locale; } getLocale() { return this.locale; } updateLocale(obj) { if (!this.cache[this.locale]) this._readLocaleFile(); for (const key in obj) { if (Object.prototype.hasOwnProperty.call(obj, key)) { this.cache[this.locale][key] = obj[key]; } } } _taggedLiteral(parts, ...args) { let str = ""; parts.forEach(function(part, i) { const arg = args[i + 1]; str += part; if (typeof arg !== "undefined") { str += "%s"; } }); return this.__.apply(this, [str].concat([].slice.call(args, 1))); } _enqueueWrite(work) { this.writeQueue.push(work); if (this.writeQueue.length === 1) this._processWriteQueue(); } _processWriteQueue() { const _this = this; const work = this.writeQueue[0]; const directory = work.directory; const locale = work.locale; const cb = work.cb; const languageFile = this._resolveLocaleFile(directory, locale); const serializedLocale = JSON.stringify(this.cache[locale], null, 2); shim.fs.writeFile(languageFile, serializedLocale, "utf-8", function(err) { _this.writeQueue.shift(); if (_this.writeQueue.length > 0) _this._processWriteQueue(); cb(err); }); } _readLocaleFile() { let localeLookup = {}; const languageFile = this._resolveLocaleFile(this.directory, this.locale); try { if (shim.fs.readFileSync) { localeLookup = JSON.parse(shim.fs.readFileSync(languageFile, "utf-8")); } } catch (err) { if (err instanceof SyntaxError) { err.message = "syntax error in " + languageFile; } if (err.code === "ENOENT") localeLookup = {}; else throw err; } this.cache[this.locale] = localeLookup; } _resolveLocaleFile(directory, locale) { let file = shim.resolve(directory, "./", locale + ".json"); if (this.fallbackToLanguage && !this._fileExistsSync(file) && ~locale.lastIndexOf("_")) { const languageFile = shim.resolve(directory, "./", locale.split("_")[0] + ".json"); if (this._fileExistsSync(languageFile)) file = languageFile; } return file; } _fileExistsSync(file) { return shim.exists(file); } }; function y18n(opts, _shim) { shim = _shim; const y18n3 = new Y18N(opts); return { __: y18n3.__.bind(y18n3), __n: y18n3.__n.bind(y18n3), setLocale: y18n3.setLocale.bind(y18n3), getLocale: y18n3.getLocale.bind(y18n3), updateLocale: y18n3.updateLocale.bind(y18n3), locale: y18n3.locale }; } // node_modules/y18n/index.mjs var y18n2 = (opts) => { return y18n(opts, node_default); }; var y18n_default = y18n2; // node_modules/yargs/lib/platform-shims/esm.mjs var REQUIRE_ERROR = "require is not supported by ESM"; var REQUIRE_DIRECTORY_ERROR = "loading a directory of commands is not supported yet for ESM"; var __dirname; try { __dirname = fileURLToPath(import.meta.url); } catch (e) { __dirname = process.cwd(); } var mainFilename = __dirname.substring(0, __dirname.lastIndexOf("node_modules")); var esm_default = { assert: { notStrictEqual, strictEqual }, cliui: ui, findUp: sync_default, getEnv: (key) => { return process.env[key]; }, inspect, getCallerFile: () => { throw new YError(REQUIRE_DIRECTORY_ERROR); }, getProcessArgvBin, mainFilename: mainFilename || process.cwd(), Parser: lib_default, path: { basename, dirname: dirname2, extname, relative, resolve: resolve4 }, process: { argv: () => process.argv, cwd: process.cwd, emitWarning: (warning, type) => process.emitWarning(warning, type), execPath: () => process.execPath, exit: process.exit, nextTick: process.nextTick, stdColumns: typeof process.stdout.columns !== "undefined" ? process.stdout.columns : null }, readFileSync: readFileSync3, require: () => { throw new YError(REQUIRE_ERROR); }, requireDirectory: () => { throw new YError(REQUIRE_DIRECTORY_ERROR); }, stringWidth: (str) => { return [...str].length; }, y18n: y18n_default({ directory: resolve4(__dirname, "../../../locales"), updateFiles: false }) }; // node_modules/yargs/build/lib/typings/common-types.js function assertNotStrictEqual(actual, expected, shim3, message) { shim3.assert.notStrictEqual(actual, expected, message); } function assertSingleKey(actual, shim3) { shim3.assert.strictEqual(typeof actual, "string"); } function objectKeys(object) { return Object.keys(object); } // node_modules/yargs/build/lib/utils/is-promise.js function isPromise(maybePromise) { return !!maybePromise && !!maybePromise.then && typeof maybePromise.then === "function"; } // node_modules/yargs/build/lib/parse-command.js function parseCommand(cmd) { const extraSpacesStrippedCommand = cmd.replace(/\s{2,}/g, " "); const splitCommand = extraSpacesStrippedCommand.split(/\s+(?![^[]*]|[^<]*>)/); const bregex = /\.*[\][<>]/g; const firstCommand = splitCommand.shift(); if (!firstCommand) throw new Error(`No command found in: ${cmd}`); const parsedCommand = { cmd: firstCommand.replace(bregex, ""), demanded: [], optional: [] }; splitCommand.forEach((cmd2, i) => { let variadic = false; cmd2 = cmd2.replace(/\s/g, ""); if (/\.+[\]>]/.test(cmd2) && i === splitCommand.length - 1) variadic = true; if (/^\[/.test(cmd2)) { parsedCommand.optional.push({ cmd: cmd2.replace(bregex, "").split("|"), variadic }); } else { parsedCommand.demanded.push({ cmd: cmd2.replace(bregex, "").split("|"), variadic }); } }); return parsedCommand; } // node_modules/yargs/build/lib/argsert.js var positionName = ["first", "second", "third", "fourth", "fifth", "sixth"]; function argsert(arg1, arg2, arg3) { function parseArgs() { return typeof arg1 === "object" ? [{ demanded: [], optional: [] }, arg1, arg2] : [ parseCommand(`cmd ${arg1}`), arg2, arg3 ]; } try { let position = 0; const [parsed, callerArguments, _length] = parseArgs(); const args = [].slice.call(callerArguments); while (args.length && args[args.length - 1] === void 0) args.pop(); const length = _length || args.length; if (length < parsed.demanded.length) { throw new YError(`Not enough arguments provided. Expected ${parsed.demanded.length} but received ${args.length}.`); } const totalCommands = parsed.demanded.length + parsed.optional.length; if (length > totalCommands) { throw new YError(`Too many arguments provided. Expected max ${totalCommands} but received ${length}.`); } parsed.demanded.forEach((demanded) => { const arg = args.shift(); const observedType = guessType(arg); const matchingTypes = demanded.cmd.filter((type) => type === observedType || type === "*"); if (matchingTypes.length === 0) argumentTypeError(observedType, demanded.cmd, position); position += 1; }); parsed.optional.forEach((optional) => { if (args.length === 0) return; const arg = args.shift(); const observedType = guessType(arg); const matchingTypes = optional.cmd.filter((type) => type === observedType || type === "*"); if (matchingTypes.length === 0) argumentTypeError(observedType, optional.cmd, position); position += 1; }); } catch (err) { console.warn(err.stack); } } function guessType(arg) { if (Array.isArray(arg)) { return "array"; } else if (arg === null) { return "null"; } return typeof arg; } function argumentTypeError(observedType, allowedTypes, position) { throw new YError(`Invalid ${positionName[position] || "manyith"} argument. Expected ${allowedTypes.join(" or ")} but received ${observedType}.`); } // node_modules/yargs/build/lib/middleware.js var GlobalMiddleware = class { constructor(yargs) { this.globalMiddleware = []; this.frozens = []; this.yargs = yargs; } addMiddleware(callback, applyBeforeValidation, global = true, mutates = false) { argsert(" [boolean] [boolean] [boolean]", [callback, applyBeforeValidation, global], arguments.length); if (Array.isArray(callback)) { for (let i = 0; i < callback.length; i++) { if (typeof callback[i] !== "function") { throw Error("middleware must be a function"); } const m = callback[i]; m.applyBeforeValidation = applyBeforeValidation; m.global = global; } Array.prototype.push.apply(this.globalMiddleware, callback); } else if (typeof callback === "function") { const m = callback; m.applyBeforeValidation = applyBeforeValidation; m.global = global; m.mutates = mutates; this.globalMiddleware.push(callback); } return this.yargs; } addCoerceMiddleware(callback, option) { const aliases = this.yargs.getAliases(); this.globalMiddleware = this.globalMiddleware.filter((m) => { const toCheck = [...aliases[option] || [], option]; if (!m.option) return true; else return !toCheck.includes(m.option); }); callback.option = option; return this.addMiddleware(callback, true, true, true); } getMiddleware() { return this.globalMiddleware; } freeze() { this.frozens.push([...this.globalMiddleware]); } unfreeze() { const frozen = this.frozens.pop(); if (frozen !== void 0) this.globalMiddleware = frozen; } reset() { this.globalMiddleware = this.globalMiddleware.filter((m) => m.global); } }; function commandMiddlewareFactory(commandMiddleware) { if (!commandMiddleware) return []; return commandMiddleware.map((middleware) => { middleware.applyBeforeValidation = false; return middleware; }); } function applyMiddleware(argv, yargs, middlewares, beforeValidation) { return middlewares.reduce((acc, middleware) => { if (middleware.applyBeforeValidation !== beforeValidation) { return acc; } if (middleware.mutates) { if (middleware.applied) return acc; middleware.applied = true; } if (isPromise(acc)) { return acc.then((initialObj) => Promise.all([initialObj, middleware(initialObj, yargs)])).then(([initialObj, middlewareObj]) => Object.assign(initialObj, middlewareObj)); } else { const result = middleware(acc, yargs); return isPromise(result) ? result.then((middlewareObj) => Object.assign(acc, middlewareObj)) : Object.assign(acc, result); } }, argv); } // node_modules/yargs/build/lib/utils/maybe-async-result.js function maybeAsyncResult(getResult, resultHandler, errorHandler = (err) => { throw err; }) { try { const result = isFunction(getResult) ? getResult() : getResult; return isPromise(result) ? result.then((result2) => resultHandler(result2)) : resultHandler(result); } catch (err) { return errorHandler(err); } } function isFunction(arg) { return typeof arg === "function"; } // node_modules/yargs/build/lib/utils/which-module.js function whichModule(exported) { if (typeof __require === "undefined") return null; for (let i = 0, files = Object.keys(__require.cache), mod; i < files.length; i++) { mod = __require.cache[files[i]]; if (mod.exports === exported) return mod; } return null; } // node_modules/yargs/build/lib/command.js var DEFAULT_MARKER = /(^\*)|(^\$0)/; var CommandInstance = class { constructor(usage2, validation2, globalMiddleware, shim3) { this.requireCache = /* @__PURE__ */ new Set(); this.handlers = {}; this.aliasMap = {}; this.frozens = []; this.shim = shim3; this.usage = usage2; this.globalMiddleware = globalMiddleware; this.validation = validation2; } addDirectory(dir, req, callerFile, opts) { opts = opts || {}; if (typeof opts.recurse !== "boolean") opts.recurse = false; if (!Array.isArray(opts.extensions)) opts.extensions = ["js"]; const parentVisit = typeof opts.visit === "function" ? opts.visit : (o) => o; opts.visit = (obj, joined, filename) => { const visited = parentVisit(obj, joined, filename); if (visited) { if (this.requireCache.has(joined)) return visited; else this.requireCache.add(joined); this.addHandler(visited); } return visited; }; this.shim.requireDirectory({ require: req, filename: callerFile }, dir, opts); } addHandler(cmd, description, builder, handler, commandMiddleware, deprecated) { let aliases = []; const middlewares = commandMiddlewareFactory(commandMiddleware); handler = handler || (() => { }); if (Array.isArray(cmd)) { if (isCommandAndAliases(cmd)) { [cmd, ...aliases] = cmd; } else { for (const command2 of cmd) { this.addHandler(command2); } } } else if (isCommandHandlerDefinition(cmd)) { let command2 = Array.isArray(cmd.command) || typeof cmd.command === "string" ? cmd.command : this.moduleName(cmd); if (cmd.aliases) command2 = [].concat(command2).concat(cmd.aliases); this.addHandler(command2, this.extractDesc(cmd), cmd.builder, cmd.handler, cmd.middlewares, cmd.deprecated); return; } else if (isCommandBuilderDefinition(builder)) { this.addHandler([cmd].concat(aliases), description, builder.builder, builder.handler, builder.middlewares, builder.deprecated); return; } if (typeof cmd === "string") { const parsedCommand = parseCommand(cmd); aliases = aliases.map((alias) => parseCommand(alias).cmd); let isDefault = false; const parsedAliases = [parsedCommand.cmd].concat(aliases).filter((c) => { if (DEFAULT_MARKER.test(c)) { isDefault = true; return false; } return true; }); if (parsedAliases.length === 0 && isDefault) parsedAliases.push("$0"); if (isDefault) { parsedCommand.cmd = parsedAliases[0]; aliases = parsedAliases.slice(1); cmd = cmd.replace(DEFAULT_MARKER, parsedCommand.cmd); } aliases.forEach((alias) => { this.aliasMap[alias] = parsedCommand.cmd; }); if (description !== false) { this.usage.command(cmd, description, isDefault, aliases, deprecated); } this.handlers[parsedCommand.cmd] = { original: cmd, description, handler, builder: builder || {}, middlewares, deprecated, demanded: parsedCommand.demanded, optional: parsedCommand.optional }; if (isDefault) this.defaultCommand = this.handlers[parsedCommand.cmd]; } } getCommandHandlers() { return this.handlers; } getCommands() { return Object.keys(this.handlers).concat(Object.keys(this.aliasMap)); } hasDefaultCommand() { return !!this.defaultCommand; } runCommand(command2, yargs, parsed, commandIndex, helpOnly, helpOrVersionSet) { const commandHandler = this.handlers[command2] || this.handlers[this.aliasMap[command2]] || this.defaultCommand; const currentContext = yargs.getInternalMethods().getContext(); const parentCommands = currentContext.commands.slice(); const isDefaultCommand = !command2; if (command2) { currentContext.commands.push(command2); currentContext.fullCommands.push(commandHandler.original); } const builderResult = this.applyBuilderUpdateUsageAndParse(isDefaultCommand, commandHandler, yargs, parsed.aliases, parentCommands, commandIndex, helpOnly, helpOrVersionSet); return isPromise(builderResult) ? builderResult.then((result) => this.applyMiddlewareAndGetResult(isDefaultCommand, commandHandler, result.innerArgv, currentContext, helpOnly, result.aliases, yargs)) : this.applyMiddlewareAndGetResult(isDefaultCommand, commandHandler, builderResult.innerArgv, currentContext, helpOnly, builderResult.aliases, yargs); } applyBuilderUpdateUsageAndParse(isDefaultCommand, commandHandler, yargs, aliases, parentCommands, commandIndex, helpOnly, helpOrVersionSet) { const builder = commandHandler.builder; let innerYargs = yargs; if (isCommandBuilderCallback(builder)) { yargs.getInternalMethods().getUsageInstance().freeze(); const builderOutput = builder(yargs.getInternalMethods().reset(aliases), helpOrVersionSet); if (isPromise(builderOutput)) { return builderOutput.then((output) => { innerYargs = isYargsInstance(output) ? output : yargs; return this.parseAndUpdateUsage(isDefaultCommand, commandHandler, innerYargs, parentCommands, commandIndex, helpOnly); }); } } else if (isCommandBuilderOptionDefinitions(builder)) { yargs.getInternalMethods().getUsageInstance().freeze(); innerYargs = yargs.getInternalMethods().reset(aliases); Object.keys(commandHandler.builder).forEach((key) => { innerYargs.option(key, builder[key]); }); } return this.parseAndUpdateUsage(isDefaultCommand, commandHandler, innerYargs, parentCommands, commandIndex, helpOnly); } parseAndUpdateUsage(isDefaultCommand, commandHandler, innerYargs, parentCommands, commandIndex, helpOnly) { if (isDefaultCommand) innerYargs.getInternalMethods().getUsageInstance().unfreeze(true); if (this.shouldUpdateUsage(innerYargs)) { innerYargs.getInternalMethods().getUsageInstance().usage(this.usageFromParentCommandsCommandHandler(parentCommands, commandHandler), commandHandler.description); } const innerArgv = innerYargs.getInternalMethods().runYargsParserAndExecuteCommands(null, void 0, true, commandIndex, helpOnly); return isPromise(innerArgv) ? innerArgv.then((argv) => ({ aliases: innerYargs.parsed.aliases, innerArgv: argv })) : { aliases: innerYargs.parsed.aliases, innerArgv }; } shouldUpdateUsage(yargs) { return !yargs.getInternalMethods().getUsageInstance().getUsageDisabled() && yargs.getInternalMethods().getUsageInstance().getUsage().length === 0; } usageFromParentCommandsCommandHandler(parentCommands, commandHandler) { const c = DEFAULT_MARKER.test(commandHandler.original) ? commandHandler.original.replace(DEFAULT_MARKER, "").trim() : commandHandler.original; const pc = parentCommands.filter((c2) => { return !DEFAULT_MARKER.test(c2); }); pc.push(c); return `$0 ${pc.join(" ")}`; } handleValidationAndGetResult(isDefaultCommand, commandHandler, innerArgv, currentContext, aliases, yargs, middlewares, positionalMap) { if (!yargs.getInternalMethods().getHasOutput()) { const validation2 = yargs.getInternalMethods().runValidation(aliases, positionalMap, yargs.parsed.error, isDefaultCommand); innerArgv = maybeAsyncResult(innerArgv, (result) => { validation2(result); return result; }); } if (commandHandler.handler && !yargs.getInternalMethods().getHasOutput()) { yargs.getInternalMethods().setHasOutput(); const populateDoubleDash = !!yargs.getOptions().configuration["populate--"]; yargs.getInternalMethods().postProcess(innerArgv, populateDoubleDash, false, false); innerArgv = applyMiddleware(innerArgv, yargs, middlewares, false); innerArgv = maybeAsyncResult(innerArgv, (result) => { const handlerResult = commandHandler.handler(result); return isPromise(handlerResult) ? handlerResult.then(() => result) : result; }); if (!isDefaultCommand) { yargs.getInternalMethods().getUsageInstance().cacheHelpMessage(); } if (isPromise(innerArgv) && !yargs.getInternalMethods().hasParseCallback()) { innerArgv.catch((error) => { try { yargs.getInternalMethods().getUsageInstance().fail(null, error); } catch (_err) { } }); } } if (!isDefaultCommand) { currentContext.commands.pop(); currentContext.fullCommands.pop(); } return innerArgv; } applyMiddlewareAndGetResult(isDefaultCommand, commandHandler, innerArgv, currentContext, helpOnly, aliases, yargs) { let positionalMap = {}; if (helpOnly) return innerArgv; if (!yargs.getInternalMethods().getHasOutput()) { positionalMap = this.populatePositionals(commandHandler, innerArgv, currentContext, yargs); } const middlewares = this.globalMiddleware.getMiddleware().slice(0).concat(commandHandler.middlewares); const maybePromiseArgv = applyMiddleware(innerArgv, yargs, middlewares, true); return isPromise(maybePromiseArgv) ? maybePromiseArgv.then((resolvedInnerArgv) => this.handleValidationAndGetResult(isDefaultCommand, commandHandler, resolvedInnerArgv, currentContext, aliases, yargs, middlewares, positionalMap)) : this.handleValidationAndGetResult(isDefaultCommand, commandHandler, maybePromiseArgv, currentContext, aliases, yargs, middlewares, positionalMap); } populatePositionals(commandHandler, argv, context, yargs) { argv._ = argv._.slice(context.commands.length); const demanded = commandHandler.demanded.slice(0); const optional = commandHandler.optional.slice(0); const positionalMap = {}; this.validation.positionalCount(demanded.length, argv._.length); while (demanded.length) { const demand = demanded.shift(); this.populatePositional(demand, argv, positionalMap); } while (optional.length) { const maybe = optional.shift(); this.populatePositional(maybe, argv, positionalMap); } argv._ = context.commands.concat(argv._.map((a) => "" + a)); this.postProcessPositionals(argv, positionalMap, this.cmdToParseOptions(commandHandler.original), yargs); return positionalMap; } populatePositional(positional, argv, positionalMap) { const cmd = positional.cmd[0]; if (positional.variadic) { positionalMap[cmd] = argv._.splice(0).map(String); } else { if (argv._.length) positionalMap[cmd] = [String(argv._.shift())]; } } cmdToParseOptions(cmdString) { const parseOptions = { array: [], default: {}, alias: {}, demand: {} }; const parsed = parseCommand(cmdString); parsed.demanded.forEach((d) => { const [cmd, ...aliases] = d.cmd; if (d.variadic) { parseOptions.array.push(cmd); parseOptions.default[cmd] = []; } parseOptions.alias[cmd] = aliases; parseOptions.demand[cmd] = true; }); parsed.optional.forEach((o) => { const [cmd, ...aliases] = o.cmd; if (o.variadic) { parseOptions.array.push(cmd); parseOptions.default[cmd] = []; } parseOptions.alias[cmd] = aliases; }); return parseOptions; } postProcessPositionals(argv, positionalMap, parseOptions, yargs) { const options = Object.assign({}, yargs.getOptions()); options.default = Object.assign(parseOptions.default, options.default); for (const key of Object.keys(parseOptions.alias)) { options.alias[key] = (options.alias[key] || []).concat(parseOptions.alias[key]); } options.array = options.array.concat(parseOptions.array); options.config = {}; const unparsed = []; Object.keys(positionalMap).forEach((key) => { positionalMap[key].map((value) => { if (options.configuration["unknown-options-as-args"]) options.key[key] = true; unparsed.push(`--${key}`); unparsed.push(value); }); }); if (!unparsed.length) return; const config = Object.assign({}, options.configuration, { "populate--": false }); const parsed = this.shim.Parser.detailed(unparsed, Object.assign({}, options, { configuration: config })); if (parsed.error) { yargs.getInternalMethods().getUsageInstance().fail(parsed.error.message, parsed.error); } else { const positionalKeys = Object.keys(positionalMap); Object.keys(positionalMap).forEach((key) => { positionalKeys.push(...parsed.aliases[key]); }); Object.keys(parsed.argv).forEach((key) => { if (positionalKeys.includes(key)) { if (!positionalMap[key]) positionalMap[key] = parsed.argv[key]; if (!this.isInConfigs(yargs, key) && !this.isDefaulted(yargs, key) && Object.prototype.hasOwnProperty.call(argv, key) && Object.prototype.hasOwnProperty.call(parsed.argv, key) && (Array.isArray(argv[key]) || Array.isArray(parsed.argv[key]))) { argv[key] = [].concat(argv[key], parsed.argv[key]); } else { argv[key] = parsed.argv[key]; } } }); } } isDefaulted(yargs, key) { const { default: defaults } = yargs.getOptions(); return Object.prototype.hasOwnProperty.call(defaults, key) || Object.prototype.hasOwnProperty.call(defaults, this.shim.Parser.camelCase(key)); } isInConfigs(yargs, key) { const { configObjects } = yargs.getOptions(); return configObjects.some((c) => Object.prototype.hasOwnProperty.call(c, key)) || configObjects.some((c) => Object.prototype.hasOwnProperty.call(c, this.shim.Parser.camelCase(key))); } runDefaultBuilderOn(yargs) { if (!this.defaultCommand) return; if (this.shouldUpdateUsage(yargs)) { const commandString = DEFAULT_MARKER.test(this.defaultCommand.original) ? this.defaultCommand.original : this.defaultCommand.original.replace(/^[^[\]<>]*/, "$0 "); yargs.getInternalMethods().getUsageInstance().usage(commandString, this.defaultCommand.description); } const builder = this.defaultCommand.builder; if (isCommandBuilderCallback(builder)) { return builder(yargs, true); } else if (!isCommandBuilderDefinition(builder)) { Object.keys(builder).forEach((key) => { yargs.option(key, builder[key]); }); } return void 0; } moduleName(obj) { const mod = whichModule(obj); if (!mod) throw new Error(`No command name given for module: ${this.shim.inspect(obj)}`); return this.commandFromFilename(mod.filename); } commandFromFilename(filename) { return this.shim.path.basename(filename, this.shim.path.extname(filename)); } extractDesc({ describe, description, desc }) { for (const test of [describe, description, desc]) { if (typeof test === "string" || test === false) return test; assertNotStrictEqual(test, true, this.shim); } return false; } freeze() { this.frozens.push({ handlers: this.handlers, aliasMap: this.aliasMap, defaultCommand: this.defaultCommand }); } unfreeze() { const frozen = this.frozens.pop(); assertNotStrictEqual(frozen, void 0, this.shim); ({ handlers: this.handlers, aliasMap: this.aliasMap, defaultCommand: this.defaultCommand } = frozen); } reset() { this.handlers = {}; this.aliasMap = {}; this.defaultCommand = void 0; this.requireCache = /* @__PURE__ */ new Set(); return this; } }; function command(usage2, validation2, globalMiddleware, shim3) { return new CommandInstance(usage2, validation2, globalMiddleware, shim3); } function isCommandBuilderDefinition(builder) { return typeof builder === "object" && !!builder.builder && typeof builder.handler === "function"; } function isCommandAndAliases(cmd) { return cmd.every((c) => typeof c === "string"); } function isCommandBuilderCallback(builder) { return typeof builder === "function"; } function isCommandBuilderOptionDefinitions(builder) { return typeof builder === "object"; } function isCommandHandlerDefinition(cmd) { return typeof cmd === "object" && !Array.isArray(cmd); } // node_modules/yargs/build/lib/utils/obj-filter.js function objFilter(original = {}, filter = () => true) { const obj = {}; objectKeys(original).forEach((key) => { if (filter(key, original[key])) { obj[key] = original[key]; } }); return obj; } // node_modules/yargs/build/lib/utils/set-blocking.js function setBlocking(blocking) { if (typeof process === "undefined") return; [process.stdout, process.stderr].forEach((_stream) => { const stream = _stream; if (stream._handle && stream.isTTY && typeof stream._handle.setBlocking === "function") { stream._handle.setBlocking(blocking); } }); } // node_modules/yargs/build/lib/usage.js function isBoolean(fail) { return typeof fail === "boolean"; } function usage(yargs, shim3) { const __ = shim3.y18n.__; const self = {}; const fails = []; self.failFn = function failFn(f) { fails.push(f); }; let failMessage = null; let globalFailMessage = null; let showHelpOnFail = true; self.showHelpOnFail = function showHelpOnFailFn(arg1 = true, arg2) { const [enabled, message] = typeof arg1 === "string" ? [true, arg1] : [arg1, arg2]; if (yargs.getInternalMethods().isGlobalContext()) { globalFailMessage = message; } failMessage = message; showHelpOnFail = enabled; return self; }; let failureOutput = false; self.fail = function fail(msg, err) { const logger = yargs.getInternalMethods().getLoggerInstance(); if (fails.length) { for (let i = fails.length - 1; i >= 0; --i) { const fail2 = fails[i]; if (isBoolean(fail2)) { if (err) throw err; else if (msg) throw Error(msg); } else { fail2(msg, err, self); } } } else { if (yargs.getExitProcess()) setBlocking(true); if (!failureOutput) { failureOutput = true; if (showHelpOnFail) { yargs.showHelp("error"); logger.error(); } if (msg || err) logger.error(msg || err); const globalOrCommandFailMessage = failMessage || globalFailMessage; if (globalOrCommandFailMessage) { if (msg || err) logger.error(""); logger.error(globalOrCommandFailMessage); } } err = err || new YError(msg); if (yargs.getExitProcess()) { return yargs.exit(1); } else if (yargs.getInternalMethods().hasParseCallback()) { return yargs.exit(1, err); } else { throw err; } } }; let usages = []; let usageDisabled = false; self.usage = (msg, description) => { if (msg === null) { usageDisabled = true; usages = []; return self; } usageDisabled = false; usages.push([msg, description || ""]); return self; }; self.getUsage = () => { return usages; }; self.getUsageDisabled = () => { return usageDisabled; }; self.getPositionalGroupName = () => { return __("Positionals:"); }; let examples = []; self.example = (cmd, description) => { examples.push([cmd, description || ""]); }; let commands = []; self.command = function command2(cmd, description, isDefault, aliases, deprecated = false) { if (isDefault) { commands = commands.map((cmdArray) => { cmdArray[2] = false; return cmdArray; }); } commands.push([cmd, description || "", isDefault, aliases, deprecated]); }; self.getCommands = () => commands; let descriptions = {}; self.describe = function describe(keyOrKeys, desc) { if (Array.isArray(keyOrKeys)) { keyOrKeys.forEach((k) => { self.describe(k, desc); }); } else if (typeof keyOrKeys === "object") { Object.keys(keyOrKeys).forEach((k) => { self.describe(k, keyOrKeys[k]); }); } else { descriptions[keyOrKeys] = desc; } }; self.getDescriptions = () => descriptions; let epilogs = []; self.epilog = (msg) => { epilogs.push(msg); }; let wrapSet = false; let wrap2; self.wrap = (cols) => { wrapSet = true; wrap2 = cols; }; self.getWrap = () => { if (shim3.getEnv("YARGS_DISABLE_WRAP")) { return null; } if (!wrapSet) { wrap2 = windowWidth(); wrapSet = true; } return wrap2; }; const deferY18nLookupPrefix = "__yargsString__:"; self.deferY18nLookup = (str) => deferY18nLookupPrefix + str; self.help = function help() { if (cachedHelpMessage) return cachedHelpMessage; normalizeAliases(); const base$0 = yargs.customScriptName ? yargs.$0 : shim3.path.basename(yargs.$0); const demandedOptions = yargs.getDemandedOptions(); const demandedCommands = yargs.getDemandedCommands(); const deprecatedOptions = yargs.getDeprecatedOptions(); const groups = yargs.getGroups(); const options = yargs.getOptions(); let keys = []; keys = keys.concat(Object.keys(descriptions)); keys = keys.concat(Object.keys(demandedOptions)); keys = keys.concat(Object.keys(demandedCommands)); keys = keys.concat(Object.keys(options.default)); keys = keys.filter(filterHiddenOptions); keys = Object.keys(keys.reduce((acc, key) => { if (key !== "_") acc[key] = true; return acc; }, {})); const theWrap = self.getWrap(); const ui2 = shim3.cliui({ width: theWrap, wrap: !!theWrap }); if (!usageDisabled) { if (usages.length) { usages.forEach((usage2) => { ui2.div({ text: `${usage2[0].replace(/\$0/g, base$0)}` }); if (usage2[1]) { ui2.div({ text: `${usage2[1]}`, padding: [1, 0, 0, 0] }); } }); ui2.div(); } else if (commands.length) { let u = null; if (demandedCommands._) { u = `${base$0} <${__("command")}> `; } else { u = `${base$0} [${__("command")}] `; } ui2.div(`${u}`); } } if (commands.length > 1 || commands.length === 1 && !commands[0][2]) { ui2.div(__("Commands:")); const context = yargs.getInternalMethods().getContext(); const parentCommands = context.commands.length ? `${context.commands.join(" ")} ` : ""; if (yargs.getInternalMethods().getParserConfiguration()["sort-commands"] === true) { commands = commands.sort((a, b) => a[0].localeCompare(b[0])); } const prefix = base$0 ? `${base$0} ` : ""; commands.forEach((command2) => { const commandString = `${prefix}${parentCommands}${command2[0].replace(/^\$0 ?/, "")}`; ui2.span({ text: commandString, padding: [0, 2, 0, 2], width: maxWidth(commands, theWrap, `${base$0}${parentCommands}`) + 4 }, { text: command2[1] }); const hints = []; if (command2[2]) hints.push(`[${__("default")}]`); if (command2[3] && command2[3].length) { hints.push(`[${__("aliases:")} ${command2[3].join(", ")}]`); } if (command2[4]) { if (typeof command2[4] === "string") { hints.push(`[${__("deprecated: %s", command2[4])}]`); } else { hints.push(`[${__("deprecated")}]`); } } if (hints.length) { ui2.div({ text: hints.join(" "), padding: [0, 0, 0, 2], align: "right" }); } else { ui2.div(); } }); ui2.div(); } const aliasKeys = (Object.keys(options.alias) || []).concat(Object.keys(yargs.parsed.newAliases) || []); keys = keys.filter((key) => !yargs.parsed.newAliases[key] && aliasKeys.every((alias) => (options.alias[alias] || []).indexOf(key) === -1)); const defaultGroup = __("Options:"); if (!groups[defaultGroup]) groups[defaultGroup] = []; addUngroupedKeys(keys, options.alias, groups, defaultGroup); const isLongSwitch = (sw) => /^--/.test(getText(sw)); const displayedGroups = Object.keys(groups).filter((groupName) => groups[groupName].length > 0).map((groupName) => { const normalizedKeys = groups[groupName].filter(filterHiddenOptions).map((key) => { if (aliasKeys.includes(key)) return key; for (let i = 0, aliasKey; (aliasKey = aliasKeys[i]) !== void 0; i++) { if ((options.alias[aliasKey] || []).includes(key)) return aliasKey; } return key; }); return { groupName, normalizedKeys }; }).filter(({ normalizedKeys }) => normalizedKeys.length > 0).map(({ groupName, normalizedKeys }) => { const switches = normalizedKeys.reduce((acc, key) => { acc[key] = [key].concat(options.alias[key] || []).map((sw) => { if (groupName === self.getPositionalGroupName()) return sw; else { return (/^[0-9]$/.test(sw) ? options.boolean.includes(key) ? "-" : "--" : sw.length > 1 ? "--" : "-") + sw; } }).sort((sw1, sw2) => isLongSwitch(sw1) === isLongSwitch(sw2) ? 0 : isLongSwitch(sw1) ? 1 : -1).join(", "); return acc; }, {}); return { groupName, normalizedKeys, switches }; }); const shortSwitchesUsed = displayedGroups.filter(({ groupName }) => groupName !== self.getPositionalGroupName()).some(({ normalizedKeys, switches }) => !normalizedKeys.every((key) => isLongSwitch(switches[key]))); if (shortSwitchesUsed) { displayedGroups.filter(({ groupName }) => groupName !== self.getPositionalGroupName()).forEach(({ normalizedKeys, switches }) => { normalizedKeys.forEach((key) => { if (isLongSwitch(switches[key])) { switches[key] = addIndentation(switches[key], "-x, ".length); } }); }); } displayedGroups.forEach(({ groupName, normalizedKeys, switches }) => { ui2.div(groupName); normalizedKeys.forEach((key) => { const kswitch = switches[key]; let desc = descriptions[key] || ""; let type = null; if (desc.includes(deferY18nLookupPrefix)) desc = __(desc.substring(deferY18nLookupPrefix.length)); if (options.boolean.includes(key)) type = `[${__("boolean")}]`; if (options.count.includes(key)) type = `[${__("count")}]`; if (options.string.includes(key)) type = `[${__("string")}]`; if (options.normalize.includes(key)) type = `[${__("string")}]`; if (options.array.includes(key)) type = `[${__("array")}]`; if (options.number.includes(key)) type = `[${__("number")}]`; const deprecatedExtra = (deprecated) => typeof deprecated === "string" ? `[${__("deprecated: %s", deprecated)}]` : `[${__("deprecated")}]`; const extra = [ key in deprecatedOptions ? deprecatedExtra(deprecatedOptions[key]) : null, type, key in demandedOptions ? `[${__("required")}]` : null, options.choices && options.choices[key] ? `[${__("choices:")} ${self.stringifiedValues(options.choices[key])}]` : null, defaultString(options.default[key], options.defaultDescription[key]) ].filter(Boolean).join(" "); ui2.span({ text: getText(kswitch), padding: [0, 2, 0, 2 + getIndentation(kswitch)], width: maxWidth(switches, theWrap) + 4 }, desc); const shouldHideOptionExtras = yargs.getInternalMethods().getUsageConfiguration()["hide-types"] === true; if (extra && !shouldHideOptionExtras) ui2.div({ text: extra, padding: [0, 0, 0, 2], align: "right" }); else ui2.div(); }); ui2.div(); }); if (examples.length) { ui2.div(__("Examples:")); examples.forEach((example) => { example[0] = example[0].replace(/\$0/g, base$0); }); examples.forEach((example) => { if (example[1] === "") { ui2.div({ text: example[0], padding: [0, 2, 0, 2] }); } else { ui2.div({ text: example[0], padding: [0, 2, 0, 2], width: maxWidth(examples, theWrap) + 4 }, { text: example[1] }); } }); ui2.div(); } if (epilogs.length > 0) { const e = epilogs.map((epilog) => epilog.replace(/\$0/g, base$0)).join("\n"); ui2.div(`${e} `); } return ui2.toString().replace(/\s*$/, ""); }; function maxWidth(table, theWrap, modifier) { let width = 0; if (!Array.isArray(table)) { table = Object.values(table).map((v) => [v]); } table.forEach((v) => { width = Math.max(shim3.stringWidth(modifier ? `${modifier} ${getText(v[0])}` : getText(v[0])) + getIndentation(v[0]), width); }); if (theWrap) width = Math.min(width, parseInt((theWrap * 0.5).toString(), 10)); return width; } function normalizeAliases() { const demandedOptions = yargs.getDemandedOptions(); const options = yargs.getOptions(); (Object.keys(options.alias) || []).forEach((key) => { options.alias[key].forEach((alias) => { if (descriptions[alias]) self.describe(key, descriptions[alias]); if (alias in demandedOptions) yargs.demandOption(key, demandedOptions[alias]); if (options.boolean.includes(alias)) yargs.boolean(key); if (options.count.includes(alias)) yargs.count(key); if (options.string.includes(alias)) yargs.string(key); if (options.normalize.includes(alias)) yargs.normalize(key); if (options.array.includes(alias)) yargs.array(key); if (options.number.includes(alias)) yargs.number(key); }); }); } let cachedHelpMessage; self.cacheHelpMessage = function() { cachedHelpMessage = this.help(); }; self.clearCachedHelpMessage = function() { cachedHelpMessage = void 0; }; self.hasCachedHelpMessage = function() { return !!cachedHelpMessage; }; function addUngroupedKeys(keys, aliases, groups, defaultGroup) { let groupedKeys = []; let toCheck = null; Object.keys(groups).forEach((group) => { groupedKeys = groupedKeys.concat(groups[group]); }); keys.forEach((key) => { toCheck = [key].concat(aliases[key]); if (!toCheck.some((k) => groupedKeys.indexOf(k) !== -1)) { groups[defaultGroup].push(key); } }); return groupedKeys; } function filterHiddenOptions(key) { return yargs.getOptions().hiddenOptions.indexOf(key) < 0 || yargs.parsed.argv[yargs.getOptions().showHiddenOpt]; } self.showHelp = (level) => { const logger = yargs.getInternalMethods().getLoggerInstance(); if (!level) level = "error"; const emit = typeof level === "function" ? level : logger[level]; emit(self.help()); }; self.functionDescription = (fn) => { const description = fn.name ? shim3.Parser.decamelize(fn.name, "-") : __("generated-value"); return ["(", description, ")"].join(""); }; self.stringifiedValues = function stringifiedValues(values, separator) { let string = ""; const sep = separator || ", "; const array = [].concat(values); if (!values || !array.length) return string; array.forEach((value) => { if (string.length) string += sep; string += JSON.stringify(value); }); return string; }; function defaultString(value, defaultDescription) { let string = `[${__("default:")} `; if (value === void 0 && !defaultDescription) return null; if (defaultDescription) { string += defaultDescription; } else { switch (typeof value) { case "string": string += `"${value}"`; break; case "object": string += JSON.stringify(value); break; default: string += value; } } return `${string}]`; } function windowWidth() { const maxWidth2 = 80; if (shim3.process.stdColumns) { return Math.min(maxWidth2, shim3.process.stdColumns); } else { return maxWidth2; } } let version = null; self.version = (ver) => { version = ver; }; self.showVersion = (level) => { const logger = yargs.getInternalMethods().getLoggerInstance(); if (!level) level = "error"; const emit = typeof level === "function" ? level : logger[level]; emit(version); }; self.reset = function reset(localLookup) { failMessage = null; failureOutput = false; usages = []; usageDisabled = false; epilogs = []; examples = []; commands = []; descriptions = objFilter(descriptions, (k) => !localLookup[k]); return self; }; const frozens = []; self.freeze = function freeze() { frozens.push({ failMessage, failureOutput, usages, usageDisabled, epilogs, examples, commands, descriptions }); }; self.unfreeze = function unfreeze(defaultCommand = false) { const frozen = frozens.pop(); if (!frozen) return; if (defaultCommand) { descriptions = { ...frozen.descriptions, ...descriptions }; commands = [...frozen.commands, ...commands]; usages = [...frozen.usages, ...usages]; examples = [...frozen.examples, ...examples]; epilogs = [...frozen.epilogs, ...epilogs]; } else { ({ failMessage, failureOutput, usages, usageDisabled, epilogs, examples, commands, descriptions } = frozen); } }; return self; } function isIndentedText(text) { return typeof text === "object"; } function addIndentation(text, indent) { return isIndentedText(text) ? { text: text.text, indentation: text.indentation + indent } : { text, indentation: indent }; } function getIndentation(text) { return isIndentedText(text) ? text.indentation : 0; } function getText(text) { return isIndentedText(text) ? text.text : text; } // node_modules/yargs/build/lib/completion-templates.js var completionShTemplate = `###-begin-{{app_name}}-completions-### # # yargs command completion script # # Installation: {{app_path}} {{completion_command}} >> ~/.bashrc # or {{app_path}} {{completion_command}} >> ~/.bash_profile on OSX. # _{{app_name}}_yargs_completions() { local cur_word args type_list cur_word="\${COMP_WORDS[COMP_CWORD]}" args=("\${COMP_WORDS[@]}") # ask yargs to generate completions. type_list=$({{app_path}} --get-yargs-completions "\${args[@]}") COMPREPLY=( $(compgen -W "\${type_list}" -- \${cur_word}) ) # if no match was found, fall back to filename completion if [ \${#COMPREPLY[@]} -eq 0 ]; then COMPREPLY=() fi return 0 } complete -o bashdefault -o default -F _{{app_name}}_yargs_completions {{app_name}} ###-end-{{app_name}}-completions-### `; var completionZshTemplate = `#compdef {{app_name}} ###-begin-{{app_name}}-completions-### # # yargs command completion script # # Installation: {{app_path}} {{completion_command}} >> ~/.zshrc # or {{app_path}} {{completion_command}} >> ~/.zprofile on OSX. # _{{app_name}}_yargs_completions() { local reply local si=$IFS IFS=$' ' reply=($(COMP_CWORD="$((CURRENT-1))" COMP_LINE="$BUFFER" COMP_POINT="$CURSOR" {{app_path}} --get-yargs-completions "\${words[@]}")) IFS=$si _describe 'values' reply } compdef _{{app_name}}_yargs_completions {{app_name}} ###-end-{{app_name}}-completions-### `; // node_modules/yargs/build/lib/completion.js var Completion = class { constructor(yargs, usage2, command2, shim3) { var _a2, _b2, _c2; this.yargs = yargs; this.usage = usage2; this.command = command2; this.shim = shim3; this.completionKey = "get-yargs-completions"; this.aliases = null; this.customCompletionFunction = null; this.indexAfterLastReset = 0; this.zshShell = (_c2 = ((_a2 = this.shim.getEnv("SHELL")) === null || _a2 === void 0 ? void 0 : _a2.includes("zsh")) || ((_b2 = this.shim.getEnv("ZSH_NAME")) === null || _b2 === void 0 ? void 0 : _b2.includes("zsh"))) !== null && _c2 !== void 0 ? _c2 : false; } defaultCompletion(args, argv, current, done) { const handlers = this.command.getCommandHandlers(); for (let i = 0, ii = args.length; i < ii; ++i) { if (handlers[args[i]] && handlers[args[i]].builder) { const builder = handlers[args[i]].builder; if (isCommandBuilderCallback(builder)) { this.indexAfterLastReset = i + 1; const y = this.yargs.getInternalMethods().reset(); builder(y, true); return y.argv; } } } const completions = []; this.commandCompletions(completions, args, current); this.optionCompletions(completions, args, argv, current); this.choicesFromOptionsCompletions(completions, args, argv, current); this.choicesFromPositionalsCompletions(completions, args, argv, current); done(null, completions); } commandCompletions(completions, args, current) { const parentCommands = this.yargs.getInternalMethods().getContext().commands; if (!current.match(/^-/) && parentCommands[parentCommands.length - 1] !== current && !this.previousArgHasChoices(args)) { this.usage.getCommands().forEach((usageCommand) => { const commandName = parseCommand(usageCommand[0]).cmd; if (args.indexOf(commandName) === -1) { if (!this.zshShell) { completions.push(commandName); } else { const desc = usageCommand[1] || ""; completions.push(commandName.replace(/:/g, "\\:") + ":" + desc); } } }); } } optionCompletions(completions, args, argv, current) { if ((current.match(/^-/) || current === "" && completions.length === 0) && !this.previousArgHasChoices(args)) { const options = this.yargs.getOptions(); const positionalKeys = this.yargs.getGroups()[this.usage.getPositionalGroupName()] || []; Object.keys(options.key).forEach((key) => { const negable = !!options.configuration["boolean-negation"] && options.boolean.includes(key); const isPositionalKey = positionalKeys.includes(key); if (!isPositionalKey && !options.hiddenOptions.includes(key) && !this.argsContainKey(args, key, negable)) { this.completeOptionKey(key, completions, current, negable && !!options.default[key]); } }); } } choicesFromOptionsCompletions(completions, args, argv, current) { if (this.previousArgHasChoices(args)) { const choices = this.getPreviousArgChoices(args); if (choices && choices.length > 0) { completions.push(...choices.map((c) => c.replace(/:/g, "\\:"))); } } } choicesFromPositionalsCompletions(completions, args, argv, current) { if (current === "" && completions.length > 0 && this.previousArgHasChoices(args)) { return; } const positionalKeys = this.yargs.getGroups()[this.usage.getPositionalGroupName()] || []; const offset = Math.max(this.indexAfterLastReset, this.yargs.getInternalMethods().getContext().commands.length + 1); const positionalKey = positionalKeys[argv._.length - offset - 1]; if (!positionalKey) { return; } const choices = this.yargs.getOptions().choices[positionalKey] || []; for (const choice of choices) { if (choice.startsWith(current)) { completions.push(choice.replace(/:/g, "\\:")); } } } getPreviousArgChoices(args) { if (args.length < 1) return; let previousArg = args[args.length - 1]; let filter = ""; if (!previousArg.startsWith("-") && args.length > 1) { filter = previousArg; previousArg = args[args.length - 2]; } if (!previousArg.startsWith("-")) return; const previousArgKey = previousArg.replace(/^-+/, ""); const options = this.yargs.getOptions(); const possibleAliases = [ previousArgKey, ...this.yargs.getAliases()[previousArgKey] || [] ]; let choices; for (const possibleAlias of possibleAliases) { if (Object.prototype.hasOwnProperty.call(options.key, possibleAlias) && Array.isArray(options.choices[possibleAlias])) { choices = options.choices[possibleAlias]; break; } } if (choices) { return choices.filter((choice) => !filter || choice.startsWith(filter)); } } previousArgHasChoices(args) { const choices = this.getPreviousArgChoices(args); return choices !== void 0 && choices.length > 0; } argsContainKey(args, key, negable) { const argsContains = (s) => args.indexOf((/^[^0-9]$/.test(s) ? "-" : "--") + s) !== -1; if (argsContains(key)) return true; if (negable && argsContains(`no-${key}`)) return true; if (this.aliases) { for (const alias of this.aliases[key]) { if (argsContains(alias)) return true; } } return false; } completeOptionKey(key, completions, current, negable) { var _a2, _b2, _c2, _d; let keyWithDesc = key; if (this.zshShell) { const descs = this.usage.getDescriptions(); const aliasKey = (_b2 = (_a2 = this === null || this === void 0 ? void 0 : this.aliases) === null || _a2 === void 0 ? void 0 : _a2[key]) === null || _b2 === void 0 ? void 0 : _b2.find((alias) => { const desc2 = descs[alias]; return typeof desc2 === "string" && desc2.length > 0; }); const descFromAlias = aliasKey ? descs[aliasKey] : void 0; const desc = (_d = (_c2 = descs[key]) !== null && _c2 !== void 0 ? _c2 : descFromAlias) !== null && _d !== void 0 ? _d : ""; keyWithDesc = `${key.replace(/:/g, "\\:")}:${desc.replace("__yargsString__:", "").replace(/(\r\n|\n|\r)/gm, " ")}`; } const startsByTwoDashes = (s) => /^--/.test(s); const isShortOption = (s) => /^[^0-9]$/.test(s); const dashes = !startsByTwoDashes(current) && isShortOption(key) ? "-" : "--"; completions.push(dashes + keyWithDesc); if (negable) { completions.push(dashes + "no-" + keyWithDesc); } } customCompletion(args, argv, current, done) { assertNotStrictEqual(this.customCompletionFunction, null, this.shim); if (isSyncCompletionFunction(this.customCompletionFunction)) { const result = this.customCompletionFunction(current, argv); if (isPromise(result)) { return result.then((list) => { this.shim.process.nextTick(() => { done(null, list); }); }).catch((err) => { this.shim.process.nextTick(() => { done(err, void 0); }); }); } return done(null, result); } else if (isFallbackCompletionFunction(this.customCompletionFunction)) { return this.customCompletionFunction(current, argv, (onCompleted = done) => this.defaultCompletion(args, argv, current, onCompleted), (completions) => { done(null, completions); }); } else { return this.customCompletionFunction(current, argv, (completions) => { done(null, completions); }); } } getCompletion(args, done) { const current = args.length ? args[args.length - 1] : ""; const argv = this.yargs.parse(args, true); const completionFunction = this.customCompletionFunction ? (argv2) => this.customCompletion(args, argv2, current, done) : (argv2) => this.defaultCompletion(args, argv2, current, done); return isPromise(argv) ? argv.then(completionFunction) : completionFunction(argv); } generateCompletionScript($0, cmd) { let script = this.zshShell ? completionZshTemplate : completionShTemplate; const name = this.shim.path.basename($0); if ($0.match(/\.js$/)) $0 = `./${$0}`; script = script.replace(/{{app_name}}/g, name); script = script.replace(/{{completion_command}}/g, cmd); return script.replace(/{{app_path}}/g, $0); } registerFunction(fn) { this.customCompletionFunction = fn; } setParsed(parsed) { this.aliases = parsed.aliases; } }; function completion(yargs, usage2, command2, shim3) { return new Completion(yargs, usage2, command2, shim3); } function isSyncCompletionFunction(completionFunction) { return completionFunction.length < 3; } function isFallbackCompletionFunction(completionFunction) { return completionFunction.length > 3; } // node_modules/yargs/build/lib/utils/levenshtein.js function levenshtein(a, b) { if (a.length === 0) return b.length; if (b.length === 0) return a.length; const matrix = []; let i; for (i = 0; i <= b.length; i++) { matrix[i] = [i]; } let j; for (j = 0; j <= a.length; j++) { matrix[0][j] = j; } for (i = 1; i <= b.length; i++) { for (j = 1; j <= a.length; j++) { if (b.charAt(i - 1) === a.charAt(j - 1)) { matrix[i][j] = matrix[i - 1][j - 1]; } else { if (i > 1 && j > 1 && b.charAt(i - 2) === a.charAt(j - 1) && b.charAt(i - 1) === a.charAt(j - 2)) { matrix[i][j] = matrix[i - 2][j - 2] + 1; } else { matrix[i][j] = Math.min(matrix[i - 1][j - 1] + 1, Math.min(matrix[i][j - 1] + 1, matrix[i - 1][j] + 1)); } } } } return matrix[b.length][a.length]; } // node_modules/yargs/build/lib/validation.js var specialKeys = ["$0", "--", "_"]; function validation(yargs, usage2, shim3) { const __ = shim3.y18n.__; const __n = shim3.y18n.__n; const self = {}; self.nonOptionCount = function nonOptionCount(argv) { const demandedCommands = yargs.getDemandedCommands(); const positionalCount = argv._.length + (argv["--"] ? argv["--"].length : 0); const _s = positionalCount - yargs.getInternalMethods().getContext().commands.length; if (demandedCommands._ && (_s < demandedCommands._.min || _s > demandedCommands._.max)) { if (_s < demandedCommands._.min) { if (demandedCommands._.minMsg !== void 0) { usage2.fail(demandedCommands._.minMsg ? demandedCommands._.minMsg.replace(/\$0/g, _s.toString()).replace(/\$1/, demandedCommands._.min.toString()) : null); } else { usage2.fail(__n("Not enough non-option arguments: got %s, need at least %s", "Not enough non-option arguments: got %s, need at least %s", _s, _s.toString(), demandedCommands._.min.toString())); } } else if (_s > demandedCommands._.max) { if (demandedCommands._.maxMsg !== void 0) { usage2.fail(demandedCommands._.maxMsg ? demandedCommands._.maxMsg.replace(/\$0/g, _s.toString()).replace(/\$1/, demandedCommands._.max.toString()) : null); } else { usage2.fail(__n("Too many non-option arguments: got %s, maximum of %s", "Too many non-option arguments: got %s, maximum of %s", _s, _s.toString(), demandedCommands._.max.toString())); } } } }; self.positionalCount = function positionalCount(required, observed) { if (observed < required) { usage2.fail(__n("Not enough non-option arguments: got %s, need at least %s", "Not enough non-option arguments: got %s, need at least %s", observed, observed + "", required + "")); } }; self.requiredArguments = function requiredArguments(argv, demandedOptions) { let missing = null; for (const key of Object.keys(demandedOptions)) { if (!Object.prototype.hasOwnProperty.call(argv, key) || typeof argv[key] === "undefined") { missing = missing || {}; missing[key] = demandedOptions[key]; } } if (missing) { const customMsgs = []; for (const key of Object.keys(missing)) { const msg = missing[key]; if (msg && customMsgs.indexOf(msg) < 0) { customMsgs.push(msg); } } const customMsg = customMsgs.length ? ` ${customMsgs.join("\n")}` : ""; usage2.fail(__n("Missing required argument: %s", "Missing required arguments: %s", Object.keys(missing).length, Object.keys(missing).join(", ") + customMsg)); } }; self.unknownArguments = function unknownArguments(argv, aliases, positionalMap, isDefaultCommand, checkPositionals = true) { var _a2; const commandKeys = yargs.getInternalMethods().getCommandInstance().getCommands(); const unknown = []; const currentContext = yargs.getInternalMethods().getContext(); Object.keys(argv).forEach((key) => { if (!specialKeys.includes(key) && !Object.prototype.hasOwnProperty.call(positionalMap, key) && !Object.prototype.hasOwnProperty.call(yargs.getInternalMethods().getParseContext(), key) && !self.isValidAndSomeAliasIsNotNew(key, aliases)) { unknown.push(key); } }); if (checkPositionals && (currentContext.commands.length > 0 || commandKeys.length > 0 || isDefaultCommand)) { argv._.slice(currentContext.commands.length).forEach((key) => { if (!commandKeys.includes("" + key)) { unknown.push("" + key); } }); } if (checkPositionals) { const demandedCommands = yargs.getDemandedCommands(); const maxNonOptDemanded = ((_a2 = demandedCommands._) === null || _a2 === void 0 ? void 0 : _a2.max) || 0; const expected = currentContext.commands.length + maxNonOptDemanded; if (expected < argv._.length) { argv._.slice(expected).forEach((key) => { key = String(key); if (!currentContext.commands.includes(key) && !unknown.includes(key)) { unknown.push(key); } }); } } if (unknown.length) { usage2.fail(__n("Unknown argument: %s", "Unknown arguments: %s", unknown.length, unknown.map((s) => s.trim() ? s : `"${s}"`).join(", "))); } }; self.unknownCommands = function unknownCommands(argv) { const commandKeys = yargs.getInternalMethods().getCommandInstance().getCommands(); const unknown = []; const currentContext = yargs.getInternalMethods().getContext(); if (currentContext.commands.length > 0 || commandKeys.length > 0) { argv._.slice(currentContext.commands.length).forEach((key) => { if (!commandKeys.includes("" + key)) { unknown.push("" + key); } }); } if (unknown.length > 0) { usage2.fail(__n("Unknown command: %s", "Unknown commands: %s", unknown.length, unknown.join(", "))); return true; } else { return false; } }; self.isValidAndSomeAliasIsNotNew = function isValidAndSomeAliasIsNotNew(key, aliases) { if (!Object.prototype.hasOwnProperty.call(aliases, key)) { return false; } const newAliases = yargs.parsed.newAliases; return [key, ...aliases[key]].some((a) => !Object.prototype.hasOwnProperty.call(newAliases, a) || !newAliases[key]); }; self.limitedChoices = function limitedChoices(argv) { const options = yargs.getOptions(); const invalid = {}; if (!Object.keys(options.choices).length) return; Object.keys(argv).forEach((key) => { if (specialKeys.indexOf(key) === -1 && Object.prototype.hasOwnProperty.call(options.choices, key)) { [].concat(argv[key]).forEach((value) => { if (options.choices[key].indexOf(value) === -1 && value !== void 0) { invalid[key] = (invalid[key] || []).concat(value); } }); } }); const invalidKeys = Object.keys(invalid); if (!invalidKeys.length) return; let msg = __("Invalid values:"); invalidKeys.forEach((key) => { msg += ` ${__("Argument: %s, Given: %s, Choices: %s", key, usage2.stringifiedValues(invalid[key]), usage2.stringifiedValues(options.choices[key]))}`; }); usage2.fail(msg); }; let implied = {}; self.implies = function implies(key, value) { argsert(" [array|number|string]", [key, value], arguments.length); if (typeof key === "object") { Object.keys(key).forEach((k) => { self.implies(k, key[k]); }); } else { yargs.global(key); if (!implied[key]) { implied[key] = []; } if (Array.isArray(value)) { value.forEach((i) => self.implies(key, i)); } else { assertNotStrictEqual(value, void 0, shim3); implied[key].push(value); } } }; self.getImplied = function getImplied() { return implied; }; function keyExists(argv, val) { const num = Number(val); val = isNaN(num) ? val : num; if (typeof val === "number") { val = argv._.length >= val; } else if (val.match(/^--no-.+/)) { val = val.match(/^--no-(.+)/)[1]; val = !Object.prototype.hasOwnProperty.call(argv, val); } else { val = Object.prototype.hasOwnProperty.call(argv, val); } return val; } self.implications = function implications(argv) { const implyFail = []; Object.keys(implied).forEach((key) => { const origKey = key; (implied[key] || []).forEach((value) => { let key2 = origKey; const origValue = value; key2 = keyExists(argv, key2); value = keyExists(argv, value); if (key2 && !value) { implyFail.push(` ${origKey} -> ${origValue}`); } }); }); if (implyFail.length) { let msg = `${__("Implications failed:")} `; implyFail.forEach((value) => { msg += value; }); usage2.fail(msg); } }; let conflicting = {}; self.conflicts = function conflicts(key, value) { argsert(" [array|string]", [key, value], arguments.length); if (typeof key === "object") { Object.keys(key).forEach((k) => { self.conflicts(k, key[k]); }); } else { yargs.global(key); if (!conflicting[key]) { conflicting[key] = []; } if (Array.isArray(value)) { value.forEach((i) => self.conflicts(key, i)); } else { conflicting[key].push(value); } } }; self.getConflicting = () => conflicting; self.conflicting = function conflictingFn(argv) { Object.keys(argv).forEach((key) => { if (conflicting[key]) { conflicting[key].forEach((value) => { if (value && argv[key] !== void 0 && argv[value] !== void 0) { usage2.fail(__("Arguments %s and %s are mutually exclusive", key, value)); } }); } }); if (yargs.getInternalMethods().getParserConfiguration()["strip-dashed"]) { Object.keys(conflicting).forEach((key) => { conflicting[key].forEach((value) => { if (value && argv[shim3.Parser.camelCase(key)] !== void 0 && argv[shim3.Parser.camelCase(value)] !== void 0) { usage2.fail(__("Arguments %s and %s are mutually exclusive", key, value)); } }); }); } }; self.recommendCommands = function recommendCommands(cmd, potentialCommands) { const threshold = 3; potentialCommands = potentialCommands.sort((a, b) => b.length - a.length); let recommended = null; let bestDistance = Infinity; for (let i = 0, candidate; (candidate = potentialCommands[i]) !== void 0; i++) { const d = levenshtein(cmd, candidate); if (d <= threshold && d < bestDistance) { bestDistance = d; recommended = candidate; } } if (recommended) usage2.fail(__("Did you mean %s?", recommended)); }; self.reset = function reset(localLookup) { implied = objFilter(implied, (k) => !localLookup[k]); conflicting = objFilter(conflicting, (k) => !localLookup[k]); return self; }; const frozens = []; self.freeze = function freeze() { frozens.push({ implied, conflicting }); }; self.unfreeze = function unfreeze() { const frozen = frozens.pop(); assertNotStrictEqual(frozen, void 0, shim3); ({ implied, conflicting } = frozen); }; return self; } // node_modules/yargs/build/lib/utils/apply-extends.js var previouslyVisitedConfigs = []; var shim2; function applyExtends(config, cwd, mergeExtends, _shim) { shim2 = _shim; let defaultConfig = {}; if (Object.prototype.hasOwnProperty.call(config, "extends")) { if (typeof config.extends !== "string") return defaultConfig; const isPath = /\.json|\..*rc$/.test(config.extends); let pathToDefault = null; if (!isPath) { try { pathToDefault = __require.resolve(config.extends); } catch (_err) { return config; } } else { pathToDefault = getPathToDefaultConfig(cwd, config.extends); } checkForCircularExtends(pathToDefault); previouslyVisitedConfigs.push(pathToDefault); defaultConfig = isPath ? JSON.parse(shim2.readFileSync(pathToDefault, "utf8")) : __require(config.extends); delete config.extends; defaultConfig = applyExtends(defaultConfig, shim2.path.dirname(pathToDefault), mergeExtends, shim2); } previouslyVisitedConfigs = []; return mergeExtends ? mergeDeep(defaultConfig, config) : Object.assign({}, defaultConfig, config); } function checkForCircularExtends(cfgPath) { if (previouslyVisitedConfigs.indexOf(cfgPath) > -1) { throw new YError(`Circular extended configurations: '${cfgPath}'.`); } } function getPathToDefaultConfig(cwd, pathToExtend) { return shim2.path.resolve(cwd, pathToExtend); } function mergeDeep(config1, config2) { const target = {}; function isObject(obj) { return obj && typeof obj === "object" && !Array.isArray(obj); } Object.assign(target, config1); for (const key of Object.keys(config2)) { if (isObject(config2[key]) && isObject(target[key])) { target[key] = mergeDeep(config1[key], config2[key]); } else { target[key] = config2[key]; } } return target; } // node_modules/yargs/build/lib/yargs-factory.js var __classPrivateFieldSet = function(receiver, state, value, kind, f) { if (kind === "m") throw new TypeError("Private method is not writable"); if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a setter"); if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot write private member to an object whose class did not declare it"); return kind === "a" ? f.call(receiver, value) : f ? f.value = value : state.set(receiver, value), value; }; var __classPrivateFieldGet = function(receiver, state, kind, f) { if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a getter"); if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it"); return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver); }; var _YargsInstance_command; var _YargsInstance_cwd; var _YargsInstance_context; var _YargsInstance_completion; var _YargsInstance_completionCommand; var _YargsInstance_defaultShowHiddenOpt; var _YargsInstance_exitError; var _YargsInstance_detectLocale; var _YargsInstance_emittedWarnings; var _YargsInstance_exitProcess; var _YargsInstance_frozens; var _YargsInstance_globalMiddleware; var _YargsInstance_groups; var _YargsInstance_hasOutput; var _YargsInstance_helpOpt; var _YargsInstance_isGlobalContext; var _YargsInstance_logger; var _YargsInstance_output; var _YargsInstance_options; var _YargsInstance_parentRequire; var _YargsInstance_parserConfig; var _YargsInstance_parseFn; var _YargsInstance_parseContext; var _YargsInstance_pkgs; var _YargsInstance_preservedGroups; var _YargsInstance_processArgs; var _YargsInstance_recommendCommands; var _YargsInstance_shim; var _YargsInstance_strict; var _YargsInstance_strictCommands; var _YargsInstance_strictOptions; var _YargsInstance_usage; var _YargsInstance_usageConfig; var _YargsInstance_versionOpt; var _YargsInstance_validation; function YargsFactory(_shim) { return (processArgs = [], cwd = _shim.process.cwd(), parentRequire) => { const yargs = new YargsInstance(processArgs, cwd, parentRequire, _shim); Object.defineProperty(yargs, "argv", { get: () => { return yargs.parse(); }, enumerable: true }); yargs.help(); yargs.version(); return yargs; }; } var kCopyDoubleDash = Symbol("copyDoubleDash"); var kCreateLogger = Symbol("copyDoubleDash"); var kDeleteFromParserHintObject = Symbol("deleteFromParserHintObject"); var kEmitWarning = Symbol("emitWarning"); var kFreeze = Symbol("freeze"); var kGetDollarZero = Symbol("getDollarZero"); var kGetParserConfiguration = Symbol("getParserConfiguration"); var kGetUsageConfiguration = Symbol("getUsageConfiguration"); var kGuessLocale = Symbol("guessLocale"); var kGuessVersion = Symbol("guessVersion"); var kParsePositionalNumbers = Symbol("parsePositionalNumbers"); var kPkgUp = Symbol("pkgUp"); var kPopulateParserHintArray = Symbol("populateParserHintArray"); var kPopulateParserHintSingleValueDictionary = Symbol("populateParserHintSingleValueDictionary"); var kPopulateParserHintArrayDictionary = Symbol("populateParserHintArrayDictionary"); var kPopulateParserHintDictionary = Symbol("populateParserHintDictionary"); var kSanitizeKey = Symbol("sanitizeKey"); var kSetKey = Symbol("setKey"); var kUnfreeze = Symbol("unfreeze"); var kValidateAsync = Symbol("validateAsync"); var kGetCommandInstance = Symbol("getCommandInstance"); var kGetContext = Symbol("getContext"); var kGetHasOutput = Symbol("getHasOutput"); var kGetLoggerInstance = Symbol("getLoggerInstance"); var kGetParseContext = Symbol("getParseContext"); var kGetUsageInstance = Symbol("getUsageInstance"); var kGetValidationInstance = Symbol("getValidationInstance"); var kHasParseCallback = Symbol("hasParseCallback"); var kIsGlobalContext = Symbol("isGlobalContext"); var kPostProcess = Symbol("postProcess"); var kRebase = Symbol("rebase"); var kReset = Symbol("reset"); var kRunYargsParserAndExecuteCommands = Symbol("runYargsParserAndExecuteCommands"); var kRunValidation = Symbol("runValidation"); var kSetHasOutput = Symbol("setHasOutput"); var kTrackManuallySetKeys = Symbol("kTrackManuallySetKeys"); var YargsInstance = class { constructor(processArgs = [], cwd, parentRequire, shim3) { this.customScriptName = false; this.parsed = false; _YargsInstance_command.set(this, void 0); _YargsInstance_cwd.set(this, void 0); _YargsInstance_context.set(this, { commands: [], fullCommands: [] }); _YargsInstance_completion.set(this, null); _YargsInstance_completionCommand.set(this, null); _YargsInstance_defaultShowHiddenOpt.set(this, "show-hidden"); _YargsInstance_exitError.set(this, null); _YargsInstance_detectLocale.set(this, true); _YargsInstance_emittedWarnings.set(this, {}); _YargsInstance_exitProcess.set(this, true); _YargsInstance_frozens.set(this, []); _YargsInstance_globalMiddleware.set(this, void 0); _YargsInstance_groups.set(this, {}); _YargsInstance_hasOutput.set(this, false); _YargsInstance_helpOpt.set(this, null); _YargsInstance_isGlobalContext.set(this, true); _YargsInstance_logger.set(this, void 0); _YargsInstance_output.set(this, ""); _YargsInstance_options.set(this, void 0); _YargsInstance_parentRequire.set(this, void 0); _YargsInstance_parserConfig.set(this, {}); _YargsInstance_parseFn.set(this, null); _YargsInstance_parseContext.set(this, null); _YargsInstance_pkgs.set(this, {}); _YargsInstance_preservedGroups.set(this, {}); _YargsInstance_processArgs.set(this, void 0); _YargsInstance_recommendCommands.set(this, false); _YargsInstance_shim.set(this, void 0); _YargsInstance_strict.set(this, false); _YargsInstance_strictCommands.set(this, false); _YargsInstance_strictOptions.set(this, false); _YargsInstance_usage.set(this, void 0); _YargsInstance_usageConfig.set(this, {}); _YargsInstance_versionOpt.set(this, null); _YargsInstance_validation.set(this, void 0); __classPrivateFieldSet(this, _YargsInstance_shim, shim3, "f"); __classPrivateFieldSet(this, _YargsInstance_processArgs, processArgs, "f"); __classPrivateFieldSet(this, _YargsInstance_cwd, cwd, "f"); __classPrivateFieldSet(this, _YargsInstance_parentRequire, parentRequire, "f"); __classPrivateFieldSet(this, _YargsInstance_globalMiddleware, new GlobalMiddleware(this), "f"); this.$0 = this[kGetDollarZero](); this[kReset](); __classPrivateFieldSet(this, _YargsInstance_command, __classPrivateFieldGet(this, _YargsInstance_command, "f"), "f"); __classPrivateFieldSet(this, _YargsInstance_usage, __classPrivateFieldGet(this, _YargsInstance_usage, "f"), "f"); __classPrivateFieldSet(this, _YargsInstance_validation, __classPrivateFieldGet(this, _YargsInstance_validation, "f"), "f"); __classPrivateFieldSet(this, _YargsInstance_options, __classPrivateFieldGet(this, _YargsInstance_options, "f"), "f"); __classPrivateFieldGet(this, _YargsInstance_options, "f").showHiddenOpt = __classPrivateFieldGet(this, _YargsInstance_defaultShowHiddenOpt, "f"); __classPrivateFieldSet(this, _YargsInstance_logger, this[kCreateLogger](), "f"); } addHelpOpt(opt, msg) { const defaultHelpOpt = "help"; argsert("[string|boolean] [string]", [opt, msg], arguments.length); if (__classPrivateFieldGet(this, _YargsInstance_helpOpt, "f")) { this[kDeleteFromParserHintObject](__classPrivateFieldGet(this, _YargsInstance_helpOpt, "f")); __classPrivateFieldSet(this, _YargsInstance_helpOpt, null, "f"); } if (opt === false && msg === void 0) return this; __classPrivateFieldSet(this, _YargsInstance_helpOpt, typeof opt === "string" ? opt : defaultHelpOpt, "f"); this.boolean(__classPrivateFieldGet(this, _YargsInstance_helpOpt, "f")); this.describe(__classPrivateFieldGet(this, _YargsInstance_helpOpt, "f"), msg || __classPrivateFieldGet(this, _YargsInstance_usage, "f").deferY18nLookup("Show help")); return this; } help(opt, msg) { return this.addHelpOpt(opt, msg); } addShowHiddenOpt(opt, msg) { argsert("[string|boolean] [string]", [opt, msg], arguments.length); if (opt === false && msg === void 0) return this; const showHiddenOpt = typeof opt === "string" ? opt : __classPrivateFieldGet(this, _YargsInstance_defaultShowHiddenOpt, "f"); this.boolean(showHiddenOpt); this.describe(showHiddenOpt, msg || __classPrivateFieldGet(this, _YargsInstance_usage, "f").deferY18nLookup("Show hidden options")); __classPrivateFieldGet(this, _YargsInstance_options, "f").showHiddenOpt = showHiddenOpt; return this; } showHidden(opt, msg) { return this.addShowHiddenOpt(opt, msg); } alias(key, value) { argsert(" [string|array]", [key, value], arguments.length); this[kPopulateParserHintArrayDictionary](this.alias.bind(this), "alias", key, value); return this; } array(keys) { argsert("", [keys], arguments.length); this[kPopulateParserHintArray]("array", keys); this[kTrackManuallySetKeys](keys); return this; } boolean(keys) { argsert("", [keys], arguments.length); this[kPopulateParserHintArray]("boolean", keys); this[kTrackManuallySetKeys](keys); return this; } check(f, global) { argsert(" [boolean]", [f, global], arguments.length); this.middleware((argv, _yargs) => { return maybeAsyncResult(() => { return f(argv, _yargs.getOptions()); }, (result) => { if (!result) { __classPrivateFieldGet(this, _YargsInstance_usage, "f").fail(__classPrivateFieldGet(this, _YargsInstance_shim, "f").y18n.__("Argument check failed: %s", f.toString())); } else if (typeof result === "string" || result instanceof Error) { __classPrivateFieldGet(this, _YargsInstance_usage, "f").fail(result.toString(), result); } return argv; }, (err) => { __classPrivateFieldGet(this, _YargsInstance_usage, "f").fail(err.message ? err.message : err.toString(), err); return argv; }); }, false, global); return this; } choices(key, value) { argsert(" [string|array]", [key, value], arguments.length); this[kPopulateParserHintArrayDictionary](this.choices.bind(this), "choices", key, value); return this; } coerce(keys, value) { argsert(" [function]", [keys, value], arguments.length); if (Array.isArray(keys)) { if (!value) { throw new YError("coerce callback must be provided"); } for (const key of keys) { this.coerce(key, value); } return this; } else if (typeof keys === "object") { for (const key of Object.keys(keys)) { this.coerce(key, keys[key]); } return this; } if (!value) { throw new YError("coerce callback must be provided"); } __classPrivateFieldGet(this, _YargsInstance_options, "f").key[keys] = true; __classPrivateFieldGet(this, _YargsInstance_globalMiddleware, "f").addCoerceMiddleware((argv, yargs) => { let aliases; const shouldCoerce = Object.prototype.hasOwnProperty.call(argv, keys); if (!shouldCoerce) { return argv; } return maybeAsyncResult(() => { aliases = yargs.getAliases(); return value(argv[keys]); }, (result) => { argv[keys] = result; const stripAliased = yargs.getInternalMethods().getParserConfiguration()["strip-aliased"]; if (aliases[keys] && stripAliased !== true) { for (const alias of aliases[keys]) { argv[alias] = result; } } return argv; }, (err) => { throw new YError(err.message); }); }, keys); return this; } conflicts(key1, key2) { argsert(" [string|array]", [key1, key2], arguments.length); __classPrivateFieldGet(this, _YargsInstance_validation, "f").conflicts(key1, key2); return this; } config(key = "config", msg, parseFn) { argsert("[object|string] [string|function] [function]", [key, msg, parseFn], arguments.length); if (typeof key === "object" && !Array.isArray(key)) { key = applyExtends(key, __classPrivateFieldGet(this, _YargsInstance_cwd, "f"), this[kGetParserConfiguration]()["deep-merge-config"] || false, __classPrivateFieldGet(this, _YargsInstance_shim, "f")); __classPrivateFieldGet(this, _YargsInstance_options, "f").configObjects = (__classPrivateFieldGet(this, _YargsInstance_options, "f").configObjects || []).concat(key); return this; } if (typeof msg === "function") { parseFn = msg; msg = void 0; } this.describe(key, msg || __classPrivateFieldGet(this, _YargsInstance_usage, "f").deferY18nLookup("Path to JSON config file")); (Array.isArray(key) ? key : [key]).forEach((k) => { __classPrivateFieldGet(this, _YargsInstance_options, "f").config[k] = parseFn || true; }); return this; } completion(cmd, desc, fn) { argsert("[string] [string|boolean|function] [function]", [cmd, desc, fn], arguments.length); if (typeof desc === "function") { fn = desc; desc = void 0; } __classPrivateFieldSet(this, _YargsInstance_completionCommand, cmd || __classPrivateFieldGet(this, _YargsInstance_completionCommand, "f") || "completion", "f"); if (!desc && desc !== false) { desc = "generate completion script"; } this.command(__classPrivateFieldGet(this, _YargsInstance_completionCommand, "f"), desc); if (fn) __classPrivateFieldGet(this, _YargsInstance_completion, "f").registerFunction(fn); return this; } command(cmd, description, builder, handler, middlewares, deprecated) { argsert(" [string|boolean] [function|object] [function] [array] [boolean|string]", [cmd, description, builder, handler, middlewares, deprecated], arguments.length); __classPrivateFieldGet(this, _YargsInstance_command, "f").addHandler(cmd, description, builder, handler, middlewares, deprecated); return this; } commands(cmd, description, builder, handler, middlewares, deprecated) { return this.command(cmd, description, builder, handler, middlewares, deprecated); } commandDir(dir, opts) { argsert(" [object]", [dir, opts], arguments.length); const req = __classPrivateFieldGet(this, _YargsInstance_parentRequire, "f") || __classPrivateFieldGet(this, _YargsInstance_shim, "f").require; __classPrivateFieldGet(this, _YargsInstance_command, "f").addDirectory(dir, req, __classPrivateFieldGet(this, _YargsInstance_shim, "f").getCallerFile(), opts); return this; } count(keys) { argsert("", [keys], arguments.length); this[kPopulateParserHintArray]("count", keys); this[kTrackManuallySetKeys](keys); return this; } default(key, value, defaultDescription) { argsert(" [*] [string]", [key, value, defaultDescription], arguments.length); if (defaultDescription) { assertSingleKey(key, __classPrivateFieldGet(this, _YargsInstance_shim, "f")); __classPrivateFieldGet(this, _YargsInstance_options, "f").defaultDescription[key] = defaultDescription; } if (typeof value === "function") { assertSingleKey(key, __classPrivateFieldGet(this, _YargsInstance_shim, "f")); if (!__classPrivateFieldGet(this, _YargsInstance_options, "f").defaultDescription[key]) __classPrivateFieldGet(this, _YargsInstance_options, "f").defaultDescription[key] = __classPrivateFieldGet(this, _YargsInstance_usage, "f").functionDescription(value); value = value.call(); } this[kPopulateParserHintSingleValueDictionary](this.default.bind(this), "default", key, value); return this; } defaults(key, value, defaultDescription) { return this.default(key, value, defaultDescription); } demandCommand(min = 1, max, minMsg, maxMsg) { argsert("[number] [number|string] [string|null|undefined] [string|null|undefined]", [min, max, minMsg, maxMsg], arguments.length); if (typeof max !== "number") { minMsg = max; max = Infinity; } this.global("_", false); __classPrivateFieldGet(this, _YargsInstance_options, "f").demandedCommands._ = { min, max, minMsg, maxMsg }; return this; } demand(keys, max, msg) { if (Array.isArray(max)) { max.forEach((key) => { assertNotStrictEqual(msg, true, __classPrivateFieldGet(this, _YargsInstance_shim, "f")); this.demandOption(key, msg); }); max = Infinity; } else if (typeof max !== "number") { msg = max; max = Infinity; } if (typeof keys === "number") { assertNotStrictEqual(msg, true, __classPrivateFieldGet(this, _YargsInstance_shim, "f")); this.demandCommand(keys, max, msg, msg); } else if (Array.isArray(keys)) { keys.forEach((key) => { assertNotStrictEqual(msg, true, __classPrivateFieldGet(this, _YargsInstance_shim, "f")); this.demandOption(key, msg); }); } else { if (typeof msg === "string") { this.demandOption(keys, msg); } else if (msg === true || typeof msg === "undefined") { this.demandOption(keys); } } return this; } demandOption(keys, msg) { argsert(" [string]", [keys, msg], arguments.length); this[kPopulateParserHintSingleValueDictionary](this.demandOption.bind(this), "demandedOptions", keys, msg); return this; } deprecateOption(option, message) { argsert(" [string|boolean]", [option, message], arguments.length); __classPrivateFieldGet(this, _YargsInstance_options, "f").deprecatedOptions[option] = message; return this; } describe(keys, description) { argsert(" [string]", [keys, description], arguments.length); this[kSetKey](keys, true); __classPrivateFieldGet(this, _YargsInstance_usage, "f").describe(keys, description); return this; } detectLocale(detect) { argsert("", [detect], arguments.length); __classPrivateFieldSet(this, _YargsInstance_detectLocale, detect, "f"); return this; } env(prefix) { argsert("[string|boolean]", [prefix], arguments.length); if (prefix === false) delete __classPrivateFieldGet(this, _YargsInstance_options, "f").envPrefix; else __classPrivateFieldGet(this, _YargsInstance_options, "f").envPrefix = prefix || ""; return this; } epilogue(msg) { argsert("", [msg], arguments.length); __classPrivateFieldGet(this, _YargsInstance_usage, "f").epilog(msg); return this; } epilog(msg) { return this.epilogue(msg); } example(cmd, description) { argsert(" [string]", [cmd, description], arguments.length); if (Array.isArray(cmd)) { cmd.forEach((exampleParams) => this.example(...exampleParams)); } else { __classPrivateFieldGet(this, _YargsInstance_usage, "f").example(cmd, description); } return this; } exit(code, err) { __classPrivateFieldSet(this, _YargsInstance_hasOutput, true, "f"); __classPrivateFieldSet(this, _YargsInstance_exitError, err, "f"); if (__classPrivateFieldGet(this, _YargsInstance_exitProcess, "f")) __classPrivateFieldGet(this, _YargsInstance_shim, "f").process.exit(code); } exitProcess(enabled = true) { argsert("[boolean]", [enabled], arguments.length); __classPrivateFieldSet(this, _YargsInstance_exitProcess, enabled, "f"); return this; } fail(f) { argsert("", [f], arguments.length); if (typeof f === "boolean" && f !== false) { throw new YError("Invalid first argument. Expected function or boolean 'false'"); } __classPrivateFieldGet(this, _YargsInstance_usage, "f").failFn(f); return this; } getAliases() { return this.parsed ? this.parsed.aliases : {}; } async getCompletion(args, done) { argsert(" [function]", [args, done], arguments.length); if (!done) { return new Promise((resolve9, reject) => { __classPrivateFieldGet(this, _YargsInstance_completion, "f").getCompletion(args, (err, completions) => { if (err) reject(err); else resolve9(completions); }); }); } else { return __classPrivateFieldGet(this, _YargsInstance_completion, "f").getCompletion(args, done); } } getDemandedOptions() { argsert([], 0); return __classPrivateFieldGet(this, _YargsInstance_options, "f").demandedOptions; } getDemandedCommands() { argsert([], 0); return __classPrivateFieldGet(this, _YargsInstance_options, "f").demandedCommands; } getDeprecatedOptions() { argsert([], 0); return __classPrivateFieldGet(this, _YargsInstance_options, "f").deprecatedOptions; } getDetectLocale() { return __classPrivateFieldGet(this, _YargsInstance_detectLocale, "f"); } getExitProcess() { return __classPrivateFieldGet(this, _YargsInstance_exitProcess, "f"); } getGroups() { return Object.assign({}, __classPrivateFieldGet(this, _YargsInstance_groups, "f"), __classPrivateFieldGet(this, _YargsInstance_preservedGroups, "f")); } getHelp() { __classPrivateFieldSet(this, _YargsInstance_hasOutput, true, "f"); if (!__classPrivateFieldGet(this, _YargsInstance_usage, "f").hasCachedHelpMessage()) { if (!this.parsed) { const parse2 = this[kRunYargsParserAndExecuteCommands](__classPrivateFieldGet(this, _YargsInstance_processArgs, "f"), void 0, void 0, 0, true); if (isPromise(parse2)) { return parse2.then(() => { return __classPrivateFieldGet(this, _YargsInstance_usage, "f").help(); }); } } const builderResponse = __classPrivateFieldGet(this, _YargsInstance_command, "f").runDefaultBuilderOn(this); if (isPromise(builderResponse)) { return builderResponse.then(() => { return __classPrivateFieldGet(this, _YargsInstance_usage, "f").help(); }); } } return Promise.resolve(__classPrivateFieldGet(this, _YargsInstance_usage, "f").help()); } getOptions() { return __classPrivateFieldGet(this, _YargsInstance_options, "f"); } getStrict() { return __classPrivateFieldGet(this, _YargsInstance_strict, "f"); } getStrictCommands() { return __classPrivateFieldGet(this, _YargsInstance_strictCommands, "f"); } getStrictOptions() { return __classPrivateFieldGet(this, _YargsInstance_strictOptions, "f"); } global(globals, global) { argsert(" [boolean]", [globals, global], arguments.length); globals = [].concat(globals); if (global !== false) { __classPrivateFieldGet(this, _YargsInstance_options, "f").local = __classPrivateFieldGet(this, _YargsInstance_options, "f").local.filter((l) => globals.indexOf(l) === -1); } else { globals.forEach((g) => { if (!__classPrivateFieldGet(this, _YargsInstance_options, "f").local.includes(g)) __classPrivateFieldGet(this, _YargsInstance_options, "f").local.push(g); }); } return this; } group(opts, groupName) { argsert(" ", [opts, groupName], arguments.length); const existing = __classPrivateFieldGet(this, _YargsInstance_preservedGroups, "f")[groupName] || __classPrivateFieldGet(this, _YargsInstance_groups, "f")[groupName]; if (__classPrivateFieldGet(this, _YargsInstance_preservedGroups, "f")[groupName]) { delete __classPrivateFieldGet(this, _YargsInstance_preservedGroups, "f")[groupName]; } const seen = {}; __classPrivateFieldGet(this, _YargsInstance_groups, "f")[groupName] = (existing || []).concat(opts).filter((key) => { if (seen[key]) return false; return seen[key] = true; }); return this; } hide(key) { argsert("", [key], arguments.length); __classPrivateFieldGet(this, _YargsInstance_options, "f").hiddenOptions.push(key); return this; } implies(key, value) { argsert(" [number|string|array]", [key, value], arguments.length); __classPrivateFieldGet(this, _YargsInstance_validation, "f").implies(key, value); return this; } locale(locale) { argsert("[string]", [locale], arguments.length); if (locale === void 0) { this[kGuessLocale](); return __classPrivateFieldGet(this, _YargsInstance_shim, "f").y18n.getLocale(); } __classPrivateFieldSet(this, _YargsInstance_detectLocale, false, "f"); __classPrivateFieldGet(this, _YargsInstance_shim, "f").y18n.setLocale(locale); return this; } middleware(callback, applyBeforeValidation, global) { return __classPrivateFieldGet(this, _YargsInstance_globalMiddleware, "f").addMiddleware(callback, !!applyBeforeValidation, global); } nargs(key, value) { argsert(" [number]", [key, value], arguments.length); this[kPopulateParserHintSingleValueDictionary](this.nargs.bind(this), "narg", key, value); return this; } normalize(keys) { argsert("", [keys], arguments.length); this[kPopulateParserHintArray]("normalize", keys); return this; } number(keys) { argsert("", [keys], arguments.length); this[kPopulateParserHintArray]("number", keys); this[kTrackManuallySetKeys](keys); return this; } option(key, opt) { argsert(" [object]", [key, opt], arguments.length); if (typeof key === "object") { Object.keys(key).forEach((k) => { this.options(k, key[k]); }); } else { if (typeof opt !== "object") { opt = {}; } this[kTrackManuallySetKeys](key); if (__classPrivateFieldGet(this, _YargsInstance_versionOpt, "f") && (key === "version" || (opt === null || opt === void 0 ? void 0 : opt.alias) === "version")) { this[kEmitWarning]([ '"version" is a reserved word.', "Please do one of the following:", '- Disable version with `yargs.version(false)` if using "version" as an option', "- Use the built-in `yargs.version` method instead (if applicable)", "- Use a different option key", "https://yargs.js.org/docs/#api-reference-version" ].join("\n"), void 0, "versionWarning"); } __classPrivateFieldGet(this, _YargsInstance_options, "f").key[key] = true; if (opt.alias) this.alias(key, opt.alias); const deprecate = opt.deprecate || opt.deprecated; if (deprecate) { this.deprecateOption(key, deprecate); } const demand = opt.demand || opt.required || opt.require; if (demand) { this.demand(key, demand); } if (opt.demandOption) { this.demandOption(key, typeof opt.demandOption === "string" ? opt.demandOption : void 0); } if (opt.conflicts) { this.conflicts(key, opt.conflicts); } if ("default" in opt) { this.default(key, opt.default); } if (opt.implies !== void 0) { this.implies(key, opt.implies); } if (opt.nargs !== void 0) { this.nargs(key, opt.nargs); } if (opt.config) { this.config(key, opt.configParser); } if (opt.normalize) { this.normalize(key); } if (opt.choices) { this.choices(key, opt.choices); } if (opt.coerce) { this.coerce(key, opt.coerce); } if (opt.group) { this.group(key, opt.group); } if (opt.boolean || opt.type === "boolean") { this.boolean(key); if (opt.alias) this.boolean(opt.alias); } if (opt.array || opt.type === "array") { this.array(key); if (opt.alias) this.array(opt.alias); } if (opt.number || opt.type === "number") { this.number(key); if (opt.alias) this.number(opt.alias); } if (opt.string || opt.type === "string") { this.string(key); if (opt.alias) this.string(opt.alias); } if (opt.count || opt.type === "count") { this.count(key); } if (typeof opt.global === "boolean") { this.global(key, opt.global); } if (opt.defaultDescription) { __classPrivateFieldGet(this, _YargsInstance_options, "f").defaultDescription[key] = opt.defaultDescription; } if (opt.skipValidation) { this.skipValidation(key); } const desc = opt.describe || opt.description || opt.desc; const descriptions = __classPrivateFieldGet(this, _YargsInstance_usage, "f").getDescriptions(); if (!Object.prototype.hasOwnProperty.call(descriptions, key) || typeof desc === "string") { this.describe(key, desc); } if (opt.hidden) { this.hide(key); } if (opt.requiresArg) { this.requiresArg(key); } } return this; } options(key, opt) { return this.option(key, opt); } parse(args, shortCircuit, _parseFn) { argsert("[string|array] [function|boolean|object] [function]", [args, shortCircuit, _parseFn], arguments.length); this[kFreeze](); if (typeof args === "undefined") { args = __classPrivateFieldGet(this, _YargsInstance_processArgs, "f"); } if (typeof shortCircuit === "object") { __classPrivateFieldSet(this, _YargsInstance_parseContext, shortCircuit, "f"); shortCircuit = _parseFn; } if (typeof shortCircuit === "function") { __classPrivateFieldSet(this, _YargsInstance_parseFn, shortCircuit, "f"); shortCircuit = false; } if (!shortCircuit) __classPrivateFieldSet(this, _YargsInstance_processArgs, args, "f"); if (__classPrivateFieldGet(this, _YargsInstance_parseFn, "f")) __classPrivateFieldSet(this, _YargsInstance_exitProcess, false, "f"); const parsed = this[kRunYargsParserAndExecuteCommands](args, !!shortCircuit); const tmpParsed = this.parsed; __classPrivateFieldGet(this, _YargsInstance_completion, "f").setParsed(this.parsed); if (isPromise(parsed)) { return parsed.then((argv) => { if (__classPrivateFieldGet(this, _YargsInstance_parseFn, "f")) __classPrivateFieldGet(this, _YargsInstance_parseFn, "f").call(this, __classPrivateFieldGet(this, _YargsInstance_exitError, "f"), argv, __classPrivateFieldGet(this, _YargsInstance_output, "f")); return argv; }).catch((err) => { if (__classPrivateFieldGet(this, _YargsInstance_parseFn, "f")) { __classPrivateFieldGet(this, _YargsInstance_parseFn, "f")(err, this.parsed.argv, __classPrivateFieldGet(this, _YargsInstance_output, "f")); } throw err; }).finally(() => { this[kUnfreeze](); this.parsed = tmpParsed; }); } else { if (__classPrivateFieldGet(this, _YargsInstance_parseFn, "f")) __classPrivateFieldGet(this, _YargsInstance_parseFn, "f").call(this, __classPrivateFieldGet(this, _YargsInstance_exitError, "f"), parsed, __classPrivateFieldGet(this, _YargsInstance_output, "f")); this[kUnfreeze](); this.parsed = tmpParsed; } return parsed; } parseAsync(args, shortCircuit, _parseFn) { const maybePromise = this.parse(args, shortCircuit, _parseFn); return !isPromise(maybePromise) ? Promise.resolve(maybePromise) : maybePromise; } parseSync(args, shortCircuit, _parseFn) { const maybePromise = this.parse(args, shortCircuit, _parseFn); if (isPromise(maybePromise)) { throw new YError(".parseSync() must not be used with asynchronous builders, handlers, or middleware"); } return maybePromise; } parserConfiguration(config) { argsert("", [config], arguments.length); __classPrivateFieldSet(this, _YargsInstance_parserConfig, config, "f"); return this; } pkgConf(key, rootPath) { argsert(" [string]", [key, rootPath], arguments.length); let conf = null; const obj = this[kPkgUp](rootPath || __classPrivateFieldGet(this, _YargsInstance_cwd, "f")); if (obj[key] && typeof obj[key] === "object") { conf = applyExtends(obj[key], rootPath || __classPrivateFieldGet(this, _YargsInstance_cwd, "f"), this[kGetParserConfiguration]()["deep-merge-config"] || false, __classPrivateFieldGet(this, _YargsInstance_shim, "f")); __classPrivateFieldGet(this, _YargsInstance_options, "f").configObjects = (__classPrivateFieldGet(this, _YargsInstance_options, "f").configObjects || []).concat(conf); } return this; } positional(key, opts) { argsert(" ", [key, opts], arguments.length); const supportedOpts = [ "default", "defaultDescription", "implies", "normalize", "choices", "conflicts", "coerce", "type", "describe", "desc", "description", "alias" ]; opts = objFilter(opts, (k, v) => { if (k === "type" && !["string", "number", "boolean"].includes(v)) return false; return supportedOpts.includes(k); }); const fullCommand = __classPrivateFieldGet(this, _YargsInstance_context, "f").fullCommands[__classPrivateFieldGet(this, _YargsInstance_context, "f").fullCommands.length - 1]; const parseOptions = fullCommand ? __classPrivateFieldGet(this, _YargsInstance_command, "f").cmdToParseOptions(fullCommand) : { array: [], alias: {}, default: {}, demand: {} }; objectKeys(parseOptions).forEach((pk) => { const parseOption = parseOptions[pk]; if (Array.isArray(parseOption)) { if (parseOption.indexOf(key) !== -1) opts[pk] = true; } else { if (parseOption[key] && !(pk in opts)) opts[pk] = parseOption[key]; } }); this.group(key, __classPrivateFieldGet(this, _YargsInstance_usage, "f").getPositionalGroupName()); return this.option(key, opts); } recommendCommands(recommend = true) { argsert("[boolean]", [recommend], arguments.length); __classPrivateFieldSet(this, _YargsInstance_recommendCommands, recommend, "f"); return this; } required(keys, max, msg) { return this.demand(keys, max, msg); } require(keys, max, msg) { return this.demand(keys, max, msg); } requiresArg(keys) { argsert(" [number]", [keys], arguments.length); if (typeof keys === "string" && __classPrivateFieldGet(this, _YargsInstance_options, "f").narg[keys]) { return this; } else { this[kPopulateParserHintSingleValueDictionary](this.requiresArg.bind(this), "narg", keys, NaN); } return this; } showCompletionScript($0, cmd) { argsert("[string] [string]", [$0, cmd], arguments.length); $0 = $0 || this.$0; __classPrivateFieldGet(this, _YargsInstance_logger, "f").log(__classPrivateFieldGet(this, _YargsInstance_completion, "f").generateCompletionScript($0, cmd || __classPrivateFieldGet(this, _YargsInstance_completionCommand, "f") || "completion")); return this; } showHelp(level) { argsert("[string|function]", [level], arguments.length); __classPrivateFieldSet(this, _YargsInstance_hasOutput, true, "f"); if (!__classPrivateFieldGet(this, _YargsInstance_usage, "f").hasCachedHelpMessage()) { if (!this.parsed) { const parse2 = this[kRunYargsParserAndExecuteCommands](__classPrivateFieldGet(this, _YargsInstance_processArgs, "f"), void 0, void 0, 0, true); if (isPromise(parse2)) { parse2.then(() => { __classPrivateFieldGet(this, _YargsInstance_usage, "f").showHelp(level); }); return this; } } const builderResponse = __classPrivateFieldGet(this, _YargsInstance_command, "f").runDefaultBuilderOn(this); if (isPromise(builderResponse)) { builderResponse.then(() => { __classPrivateFieldGet(this, _YargsInstance_usage, "f").showHelp(level); }); return this; } } __classPrivateFieldGet(this, _YargsInstance_usage, "f").showHelp(level); return this; } scriptName(scriptName) { this.customScriptName = true; this.$0 = scriptName; return this; } showHelpOnFail(enabled, message) { argsert("[boolean|string] [string]", [enabled, message], arguments.length); __classPrivateFieldGet(this, _YargsInstance_usage, "f").showHelpOnFail(enabled, message); return this; } showVersion(level) { argsert("[string|function]", [level], arguments.length); __classPrivateFieldGet(this, _YargsInstance_usage, "f").showVersion(level); return this; } skipValidation(keys) { argsert("", [keys], arguments.length); this[kPopulateParserHintArray]("skipValidation", keys); return this; } strict(enabled) { argsert("[boolean]", [enabled], arguments.length); __classPrivateFieldSet(this, _YargsInstance_strict, enabled !== false, "f"); return this; } strictCommands(enabled) { argsert("[boolean]", [enabled], arguments.length); __classPrivateFieldSet(this, _YargsInstance_strictCommands, enabled !== false, "f"); return this; } strictOptions(enabled) { argsert("[boolean]", [enabled], arguments.length); __classPrivateFieldSet(this, _YargsInstance_strictOptions, enabled !== false, "f"); return this; } string(keys) { argsert("", [keys], arguments.length); this[kPopulateParserHintArray]("string", keys); this[kTrackManuallySetKeys](keys); return this; } terminalWidth() { argsert([], 0); return __classPrivateFieldGet(this, _YargsInstance_shim, "f").process.stdColumns; } updateLocale(obj) { return this.updateStrings(obj); } updateStrings(obj) { argsert("", [obj], arguments.length); __classPrivateFieldSet(this, _YargsInstance_detectLocale, false, "f"); __classPrivateFieldGet(this, _YargsInstance_shim, "f").y18n.updateLocale(obj); return this; } usage(msg, description, builder, handler) { argsert(" [string|boolean] [function|object] [function]", [msg, description, builder, handler], arguments.length); if (description !== void 0) { assertNotStrictEqual(msg, null, __classPrivateFieldGet(this, _YargsInstance_shim, "f")); if ((msg || "").match(/^\$0( |$)/)) { return this.command(msg, description, builder, handler); } else { throw new YError(".usage() description must start with $0 if being used as alias for .command()"); } } else { __classPrivateFieldGet(this, _YargsInstance_usage, "f").usage(msg); return this; } } usageConfiguration(config) { argsert("", [config], arguments.length); __classPrivateFieldSet(this, _YargsInstance_usageConfig, config, "f"); return this; } version(opt, msg, ver) { const defaultVersionOpt = "version"; argsert("[boolean|string] [string] [string]", [opt, msg, ver], arguments.length); if (__classPrivateFieldGet(this, _YargsInstance_versionOpt, "f")) { this[kDeleteFromParserHintObject](__classPrivateFieldGet(this, _YargsInstance_versionOpt, "f")); __classPrivateFieldGet(this, _YargsInstance_usage, "f").version(void 0); __classPrivateFieldSet(this, _YargsInstance_versionOpt, null, "f"); } if (arguments.length === 0) { ver = this[kGuessVersion](); opt = defaultVersionOpt; } else if (arguments.length === 1) { if (opt === false) { return this; } ver = opt; opt = defaultVersionOpt; } else if (arguments.length === 2) { ver = msg; msg = void 0; } __classPrivateFieldSet(this, _YargsInstance_versionOpt, typeof opt === "string" ? opt : defaultVersionOpt, "f"); msg = msg || __classPrivateFieldGet(this, _YargsInstance_usage, "f").deferY18nLookup("Show version number"); __classPrivateFieldGet(this, _YargsInstance_usage, "f").version(ver || void 0); this.boolean(__classPrivateFieldGet(this, _YargsInstance_versionOpt, "f")); this.describe(__classPrivateFieldGet(this, _YargsInstance_versionOpt, "f"), msg); return this; } wrap(cols) { argsert("", [cols], arguments.length); __classPrivateFieldGet(this, _YargsInstance_usage, "f").wrap(cols); return this; } [(_YargsInstance_command = /* @__PURE__ */ new WeakMap(), _YargsInstance_cwd = /* @__PURE__ */ new WeakMap(), _YargsInstance_context = /* @__PURE__ */ new WeakMap(), _YargsInstance_completion = /* @__PURE__ */ new WeakMap(), _YargsInstance_completionCommand = /* @__PURE__ */ new WeakMap(), _YargsInstance_defaultShowHiddenOpt = /* @__PURE__ */ new WeakMap(), _YargsInstance_exitError = /* @__PURE__ */ new WeakMap(), _YargsInstance_detectLocale = /* @__PURE__ */ new WeakMap(), _YargsInstance_emittedWarnings = /* @__PURE__ */ new WeakMap(), _YargsInstance_exitProcess = /* @__PURE__ */ new WeakMap(), _YargsInstance_frozens = /* @__PURE__ */ new WeakMap(), _YargsInstance_globalMiddleware = /* @__PURE__ */ new WeakMap(), _YargsInstance_groups = /* @__PURE__ */ new WeakMap(), _YargsInstance_hasOutput = /* @__PURE__ */ new WeakMap(), _YargsInstance_helpOpt = /* @__PURE__ */ new WeakMap(), _YargsInstance_isGlobalContext = /* @__PURE__ */ new WeakMap(), _YargsInstance_logger = /* @__PURE__ */ new WeakMap(), _YargsInstance_output = /* @__PURE__ */ new WeakMap(), _YargsInstance_options = /* @__PURE__ */ new WeakMap(), _YargsInstance_parentRequire = /* @__PURE__ */ new WeakMap(), _YargsInstance_parserConfig = /* @__PURE__ */ new WeakMap(), _YargsInstance_parseFn = /* @__PURE__ */ new WeakMap(), _YargsInstance_parseContext = /* @__PURE__ */ new WeakMap(), _YargsInstance_pkgs = /* @__PURE__ */ new WeakMap(), _YargsInstance_preservedGroups = /* @__PURE__ */ new WeakMap(), _YargsInstance_processArgs = /* @__PURE__ */ new WeakMap(), _YargsInstance_recommendCommands = /* @__PURE__ */ new WeakMap(), _YargsInstance_shim = /* @__PURE__ */ new WeakMap(), _YargsInstance_strict = /* @__PURE__ */ new WeakMap(), _YargsInstance_strictCommands = /* @__PURE__ */ new WeakMap(), _YargsInstance_strictOptions = /* @__PURE__ */ new WeakMap(), _YargsInstance_usage = /* @__PURE__ */ new WeakMap(), _YargsInstance_usageConfig = /* @__PURE__ */ new WeakMap(), _YargsInstance_versionOpt = /* @__PURE__ */ new WeakMap(), _YargsInstance_validation = /* @__PURE__ */ new WeakMap(), kCopyDoubleDash)](argv) { if (!argv._ || !argv["--"]) return argv; argv._.push.apply(argv._, argv["--"]); try { delete argv["--"]; } catch (_err) { } return argv; } [kCreateLogger]() { return { log: (...args) => { if (!this[kHasParseCallback]()) console.log(...args); __classPrivateFieldSet(this, _YargsInstance_hasOutput, true, "f"); if (__classPrivateFieldGet(this, _YargsInstance_output, "f").length) __classPrivateFieldSet(this, _YargsInstance_output, __classPrivateFieldGet(this, _YargsInstance_output, "f") + "\n", "f"); __classPrivateFieldSet(this, _YargsInstance_output, __classPrivateFieldGet(this, _YargsInstance_output, "f") + args.join(" "), "f"); }, error: (...args) => { if (!this[kHasParseCallback]()) console.error(...args); __classPrivateFieldSet(this, _YargsInstance_hasOutput, true, "f"); if (__classPrivateFieldGet(this, _YargsInstance_output, "f").length) __classPrivateFieldSet(this, _YargsInstance_output, __classPrivateFieldGet(this, _YargsInstance_output, "f") + "\n", "f"); __classPrivateFieldSet(this, _YargsInstance_output, __classPrivateFieldGet(this, _YargsInstance_output, "f") + args.join(" "), "f"); } }; } [kDeleteFromParserHintObject](optionKey) { objectKeys(__classPrivateFieldGet(this, _YargsInstance_options, "f")).forEach((hintKey) => { if (/* @__PURE__ */ ((key) => key === "configObjects")(hintKey)) return; const hint = __classPrivateFieldGet(this, _YargsInstance_options, "f")[hintKey]; if (Array.isArray(hint)) { if (hint.includes(optionKey)) hint.splice(hint.indexOf(optionKey), 1); } else if (typeof hint === "object") { delete hint[optionKey]; } }); delete __classPrivateFieldGet(this, _YargsInstance_usage, "f").getDescriptions()[optionKey]; } [kEmitWarning](warning, type, deduplicationId) { if (!__classPrivateFieldGet(this, _YargsInstance_emittedWarnings, "f")[deduplicationId]) { __classPrivateFieldGet(this, _YargsInstance_shim, "f").process.emitWarning(warning, type); __classPrivateFieldGet(this, _YargsInstance_emittedWarnings, "f")[deduplicationId] = true; } } [kFreeze]() { __classPrivateFieldGet(this, _YargsInstance_frozens, "f").push({ options: __classPrivateFieldGet(this, _YargsInstance_options, "f"), configObjects: __classPrivateFieldGet(this, _YargsInstance_options, "f").configObjects.slice(0), exitProcess: __classPrivateFieldGet(this, _YargsInstance_exitProcess, "f"), groups: __classPrivateFieldGet(this, _YargsInstance_groups, "f"), strict: __classPrivateFieldGet(this, _YargsInstance_strict, "f"), strictCommands: __classPrivateFieldGet(this, _YargsInstance_strictCommands, "f"), strictOptions: __classPrivateFieldGet(this, _YargsInstance_strictOptions, "f"), completionCommand: __classPrivateFieldGet(this, _YargsInstance_completionCommand, "f"), output: __classPrivateFieldGet(this, _YargsInstance_output, "f"), exitError: __classPrivateFieldGet(this, _YargsInstance_exitError, "f"), hasOutput: __classPrivateFieldGet(this, _YargsInstance_hasOutput, "f"), parsed: this.parsed, parseFn: __classPrivateFieldGet(this, _YargsInstance_parseFn, "f"), parseContext: __classPrivateFieldGet(this, _YargsInstance_parseContext, "f") }); __classPrivateFieldGet(this, _YargsInstance_usage, "f").freeze(); __classPrivateFieldGet(this, _YargsInstance_validation, "f").freeze(); __classPrivateFieldGet(this, _YargsInstance_command, "f").freeze(); __classPrivateFieldGet(this, _YargsInstance_globalMiddleware, "f").freeze(); } [kGetDollarZero]() { let $0 = ""; let default$0; if (/\b(node|iojs|electron)(\.exe)?$/.test(__classPrivateFieldGet(this, _YargsInstance_shim, "f").process.argv()[0])) { default$0 = __classPrivateFieldGet(this, _YargsInstance_shim, "f").process.argv().slice(1, 2); } else { default$0 = __classPrivateFieldGet(this, _YargsInstance_shim, "f").process.argv().slice(0, 1); } $0 = default$0.map((x) => { const b = this[kRebase](__classPrivateFieldGet(this, _YargsInstance_cwd, "f"), x); return x.match(/^(\/|([a-zA-Z]:)?\\)/) && b.length < x.length ? b : x; }).join(" ").trim(); if (__classPrivateFieldGet(this, _YargsInstance_shim, "f").getEnv("_") && __classPrivateFieldGet(this, _YargsInstance_shim, "f").getProcessArgvBin() === __classPrivateFieldGet(this, _YargsInstance_shim, "f").getEnv("_")) { $0 = __classPrivateFieldGet(this, _YargsInstance_shim, "f").getEnv("_").replace(`${__classPrivateFieldGet(this, _YargsInstance_shim, "f").path.dirname(__classPrivateFieldGet(this, _YargsInstance_shim, "f").process.execPath())}/`, ""); } return $0; } [kGetParserConfiguration]() { return __classPrivateFieldGet(this, _YargsInstance_parserConfig, "f"); } [kGetUsageConfiguration]() { return __classPrivateFieldGet(this, _YargsInstance_usageConfig, "f"); } [kGuessLocale]() { if (!__classPrivateFieldGet(this, _YargsInstance_detectLocale, "f")) return; const locale = __classPrivateFieldGet(this, _YargsInstance_shim, "f").getEnv("LC_ALL") || __classPrivateFieldGet(this, _YargsInstance_shim, "f").getEnv("LC_MESSAGES") || __classPrivateFieldGet(this, _YargsInstance_shim, "f").getEnv("LANG") || __classPrivateFieldGet(this, _YargsInstance_shim, "f").getEnv("LANGUAGE") || "en_US"; this.locale(locale.replace(/[.:].*/, "")); } [kGuessVersion]() { const obj = this[kPkgUp](); return obj.version || "unknown"; } [kParsePositionalNumbers](argv) { const args = argv["--"] ? argv["--"] : argv._; for (let i = 0, arg; (arg = args[i]) !== void 0; i++) { if (__classPrivateFieldGet(this, _YargsInstance_shim, "f").Parser.looksLikeNumber(arg) && Number.isSafeInteger(Math.floor(parseFloat(`${arg}`)))) { args[i] = Number(arg); } } return argv; } [kPkgUp](rootPath) { const npath = rootPath || "*"; if (__classPrivateFieldGet(this, _YargsInstance_pkgs, "f")[npath]) return __classPrivateFieldGet(this, _YargsInstance_pkgs, "f")[npath]; let obj = {}; try { let startDir = rootPath || __classPrivateFieldGet(this, _YargsInstance_shim, "f").mainFilename; if (!rootPath && __classPrivateFieldGet(this, _YargsInstance_shim, "f").path.extname(startDir)) { startDir = __classPrivateFieldGet(this, _YargsInstance_shim, "f").path.dirname(startDir); } const pkgJsonPath = __classPrivateFieldGet(this, _YargsInstance_shim, "f").findUp(startDir, (dir, names) => { if (names.includes("package.json")) { return "package.json"; } else { return void 0; } }); assertNotStrictEqual(pkgJsonPath, void 0, __classPrivateFieldGet(this, _YargsInstance_shim, "f")); obj = JSON.parse(__classPrivateFieldGet(this, _YargsInstance_shim, "f").readFileSync(pkgJsonPath, "utf8")); } catch (_noop) { } __classPrivateFieldGet(this, _YargsInstance_pkgs, "f")[npath] = obj || {}; return __classPrivateFieldGet(this, _YargsInstance_pkgs, "f")[npath]; } [kPopulateParserHintArray](type, keys) { keys = [].concat(keys); keys.forEach((key) => { key = this[kSanitizeKey](key); __classPrivateFieldGet(this, _YargsInstance_options, "f")[type].push(key); }); } [kPopulateParserHintSingleValueDictionary](builder, type, key, value) { this[kPopulateParserHintDictionary](builder, type, key, value, (type2, key2, value2) => { __classPrivateFieldGet(this, _YargsInstance_options, "f")[type2][key2] = value2; }); } [kPopulateParserHintArrayDictionary](builder, type, key, value) { this[kPopulateParserHintDictionary](builder, type, key, value, (type2, key2, value2) => { __classPrivateFieldGet(this, _YargsInstance_options, "f")[type2][key2] = (__classPrivateFieldGet(this, _YargsInstance_options, "f")[type2][key2] || []).concat(value2); }); } [kPopulateParserHintDictionary](builder, type, key, value, singleKeyHandler) { if (Array.isArray(key)) { key.forEach((k) => { builder(k, value); }); } else if (/* @__PURE__ */ ((key2) => typeof key2 === "object")(key)) { for (const k of objectKeys(key)) { builder(k, key[k]); } } else { singleKeyHandler(type, this[kSanitizeKey](key), value); } } [kSanitizeKey](key) { if (key === "__proto__") return "___proto___"; return key; } [kSetKey](key, set) { this[kPopulateParserHintSingleValueDictionary](this[kSetKey].bind(this), "key", key, set); return this; } [kUnfreeze]() { var _a2, _b2, _c2, _d, _e, _f, _g, _h, _j, _k, _l, _m; const frozen = __classPrivateFieldGet(this, _YargsInstance_frozens, "f").pop(); assertNotStrictEqual(frozen, void 0, __classPrivateFieldGet(this, _YargsInstance_shim, "f")); let configObjects; _a2 = this, _b2 = this, _c2 = this, _d = this, _e = this, _f = this, _g = this, _h = this, _j = this, _k = this, _l = this, _m = this, { options: { set value(_o) { __classPrivateFieldSet(_a2, _YargsInstance_options, _o, "f"); } }.value, configObjects, exitProcess: { set value(_o) { __classPrivateFieldSet(_b2, _YargsInstance_exitProcess, _o, "f"); } }.value, groups: { set value(_o) { __classPrivateFieldSet(_c2, _YargsInstance_groups, _o, "f"); } }.value, output: { set value(_o) { __classPrivateFieldSet(_d, _YargsInstance_output, _o, "f"); } }.value, exitError: { set value(_o) { __classPrivateFieldSet(_e, _YargsInstance_exitError, _o, "f"); } }.value, hasOutput: { set value(_o) { __classPrivateFieldSet(_f, _YargsInstance_hasOutput, _o, "f"); } }.value, parsed: this.parsed, strict: { set value(_o) { __classPrivateFieldSet(_g, _YargsInstance_strict, _o, "f"); } }.value, strictCommands: { set value(_o) { __classPrivateFieldSet(_h, _YargsInstance_strictCommands, _o, "f"); } }.value, strictOptions: { set value(_o) { __classPrivateFieldSet(_j, _YargsInstance_strictOptions, _o, "f"); } }.value, completionCommand: { set value(_o) { __classPrivateFieldSet(_k, _YargsInstance_completionCommand, _o, "f"); } }.value, parseFn: { set value(_o) { __classPrivateFieldSet(_l, _YargsInstance_parseFn, _o, "f"); } }.value, parseContext: { set value(_o) { __classPrivateFieldSet(_m, _YargsInstance_parseContext, _o, "f"); } }.value } = frozen; __classPrivateFieldGet(this, _YargsInstance_options, "f").configObjects = configObjects; __classPrivateFieldGet(this, _YargsInstance_usage, "f").unfreeze(); __classPrivateFieldGet(this, _YargsInstance_validation, "f").unfreeze(); __classPrivateFieldGet(this, _YargsInstance_command, "f").unfreeze(); __classPrivateFieldGet(this, _YargsInstance_globalMiddleware, "f").unfreeze(); } [kValidateAsync](validation2, argv) { return maybeAsyncResult(argv, (result) => { validation2(result); return result; }); } getInternalMethods() { return { getCommandInstance: this[kGetCommandInstance].bind(this), getContext: this[kGetContext].bind(this), getHasOutput: this[kGetHasOutput].bind(this), getLoggerInstance: this[kGetLoggerInstance].bind(this), getParseContext: this[kGetParseContext].bind(this), getParserConfiguration: this[kGetParserConfiguration].bind(this), getUsageConfiguration: this[kGetUsageConfiguration].bind(this), getUsageInstance: this[kGetUsageInstance].bind(this), getValidationInstance: this[kGetValidationInstance].bind(this), hasParseCallback: this[kHasParseCallback].bind(this), isGlobalContext: this[kIsGlobalContext].bind(this), postProcess: this[kPostProcess].bind(this), reset: this[kReset].bind(this), runValidation: this[kRunValidation].bind(this), runYargsParserAndExecuteCommands: this[kRunYargsParserAndExecuteCommands].bind(this), setHasOutput: this[kSetHasOutput].bind(this) }; } [kGetCommandInstance]() { return __classPrivateFieldGet(this, _YargsInstance_command, "f"); } [kGetContext]() { return __classPrivateFieldGet(this, _YargsInstance_context, "f"); } [kGetHasOutput]() { return __classPrivateFieldGet(this, _YargsInstance_hasOutput, "f"); } [kGetLoggerInstance]() { return __classPrivateFieldGet(this, _YargsInstance_logger, "f"); } [kGetParseContext]() { return __classPrivateFieldGet(this, _YargsInstance_parseContext, "f") || {}; } [kGetUsageInstance]() { return __classPrivateFieldGet(this, _YargsInstance_usage, "f"); } [kGetValidationInstance]() { return __classPrivateFieldGet(this, _YargsInstance_validation, "f"); } [kHasParseCallback]() { return !!__classPrivateFieldGet(this, _YargsInstance_parseFn, "f"); } [kIsGlobalContext]() { return __classPrivateFieldGet(this, _YargsInstance_isGlobalContext, "f"); } [kPostProcess](argv, populateDoubleDash, calledFromCommand, runGlobalMiddleware) { if (calledFromCommand) return argv; if (isPromise(argv)) return argv; if (!populateDoubleDash) { argv = this[kCopyDoubleDash](argv); } const parsePositionalNumbers = this[kGetParserConfiguration]()["parse-positional-numbers"] || this[kGetParserConfiguration]()["parse-positional-numbers"] === void 0; if (parsePositionalNumbers) { argv = this[kParsePositionalNumbers](argv); } if (runGlobalMiddleware) { argv = applyMiddleware(argv, this, __classPrivateFieldGet(this, _YargsInstance_globalMiddleware, "f").getMiddleware(), false); } return argv; } [kReset](aliases = {}) { __classPrivateFieldSet(this, _YargsInstance_options, __classPrivateFieldGet(this, _YargsInstance_options, "f") || {}, "f"); const tmpOptions = {}; tmpOptions.local = __classPrivateFieldGet(this, _YargsInstance_options, "f").local || []; tmpOptions.configObjects = __classPrivateFieldGet(this, _YargsInstance_options, "f").configObjects || []; const localLookup = {}; tmpOptions.local.forEach((l) => { localLookup[l] = true; (aliases[l] || []).forEach((a) => { localLookup[a] = true; }); }); Object.assign(__classPrivateFieldGet(this, _YargsInstance_preservedGroups, "f"), Object.keys(__classPrivateFieldGet(this, _YargsInstance_groups, "f")).reduce((acc, groupName) => { const keys = __classPrivateFieldGet(this, _YargsInstance_groups, "f")[groupName].filter((key) => !(key in localLookup)); if (keys.length > 0) { acc[groupName] = keys; } return acc; }, {})); __classPrivateFieldSet(this, _YargsInstance_groups, {}, "f"); const arrayOptions = [ "array", "boolean", "string", "skipValidation", "count", "normalize", "number", "hiddenOptions" ]; const objectOptions = [ "narg", "key", "alias", "default", "defaultDescription", "config", "choices", "demandedOptions", "demandedCommands", "deprecatedOptions" ]; arrayOptions.forEach((k) => { tmpOptions[k] = (__classPrivateFieldGet(this, _YargsInstance_options, "f")[k] || []).filter((k2) => !localLookup[k2]); }); objectOptions.forEach((k) => { tmpOptions[k] = objFilter(__classPrivateFieldGet(this, _YargsInstance_options, "f")[k], (k2) => !localLookup[k2]); }); tmpOptions.envPrefix = __classPrivateFieldGet(this, _YargsInstance_options, "f").envPrefix; __classPrivateFieldSet(this, _YargsInstance_options, tmpOptions, "f"); __classPrivateFieldSet(this, _YargsInstance_usage, __classPrivateFieldGet(this, _YargsInstance_usage, "f") ? __classPrivateFieldGet(this, _YargsInstance_usage, "f").reset(localLookup) : usage(this, __classPrivateFieldGet(this, _YargsInstance_shim, "f")), "f"); __classPrivateFieldSet(this, _YargsInstance_validation, __classPrivateFieldGet(this, _YargsInstance_validation, "f") ? __classPrivateFieldGet(this, _YargsInstance_validation, "f").reset(localLookup) : validation(this, __classPrivateFieldGet(this, _YargsInstance_usage, "f"), __classPrivateFieldGet(this, _YargsInstance_shim, "f")), "f"); __classPrivateFieldSet(this, _YargsInstance_command, __classPrivateFieldGet(this, _YargsInstance_command, "f") ? __classPrivateFieldGet(this, _YargsInstance_command, "f").reset() : command(__classPrivateFieldGet(this, _YargsInstance_usage, "f"), __classPrivateFieldGet(this, _YargsInstance_validation, "f"), __classPrivateFieldGet(this, _YargsInstance_globalMiddleware, "f"), __classPrivateFieldGet(this, _YargsInstance_shim, "f")), "f"); if (!__classPrivateFieldGet(this, _YargsInstance_completion, "f")) __classPrivateFieldSet(this, _YargsInstance_completion, completion(this, __classPrivateFieldGet(this, _YargsInstance_usage, "f"), __classPrivateFieldGet(this, _YargsInstance_command, "f"), __classPrivateFieldGet(this, _YargsInstance_shim, "f")), "f"); __classPrivateFieldGet(this, _YargsInstance_globalMiddleware, "f").reset(); __classPrivateFieldSet(this, _YargsInstance_completionCommand, null, "f"); __classPrivateFieldSet(this, _YargsInstance_output, "", "f"); __classPrivateFieldSet(this, _YargsInstance_exitError, null, "f"); __classPrivateFieldSet(this, _YargsInstance_hasOutput, false, "f"); this.parsed = false; return this; } [kRebase](base, dir) { return __classPrivateFieldGet(this, _YargsInstance_shim, "f").path.relative(base, dir); } [kRunYargsParserAndExecuteCommands](args, shortCircuit, calledFromCommand, commandIndex = 0, helpOnly = false) { let skipValidation = !!calledFromCommand || helpOnly; args = args || __classPrivateFieldGet(this, _YargsInstance_processArgs, "f"); __classPrivateFieldGet(this, _YargsInstance_options, "f").__ = __classPrivateFieldGet(this, _YargsInstance_shim, "f").y18n.__; __classPrivateFieldGet(this, _YargsInstance_options, "f").configuration = this[kGetParserConfiguration](); const populateDoubleDash = !!__classPrivateFieldGet(this, _YargsInstance_options, "f").configuration["populate--"]; const config = Object.assign({}, __classPrivateFieldGet(this, _YargsInstance_options, "f").configuration, { "populate--": true }); const parsed = __classPrivateFieldGet(this, _YargsInstance_shim, "f").Parser.detailed(args, Object.assign({}, __classPrivateFieldGet(this, _YargsInstance_options, "f"), { configuration: { "parse-positional-numbers": false, ...config } })); const argv = Object.assign(parsed.argv, __classPrivateFieldGet(this, _YargsInstance_parseContext, "f")); let argvPromise = void 0; const aliases = parsed.aliases; let helpOptSet = false; let versionOptSet = false; Object.keys(argv).forEach((key) => { if (key === __classPrivateFieldGet(this, _YargsInstance_helpOpt, "f") && argv[key]) { helpOptSet = true; } else if (key === __classPrivateFieldGet(this, _YargsInstance_versionOpt, "f") && argv[key]) { versionOptSet = true; } }); argv.$0 = this.$0; this.parsed = parsed; if (commandIndex === 0) { __classPrivateFieldGet(this, _YargsInstance_usage, "f").clearCachedHelpMessage(); } try { this[kGuessLocale](); if (shortCircuit) { return this[kPostProcess](argv, populateDoubleDash, !!calledFromCommand, false); } if (__classPrivateFieldGet(this, _YargsInstance_helpOpt, "f")) { const helpCmds = [__classPrivateFieldGet(this, _YargsInstance_helpOpt, "f")].concat(aliases[__classPrivateFieldGet(this, _YargsInstance_helpOpt, "f")] || []).filter((k) => k.length > 1); if (helpCmds.includes("" + argv._[argv._.length - 1])) { argv._.pop(); helpOptSet = true; } } __classPrivateFieldSet(this, _YargsInstance_isGlobalContext, false, "f"); const handlerKeys = __classPrivateFieldGet(this, _YargsInstance_command, "f").getCommands(); const requestCompletions = __classPrivateFieldGet(this, _YargsInstance_completion, "f").completionKey in argv; const skipRecommendation = helpOptSet || requestCompletions || helpOnly; if (argv._.length) { if (handlerKeys.length) { let firstUnknownCommand; for (let i = commandIndex || 0, cmd; argv._[i] !== void 0; i++) { cmd = String(argv._[i]); if (handlerKeys.includes(cmd) && cmd !== __classPrivateFieldGet(this, _YargsInstance_completionCommand, "f")) { const innerArgv = __classPrivateFieldGet(this, _YargsInstance_command, "f").runCommand(cmd, this, parsed, i + 1, helpOnly, helpOptSet || versionOptSet || helpOnly); return this[kPostProcess](innerArgv, populateDoubleDash, !!calledFromCommand, false); } else if (!firstUnknownCommand && cmd !== __classPrivateFieldGet(this, _YargsInstance_completionCommand, "f")) { firstUnknownCommand = cmd; break; } } if (!__classPrivateFieldGet(this, _YargsInstance_command, "f").hasDefaultCommand() && __classPrivateFieldGet(this, _YargsInstance_recommendCommands, "f") && firstUnknownCommand && !skipRecommendation) { __classPrivateFieldGet(this, _YargsInstance_validation, "f").recommendCommands(firstUnknownCommand, handlerKeys); } } if (__classPrivateFieldGet(this, _YargsInstance_completionCommand, "f") && argv._.includes(__classPrivateFieldGet(this, _YargsInstance_completionCommand, "f")) && !requestCompletions) { if (__classPrivateFieldGet(this, _YargsInstance_exitProcess, "f")) setBlocking(true); this.showCompletionScript(); this.exit(0); } } if (__classPrivateFieldGet(this, _YargsInstance_command, "f").hasDefaultCommand() && !skipRecommendation) { const innerArgv = __classPrivateFieldGet(this, _YargsInstance_command, "f").runCommand(null, this, parsed, 0, helpOnly, helpOptSet || versionOptSet || helpOnly); return this[kPostProcess](innerArgv, populateDoubleDash, !!calledFromCommand, false); } if (requestCompletions) { if (__classPrivateFieldGet(this, _YargsInstance_exitProcess, "f")) setBlocking(true); args = [].concat(args); const completionArgs = args.slice(args.indexOf(`--${__classPrivateFieldGet(this, _YargsInstance_completion, "f").completionKey}`) + 1); __classPrivateFieldGet(this, _YargsInstance_completion, "f").getCompletion(completionArgs, (err, completions) => { if (err) throw new YError(err.message); (completions || []).forEach((completion2) => { __classPrivateFieldGet(this, _YargsInstance_logger, "f").log(completion2); }); this.exit(0); }); return this[kPostProcess](argv, !populateDoubleDash, !!calledFromCommand, false); } if (!__classPrivateFieldGet(this, _YargsInstance_hasOutput, "f")) { if (helpOptSet) { if (__classPrivateFieldGet(this, _YargsInstance_exitProcess, "f")) setBlocking(true); skipValidation = true; this.showHelp("log"); this.exit(0); } else if (versionOptSet) { if (__classPrivateFieldGet(this, _YargsInstance_exitProcess, "f")) setBlocking(true); skipValidation = true; __classPrivateFieldGet(this, _YargsInstance_usage, "f").showVersion("log"); this.exit(0); } } if (!skipValidation && __classPrivateFieldGet(this, _YargsInstance_options, "f").skipValidation.length > 0) { skipValidation = Object.keys(argv).some((key) => __classPrivateFieldGet(this, _YargsInstance_options, "f").skipValidation.indexOf(key) >= 0 && argv[key] === true); } if (!skipValidation) { if (parsed.error) throw new YError(parsed.error.message); if (!requestCompletions) { const validation2 = this[kRunValidation](aliases, {}, parsed.error); if (!calledFromCommand) { argvPromise = applyMiddleware(argv, this, __classPrivateFieldGet(this, _YargsInstance_globalMiddleware, "f").getMiddleware(), true); } argvPromise = this[kValidateAsync](validation2, argvPromise !== null && argvPromise !== void 0 ? argvPromise : argv); if (isPromise(argvPromise) && !calledFromCommand) { argvPromise = argvPromise.then(() => { return applyMiddleware(argv, this, __classPrivateFieldGet(this, _YargsInstance_globalMiddleware, "f").getMiddleware(), false); }); } } } } catch (err) { if (err instanceof YError) __classPrivateFieldGet(this, _YargsInstance_usage, "f").fail(err.message, err); else throw err; } return this[kPostProcess](argvPromise !== null && argvPromise !== void 0 ? argvPromise : argv, populateDoubleDash, !!calledFromCommand, true); } [kRunValidation](aliases, positionalMap, parseErrors, isDefaultCommand) { const demandedOptions = { ...this.getDemandedOptions() }; return (argv) => { if (parseErrors) throw new YError(parseErrors.message); __classPrivateFieldGet(this, _YargsInstance_validation, "f").nonOptionCount(argv); __classPrivateFieldGet(this, _YargsInstance_validation, "f").requiredArguments(argv, demandedOptions); let failedStrictCommands = false; if (__classPrivateFieldGet(this, _YargsInstance_strictCommands, "f")) { failedStrictCommands = __classPrivateFieldGet(this, _YargsInstance_validation, "f").unknownCommands(argv); } if (__classPrivateFieldGet(this, _YargsInstance_strict, "f") && !failedStrictCommands) { __classPrivateFieldGet(this, _YargsInstance_validation, "f").unknownArguments(argv, aliases, positionalMap, !!isDefaultCommand); } else if (__classPrivateFieldGet(this, _YargsInstance_strictOptions, "f")) { __classPrivateFieldGet(this, _YargsInstance_validation, "f").unknownArguments(argv, aliases, {}, false, false); } __classPrivateFieldGet(this, _YargsInstance_validation, "f").limitedChoices(argv); __classPrivateFieldGet(this, _YargsInstance_validation, "f").implications(argv); __classPrivateFieldGet(this, _YargsInstance_validation, "f").conflicting(argv); }; } [kSetHasOutput]() { __classPrivateFieldSet(this, _YargsInstance_hasOutput, true, "f"); } [kTrackManuallySetKeys](keys) { if (typeof keys === "string") { __classPrivateFieldGet(this, _YargsInstance_options, "f").key[keys] = true; } else { for (const k of keys) { __classPrivateFieldGet(this, _YargsInstance_options, "f").key[k] = true; } } } }; function isYargsInstance(y) { return !!y && typeof y.getInternalMethods === "function"; } // node_modules/yargs/index.mjs var Yargs = YargsFactory(esm_default); var yargs_default = Yargs; // packages/cli/src/config/config.ts import process3 from "node:process"; import * as path6 from "node:path"; // packages/cli/src/commands/utils.ts async function exitCli(exitCode = 0) { await runExitCleanup(); process.exit(exitCode); } // packages/cli/src/commands/mcp/add.ts async function addMcpServer(name, commandOrUrl, args, options) { const { scope, transport, env: env2, header, timeout, trust, description, includeTools, excludeTools } = options; const settings = loadSettings(process.cwd()); const inHome = settings.workspace.path === settings.user.path; if (scope === "project" && inHome) { debugLogger.error( "Error: Please use --scope user to edit settings in the home directory." ); process.exit(1); } const settingsScope = scope === "user" ? "User" /* User */ : "Workspace" /* Workspace */; let newServer = {}; const headers = header?.reduce( (acc, curr) => { const [key, ...valueParts] = curr.split(":"); const value = valueParts.join(":").trim(); if (key.trim() && value) { acc[key.trim()] = value; } return acc; }, {} ); switch (transport) { case "sse": newServer = { url: commandOrUrl, type: "sse", headers, timeout, trust, description, includeTools, excludeTools }; break; case "http": newServer = { url: commandOrUrl, type: "http", headers, timeout, trust, description, includeTools, excludeTools }; break; case "stdio": default: newServer = { command: commandOrUrl, args: args?.map(String), env: env2?.reduce( (acc, curr) => { const [key, value] = curr.split("="); if (key && value) { acc[key] = value; } return acc; }, {} ), timeout, trust, description, includeTools, excludeTools }; break; } const existingSettings = settings.forScope(settingsScope).settings; const mcpServers = existingSettings.mcpServers || {}; const isExistingServer = !!mcpServers[name]; if (isExistingServer) { debugLogger.log( `MCP server "${name}" is already configured within ${scope} settings.` ); } mcpServers[name] = newServer; settings.setValue(settingsScope, "mcpServers", mcpServers); if (isExistingServer) { debugLogger.log(`MCP server "${name}" updated in ${scope} settings.`); } else { debugLogger.log( `MCP server "${name}" added to ${scope} settings. (${transport})` ); } } var addCommand = { command: "add [args...]", describe: "Add a server", builder: (yargs) => yargs.usage("Usage: gemini mcp add [options] [args...]").parserConfiguration({ "unknown-options-as-args": true, // Pass unknown options as server args "populate--": true // Populate server args after -- separator }).positional("name", { describe: "Name of the server", type: "string", demandOption: true }).positional("commandOrUrl", { describe: "Command (stdio) or URL (sse, http)", type: "string", demandOption: true }).option("scope", { alias: "s", describe: "Configuration scope (user or project)", type: "string", default: "project", choices: ["user", "project"] }).option("transport", { alias: ["t", "type"], describe: "Transport type (stdio, sse, http)", type: "string", default: "stdio", choices: ["stdio", "sse", "http"] }).option("env", { alias: "e", describe: "Set environment variables (e.g. -e KEY=value)", type: "array", string: true, nargs: 1 }).option("header", { alias: "H", describe: 'Set HTTP headers for SSE and HTTP transports (e.g. -H "X-Api-Key: abc123" -H "Authorization: Bearer abc123")', type: "array", string: true, nargs: 1 }).option("timeout", { describe: "Set connection timeout in milliseconds", type: "number" }).option("trust", { describe: "Trust the server (bypass all tool call confirmation prompts)", type: "boolean" }).option("description", { describe: "Set the description for the server", type: "string" }).option("include-tools", { describe: "A comma-separated list of tools to include", type: "array", string: true }).option("exclude-tools", { describe: "A comma-separated list of tools to exclude", type: "array", string: true }).middleware((argv) => { if (argv["--"]) { const existingArgs = argv["args"] || []; argv["args"] = [...existingArgs, ...argv["--"]]; } }), handler: async (argv) => { await addMcpServer( // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion argv["name"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion argv["commandOrUrl"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion argv["args"], { // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion scope: argv["scope"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion transport: argv["transport"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion env: argv["env"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion header: argv["header"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion timeout: argv["timeout"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion trust: argv["trust"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion description: argv["description"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion includeTools: argv["includeTools"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion excludeTools: argv["excludeTools"] } ); await exitCli(); } }; // packages/cli/src/commands/mcp/remove.ts async function removeMcpServer(name, options) { const { scope } = options; const settingsScope = scope === "user" ? "User" /* User */ : "Workspace" /* Workspace */; const settings = loadSettings(); const existingSettings = settings.forScope(settingsScope).settings; const mcpServers = existingSettings.mcpServers || {}; if (!mcpServers[name]) { debugLogger.log(`Server "${name}" not found in ${scope} settings.`); return; } delete mcpServers[name]; settings.setValue(settingsScope, "mcpServers", mcpServers); debugLogger.log(`Server "${name}" removed from ${scope} settings.`); } var removeCommand = { command: "remove ", describe: "Remove a server", builder: (yargs) => yargs.usage("Usage: gemini mcp remove [options] ").positional("name", { describe: "Name of the server", type: "string", demandOption: true }).option("scope", { alias: "s", describe: "Configuration scope (user or project)", type: "string", default: "project", choices: ["user", "project"] }), handler: async (argv) => { await removeMcpServer(argv["name"], { // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion scope: argv["scope"] }); await exitCli(); } }; // packages/cli/src/commands/mcp/list.ts var import_chalk = __toESM(require_source(), 1); async function getMcpServersFromConfig(settings) { if (!settings) { settings = loadSettings().merged; } const extensionManager = new ExtensionManager({ settings, workspaceDir: process.cwd(), requestConsent: requestConsentNonInteractive, requestSetting: promptForSetting }); const extensions = await extensionManager.loadExtensions(); const mcpServers = { ...settings.mcpServers }; for (const extension of extensions) { Object.entries(extension.mcpServers || {}).forEach(([key, server]) => { if (mcpServers[key]) { return; } mcpServers[key] = { // eslint-disable-next-line @typescript-eslint/no-misused-spread ...server, extension }; }); } const adminAllowlist = settings.admin?.mcp?.config; const filteredResult = applyAdminAllowlist(mcpServers, adminAllowlist); return filteredResult; } async function testMCPConnection(serverName, config, isTrusted, activeSettings) { const isStdio = !!config.command; if (isStdio && !isTrusted) { return MCPServerStatus.DISCONNECTED; } const client = new Client({ name: "mcp-test-client", version: "0.0.1" }); const mcpContext = { sanitizationConfig: { enableEnvironmentVariableRedaction: true, allowedEnvironmentVariables: [], blockedEnvironmentVariables: activeSettings.advanced.excludedEnvVars }, emitMcpDiagnostic: (severity, message, error, serverName2) => { if (severity === "error") { debugLogger.error( import_chalk.default.red(`Error${serverName2 ? ` (${serverName2})` : ""}: ${message}`), error ); } else if (severity === "warning") { debugLogger.warn( import_chalk.default.yellow( `Warning${serverName2 ? ` (${serverName2})` : ""}: ${message}` ), error ); } else { debugLogger.log(message, error); } }, isTrustedFolder: () => isTrusted }; let transport; try { transport = await createTransport(serverName, config, false, mcpContext); } catch (_error) { await client.close(); return MCPServerStatus.DISCONNECTED; } try { await client.connect(transport, { timeout: 5e3 }); await client.ping(); await client.close(); return MCPServerStatus.CONNECTED; } catch (_error) { await transport.close(); return MCPServerStatus.DISCONNECTED; } } async function getServerStatus(serverName, server, isTrusted, activeSettings) { const mcpEnablementManager = McpServerEnablementManager.getInstance(); const loadResult = await canLoadServer(serverName, { adminMcpEnabled: activeSettings.admin?.mcp?.enabled ?? true, allowedList: activeSettings.mcp?.allowed, excludedList: activeSettings.mcp?.excluded, enablement: mcpEnablementManager.getEnablementCallbacks() }); if (!loadResult.allowed) { if (loadResult.blockType === "admin" || loadResult.blockType === "allowlist" || loadResult.blockType === "excludelist") { return MCPServerStatus.BLOCKED; } return MCPServerStatus.DISABLED; } return testMCPConnection(serverName, server, isTrusted, activeSettings); } async function listMcpServers(loadedSettingsArg) { const loadedSettings = loadedSettingsArg ?? loadSettings(); const activeSettings = loadedSettings.merged; const { mcpServers, blockedServerNames } = await getMcpServersFromConfig(activeSettings); const serverNames = Object.keys(mcpServers); if (blockedServerNames.length > 0) { const message = getAdminBlockedMcpServersMessage( blockedServerNames, void 0 ); debugLogger.log(import_chalk.default.yellow(message + "\n")); } if (serverNames.length === 0) { if (blockedServerNames.length === 0) { debugLogger.log("No MCP servers configured."); } return; } debugLogger.log("Configured MCP servers:\n"); for (const serverName of serverNames) { const server = mcpServers[serverName]; const status = await getServerStatus( serverName, server, loadedSettings.isTrusted, activeSettings ); let statusIndicator = ""; let statusText = ""; switch (status) { case MCPServerStatus.CONNECTED: statusIndicator = import_chalk.default.green("\u2713"); statusText = "Connected"; break; case MCPServerStatus.CONNECTING: statusIndicator = import_chalk.default.yellow("\u2026"); statusText = "Connecting"; break; case MCPServerStatus.BLOCKED: statusIndicator = import_chalk.default.red("\u26D4"); statusText = "Blocked"; break; case MCPServerStatus.DISABLED: statusIndicator = import_chalk.default.gray("\u25CB"); statusText = "Disabled"; break; case MCPServerStatus.DISCONNECTED: default: statusIndicator = import_chalk.default.red("\u2717"); statusText = "Disconnected"; break; } let serverInfo = serverName + (server.extension?.name ? ` (from ${server.extension.name})` : "") + ": "; if (server.httpUrl) { serverInfo += `${server.httpUrl} (http)`; } else if (server.url) { const type = server.type || "http"; serverInfo += `${server.url} (${type})`; } else if (server.command) { serverInfo += `${server.command} ${server.args?.join(" ") || ""} (stdio)`; } debugLogger.log(`${statusIndicator} ${serverInfo} - ${statusText}`); } } var listCommand = { command: "list", describe: "List all configured MCP servers", handler: async (argv) => { await listMcpServers(argv.loadedSettings); await exitCli(); } }; // packages/cli/src/commands/mcp/enableDisable.ts var GREEN = "\x1B[32m"; var YELLOW = "\x1B[33m"; var RED = "\x1B[31m"; var RESET = "\x1B[0m"; async function handleEnable(args) { const manager = McpServerEnablementManager.getInstance(); const name = normalizeServerId(args.name); const settings = loadSettings(); const servers = await getMcpServersFromConfig(); const normalizedServerNames = Object.keys(servers).map(normalizeServerId); if (!normalizedServerNames.includes(name)) { debugLogger.log( `${RED}Error:${RESET} Server '${args.name}' not found. Use 'gemini mcp' to see available servers.` ); return; } const result = await canLoadServer(name, { adminMcpEnabled: settings.merged.admin?.mcp?.enabled ?? true, allowedList: settings.merged.mcp?.allowed, excludedList: settings.merged.mcp?.excluded }); if (!result.allowed && (result.blockType === "allowlist" || result.blockType === "excludelist")) { debugLogger.log(`${RED}Error:${RESET} ${result.reason}`); return; } if (args.session) { manager.clearSessionDisable(name); debugLogger.log(`${GREEN}\u2713${RESET} Session disable cleared for '${name}'.`); } else { await manager.enable(name); debugLogger.log(`${GREEN}\u2713${RESET} MCP server '${name}' enabled.`); } if (result.blockType === "admin") { debugLogger.log( `${YELLOW}Warning:${RESET} MCP servers are disabled by administrator.` ); } } async function handleDisable(args) { const manager = McpServerEnablementManager.getInstance(); const name = normalizeServerId(args.name); const servers = await getMcpServersFromConfig(); const normalizedServerNames = Object.keys(servers).map(normalizeServerId); if (!normalizedServerNames.includes(name)) { debugLogger.log( `${RED}Error:${RESET} Server '${args.name}' not found. Use 'gemini mcp' to see available servers.` ); return; } if (args.session) { manager.disableForSession(name); debugLogger.log( `${GREEN}\u2713${RESET} MCP server '${name}' disabled for this session.` ); } else { await manager.disable(name); debugLogger.log(`${GREEN}\u2713${RESET} MCP server '${name}' disabled.`); } } var enableCommand = { command: "enable ", describe: "Enable an MCP server", builder: (yargs) => yargs.positional("name", { describe: "MCP server name to enable", type: "string", demandOption: true }).option("session", { describe: "Clear session-only disable", type: "boolean", default: false }), handler: async (argv) => { await handleEnable(argv); await exitCli(); } }; var disableCommand = { command: "disable ", describe: "Disable an MCP server", builder: (yargs) => yargs.positional("name", { describe: "MCP server name to disable", type: "string", demandOption: true }).option("session", { describe: "Disable for current session only", type: "boolean", default: false }), handler: async (argv) => { await handleDisable(argv); await exitCli(); } }; // packages/cli/src/deferred.ts import process2 from "node:process"; var deferredCommand; function setDeferredCommand(command2) { deferredCommand = command2; } async function runDeferredCommand(settings) { if (!deferredCommand) { return; } const adminSettings = settings.admin; const commandName = deferredCommand.commandName; if (commandName === "mcp" && adminSettings?.mcp?.enabled === false) { coreEvents.emitFeedback( "error", getAdminErrorMessage( "MCP", void 0 /* config */ ) ); await runExitCleanup(); process2.exit(ExitCodes.FATAL_CONFIG_ERROR); } if (commandName === "extensions" && adminSettings?.extensions?.enabled === false) { coreEvents.emitFeedback( "error", getAdminErrorMessage( "Extensions", void 0 /* config */ ) ); await runExitCleanup(); process2.exit(ExitCodes.FATAL_CONFIG_ERROR); } if (commandName === "skills" && adminSettings?.skills?.enabled === false) { coreEvents.emitFeedback( "error", getAdminErrorMessage( "Agent skills", void 0 /* config */ ) ); await runExitCleanup(); process2.exit(ExitCodes.FATAL_CONFIG_ERROR); } const argvWithSettings = { ...deferredCommand.argv, settings }; await deferredCommand.handler(argvWithSettings); await runExitCleanup(); process2.exit(ExitCodes.SUCCESS); } function defer(commandModule, parentCommandName) { return { ...commandModule, handler: (argv) => { setDeferredCommand({ // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion handler: commandModule.handler, // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion argv, commandName: parentCommandName || "unknown" }); } }; } // packages/cli/src/commands/mcp.ts var mcpCommand = { command: "mcp", describe: "Manage MCP servers", builder: (yargs) => yargs.middleware((argv) => { initializeOutputListenersAndFlush(); argv["isCommand"] = true; }).command(defer(addCommand, "mcp")).command(defer(removeCommand, "mcp")).command(defer(listCommand, "mcp")).command(defer(enableCommand, "mcp")).command(defer(disableCommand, "mcp")).demandCommand(1, "You need at least one command before continuing.").version(false), handler: () => { } }; // packages/cli/src/commands/extensions/install.ts var import_chalk2 = __toESM(require_source(), 1); import * as path from "node:path"; async function handleInstall(args) { try { const { source } = args; const installMetadata = await inferInstallMetadata(source, { ref: args.ref, autoUpdate: args.autoUpdate, allowPreRelease: args.allowPreRelease }); const workspaceDir = process.cwd(); const settings = loadSettings(workspaceDir).merged; if (installMetadata.type === "local" || installMetadata.type === "link") { const absolutePath = path.resolve(source); const realPath = getRealPath(absolutePath); installMetadata.source = absolutePath; const trustResult = isWorkspaceTrusted(settings, absolutePath); if (trustResult.isTrusted !== true) { const discoveryResults = await FolderTrustDiscoveryService.discover(realPath); const hasDiscovery = discoveryResults.commands.length > 0 || discoveryResults.mcps.length > 0 || discoveryResults.hooks.length > 0 || discoveryResults.skills.length > 0 || discoveryResults.settings.length > 0; const promptLines = [ "", import_chalk2.default.bold("Do you trust the files in this folder?"), "", `The extension source at "${absolutePath}" is not trusted.`, "", "Trusting a folder allows Gemini CLI to load its local configurations,", "including custom commands, hooks, MCP servers, agent skills, and", "settings. These configurations could execute code on your behalf or", "change the behavior of the CLI.", "" ]; if (discoveryResults.discoveryErrors.length > 0) { promptLines.push(import_chalk2.default.red("\u274C Discovery Errors:")); for (const error of discoveryResults.discoveryErrors) { promptLines.push(import_chalk2.default.red(` \u2022 ${error}`)); } promptLines.push(""); } if (discoveryResults.securityWarnings.length > 0) { promptLines.push(import_chalk2.default.yellow("\u26A0\uFE0F Security Warnings:")); for (const warning of discoveryResults.securityWarnings) { promptLines.push(import_chalk2.default.yellow(` \u2022 ${warning}`)); } promptLines.push(""); } if (hasDiscovery) { promptLines.push(import_chalk2.default.bold("This folder contains:")); const groups = [ { label: "Commands", items: discoveryResults.commands ?? [] }, { label: "MCP Servers", items: discoveryResults.mcps ?? [] }, { label: "Hooks", items: discoveryResults.hooks ?? [] }, { label: "Skills", items: discoveryResults.skills ?? [] }, { label: "Agents", items: discoveryResults.agents ?? [] }, { label: "Setting overrides", items: discoveryResults.settings ?? [] } ].filter((g) => g.items.length > 0); for (const group of groups) { promptLines.push( ` \u2022 ${import_chalk2.default.bold(group.label)} (${group.items.length}):` ); for (const item of group.items) { promptLines.push(` - ${item}`); } } promptLines.push(""); } promptLines.push( import_chalk2.default.yellow( "Do you want to trust this folder and continue with the installation? [y/N]: " ) ); const confirmed = await promptForConsentNonInteractive( promptLines.join("\n"), false ); if (confirmed) { const trustedFolders = loadTrustedFolders(); await trustedFolders.setValue(realPath, "TRUST_FOLDER" /* TRUST_FOLDER */); } else { throw new Error( `Installation aborted: Folder "${absolutePath}" is not trusted.` ); } } } const requestConsent = args.consent ? () => Promise.resolve(true) : requestConsentNonInteractive; if (args.consent) { debugLogger.log("You have consented to the following:"); debugLogger.log(INSTALL_WARNING_MESSAGE); } const extensionManager = new ExtensionManager({ workspaceDir, requestConsent, requestSetting: args.skipSettings ? null : promptForSetting, settings }); await extensionManager.loadExtensions(); const extension = await extensionManager.installOrUpdateExtension(installMetadata); debugLogger.log( `Extension "${extension.name}" installed successfully and enabled.` ); } catch (error) { debugLogger.error(getErrorMessage(error)); process.exit(1); } } var installCommand = { command: "install [--auto-update] [--pre-release]", describe: "Installs an extension from a git repository URL or a local path.", builder: (yargs) => yargs.positional("source", { describe: "The github URL or local path of the extension to install.", type: "string", demandOption: true }).option("ref", { describe: "The git ref to install from.", type: "string" }).option("auto-update", { describe: "Enable auto-update for this extension.", type: "boolean" }).option("pre-release", { describe: "Enable pre-release versions for this extension.", type: "boolean" }).option("consent", { describe: "Acknowledge the security risks of installing an extension and skip the confirmation prompt.", type: "boolean", default: false }).option("skip-settings", { describe: "Skip the configuration on install process.", type: "boolean", default: false }).check((argv) => { if (!argv.source) { throw new Error("The source argument must be provided."); } return true; }), handler: async (argv) => { await handleInstall({ // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion source: argv["source"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion ref: argv["ref"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion autoUpdate: argv["auto-update"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion allowPreRelease: argv["pre-release"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion consent: argv["consent"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion skipSettings: argv["skip-settings"] }); await exitCli(); } }; // packages/cli/src/commands/extensions/uninstall.ts async function handleUninstall(args) { try { const workspaceDir = process.cwd(); const extensionManager = new ExtensionManager({ workspaceDir, requestConsent: requestConsentNonInteractive, requestSetting: promptForSetting, settings: loadSettings(workspaceDir).merged }); await extensionManager.loadExtensions(); let namesToUninstall = []; if (args.all) { namesToUninstall = extensionManager.getExtensions().map((ext) => ext.name); } else if (args.names) { namesToUninstall = [...new Set(args.names)]; } if (namesToUninstall.length === 0) { if (args.all) { debugLogger.log("No extensions currently installed."); } return; } const errors = []; for (const name of namesToUninstall) { try { await extensionManager.uninstallExtension(name, false); debugLogger.log(`Extension "${name}" successfully uninstalled.`); } catch (error) { errors.push({ name, error: getErrorMessage(error) }); } } if (errors.length > 0) { for (const { name, error } of errors) { debugLogger.error(`Failed to uninstall "${name}": ${error}`); } process.exit(1); } } catch (error) { debugLogger.error(getErrorMessage(error)); process.exit(1); } } var uninstallCommand = { command: "uninstall [names..]", describe: "Uninstalls one or more extensions.", builder: (yargs) => yargs.positional("names", { describe: "The name(s) or source path(s) of the extension(s) to uninstall.", type: "string", array: true }).option("all", { type: "boolean", describe: "Uninstall all installed extensions.", default: false }).check((argv) => { if (!argv.all && (!argv.names || argv.names.length === 0)) { throw new Error( "Please include at least one extension name to uninstall as a positional argument, or use the --all flag." ); } return true; }), handler: async (argv) => { await handleUninstall({ // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion names: argv["names"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion all: argv["all"] }); await exitCli(); } }; // packages/cli/src/commands/extensions/list.ts async function handleList(options) { try { const workspaceDir = process.cwd(); const extensionManager = new ExtensionManager({ workspaceDir, requestConsent: requestConsentNonInteractive, requestSetting: promptForSetting, settings: loadSettings(workspaceDir).merged }); const extensions = await extensionManager.loadExtensions(); if (extensions.length === 0) { if (options?.outputFormat === "json") { debugLogger.log("[]"); } else { debugLogger.log("No extensions installed."); } return; } if (options?.outputFormat === "json") { debugLogger.log(JSON.stringify(extensions, null, 2)); } else { debugLogger.log( extensions.map( (extension, _) => extensionManager.toOutputString(extension) ).join("\n\n") ); } } catch (error) { debugLogger.error(getErrorMessage(error)); process.exit(1); } } var listCommand2 = { command: "list", describe: "Lists installed extensions.", builder: (yargs) => yargs.option("output-format", { alias: "o", type: "string", describe: "The format of the CLI output.", choices: ["text", "json"], default: "text" }), handler: async (argv) => { await handleList({ // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion outputFormat: argv["output-format"] }); await exitCli(); } }; // packages/cli/src/commands/extensions/update.ts var updateOutput = (info) => `Extension "${info.name}" successfully updated: ${info.originalVersion} \u2192 ${info.updatedVersion}.`; async function handleUpdate(args) { const workspaceDir = process.cwd(); const settings = loadSettings(workspaceDir).merged; const extensionManager = new ExtensionManager({ workspaceDir, requestConsent: requestConsentNonInteractive, requestSetting: promptForSetting, settings }); const extensions = await extensionManager.loadExtensions(); if (args.name) { try { const extension = extensions.find( (extension2) => extension2.name === args.name ); if (!extension) { if (extensions.length === 0) { coreEvents.emitFeedback( "error", `Extension "${args.name}" not found. No extensions installed.` ); return; } const installedExtensions = extensions.map((extension2) => `${extension2.name} (${extension2.version})`).join("\n"); coreEvents.emitFeedback( "error", `Extension "${args.name}" not found. Installed extensions: ${installedExtensions} Run "gemini extensions list" for details.` ); return; } if (!extension.installMetadata) { debugLogger.log( `Unable to install extension "${args.name}" due to missing install metadata` ); return; } const updateState = await checkForExtensionUpdate( extension, extensionManager ); if (updateState !== "update available" /* UPDATE_AVAILABLE */) { debugLogger.log(`Extension "${args.name}" is already up to date.`); return; } const updatedExtensionInfo = await updateExtension( extension, extensionManager, updateState, () => { }, settings.experimental?.extensionReloading ); if (updatedExtensionInfo.originalVersion !== updatedExtensionInfo.updatedVersion) { debugLogger.log( `Extension "${args.name}" successfully updated: ${updatedExtensionInfo.originalVersion} \u2192 ${updatedExtensionInfo.updatedVersion}.` ); } else { debugLogger.log(`Extension "${args.name}" is already up to date.`); } } catch (error) { debugLogger.error(getErrorMessage(error)); } } if (args.all) { try { const extensionState = /* @__PURE__ */ new Map(); await checkForAllExtensionUpdates( extensions, extensionManager, (action) => { if (action.type === "SET_STATE") { extensionState.set(action.payload.name, { status: action.payload.state }); } } ); let updateInfos = await updateAllUpdatableExtensions( extensions, extensionState, extensionManager, () => { } ); updateInfos = updateInfos.filter( (info) => info.originalVersion !== info.updatedVersion ); if (updateInfos.length === 0) { debugLogger.log("No extensions to update."); return; } debugLogger.log(updateInfos.map((info) => updateOutput(info)).join("\n")); } catch (error) { debugLogger.error(getErrorMessage(error)); } } } var updateCommand = { command: "update [] [--all]", describe: "Updates all extensions or a named extension to the latest version.", builder: (yargs) => yargs.positional("name", { describe: "The name of the extension to update.", type: "string" }).option("all", { describe: "Update all extensions.", type: "boolean" }).conflicts("name", "all").check((argv) => { if (!argv.all && !argv.name) { throw new Error("Either an extension name or --all must be provided"); } return true; }), handler: async (argv) => { await handleUpdate({ // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion name: argv["name"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion all: argv["all"] }); await exitCli(); } }; // packages/cli/src/commands/extensions/disable.ts async function handleDisable2(args) { const workspaceDir = process.cwd(); const extensionManager = new ExtensionManager({ workspaceDir, requestConsent: requestConsentNonInteractive, requestSetting: promptForSetting, settings: loadSettings(workspaceDir).merged }); await extensionManager.loadExtensions(); try { if (args.scope?.toLowerCase() === "workspace") { await extensionManager.disableExtension( args.name, "Workspace" /* Workspace */ ); } else { await extensionManager.disableExtension(args.name, "User" /* User */); } debugLogger.log( `Extension "${args.name}" successfully disabled for scope "${args.scope}".` ); } catch (error) { debugLogger.error(getErrorMessage(error)); process.exit(1); } } var disableCommand2 = { command: "disable [--scope] ", describe: "Disables an extension.", builder: (yargs) => yargs.positional("name", { describe: "The name of the extension to disable.", type: "string" }).option("scope", { describe: "The scope to disable the extension in.", type: "string", default: "User" /* User */ }).check((argv) => { if (argv.scope && !Object.values(SettingScope).map((s) => s.toLowerCase()).includes(argv.scope.toLowerCase())) { throw new Error( `Invalid scope: ${argv.scope}. Please use one of ${Object.values( SettingScope ).map((s) => s.toLowerCase()).join(", ")}.` ); } return true; }), handler: async (argv) => { await handleDisable2({ // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion name: argv["name"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion scope: argv["scope"] }); await exitCli(); } }; // packages/cli/src/commands/extensions/enable.ts async function handleEnable2(args) { const workingDir = process.cwd(); const extensionManager = new ExtensionManager({ workspaceDir: workingDir, requestConsent: requestConsentNonInteractive, requestSetting: promptForSetting, settings: loadSettings(workingDir).merged }); await extensionManager.loadExtensions(); try { if (args.scope?.toLowerCase() === "workspace") { await extensionManager.enableExtension(args.name, "Workspace" /* Workspace */); } else { await extensionManager.enableExtension(args.name, "User" /* User */); } const extension = extensionManager.getExtensions().find((e) => e.name === args.name); if (extension?.mcpServers) { const mcpEnablementManager = McpServerEnablementManager.getInstance(); const enabledServers = await mcpEnablementManager.autoEnableServers( Object.keys(extension.mcpServers ?? {}) ); for (const serverName of enabledServers) { debugLogger.log( `MCP server '${serverName}' was disabled - now enabled.` ); } } if (args.scope) { debugLogger.log( `Extension "${args.name}" successfully enabled for scope "${args.scope}".` ); } else { debugLogger.log( `Extension "${args.name}" successfully enabled in all scopes.` ); } } catch (error) { throw new FatalConfigError(getErrorMessage(error)); } } var enableCommand2 = { command: "enable [--scope] ", describe: "Enables an extension.", builder: (yargs) => yargs.positional("name", { describe: "The name of the extension to enable.", type: "string" }).option("scope", { describe: "The scope to enable the extension in. If not set, will be enabled in all scopes.", type: "string" }).check((argv) => { if (argv.scope && !Object.values(SettingScope).map((s) => s.toLowerCase()).includes(argv.scope.toLowerCase())) { throw new Error( `Invalid scope: ${argv.scope}. Please use one of ${Object.values( SettingScope ).map((s) => s.toLowerCase()).join(", ")}.` ); } return true; }), handler: async (argv) => { await handleEnable2({ // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion name: argv["name"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion scope: argv["scope"] }); await exitCli(); } }; // packages/cli/src/commands/extensions/link.ts var import_chalk3 = __toESM(require_source(), 1); async function handleLink(args) { try { const installMetadata = { source: args.path, type: "link" }; const requestConsent = args.consent ? () => Promise.resolve(true) : requestConsentNonInteractive; if (args.consent) { debugLogger.log("You have consented to the following:"); debugLogger.log(INSTALL_WARNING_MESSAGE); } const workspaceDir = process.cwd(); const extensionManager = new ExtensionManager({ workspaceDir, requestConsent, requestSetting: promptForSetting, settings: loadSettings(workspaceDir).merged }); await extensionManager.loadExtensions(); const extension = await extensionManager.installOrUpdateExtension(installMetadata); debugLogger.log( import_chalk3.default.green( `Extension "${extension.name}" linked successfully and enabled.` ) ); } catch (error) { debugLogger.error(getErrorMessage(error)); process.exit(1); } } var linkCommand = { command: "link ", describe: "Links an extension from a local path. Updates made to the local path will always be reflected.", builder: (yargs) => yargs.positional("path", { describe: "The name of the extension to link.", type: "string" }).option("consent", { describe: "Acknowledge the security risks of installing an extension and skip the confirmation prompt.", type: "boolean", default: false }).check((_) => true), handler: async (argv) => { await handleLink({ // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion path: argv["path"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion consent: argv["consent"] }); await exitCli(); } }; // packages/cli/src/commands/extensions/new.ts import { access, cp, mkdir, readdir, writeFile as writeFile2 } from "node:fs/promises"; import { join, dirname as dirname3, basename as basename2 } from "node:path"; import { fileURLToPath as fileURLToPath2 } from "node:url"; var __filename = fileURLToPath2(import.meta.url); var __dirname2 = dirname3(__filename); var EXAMPLES_PATH = join(__dirname2, "examples"); async function pathExists(path14) { try { await access(path14); return true; } catch (_e) { return false; } } async function createDirectory(path14) { if (await pathExists(path14)) { throw new Error(`Path already exists: ${path14}`); } await mkdir(path14, { recursive: true }); } async function copyDirectory(template, path14) { await createDirectory(path14); const examplePath = join(EXAMPLES_PATH, template); const entries = await readdir(examplePath, { withFileTypes: true }); for (const entry of entries) { const srcPath = join(examplePath, entry.name); const destPath = join(path14, entry.name); await cp(srcPath, destPath, { recursive: true }); } } async function handleNew(args) { if (args.template) { await copyDirectory(args.template, args.path); debugLogger.log( `Successfully created new extension from template "${args.template}" at ${args.path}.` ); } else { await createDirectory(args.path); const extensionName = basename2(args.path); const manifest = { name: extensionName, version: "1.0.0" }; await writeFile2( join(args.path, "gemini-extension.json"), JSON.stringify(manifest, null, 2) ); debugLogger.log(`Successfully created new extension at ${args.path}.`); } debugLogger.log( `You can install this using "gemini extensions link ${args.path}" to test it out.` ); } async function getBoilerplateChoices() { const entries = await readdir(EXAMPLES_PATH, { withFileTypes: true }); return entries.filter((entry) => entry.isDirectory()).map((entry) => entry.name); } var newCommand = { command: "new [template]", describe: "Create a new extension from a boilerplate example.", builder: async (yargs) => { const choices = await getBoilerplateChoices(); return yargs.positional("path", { describe: "The path to create the extension in.", type: "string" }).positional("template", { describe: "The boilerplate template to use.", type: "string", choices }); }, handler: async (args) => { await handleNew({ // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion path: args["path"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion template: args["template"] }); await exitCli(); } }; // packages/cli/src/commands/extensions/validate.ts var import_semver = __toESM(require_semver(), 1); import * as fs from "node:fs"; import * as path2 from "node:path"; async function handleValidate(args) { try { await validateExtension(args); debugLogger.log(`Extension ${args.path} has been successfully validated.`); } catch (error) { debugLogger.error(getErrorMessage(error)); process.exit(1); } } async function validateExtension(args) { const workspaceDir = process.cwd(); const extensionManager = new ExtensionManager({ workspaceDir, requestConsent: requestConsentNonInteractive, requestSetting: promptForSetting, settings: loadSettings(workspaceDir).merged }); const absoluteInputPath = path2.resolve(args.path); const extensionConfig = await extensionManager.loadExtensionConfig(absoluteInputPath); const warnings = []; const errors = []; if (extensionConfig.contextFileName) { const contextFileNames = Array.isArray(extensionConfig.contextFileName) ? extensionConfig.contextFileName : [extensionConfig.contextFileName]; const missingContextFiles = []; for (const contextFilePath of contextFileNames) { const contextFileAbsolutePath = path2.resolve( absoluteInputPath, contextFilePath ); if (!fs.existsSync(contextFileAbsolutePath)) { missingContextFiles.push(contextFilePath); } } if (missingContextFiles.length > 0) { errors.push( `The following context files referenced in gemini-extension.json are missing: ${missingContextFiles}` ); } } if (!import_semver.default.valid(extensionConfig.version)) { warnings.push( `Warning: Version '${extensionConfig.version}' does not appear to be standard semver (e.g., 1.0.0).` ); } if (warnings.length > 0) { debugLogger.warn("Validation warnings:"); for (const warning of warnings) { debugLogger.warn(` - ${warning}`); } } if (errors.length > 0) { debugLogger.error("Validation failed with the following errors:"); for (const error of errors) { debugLogger.error(` - ${error}`); } throw new Error("Extension validation failed."); } } var validateCommand = { command: "validate ", describe: "Validates an extension from a local path.", builder: (yargs) => yargs.positional("path", { describe: "The path of the extension to validate.", type: "string", demandOption: true }), handler: async (args) => { await handleValidate({ // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion path: args["path"] }); await exitCli(); } }; // packages/cli/src/commands/extensions/configure.ts var configureCommand = { command: "config [name] [setting]", describe: "Configure extension settings.", builder: (yargs) => yargs.positional("name", { describe: "Name of the extension to configure.", type: "string" }).positional("setting", { describe: "The specific setting to configure (name or env var).", type: "string" }).option("scope", { describe: "The scope to set the setting in.", type: "string", choices: ["user", "workspace"], default: "user" }), handler: async (args) => { const { name, setting, scope } = args; const settings = loadSettings(process.cwd()).merged; if (!(settings.experimental?.extensionConfig ?? true)) { coreEvents.emitFeedback( "error", 'Extension configuration is currently disabled. Enable it by setting "experimental.extensionConfig" to true.' ); await exitCli(); return; } if (name) { if (name.includes("/") || name.includes("\\") || name.includes("..")) { debugLogger.error( 'Invalid extension name. Names cannot contain path separators or "..".' ); return; } } const extensionManager = await getExtensionManager(); if (name && setting) { await configureSpecificSetting( extensionManager, name, setting, // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion scope ); } else if (name) { await configureExtension( extensionManager, name, // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion scope ); } else { await configureAllExtensions( extensionManager, // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion scope ); } await exitCli(); } }; // packages/cli/src/commands/extensions.tsx var extensionsCommand = { command: "extensions ", aliases: ["extension"], describe: "Manage Gemini CLI extensions.", builder: (yargs) => yargs.middleware((argv) => { initializeOutputListenersAndFlush(); argv["isCommand"] = true; }).command(defer(installCommand, "extensions")).command(defer(uninstallCommand, "extensions")).command(defer(listCommand2, "extensions")).command(defer(updateCommand, "extensions")).command(defer(disableCommand2, "extensions")).command(defer(enableCommand2, "extensions")).command(defer(linkCommand, "extensions")).command(defer(newCommand, "extensions")).command(defer(validateCommand, "extensions")).command(defer(configureCommand, "extensions")).demandCommand(1, "You need at least one command before continuing.").version(false), handler: () => { } }; // packages/cli/src/commands/skills/list.ts var import_chalk4 = __toESM(require_source(), 1); async function handleList2(args) { const workspaceDir = process.cwd(); const settings = loadSettings(workspaceDir); const config = await loadCliConfig( settings.merged, "skills-list-session", // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion { debug: false }, { cwd: workspaceDir } ); await config.initialize(); const skillManager = config.getSkillManager(); const skills = args.all ? skillManager.getAllSkills() : skillManager.getAllSkills().filter((s) => !s.isBuiltin); skills.sort((a, b) => { if (a.isBuiltin === b.isBuiltin) { return a.name.localeCompare(b.name); } return a.isBuiltin ? 1 : -1; }); if (skills.length === 0) { debugLogger.log("No skills discovered."); return; } debugLogger.log(import_chalk4.default.bold("Discovered Agent Skills:")); debugLogger.log(""); for (const skill of skills) { const status = skill.disabled ? import_chalk4.default.red("[Disabled]") : import_chalk4.default.green("[Enabled]"); const builtinSuffix = skill.isBuiltin ? import_chalk4.default.gray(" [Built-in]") : ""; debugLogger.log(`${import_chalk4.default.bold(skill.name)} ${status}${builtinSuffix}`); debugLogger.log(` Description: ${skill.description}`); debugLogger.log(` Location: ${skill.location}`); debugLogger.log(""); } } var listCommand3 = { command: "list [--all]", describe: "Lists discovered agent skills.", builder: (yargs) => yargs.option("all", { type: "boolean", description: "Show all skills, including built-in ones.", default: false }), handler: async (argv) => { await handleList2({ all: argv["all"] }); await exitCli(); } }; // packages/cli/src/commands/skills/enable.ts var import_chalk5 = __toESM(require_source(), 1); async function handleEnable3(args) { const { name } = args; const workspaceDir = process.cwd(); const settings = loadSettings(workspaceDir); const result = enableSkill(settings, name); const feedback = renderSkillActionFeedback( result, (label, path14) => `${import_chalk5.default.bold(label)} (${import_chalk5.default.dim(path14)})` ); debugLogger.log(feedback); } var enableCommand3 = { command: "enable ", describe: "Enables an agent skill.", builder: (yargs) => yargs.positional("name", { describe: "The name of the skill to enable.", type: "string", demandOption: true }), handler: async (argv) => { await handleEnable3({ // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion name: argv["name"] }); await exitCli(); } }; // packages/cli/src/commands/skills/disable.ts var import_chalk6 = __toESM(require_source(), 1); async function handleDisable3(args) { const { name, scope } = args; const workspaceDir = process.cwd(); const settings = loadSettings(workspaceDir); const result = disableSkill(settings, name, scope); const feedback = renderSkillActionFeedback( result, (label, path14) => `${import_chalk6.default.bold(label)} (${import_chalk6.default.dim(path14)})` ); debugLogger.log(feedback); } var disableCommand3 = { command: "disable [--scope]", describe: "Disables an agent skill.", builder: (yargs) => yargs.positional("name", { describe: "The name of the skill to disable.", type: "string", demandOption: true }).option("scope", { alias: "s", describe: "The scope to disable the skill in (user or workspace).", type: "string", default: "workspace", choices: ["user", "workspace"] }), handler: async (argv) => { const scope = argv["scope"] === "workspace" ? "Workspace" /* Workspace */ : "User" /* User */; await handleDisable3({ // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion name: argv["name"], scope }); await exitCli(); } }; // packages/cli/src/commands/skills/install.ts var import_chalk7 = __toESM(require_source(), 1); async function handleInstall2(args) { try { const { source, consent } = args; const scope = args.scope ?? "user"; const subpath = args.path; const requestConsent = async (skills, targetDir) => { if (consent) { debugLogger.log("You have consented to the following:"); debugLogger.log(await skillsConsentString(skills, source, targetDir)); return true; } return requestConsentNonInteractive( await skillsConsentString(skills, source, targetDir) ); }; const installedSkills = await installSkill( source, scope, subpath, (msg) => { debugLogger.log(msg); }, requestConsent ); for (const skill of installedSkills) { debugLogger.log( import_chalk7.default.green( `Successfully installed skill: ${import_chalk7.default.bold(skill.name)} (scope: ${scope}, location: ${skill.location})` ) ); } } catch (error) { debugLogger.error(getErrorMessage(error)); await exitCli(1); } } var installCommand2 = { command: "install [--scope] [--path]", describe: "Installs an agent skill from a git repository URL or a local path.", builder: (yargs) => yargs.positional("source", { describe: "The git repository URL or local path of the skill to install.", type: "string", demandOption: true }).option("scope", { describe: 'The scope to install the skill into. Defaults to "user" (global).', choices: ["user", "workspace"], default: "user" }).option("path", { describe: "Sub-path within the repository to install from (only used for git repository sources).", type: "string" }).option("consent", { describe: "Acknowledge the security risks of installing a skill and skip the confirmation prompt.", type: "boolean", default: false }).check((argv) => { if (!argv.source) { throw new Error("The source argument must be provided."); } return true; }), handler: async (argv) => { await handleInstall2({ // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion source: argv["source"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion scope: argv["scope"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion path: argv["path"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion consent: argv["consent"] }); await exitCli(); } }; // packages/cli/src/commands/skills/link.ts var import_chalk8 = __toESM(require_source(), 1); async function handleLink2(args) { try { const { scope = "user", consent } = args; await linkSkill( args.path, scope, (msg) => debugLogger.log(msg), async (skills, targetDir) => { const consentString = await skillsConsentString( skills, args.path, targetDir, true ); if (consent) { debugLogger.log("You have consented to the following:"); debugLogger.log(consentString); return true; } return requestConsentNonInteractive(consentString); } ); debugLogger.log(import_chalk8.default.green("\nSuccessfully linked skills.")); } catch (error) { debugLogger.error(getErrorMessage(error)); await exitCli(1); } } var linkCommand2 = { command: "link ", describe: "Links an agent skill from a local path. Updates to the source will be reflected immediately.", builder: (yargs) => yargs.positional("path", { describe: "The local path of the skill to link.", type: "string", demandOption: true }).option("scope", { describe: 'The scope to link the skill into. Defaults to "user" (global).', choices: ["user", "workspace"], default: "user" }).option("consent", { describe: "Acknowledge the security risks of linking a skill and skip the confirmation prompt.", type: "boolean", default: false }).check((argv) => { if (!argv.path) { throw new Error("The path argument must be provided."); } return true; }), handler: async (argv) => { await handleLink2({ // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion path: argv["path"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion scope: argv["scope"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion consent: argv["consent"] }); await exitCli(); } }; // packages/cli/src/commands/skills/uninstall.ts var import_chalk9 = __toESM(require_source(), 1); async function handleUninstall2(args) { try { const { name } = args; const scope = args.scope ?? "user"; const result = await uninstallSkill(name, scope); if (result) { debugLogger.log( import_chalk9.default.green( `Successfully uninstalled skill: ${import_chalk9.default.bold(name)} (scope: ${scope}, location: ${result.location})` ) ); } else { debugLogger.error( `Skill "${name}" is not installed in the ${scope} scope.` ); } } catch (error) { debugLogger.error(getErrorMessage(error)); await exitCli(1); } } var uninstallCommand2 = { command: "uninstall [--scope]", describe: "Uninstalls an agent skill by name.", builder: (yargs) => yargs.positional("name", { describe: "The name of the skill to uninstall.", type: "string", demandOption: true }).option("scope", { describe: 'The scope to uninstall the skill from. Defaults to "user" (global).', choices: ["user", "workspace"], default: "user" }).check((argv) => { if (!argv.name) { throw new Error("The skill name must be provided."); } return true; }), handler: async (argv) => { await handleUninstall2({ // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion name: argv["name"], // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion scope: argv["scope"] }); await exitCli(); } }; // packages/cli/src/commands/skills.tsx var skillsCommand = { command: "skills ", aliases: ["skill"], describe: "Manage agent skills.", builder: (yargs) => yargs.middleware((argv) => { initializeOutputListenersAndFlush(); argv["isCommand"] = true; }).command(defer(listCommand3, "skills")).command(defer(enableCommand3, "skills")).command(defer(disableCommand3, "skills")).command(defer(installCommand2, "skills")).command(defer(linkCommand2, "skills")).command(defer(uninstallCommand2, "skills")).demandCommand(1, "You need at least one command before continuing.").version(false), handler: () => { } }; // packages/cli/src/commands/hooks/migrate.ts import * as fs2 from "node:fs"; import * as path3 from "node:path"; var import_strip_json_comments = __toESM(require_strip_json_comments(), 1); var EVENT_MAPPING = { PreToolUse: "BeforeTool", PostToolUse: "AfterTool", UserPromptSubmit: "BeforeAgent", Stop: "AfterAgent", SubAgentStop: "AfterAgent", // Gemini doesn't have sub-agents, map to AfterAgent SessionStart: "SessionStart", SessionEnd: "SessionEnd", PreCompact: "PreCompress", Notification: "Notification" }; var TOOL_NAME_MAPPING = { Edit: "replace", Bash: "run_shell_command", Read: "read_file", Write: "write_file", Glob: "glob", Grep: "grep", LS: "ls" }; function transformMatcher(matcher) { if (!matcher) return matcher; let transformed = matcher; for (const [claudeName, geminiName] of Object.entries(TOOL_NAME_MAPPING)) { transformed = transformed.replace( new RegExp(`\\b${claudeName}\\b`, "g"), geminiName ); } return transformed; } function migrateClaudeHook(claudeHook) { if (!claudeHook || typeof claudeHook !== "object") { return claudeHook; } const hook = claudeHook; const migrated = {}; if ("command" in hook) { migrated["command"] = hook["command"]; if (typeof migrated["command"] === "string") { migrated["command"] = migrated["command"].replace( /\$CLAUDE_PROJECT_DIR/g, "$GEMINI_PROJECT_DIR" ); } } if ("type" in hook && hook["type"] === "command") { migrated["type"] = "command"; } if ("timeout" in hook && typeof hook["timeout"] === "number") { migrated["timeout"] = hook["timeout"]; } return migrated; } function migrateClaudeHooks(claudeConfig) { if (!claudeConfig || typeof claudeConfig !== "object") { return {}; } const config = claudeConfig; const geminiHooks = {}; const hooksSection = config["hooks"]; if (!hooksSection || typeof hooksSection !== "object") { return {}; } for (const [eventName, eventConfig] of Object.entries(hooksSection)) { const geminiEventName = EVENT_MAPPING[eventName] || eventName; if (!Array.isArray(eventConfig)) { continue; } const migratedDefinitions = eventConfig.map((def) => { if (!def || typeof def !== "object") { return def; } const definition = def; const migratedDef = {}; if ("matcher" in definition && // eslint-disable-next-line no-restricted-syntax typeof definition["matcher"] === "string") { migratedDef["matcher"] = transformMatcher(definition["matcher"]); } if ("sequential" in definition) { migratedDef["sequential"] = definition["sequential"]; } if ("hooks" in definition && Array.isArray(definition["hooks"])) { migratedDef["hooks"] = definition["hooks"].map(migrateClaudeHook); } return migratedDef; }); geminiHooks[geminiEventName] = migratedDefinitions; } return geminiHooks; } async function handleMigrateFromClaude() { const workingDir = process.cwd(); const claudeDir = path3.join(workingDir, ".claude"); const claudeSettingsPath = path3.join(claudeDir, "settings.json"); const claudeLocalSettingsPath = path3.join(claudeDir, "settings.local.json"); let claudeSettings = null; let sourceFile = ""; if (fs2.existsSync(claudeLocalSettingsPath)) { sourceFile = claudeLocalSettingsPath; try { const content = fs2.readFileSync(claudeLocalSettingsPath, "utf-8"); claudeSettings = JSON.parse((0, import_strip_json_comments.default)(content)); } catch (error) { debugLogger.error( `Error reading ${claudeLocalSettingsPath}: ${getErrorMessage(error)}` ); } } else if (fs2.existsSync(claudeSettingsPath)) { sourceFile = claudeSettingsPath; try { const content = fs2.readFileSync(claudeSettingsPath, "utf-8"); claudeSettings = JSON.parse((0, import_strip_json_comments.default)(content)); } catch (error) { debugLogger.error( `Error reading ${claudeSettingsPath}: ${getErrorMessage(error)}` ); } } else { debugLogger.error( "No Claude Code settings found in .claude directory. Expected settings.json or settings.local.json" ); return; } if (!claudeSettings) { return; } debugLogger.log(`Found Claude Code settings in: ${sourceFile}`); const migratedHooks = migrateClaudeHooks(claudeSettings); if (Object.keys(migratedHooks).length === 0) { debugLogger.log("No hooks found in Claude Code settings to migrate."); return; } debugLogger.log( `Migrating ${Object.keys(migratedHooks).length} hook event(s)...` ); const settings = loadSettings(workingDir); const existingHooks = settings.merged?.hooks || {}; const mergedHooks = { ...existingHooks, ...migratedHooks }; try { settings.setValue("Workspace" /* Workspace */, "hooks", mergedHooks); debugLogger.log("\u2713 Hooks successfully migrated to .gemini/settings.json"); debugLogger.log( "\nMigration complete! Please review the migrated hooks in .gemini/settings.json" ); } catch (error) { debugLogger.error(`Error saving migrated hooks: ${getErrorMessage(error)}`); } } var migrateCommand = { command: "migrate", describe: "Migrate hooks from Claude Code to Gemini CLI", builder: (yargs) => yargs.option("from-claude", { describe: "Migrate from Claude Code hooks", type: "boolean", default: false }), handler: async (argv) => { const args = argv; if (args.fromClaude) { await handleMigrateFromClaude(); } else { debugLogger.log( "Usage: gemini hooks migrate --from-claude\n\nMigrate hooks from Claude Code to Gemini CLI format." ); } await exitCli(); } }; // packages/cli/src/commands/hooks.tsx var hooksCommand = { command: "hooks ", aliases: ["hook"], describe: "Manage Gemini CLI hooks.", builder: (yargs) => yargs.middleware((argv) => { initializeOutputListenersAndFlush(); argv["isCommand"] = true; }).command(migrateCommand).demandCommand(1, "You need at least one command before continuing.").version(false), handler: () => { } }; // packages/cli/src/config/sandboxConfig.ts var import_command_exists = __toESM(require_command_exists2(), 1); import * as os from "node:os"; import { fileURLToPath as fileURLToPath3 } from "node:url"; import path4 from "node:path"; var __filename2 = fileURLToPath3(import.meta.url); var __dirname3 = path4.dirname(__filename2); var VALID_SANDBOX_COMMANDS = [ "docker", "podman", "sandbox-exec", "runsc", "lxc", "windows-native" ]; function isSandboxCommand(value) { return VALID_SANDBOX_COMMANDS.includes( value ); } function getSandboxCommand(sandbox) { if (process.env["SANDBOX"]) { return ""; } const environmentConfiguredSandbox = process.env["GEMINI_SANDBOX"]?.toLowerCase().trim() ?? ""; sandbox = environmentConfiguredSandbox?.length > 0 ? environmentConfiguredSandbox : sandbox; if (sandbox === "1" || sandbox === "true") sandbox = true; else if (sandbox === "0" || sandbox === "false" || !sandbox) sandbox = false; if (sandbox === false) { return ""; } if (typeof sandbox === "string" && sandbox) { if (!isSandboxCommand(sandbox)) { throw new FatalSandboxError( `Invalid sandbox command '${sandbox}'. Must be one of ${VALID_SANDBOX_COMMANDS.join( ", " )}` ); } if (sandbox === "runsc" && os.platform() !== "linux") { throw new FatalSandboxError( "gVisor (runsc) sandboxing is only supported on Linux" ); } if (sandbox === "windows-native" && os.platform() !== "win32") { throw new FatalSandboxError( "Windows native sandboxing is only supported on Windows" ); } if (sandbox !== "windows-native" && !import_command_exists.default.sync(sandbox)) { throw new FatalSandboxError( `Missing sandbox command '${sandbox}' (from GEMINI_SANDBOX)` ); } if (sandbox === "runsc" && !import_command_exists.default.sync("docker")) { throw new FatalSandboxError( "runsc (gVisor) requires Docker. Install Docker, or use sandbox: 'docker'." ); } return sandbox; } if (os.platform() === "darwin" && import_command_exists.default.sync("sandbox-exec")) { return "sandbox-exec"; } else if (import_command_exists.default.sync("docker") && sandbox === true) { return "docker"; } else if (import_command_exists.default.sync("podman") && sandbox === true) { return "podman"; } if (sandbox === true) { throw new FatalSandboxError( "GEMINI_SANDBOX is true but failed to determine command for sandbox; install docker or podman or specify command in GEMINI_SANDBOX" ); } return ""; } async function loadSandboxConfig(settings, argv) { const sandboxOption = argv.sandbox ?? settings.tools?.sandbox; let sandboxValue; let allowedPaths = []; let networkAccess = true; let customImage; if (typeof sandboxOption === "object" && sandboxOption !== null && !Array.isArray(sandboxOption)) { const config = sandboxOption; sandboxValue = config.enabled ? config.command ?? true : false; allowedPaths = config.allowedPaths ?? []; networkAccess = config.networkAccess ?? true; customImage = config.image; } else if (typeof sandboxOption !== "object" || sandboxOption === null) { sandboxValue = sandboxOption; } const command2 = getSandboxCommand(sandboxValue); const packageJson = await getPackageJson(__dirname3); const image = process.env["GEMINI_SANDBOX_IMAGE"] ?? "us-docker.pkg.dev/gemini-code-dev/gemini-cli/sandbox:0.36.0" ?? customImage ?? packageJson?.config?.sandboxImageUri; const isNative = command2 === "windows-native" || command2 === "sandbox-exec" || command2 === "lxc"; return command2 && (image || isNative) ? { enabled: true, allowedPaths, networkAccess, command: command2, image } : void 0; } // packages/cli/src/utils/resolvePath.ts import * as path5 from "node:path"; function resolvePath(p) { if (!p) { return ""; } let expandedPath = p; if (p.toLowerCase().startsWith("%userprofile%")) { expandedPath = homedir() + p.substring("%userprofile%".length); } else if (p === "~" || p.startsWith("~/")) { expandedPath = homedir() + p.substring(1); } return path5.normalize(expandedPath); } // packages/cli/src/config/policy.ts var autoAcceptWorkspacePolicies = true; var disableWorkspacePolicies = true; async function createPolicyEngineConfig2(settings, approvalMode, workspacePoliciesDir) { const policySettings = { mcp: settings.mcp, tools: settings.tools, mcpServers: settings.mcpServers, policyPaths: settings.policyPaths, adminPolicyPaths: settings.adminPolicyPaths, workspacePoliciesDir, disableAlwaysAllow: settings.security?.disableAlwaysAllow || settings.admin?.secureModeEnabled }; return createPolicyEngineConfig(policySettings, approvalMode); } function createPolicyUpdater2(policyEngine, messageBus, storage) { return createPolicyUpdater(policyEngine, messageBus, storage); } async function resolveWorkspacePolicyState(options) { const { cwd, trustedFolder, interactive } = options; let workspacePoliciesDir; let policyUpdateConfirmationRequest; if (trustedFolder && !disableWorkspacePolicies) { const storage = new Storage(cwd); if (storage.isWorkspaceHomeDir()) { return { workspacePoliciesDir: void 0 }; } const potentialWorkspacePoliciesDir = storage.getWorkspacePoliciesDir(); const integrityManager = new PolicyIntegrityManager(); const integrityResult = await integrityManager.checkIntegrity( "workspace", cwd, potentialWorkspacePoliciesDir ); if (integrityResult.status === IntegrityStatus.MATCH) { workspacePoliciesDir = potentialWorkspacePoliciesDir; } else if (integrityResult.status === IntegrityStatus.NEW && integrityResult.fileCount === 0) { workspacePoliciesDir = void 0; } else if (interactive && !autoAcceptWorkspacePolicies) { policyUpdateConfirmationRequest = { scope: "workspace", identifier: cwd, policyDir: potentialWorkspacePoliciesDir, newHash: integrityResult.hash }; } else { await integrityManager.acceptIntegrity( "workspace", cwd, integrityResult.hash ); workspacePoliciesDir = potentialWorkspacePoliciesDir; if (!interactive) { writeToStderr( "WARNING: Workspace policies changed or are new. Automatically accepting and loading them.\n" ); } else { debugLogger.warn( "Workspace policies changed or are new. Automatically accepting and loading them." ); } } } return { workspacePoliciesDir, policyUpdateConfirmationRequest }; } // packages/cli/src/config/config.ts var coerceCommaSeparated = (values) => { if (values.length === 1 && values[0] === "") { return [""]; } return values.flatMap( (v) => v.split(",").map((s) => s.trim()).filter(Boolean) ); }; function getWorktreeArg(argv) { const result = yargs_default(hideBin(argv)).help(false).version(false).option("worktree", { alias: "w", type: "string" }).strict(false).exitProcess(false).parseSync(); if (result.worktree === void 0) return void 0; return typeof result.worktree === "string" ? result.worktree.trim() : ""; } function getRequestedWorktreeName(settings) { if (!isWorktreeEnabled(settings)) { return void 0; } return getWorktreeArg(process3.argv); } async function parseArguments(settings) { const rawArgv = hideBin(process3.argv); const startupMessages = []; const yargsInstance = yargs_default(rawArgv).locale("en").scriptName("gemini").usage( "Usage: gemini [options] [command]\n\nGemini CLI - Defaults to interactive mode. Use -p/--prompt for non-interactive (headless) mode." ).option("isCommand", { type: "boolean", hidden: true, description: "Internal flag to indicate if a subcommand is being run" }).option("debug", { alias: "d", type: "boolean", description: "Run in debug mode (open debug console with F12)", default: false }).middleware((argv) => { const commandModules = [ mcpCommand, extensionsCommand, skillsCommand, hooksCommand ]; const subcommands = commandModules.flatMap((mod) => { const names = []; const cmd = mod.command; if (cmd) { if (Array.isArray(cmd)) { for (const c of cmd) { names.push(String(c).split(" ")[0]); } } else { names.push(String(cmd).split(" ")[0]); } } const aliases = mod.aliases; if (aliases) { if (Array.isArray(aliases)) { for (const a of aliases) { names.push(String(a).split(" ")[0]); } } else { names.push(String(aliases).split(" ")[0]); } } return names; }); const firstArg = argv._[0]; if (typeof firstArg === "string" && subcommands.includes(firstArg)) { argv["isCommand"] = true; } }, true).fail((msg, err) => { if (err) throw err; throw new Error(msg); }).check((argv) => { const queryArg2 = argv["query"]; const query = typeof queryArg2 === "string" || Array.isArray(queryArg2) ? queryArg2 : void 0; const hasPositionalQuery = Array.isArray(query) ? query.length > 0 : !!query; if (argv["prompt"] && hasPositionalQuery) { return "Cannot use both a positional prompt and the --prompt (-p) flag together"; } if (argv["prompt"] && argv["promptInteractive"]) { return "Cannot use both --prompt (-p) and --prompt-interactive (-i) together"; } if (argv["yolo"] && argv["approvalMode"]) { return "Cannot use both --yolo (-y) and --approval-mode together. Use --approval-mode=yolo instead."; } const outputFormat = argv["outputFormat"]; if (typeof outputFormat === "string" && !["text", "json", "stream-json"].includes(outputFormat)) { return `Invalid values: Argument: output-format, Given: "${outputFormat}", Choices: "text", "json", "stream-json"`; } if (argv["worktree"] && !settings.experimental?.worktrees) { return "The --worktree flag is only available when experimental.worktrees is enabled in your settings."; } return true; }); yargsInstance.command(mcpCommand); yargsInstance.command(extensionsCommand); yargsInstance.command(skillsCommand); yargsInstance.command(hooksCommand); yargsInstance.command( "$0 [query..]", "Launch Gemini CLI", (yargsInstance2) => yargsInstance2.positional("query", { description: "Initial prompt. Runs in interactive mode by default; use -p/--prompt for non-interactive." }).option("model", { alias: "m", type: "string", nargs: 1, description: `Model` }).option("prompt", { alias: "p", type: "string", nargs: 1, description: "Run in non-interactive (headless) mode with the given prompt. Appended to input on stdin (if any)." }).option("prompt-interactive", { alias: "i", type: "string", nargs: 1, description: "Execute the provided prompt and continue in interactive mode" }).option("worktree", { alias: "w", type: "string", skipValidation: true, description: "Start Gemini in a new git worktree. If no name is provided, one is generated automatically.", coerce: (value) => { const trimmed = typeof value === "string" ? value.trim() : ""; if (trimmed === "") { return Math.random().toString(36).substring(2, 10); } return trimmed; } }).option("sandbox", { alias: "s", type: "boolean", description: "Run in sandbox?" }).option("yolo", { alias: "y", type: "boolean", description: "Automatically accept all actions (aka YOLO mode, see https://www.youtube.com/watch?v=xvFZjo5PgG0 for more details)?", default: false }).option("approval-mode", { type: "string", nargs: 1, choices: ["default", "auto_edit", "yolo", "plan"], description: "Set the approval mode: default (prompt for approval), auto_edit (auto-approve edit tools), yolo (auto-approve all tools), plan (read-only mode)" }).option("policy", { type: "array", string: true, nargs: 1, description: "Additional policy files or directories to load (comma-separated or multiple --policy)", coerce: coerceCommaSeparated }).option("admin-policy", { type: "array", string: true, nargs: 1, description: "Additional admin policy files or directories to load (comma-separated or multiple --admin-policy)", coerce: coerceCommaSeparated }).option("acp", { type: "boolean", description: "Starts the agent in ACP mode" }).option("experimental-acp", { type: "boolean", description: "Starts the agent in ACP mode (deprecated, use --acp instead)" }).option("allowed-mcp-server-names", { type: "array", string: true, nargs: 1, description: "Allowed MCP server names", coerce: coerceCommaSeparated }).option("allowed-tools", { type: "array", string: true, nargs: 1, description: "[DEPRECATED: Use Policy Engine instead See https://geminicli.com/docs/core/policy-engine] Tools that are allowed to run without confirmation", coerce: coerceCommaSeparated }).option("extensions", { alias: "e", type: "array", string: true, nargs: 1, description: "A list of extensions to use. If not provided, all extensions are used.", coerce: coerceCommaSeparated }).option("list-extensions", { alias: "l", type: "boolean", description: "List all available extensions and exit." }).option("resume", { alias: "r", type: "string", // `skipValidation` so that we can distinguish between it being passed with a value, without // one, and not being passed at all. skipValidation: true, description: 'Resume a previous session. Use "latest" for most recent or index number (e.g. --resume 5)', coerce: (value) => { const trimmed = value.trim(); if (trimmed === "") { return RESUME_LATEST; } return trimmed; } }).option("list-sessions", { type: "boolean", description: "List available sessions for the current project and exit." }).option("delete-session", { type: "string", description: "Delete a session by index number (use --list-sessions to see available sessions)." }).option("include-directories", { type: "array", string: true, nargs: 1, description: "Additional directories to include in the workspace (comma-separated or multiple --include-directories)", coerce: coerceCommaSeparated }).option("screen-reader", { type: "boolean", description: "Enable screen reader mode for accessibility." }).option("output-format", { alias: "o", type: "string", nargs: 1, description: "The format of the CLI output.", choices: ["text", "json", "stream-json"] }).option("fake-responses", { type: "string", description: "Path to a file with fake model responses for testing.", hidden: true }).option("record-responses", { type: "string", description: "Path to a file to record model responses for testing.", hidden: true }).option("raw-output", { type: "boolean", description: "Disable sanitization of model output (e.g. allow ANSI escape sequences). WARNING: This can be a security risk if the model output is untrusted." }).option("accept-raw-output-risk", { type: "boolean", description: "Suppress the security warning when using --raw-output." }) ).version(await getVersion()).alias("v", "version").help().alias("h", "help").strict().demandCommand(0, 0).exitProcess(false); yargsInstance.wrap(yargsInstance.terminalWidth()); let result; try { result = await yargsInstance.parse(); } catch (e) { const msg = e instanceof Error ? e.message : String(e); debugLogger.error(msg); yargsInstance.showHelp(); await runExitCleanup(); process3.exit(1); } if (result["help"] || result["version"]) { await runExitCleanup(); process3.exit(0); } const queryArg = result.query; const q = Array.isArray(queryArg) ? queryArg.join(" ") : queryArg; if (q && !result["prompt"]) { if (!isHeadlessMode()) { startupMessages.push( "Positional arguments now default to interactive mode. To run in non-interactive mode, use the --prompt (-p) flag." ); result["promptInteractive"] = q; } else { result["prompt"] = q; } } result["query"] = q || void 0; result["startupMessages"] = startupMessages; return result; } function isDebugMode(argv) { return argv.debug || [process3.env["DEBUG"], process3.env["DEBUG_MODE"]].some( (v) => v === "true" || v === "1" ); } async function loadCliConfig(settings, sessionId2, argv, options = {}) { const { cwd = process3.cwd(), projectHooks } = options; const debugMode = isDebugMode(argv); const worktreeSettings = options.worktreeSettings ?? await resolveWorktreeSettings(cwd); if (argv.sandbox) { process3.env["GEMINI_SANDBOX"] = "true"; } const memoryImportFormat = settings.context?.importFormat || "tree"; const includeDirectoryTree = settings.context?.includeDirectoryTree ?? true; const ideMode = settings.ide?.enabled ?? false; const folderTrust = process3.env["GEMINI_CLI_INTEGRATION_TEST"] === "true" || process3.env["VITEST"] === "true" ? false : settings.security?.folderTrust?.enabled ?? false; const trustedFolder = isWorkspaceTrusted(settings, cwd, void 0, { prompt: argv.prompt, query: argv.query })?.isTrusted ?? false; if (settings.context?.fileName) { setGeminiMdFilename(settings.context.fileName); } else { setGeminiMdFilename(getCurrentGeminiMdFilename()); } const fileService = new FileDiscoveryService(cwd); const memoryFileFiltering = { ...DEFAULT_MEMORY_FILE_FILTERING_OPTIONS, ...settings.context?.fileFiltering }; const fileFiltering = { ...DEFAULT_FILE_FILTERING_OPTIONS, ...settings.context?.fileFiltering }; const includeDirectories = (settings.context?.includeDirectories || []).map(resolvePath).concat((argv.includeDirectories || []).map(resolvePath)); const ideWorkspacePath = process3.env["GEMINI_CLI_IDE_WORKSPACE_PATH"]; if (ideWorkspacePath) { const realCwd = resolveToRealPath(cwd); const ideFolders = ideWorkspacePath.split(path6.delimiter).filter((p) => { const trimmedPath = p.trim(); if (!trimmedPath) return false; try { return resolveToRealPath(trimmedPath) !== realCwd; } catch (e) { debugLogger.debug( `[IDE] Skipping inaccessible workspace folder: ${trimmedPath} (${e instanceof Error ? e.message : String(e)})` ); return false; } }); includeDirectories.push(...ideFolders); } const extensionManager = new ExtensionManager({ settings, requestConsent: requestConsentNonInteractive, requestSetting: promptForSetting, workspaceDir: cwd, enabledExtensionOverrides: argv.extensions, // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion eventEmitter: coreEvents, clientVersion: await getVersion() }); await extensionManager.loadExtensions(); const extensionPlanSettings = extensionManager.getExtensions().find((ext) => ext.isActive && ext.plan?.directory)?.plan; const experimentalJitContext = settings.experimental.jitContext; let extensionRegistryURI = process3.env["GEMINI_CLI_EXTENSION_REGISTRY_URI"] ?? (trustedFolder ? settings.experimental?.extensionRegistryURI : void 0); if (extensionRegistryURI && !extensionRegistryURI.startsWith("http")) { extensionRegistryURI = resolveToRealPath( path6.resolve(cwd, resolvePath(extensionRegistryURI)) ); } let memoryContent = ""; let fileCount = 0; let filePaths = []; if (!experimentalJitContext) { const result = await loadServerHierarchicalMemory( cwd, settings.context?.loadMemoryFromIncludeDirectories || false ? includeDirectories : [], fileService, extensionManager, trustedFolder, memoryImportFormat, memoryFileFiltering, settings.context?.discoveryMaxDirs ); memoryContent = result.memoryContent; fileCount = result.fileCount; filePaths = result.filePaths; } const question = argv.promptInteractive || argv.prompt || ""; let approvalMode; const rawApprovalMode = argv.approvalMode || (argv.yolo ? "yolo" : void 0) || (settings.general?.defaultApprovalMode !== "yolo" ? settings.general?.defaultApprovalMode : void 0); if (rawApprovalMode) { switch (rawApprovalMode) { case "yolo": approvalMode = ApprovalMode.YOLO; break; case "auto_edit": approvalMode = ApprovalMode.AUTO_EDIT; break; case "plan": if (!(settings.experimental?.plan ?? false)) { debugLogger.warn( 'Approval mode "plan" is only available when experimental.plan is enabled. Falling back to "default".' ); approvalMode = ApprovalMode.DEFAULT; } else { approvalMode = ApprovalMode.PLAN; } break; case "default": approvalMode = ApprovalMode.DEFAULT; break; default: throw new Error( `Invalid approval mode: ${rawApprovalMode}. Valid values are: yolo, auto_edit, plan, default` ); } } else { approvalMode = ApprovalMode.DEFAULT; } if (settings.security?.disableYoloMode || settings.admin?.secureModeEnabled) { if (approvalMode === ApprovalMode.YOLO) { if (settings.admin?.secureModeEnabled) { debugLogger.error( 'YOLO mode is disabled by "secureModeEnabled" setting.' ); } else { debugLogger.error( 'YOLO mode is disabled by the "disableYolo" setting.' ); } throw new FatalConfigError( getAdminErrorMessage( "YOLO mode", void 0 /* config */ ) ); } } else if (approvalMode === ApprovalMode.YOLO) { debugLogger.warn( "YOLO mode is enabled. All tool calls will be automatically approved." ); } if (!trustedFolder && approvalMode !== ApprovalMode.DEFAULT) { debugLogger.warn( `Approval mode overridden to "default" because the current folder is not trusted.` ); approvalMode = ApprovalMode.DEFAULT; } let telemetrySettings; try { telemetrySettings = await resolveTelemetrySettings({ // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion env: process3.env, settings: settings.telemetry }); } catch (err) { if (err instanceof FatalConfigError) { throw new FatalConfigError( `Invalid telemetry configuration: ${err.message}.` ); } throw err; } const interactive = !!argv.promptInteractive || !!argv.acp || !!argv.experimentalAcp || !isHeadlessMode({ prompt: argv.prompt, query: argv.query }) && !argv.isCommand; const allowedTools = argv.allowedTools || settings.tools?.allowed || []; const isAcpMode = !!argv.acp || !!argv.experimentalAcp; const extraExcludes = []; if (!interactive || isAcpMode) { extraExcludes.push(ASK_USER_TOOL_NAME); } const excludeTools = mergeExcludeTools(settings, extraExcludes); const effectiveSettings = { ...settings, tools: { ...settings.tools, allowed: allowedTools, exclude: excludeTools }, mcp: { ...settings.mcp, allowed: argv.allowedMcpServerNames ?? settings.mcp?.allowed }, policyPaths: (argv.policy ?? settings.policyPaths)?.map( (p) => resolvePath(p) ), adminPolicyPaths: (argv.adminPolicy ?? settings.adminPolicyPaths)?.map( (p) => resolvePath(p) ) }; const { workspacePoliciesDir, policyUpdateConfirmationRequest } = await resolveWorkspacePolicyState({ cwd, trustedFolder, interactive }); const policyEngineConfig = await createPolicyEngineConfig2( effectiveSettings, approvalMode, workspacePoliciesDir ); policyEngineConfig.nonInteractive = !interactive; const defaultModel = PREVIEW_GEMINI_MODEL_AUTO; const specifiedModel = argv.model || process3.env["GEMINI_MODEL"] || settings.model?.name; const resolvedModel = specifiedModel === GEMINI_MODEL_ALIAS_AUTO ? defaultModel : specifiedModel || defaultModel; const sandboxConfig = await loadSandboxConfig(settings, argv); if (sandboxConfig) { const existingPaths = sandboxConfig.allowedPaths || []; if (settings.tools.sandboxAllowedPaths?.length) { sandboxConfig.allowedPaths = [ .../* @__PURE__ */ new Set([...existingPaths, ...settings.tools.sandboxAllowedPaths]) ]; } if (settings.tools.sandboxNetworkAccess !== void 0) { sandboxConfig.networkAccess = sandboxConfig.networkAccess || settings.tools.sandboxNetworkAccess; } } const screenReader = argv.screenReader !== void 0 ? argv.screenReader : settings.ui?.accessibility?.screenReader ?? false; const ptyInfo = await getPty(); const mcpEnabled = settings.admin?.mcp?.enabled ?? true; const extensionsEnabled = settings.admin?.extensions?.enabled ?? true; const adminSkillsEnabled = settings.admin?.skills?.enabled ?? true; const mcpEnablementManager = McpServerEnablementManager.getInstance(); const mcpEnablementCallbacks = mcpEnabled ? mcpEnablementManager.getEnablementCallbacks() : void 0; const adminAllowlist = settings.admin?.mcp?.config; let mcpServerCommand = mcpEnabled ? settings.mcp?.serverCommand : void 0; let mcpServers = mcpEnabled ? settings.mcpServers : {}; if (mcpEnabled && adminAllowlist && Object.keys(adminAllowlist).length > 0) { const result = applyAdminAllowlist(mcpServers, adminAllowlist); mcpServers = result.mcpServers; mcpServerCommand = void 0; if (result.blockedServerNames && result.blockedServerNames.length > 0) { const message = getAdminBlockedMcpServersMessage( result.blockedServerNames, void 0 ); coreEvents.emitConsoleLog("warn", message); } } if (mcpEnabled) { const requiredMcpConfig = settings.admin?.mcp?.requiredConfig; if (requiredMcpConfig && Object.keys(requiredMcpConfig).length > 0) { const requiredResult = applyRequiredServers( mcpServers ?? {}, requiredMcpConfig ); mcpServers = requiredResult.mcpServers; if (requiredResult.requiredServerNames.length > 0) { coreEvents.emitConsoleLog( "info", `Admin-required MCP servers injected: ${requiredResult.requiredServerNames.join(", ")}` ); } } } let clientName = void 0; if (isAcpMode) { const ide = detectIdeFromEnv(); if (ide && (ide.name !== "vscode" || process3.env["TERM_PROGRAM"] === "vscode")) { clientName = `acp-${ide.name}`; } } return new Config({ acpMode: isAcpMode, clientName, sessionId: sessionId2, clientVersion: await getVersion(), embeddingModel: DEFAULT_GEMINI_EMBEDDING_MODEL, sandbox: sandboxConfig, toolSandboxing: settings.security?.toolSandboxing ?? false, targetDir: cwd, includeDirectoryTree, includeDirectories, loadMemoryFromIncludeDirectories: settings.context?.loadMemoryFromIncludeDirectories || false, discoveryMaxDirs: settings.context?.discoveryMaxDirs, importFormat: settings.context?.importFormat, debugMode, question, worktreeSettings, coreTools: settings.tools?.core || void 0, allowedTools: allowedTools.length > 0 ? allowedTools : void 0, policyEngineConfig, policyUpdateConfirmationRequest, excludeTools, toolDiscoveryCommand: settings.tools?.discoveryCommand, toolCallCommand: settings.tools?.callCommand, mcpServerCommand, mcpServers, mcpEnablementCallbacks, mcpEnabled, extensionsEnabled, agents: settings.agents, adminSkillsEnabled, allowedMcpServers: mcpEnabled ? argv.allowedMcpServerNames ?? settings.mcp?.allowed : void 0, blockedMcpServers: mcpEnabled ? argv.allowedMcpServerNames ? void 0 : settings.mcp?.excluded : void 0, blockedEnvironmentVariables: settings.security?.environmentVariableRedaction?.blocked, enableEnvironmentVariableRedaction: settings.security?.environmentVariableRedaction?.enabled, userMemory: memoryContent, geminiMdFileCount: fileCount, geminiMdFilePaths: filePaths, approvalMode, disableYoloMode: settings.security?.disableYoloMode || settings.admin?.secureModeEnabled, disableAlwaysAllow: settings.security?.disableAlwaysAllow || settings.admin?.secureModeEnabled, showMemoryUsage: settings.ui?.showMemoryUsage || false, accessibility: { ...settings.ui?.accessibility, screenReader }, telemetry: telemetrySettings, usageStatisticsEnabled: settings.privacy?.usageStatisticsEnabled, fileFiltering, checkpointing: settings.general?.checkpointing?.enabled, proxy: process3.env["HTTPS_PROXY"] || process3.env["https_proxy"] || process3.env["HTTP_PROXY"] || process3.env["http_proxy"], cwd, fileDiscoveryService: fileService, bugCommand: settings.advanced?.bugCommand, model: resolvedModel, maxSessionTurns: settings.model?.maxSessionTurns, listExtensions: argv.listExtensions || false, listSessions: argv.listSessions || false, deleteSession: argv.deleteSession, enabledExtensions: argv.extensions, extensionLoader: extensionManager, extensionRegistryURI, enableExtensionReloading: settings.experimental?.extensionReloading, enableAgents: settings.experimental?.enableAgents, plan: settings.experimental?.plan, tracker: settings.experimental?.taskTracker, directWebFetch: settings.experimental?.directWebFetch, planSettings: settings.general?.plan?.directory ? settings.general.plan : extensionPlanSettings ?? settings.general?.plan, enableEventDrivenScheduler: true, skillsSupport: settings.skills?.enabled ?? true, disabledSkills: settings.skills?.disabled, experimentalJitContext: settings.experimental?.jitContext, experimentalMemoryManager: settings.experimental?.memoryManager, modelSteering: settings.experimental?.modelSteering, topicUpdateNarration: settings.experimental?.topicUpdateNarration, toolOutputMasking: settings.experimental?.toolOutputMasking, noBrowser: !!process3.env["NO_BROWSER"], summarizeToolOutput: settings.model?.summarizeToolOutput, ideMode, disableLoopDetection: settings.model?.disableLoopDetection, compressionThreshold: settings.model?.compressionThreshold, folderTrust, interactive, trustedFolder, useBackgroundColor: settings.ui?.useBackgroundColor, useAlternateBuffer: settings.ui?.useAlternateBuffer, useRipgrep: settings.tools?.useRipgrep, enableInteractiveShell: settings.tools?.shell?.enableInteractiveShell, shellToolInactivityTimeout: settings.tools?.shell?.inactivityTimeout, enableShellOutputEfficiency: settings.tools?.shell?.enableShellOutputEfficiency ?? true, skipNextSpeakerCheck: settings.model?.skipNextSpeakerCheck, truncateToolOutputThreshold: settings.tools?.truncateToolOutputThreshold, eventEmitter: coreEvents, useWriteTodos: argv.useWriteTodos ?? settings.useWriteTodos, output: { // eslint-disable-next-line @typescript-eslint/no-unsafe-type-assertion format: argv.outputFormat ?? settings.output?.format }, gemmaModelRouter: settings.experimental?.gemmaModelRouter, fakeResponses: argv.fakeResponses, recordResponses: argv.recordResponses, retryFetchErrors: settings.general?.retryFetchErrors, billing: settings.billing, maxAttempts: settings.general?.maxAttempts, ptyInfo: ptyInfo?.name, disableLLMCorrection: settings.tools?.disableLLMCorrection, rawOutput: argv.rawOutput, acceptRawOutputRisk: argv.acceptRawOutputRisk, dynamicModelConfiguration: settings.experimental?.dynamicModelConfiguration, modelConfigServiceConfig: settings.modelConfigs, // TODO: loading of hooks based on workspace trust enableHooks: settings.hooksConfig.enabled, enableHooksUI: settings.hooksConfig.enabled, hooks: settings.hooks || {}, disabledHooks: settings.hooksConfig?.disabled || [], projectHooks: projectHooks || {}, onModelChange: (model) => saveModelChange(loadSettings(cwd), model), onReload: async () => { const refreshedSettings = loadSettings(cwd); return { disabledSkills: refreshedSettings.merged.skills.disabled, agents: refreshedSettings.merged.agents }; }, enableConseca: settings.security?.enableConseca }); } function mergeExcludeTools(settings, extraExcludes = []) { const allExcludeTools = /* @__PURE__ */ new Set([ ...settings.tools.exclude || [], ...extraExcludes ]); return Array.from(allExcludeTools); } async function resolveWorktreeSettings(cwd) { let worktreePath; try { const { stdout } = await execa("git", ["rev-parse", "--show-toplevel"], { cwd }); const toplevel = stdout.trim(); const projectRoot = await getProjectRootForWorktree(toplevel); if (isGeminiWorktree(toplevel, projectRoot)) { worktreePath = toplevel; } } catch (_e) { return void 0; } if (!worktreePath) { return void 0; } let worktreeBaseSha; try { const { stdout } = await execa("git", ["rev-parse", "HEAD"], { cwd: worktreePath }); worktreeBaseSha = stdout.trim(); } catch (e) { debugLogger.debug( `Failed to resolve worktree base SHA at ${worktreePath}: ${e instanceof Error ? e.message : String(e)}` ); } if (!worktreeBaseSha) { return void 0; } return { name: path6.basename(worktreePath), path: worktreePath, baseSha: worktreeBaseSha }; } // packages/cli/src/utils/readStdin.ts async function readStdin() { const MAX_STDIN_SIZE = 8 * 1024 * 1024; return new Promise((resolve9, reject) => { let data = ""; let totalSize = 0; process.stdin.setEncoding("utf8"); const pipedInputShouldBeAvailableInMs = 500; let pipedInputTimerId = setTimeout(() => { onEnd(); }, pipedInputShouldBeAvailableInMs); const onReadable = () => { let chunk; while ((chunk = process.stdin.read()) !== null) { if (pipedInputTimerId) { clearTimeout(pipedInputTimerId); pipedInputTimerId = null; } if (totalSize + chunk.length > MAX_STDIN_SIZE) { const remainingSize = MAX_STDIN_SIZE - totalSize; data += chunk.slice(0, remainingSize); debugLogger.warn( `Warning: stdin input truncated to ${MAX_STDIN_SIZE} bytes.` ); process.stdin.destroy(); onEnd(); break; } data += chunk; totalSize += chunk.length; } }; const onEnd = () => { cleanup(); resolve9(data); }; const onError = (err) => { cleanup(); reject(err); }; const cleanup = () => { if (pipedInputTimerId) { clearTimeout(pipedInputTimerId); pipedInputTimerId = null; } process.stdin.removeListener("readable", onReadable); process.stdin.removeListener("end", onEnd); process.stdin.removeListener("error", onError); if (process.stdin.listenerCount("error") === 0) { process.stdin.on("error", noopErrorHandler); } }; process.stdin.on("readable", onReadable); process.stdin.on("end", onEnd); process.stdin.on("error", onError); }); } function noopErrorHandler() { } // packages/cli/src/gemini.tsx import { createHash } from "node:crypto"; import v8 from "node:v8"; import os6 from "node:os"; import dns from "node:dns"; // packages/cli/src/utils/sandbox.ts var import_shell_quote2 = __toESM(require_shell_quote(), 1); import { exec, execFile, execSync, spawn, spawnSync } from "node:child_process"; import path7 from "node:path"; import fs4 from "node:fs"; import os3 from "node:os"; import { fileURLToPath as fileURLToPath4 } from "node:url"; import { promisify } from "node:util"; import { randomBytes } from "node:crypto"; // packages/cli/src/utils/sandboxUtils.ts var import_shell_quote = __toESM(require_shell_quote(), 1); import os2 from "node:os"; import fs3 from "node:fs"; import { readFile } from "node:fs/promises"; var LOCAL_DEV_SANDBOX_IMAGE_NAME = "gemini-cli-sandbox"; var SANDBOX_NETWORK_NAME = "gemini-cli-sandbox"; var SANDBOX_PROXY_NAME = "gemini-cli-sandbox-proxy"; var BUILTIN_SEATBELT_PROFILES = [ "permissive-open", "permissive-proxied", "restrictive-open", "restrictive-proxied", "strict-open", "strict-proxied" ]; function getContainerPath(hostPath) { if (os2.platform() !== "win32") { return hostPath; } const withForwardSlashes = hostPath.replace(/\\/g, "/"); const match = withForwardSlashes.match(/^([A-Z]):\/(.*)/i); if (match) { return `/${match[1].toLowerCase()}/${match[2]}`; } return withForwardSlashes; } async function shouldUseCurrentUserInSandbox() { const envVar = process.env["SANDBOX_SET_UID_GID"]?.toLowerCase().trim(); if (envVar === "1" || envVar === "true") { return true; } if (envVar === "0" || envVar === "false") { return false; } if (os2.platform() === "linux") { try { const osReleaseContent = await readFile("/etc/os-release", "utf8"); if (osReleaseContent.includes("ID=debian") || osReleaseContent.includes("ID=ubuntu") || osReleaseContent.match(/^ID_LIKE=.*debian.*/m) || // Covers derivatives osReleaseContent.match(/^ID_LIKE=.*ubuntu.*/m)) { debugLogger.log( "Defaulting to use current user UID/GID for Debian/Ubuntu-based Linux." ); return true; } } catch (_err) { debugLogger.warn( "Warning: Could not read /etc/os-release to auto-detect Debian/Ubuntu for UID/GID default." ); } } return false; } function parseImageName(image) { const [fullName, tag] = image.split(":"); const name = fullName.split("/").at(-1) ?? "unknown-image"; return tag ? `${name}-${tag}` : name; } function ports() { return (process.env["SANDBOX_PORTS"] ?? "").split(",").filter((p) => p.trim()).map((p) => p.trim()); } function entrypoint(workdir, cliArgs) { const isWindows = os2.platform() === "win32"; const containerWorkdir = getContainerPath(workdir); const shellCmds = []; const pathSeparator = isWindows ? ";" : ":"; let pathSuffix = ""; if (process.env["PATH"]) { const paths = process.env["PATH"].split(pathSeparator); for (const p of paths) { const containerPath = getContainerPath(p); if (containerPath.toLowerCase().startsWith(containerWorkdir.toLowerCase())) { pathSuffix += `:${containerPath}`; } } } if (pathSuffix) { shellCmds.push(`export PATH="$PATH${pathSuffix}";`); } let pythonPathSuffix = ""; if (process.env["PYTHONPATH"]) { const paths = process.env["PYTHONPATH"].split(pathSeparator); for (const p of paths) { const containerPath = getContainerPath(p); if (containerPath.toLowerCase().startsWith(containerWorkdir.toLowerCase())) { pythonPathSuffix += `:${containerPath}`; } } } if (pythonPathSuffix) { shellCmds.push(`export PYTHONPATH="$PYTHONPATH${pythonPathSuffix}";`); } const projectSandboxBashrc = `${GEMINI_DIR}/sandbox.bashrc`; if (fs3.existsSync(projectSandboxBashrc)) { shellCmds.push(`source ${getContainerPath(projectSandboxBashrc)};`); } ports().forEach( (p) => shellCmds.push( `socat TCP4-LISTEN:${p},bind=$(hostname -i),fork,reuseaddr TCP4:127.0.0.1:${p} 2> /dev/null &` ) ); const quotedCliArgs = cliArgs.slice(2).map((arg) => (0, import_shell_quote.quote)([arg])); const isDebugMode2 = process.env["DEBUG"] === "true" || process.env["DEBUG"] === "1"; const cliCmd = process.env["NODE_ENV"] === "development" ? isDebugMode2 ? "npm run debug --" : "npm rebuild && npm run start --" : isDebugMode2 ? `node --inspect-brk=0.0.0.0:${process.env["DEBUG_PORT"] || "9229"} $(which gemini)` : "gemini"; const args = [...shellCmds, cliCmd, ...quotedCliArgs]; return ["bash", "-c", args.join(" ")]; } // packages/cli/src/utils/sandbox.ts var execAsync = promisify(exec); var execFileAsync = promisify(execFile); async function start_sandbox(config, nodeArgs = [], cliConfig, cliArgs = []) { const patcher = new ConsolePatcher({ debugMode: cliConfig?.getDebugMode() || !!process.env["DEBUG"], stderr: true }); patcher.patch(); try { if (config.command === "sandbox-exec") { if (process.env["BUILD_SANDBOX"]) { throw new FatalSandboxError( "Cannot BUILD_SANDBOX when using macOS Seatbelt" ); } const profile = process.env["SEATBELT_PROFILE"] ??= "permissive-open"; let profileFile = fileURLToPath4( new URL(`sandbox-macos-${profile}.sb`, import.meta.url) ); if (!BUILTIN_SEATBELT_PROFILES.includes(profile)) { profileFile = path7.join(GEMINI_DIR, `sandbox-macos-${profile}.sb`); } if (!fs4.existsSync(profileFile)) { throw new FatalSandboxError( `Missing macos seatbelt profile file '${profileFile}'` ); } debugLogger.log(`using macos seatbelt (profile: ${profile}) ...`); const nodeOptions = [ ...process.env["DEBUG"] ? ["--inspect-brk"] : [], ...nodeArgs ].join(" "); const args2 = [ "-D", `TARGET_DIR=${fs4.realpathSync(process.cwd())}`, "-D", `TMP_DIR=${fs4.realpathSync(os3.tmpdir())}`, "-D", `HOME_DIR=${fs4.realpathSync(homedir())}`, "-D", `CACHE_DIR=${fs4.realpathSync((await execAsync("getconf DARWIN_USER_CACHE_DIR")).stdout.trim())}` ]; const MAX_INCLUDE_DIRS = 5; const targetDir = fs4.realpathSync(cliConfig?.getTargetDir() || ""); const includedDirs = []; if (cliConfig) { const workspaceContext = cliConfig.getWorkspaceContext(); const directories = workspaceContext.getDirectories(); for (const dir of directories) { const realDir = fs4.realpathSync(dir); if (realDir !== targetDir) { includedDirs.push(realDir); } } } if (config.allowedPaths) { for (const hostPath of config.allowedPaths) { if (hostPath && path7.isAbsolute(hostPath) && fs4.existsSync(hostPath)) { const realDir = fs4.realpathSync(hostPath); if (!includedDirs.includes(realDir) && realDir !== targetDir) { includedDirs.push(realDir); } } } } for (let i = 0; i < MAX_INCLUDE_DIRS; i++) { let dirPath = "/dev/null"; if (i < includedDirs.length) { dirPath = includedDirs[i]; } args2.push("-D", `INCLUDE_DIR_${i}=${dirPath}`); } const finalArgv = cliArgs; args2.push( "-f", profileFile, "sh", "-c", [ `SANDBOX=sandbox-exec`, `NODE_OPTIONS="${nodeOptions}"`, ...finalArgv.map((arg) => (0, import_shell_quote2.quote)([arg])) ].join(" ") ); const proxyCommand2 = process.env["GEMINI_SANDBOX_PROXY_COMMAND"]; let proxyProcess2 = void 0; let sandboxProcess2 = void 0; const sandboxEnv = { ...process.env }; if (proxyCommand2) { const proxy = process.env["HTTPS_PROXY"] || process.env["https_proxy"] || process.env["HTTP_PROXY"] || process.env["http_proxy"] || "http://localhost:8877"; sandboxEnv["HTTPS_PROXY"] = proxy; sandboxEnv["https_proxy"] = proxy; sandboxEnv["HTTP_PROXY"] = proxy; sandboxEnv["http_proxy"] = proxy; const noProxy = process.env["NO_PROXY"] || process.env["no_proxy"]; if (noProxy) { sandboxEnv["NO_PROXY"] = noProxy; sandboxEnv["no_proxy"] = noProxy; } proxyProcess2 = spawn(proxyCommand2, { stdio: ["ignore", "pipe", "pipe"], shell: true, detached: true }); const stopProxy = () => { debugLogger.log("stopping proxy ..."); if (proxyProcess2?.pid) { process.kill(-proxyProcess2.pid, "SIGTERM"); } }; process.off("exit", stopProxy); process.on("exit", stopProxy); process.off("SIGINT", stopProxy); process.on("SIGINT", stopProxy); process.off("SIGTERM", stopProxy); process.on("SIGTERM", stopProxy); proxyProcess2.stderr?.on("data", (data) => { debugLogger.debug(`[PROXY STDERR]: ${data.toString().trim()}`); }); proxyProcess2.on("close", (code, signal) => { if (sandboxProcess2?.pid) { process.kill(-sandboxProcess2.pid, "SIGTERM"); } throw new FatalSandboxError( `Proxy command '${proxyCommand2}' exited with code ${code}, signal ${signal}` ); }); debugLogger.log("waiting for proxy to start ..."); await execAsync( `until timeout 0.25 curl -s http://localhost:8877; do sleep 0.25; done` ); } process.stdin.pause(); sandboxProcess2 = spawn(config.command, args2, { stdio: "inherit" }); return await new Promise((resolve9, reject) => { sandboxProcess2?.on("error", reject); sandboxProcess2?.on("close", (code) => { process.stdin.resume(); resolve9(code ?? 1); }); }); } if (config.command === "lxc") { return await start_lxc_sandbox(config, nodeArgs, cliArgs); } const command2 = config.command === "runsc" ? "docker" : config.command; if (!command2) throw new FatalSandboxError("Sandbox command is required"); debugLogger.log(`hopping into sandbox (command: ${command2}) ...`); const gcPath = process.argv[1] ? fs4.realpathSync(process.argv[1]) : ""; const projectSandboxDockerfile = path7.join( GEMINI_DIR, "sandbox.Dockerfile" ); const isCustomProjectSandbox = fs4.existsSync(projectSandboxDockerfile); const image = config.image; if (!image) throw new FatalSandboxError("Sandbox image is required"); if (!/^[a-zA-Z0-9_.:/-]+$/.test(image)) throw new FatalSandboxError("Invalid sandbox image name"); const workdir = path7.resolve(process.cwd()); const containerWorkdir = getContainerPath(workdir); if (process.env["BUILD_SANDBOX"]) { if (!gcPath.includes("gemini-cli/packages/")) { throw new FatalSandboxError( "Cannot build sandbox using installed gemini binary; run `npm link ./packages/cli` under gemini-cli repo to switch to linked binary." ); } else { debugLogger.log("building sandbox ..."); const gcRoot = gcPath.split("/packages/")[0]; let buildArgs = ""; const projectSandboxDockerfile2 = path7.join( GEMINI_DIR, "sandbox.Dockerfile" ); if (isCustomProjectSandbox) { debugLogger.log(`using ${projectSandboxDockerfile2} for sandbox`); buildArgs += `-f ${path7.resolve(projectSandboxDockerfile2)} -i ${image}`; } execSync( `cd ${gcRoot} && node scripts/build_sandbox.js -s ${buildArgs}`, { stdio: "inherit", env: { ...process.env, GEMINI_SANDBOX: command2 // in case sandbox is enabled via flags (see config.ts under cli package) } } ); } } if (!await ensureSandboxImageIsPresent(command2, image, cliConfig)) { const remedy = image === LOCAL_DEV_SANDBOX_IMAGE_NAME ? "Try running `npm run build:all` or `npm run build:sandbox` under the gemini-cli repo to build it locally, or check the image name and your network connection." : "Please check the image name, your network connection, or notify gemini-cli-dev@google.com if the issue persists."; throw new FatalSandboxError( `Sandbox image '${image}' is missing or could not be pulled. ${remedy}` ); } const args = ["run", "-i", "--rm", "--init", "--workdir", containerWorkdir]; if (config.command === "runsc") { args.push("--runtime=runsc"); } if (process.env["SANDBOX_FLAGS"]) { const flags = (0, import_shell_quote2.parse)(process.env["SANDBOX_FLAGS"], process.env).filter( (f) => typeof f === "string" ); args.push(...flags); } if (process.stdin.isTTY) { args.push("-t"); } args.push("--add-host", "host.docker.internal:host-gateway"); args.push("--volume", `${workdir}:${containerWorkdir}`); const userHomeDirOnHost = homedir(); const userSettingsDirInSandbox = getContainerPath( `/home/node/${GEMINI_DIR}` ); if (!fs4.existsSync(userHomeDirOnHost)) { fs4.mkdirSync(userHomeDirOnHost, { recursive: true }); } const userSettingsDirOnHost = path7.join(userHomeDirOnHost, GEMINI_DIR); if (!fs4.existsSync(userSettingsDirOnHost)) { fs4.mkdirSync(userSettingsDirOnHost, { recursive: true }); } args.push( "--volume", `${userSettingsDirOnHost}:${userSettingsDirInSandbox}` ); if (userSettingsDirInSandbox !== getContainerPath(userSettingsDirOnHost)) { args.push( "--volume", `${userSettingsDirOnHost}:${getContainerPath(userSettingsDirOnHost)}` ); } args.push("--volume", `${os3.tmpdir()}:${getContainerPath(os3.tmpdir())}`); if (userHomeDirOnHost !== os3.homedir()) { args.push( "--volume", `${userHomeDirOnHost}:${getContainerPath(userHomeDirOnHost)}` ); } const gcloudConfigDir = path7.join(homedir(), ".config", "gcloud"); if (fs4.existsSync(gcloudConfigDir)) { args.push( "--volume", `${gcloudConfigDir}:${getContainerPath(gcloudConfigDir)}:ro` ); } if (process.env["GOOGLE_APPLICATION_CREDENTIALS"]) { const adcFile = process.env["GOOGLE_APPLICATION_CREDENTIALS"]; if (fs4.existsSync(adcFile)) { args.push("--volume", `${adcFile}:${getContainerPath(adcFile)}:ro`); args.push( "--env", `GOOGLE_APPLICATION_CREDENTIALS=${getContainerPath(adcFile)}` ); } } if (process.env["SANDBOX_MOUNTS"]) { for (let mount of process.env["SANDBOX_MOUNTS"].split(",")) { if (mount.trim()) { let [from, to, opts] = mount.trim().split(":"); to = to || from; opts = opts || "ro"; mount = `${from}:${to}:${opts}`; if (!path7.isAbsolute(from)) { throw new FatalSandboxError( `Path '${from}' listed in SANDBOX_MOUNTS must be absolute` ); } if (!fs4.existsSync(from)) { throw new FatalSandboxError( `Missing mount path '${from}' listed in SANDBOX_MOUNTS` ); } debugLogger.log(`SANDBOX_MOUNTS: ${from} -> ${to} (${opts})`); args.push("--volume", mount); } } } if (config.allowedPaths) { for (const hostPath of config.allowedPaths) { if (hostPath && path7.isAbsolute(hostPath) && fs4.existsSync(hostPath)) { const containerPath = getContainerPath(hostPath); debugLogger.log( `Config allowedPath: ${hostPath} -> ${containerPath} (ro)` ); args.push("--volume", `${hostPath}:${containerPath}:ro`); } } } ports().forEach((p) => args.push("--publish", `${p}:${p}`)); if (process.env["DEBUG"]) { const debugPort = process.env["DEBUG_PORT"] || "9229"; args.push(`--publish`, `${debugPort}:${debugPort}`); } const proxyCommand = process.env["GEMINI_SANDBOX_PROXY_COMMAND"]; if (proxyCommand) { let proxy = process.env["HTTPS_PROXY"] || process.env["https_proxy"] || process.env["HTTP_PROXY"] || process.env["http_proxy"] || "http://localhost:8877"; proxy = proxy.replace("localhost", SANDBOX_PROXY_NAME); if (proxy) { args.push("--env", `HTTPS_PROXY=${proxy}`); args.push("--env", `https_proxy=${proxy}`); args.push("--env", `HTTP_PROXY=${proxy}`); args.push("--env", `http_proxy=${proxy}`); } const noProxy = process.env["NO_PROXY"] || process.env["no_proxy"]; if (noProxy) { args.push("--env", `NO_PROXY=${noProxy}`); args.push("--env", `no_proxy=${noProxy}`); } } if (!config.networkAccess || proxyCommand) { const isInternal = !config.networkAccess || !!proxyCommand; const networkFlags = isInternal ? "--internal" : ""; execSync( `${command2} network inspect ${SANDBOX_NETWORK_NAME} || ${command2} network create ${networkFlags} ${SANDBOX_NETWORK_NAME}`, { stdio: "ignore" } ); args.push("--network", SANDBOX_NETWORK_NAME); if (proxyCommand) { execSync( `${command2} network inspect ${SANDBOX_PROXY_NAME} || ${command2} network create ${SANDBOX_PROXY_NAME}`, { stdio: "ignore" } ); } } const imageName = parseImageName(image); const isIntegrationTest = process.env["GEMINI_CLI_INTEGRATION_TEST"] === "true"; let containerName; if (isIntegrationTest) { containerName = `gemini-cli-integration-test-${randomBytes(4).toString( "hex" )}`; debugLogger.log(`ContainerName: ${containerName}`); } else { let index = 0; const containerNameCheck = (await execAsync(`${command2} ps -a --format "{{.Names}}"`)).stdout.trim(); while (containerNameCheck.includes(`${imageName}-${index}`)) { index++; } containerName = `${imageName}-${index}`; debugLogger.log(`ContainerName (regular): ${containerName}`); } args.push("--name", containerName, "--hostname", containerName); if (process.env["GEMINI_CLI_TEST_VAR"]) { args.push( "--env", `GEMINI_CLI_TEST_VAR=${process.env["GEMINI_CLI_TEST_VAR"]}` ); } if (process.env["GEMINI_API_KEY"]) { args.push("--env", `GEMINI_API_KEY=${process.env["GEMINI_API_KEY"]}`); } if (process.env["GOOGLE_API_KEY"]) { args.push("--env", `GOOGLE_API_KEY=${process.env["GOOGLE_API_KEY"]}`); } if (process.env["GOOGLE_GEMINI_BASE_URL"]) { args.push( "--env", `GOOGLE_GEMINI_BASE_URL=${process.env["GOOGLE_GEMINI_BASE_URL"]}` ); } if (process.env["GOOGLE_VERTEX_BASE_URL"]) { args.push( "--env", `GOOGLE_VERTEX_BASE_URL=${process.env["GOOGLE_VERTEX_BASE_URL"]}` ); } if (process.env["GOOGLE_GENAI_USE_VERTEXAI"]) { args.push( "--env", `GOOGLE_GENAI_USE_VERTEXAI=${process.env["GOOGLE_GENAI_USE_VERTEXAI"]}` ); } if (process.env["GOOGLE_GENAI_USE_GCA"]) { args.push( "--env", `GOOGLE_GENAI_USE_GCA=${process.env["GOOGLE_GENAI_USE_GCA"]}` ); } if (process.env["GOOGLE_CLOUD_PROJECT"]) { args.push( "--env", `GOOGLE_CLOUD_PROJECT=${process.env["GOOGLE_CLOUD_PROJECT"]}` ); } if (process.env["GOOGLE_CLOUD_LOCATION"]) { args.push( "--env", `GOOGLE_CLOUD_LOCATION=${process.env["GOOGLE_CLOUD_LOCATION"]}` ); } if (process.env["GEMINI_MODEL"]) { args.push("--env", `GEMINI_MODEL=${process.env["GEMINI_MODEL"]}`); } if (process.env["TERM"]) { args.push("--env", `TERM=${process.env["TERM"]}`); } if (process.env["COLORTERM"]) { args.push("--env", `COLORTERM=${process.env["COLORTERM"]}`); } for (const envVar of [ "GEMINI_CLI_IDE_SERVER_PORT", "GEMINI_CLI_IDE_WORKSPACE_PATH", "TERM_PROGRAM" ]) { if (process.env[envVar]) { args.push("--env", `${envVar}=${process.env[envVar]}`); } } if (process.env["VIRTUAL_ENV"]?.toLowerCase().startsWith(workdir.toLowerCase())) { const sandboxVenvPath = path7.resolve(GEMINI_DIR, "sandbox.venv"); if (!fs4.existsSync(sandboxVenvPath)) { fs4.mkdirSync(sandboxVenvPath, { recursive: true }); } args.push( "--volume", `${sandboxVenvPath}:${getContainerPath(process.env["VIRTUAL_ENV"])}` ); args.push( "--env", `VIRTUAL_ENV=${getContainerPath(process.env["VIRTUAL_ENV"])}` ); } if (process.env["SANDBOX_ENV"]) { for (let env2 of process.env["SANDBOX_ENV"].split(",")) { if (env2 = env2.trim()) { if (env2.includes("=")) { debugLogger.log(`SANDBOX_ENV: ${env2}`); args.push("--env", env2); } else { throw new FatalSandboxError( "SANDBOX_ENV must be a comma-separated list of key=value pairs" ); } } } } const existingNodeOptions = process.env["NODE_OPTIONS"] || ""; const allNodeOptions = [ ...existingNodeOptions ? [existingNodeOptions] : [], ...nodeArgs ].join(" "); if (allNodeOptions.length > 0) { args.push("--env", `NODE_OPTIONS="${allNodeOptions}"`); } args.push("--env", `SANDBOX=${containerName}`); if (command2 === "podman") { const emptyAuthFilePath = path7.join(os3.tmpdir(), "empty_auth.json"); fs4.writeFileSync(emptyAuthFilePath, "{}", "utf-8"); args.push("--authfile", emptyAuthFilePath); } let userFlag = ""; const finalEntrypoint = entrypoint(workdir, cliArgs); if (process.env["GEMINI_CLI_INTEGRATION_TEST"] === "true") { args.push("--user", "root"); userFlag = "--user root"; } else if (await shouldUseCurrentUserInSandbox()) { args.push("--user", "root"); const uid = (await execAsync("id -u")).stdout.trim(); const gid = (await execAsync("id -g")).stdout.trim(); const username = "gemini"; const homeDir = getContainerPath(homedir()); const setupUserCommands = [ // Use -f with groupadd to avoid errors if the group already exists. `groupadd -f -g ${gid} ${username}`, // Create user only if it doesn't exist. Use -o for non-unique UID. `id -u ${username} &>/dev/null || useradd -o -u ${uid} -g ${gid} -d ${homeDir} -s /bin/bash ${username}` ].join(" && "); const originalCommand = finalEntrypoint[2]; const escapedOriginalCommand = originalCommand.replace(/'/g, "'\\''"); const suCommand = `su -p ${username} -c '${escapedOriginalCommand}'`; finalEntrypoint[2] = `${setupUserCommands} && ${suCommand}`; userFlag = `--user ${uid}:${gid}`; args.push("--env", `HOME=${homedir()}`); } args.push(image); args.push(...finalEntrypoint); let proxyProcess = void 0; let sandboxProcess = void 0; if (proxyCommand) { const proxyContainerArgs = [ "run", "--rm", "--init", ...userFlag ? userFlag.split(" ") : [], "--name", SANDBOX_PROXY_NAME, "--network", SANDBOX_PROXY_NAME, "-p", "8877:8877", "-v", `${process.cwd()}:${workdir}`, "--workdir", workdir, image, // proxyCommand may be a shell string, so parse it into tokens safely ...(0, import_shell_quote2.parse)(proxyCommand, process.env).filter( (f) => typeof f === "string" ) ]; proxyProcess = spawn(command2, proxyContainerArgs, { stdio: ["ignore", "pipe", "pipe"], shell: false, // <-- no shell; args are passed directly detached: true }); const stopProxy = () => { debugLogger.log("stopping proxy container ..."); execSync(`${command2} rm -f ${SANDBOX_PROXY_NAME}`); }; process.off("exit", stopProxy); process.on("exit", stopProxy); process.off("SIGINT", stopProxy); process.on("SIGINT", stopProxy); process.off("SIGTERM", stopProxy); process.on("SIGTERM", stopProxy); proxyProcess.stderr?.on("data", (data) => { debugLogger.debug(`[PROXY STDERR]: ${data.toString().trim()}`); }); proxyProcess.on("close", (code, signal) => { if (sandboxProcess?.pid) { process.kill(-sandboxProcess.pid, "SIGTERM"); } throw new FatalSandboxError( `Proxy container command '${command2} ${proxyContainerArgs.join(" ")}' exited with code ${code}, signal ${signal}` ); }); debugLogger.log("waiting for proxy to start ..."); await execAsync( `until timeout 0.25 curl -s http://localhost:8877; do sleep 0.25; done` ); await execAsync( `${command2} network connect ${SANDBOX_NETWORK_NAME} ${SANDBOX_PROXY_NAME}` ); } process.stdin.pause(); sandboxProcess = spawn(command2, args, { stdio: "inherit" }); return await new Promise((resolve9, reject) => { sandboxProcess.on("error", (err) => { coreEvents.emitFeedback("error", "Sandbox process error", err); reject(err); }); sandboxProcess?.on("close", (code, signal) => { process.stdin.resume(); if (code !== 0 && code !== null) { debugLogger.log( `Sandbox process exited with code: ${code}, signal: ${signal}` ); } resolve9(code ?? 1); }); }); } finally { patcher.cleanup(); } } async function start_lxc_sandbox(config, nodeArgs = [], cliArgs = []) { const containerName = config.image || "gemini-sandbox"; const workdir = path7.resolve(process.cwd()); debugLogger.log( `starting lxc sandbox (container: ${containerName}, workdir: ${workdir}) ...` ); let listOutput; try { const { stdout } = await execFileAsync("lxc", [ "list", containerName, "--format=json" ]); listOutput = stdout.trim(); } catch (err) { throw new FatalSandboxError( `Failed to query LXC container '${containerName}': ${err instanceof Error ? err.message : String(err)}. Make sure LXC/LXD is installed and '${containerName}' container exists. Create one with: lxc launch ubuntu:24.04 ${containerName}` ); } let containers = []; try { const parsed = JSON.parse(listOutput); if (Array.isArray(parsed)) { containers = parsed.filter( (item) => item !== null && typeof item === "object" && "name" in item && "status" in item ).map((item) => ({ name: String(item["name"]), status: String(item["status"]) })); } } catch { containers = []; } const container = containers.find((c) => c.name === containerName); if (!container) { throw new FatalSandboxError( `LXC container '${containerName}' not found. Create one with: lxc launch ubuntu:24.04 ${containerName}` ); } if (container.status.toLowerCase() !== "running") { throw new FatalSandboxError( `LXC container '${containerName}' is not running (current status: ${container.status}). Start it with: lxc start ${containerName}` ); } const devicesToRemove = []; const removeDevices = () => { for (const deviceName of devicesToRemove) { try { spawnSync( "lxc", ["config", "device", "remove", containerName, deviceName], { timeout: 1e3, killSignal: "SIGKILL", stdio: "ignore" } ); } catch { } } }; try { const workspaceDeviceName = `gemini-workspace-${randomBytes(4).toString( "hex" )}`; devicesToRemove.push(workspaceDeviceName); try { await execFileAsync("lxc", [ "config", "device", "add", containerName, workspaceDeviceName, "disk", `source=${workdir}`, `path=${workdir}` ]); debugLogger.log( `mounted workspace '${workdir}' into container as device '${workspaceDeviceName}'` ); } catch (err) { throw new FatalSandboxError( `Failed to mount workspace into LXC container '${containerName}': ${err instanceof Error ? err.message : String(err)}` ); } if (config.allowedPaths) { for (const hostPath of config.allowedPaths) { if (hostPath && path7.isAbsolute(hostPath) && fs4.existsSync(hostPath)) { const allowedDeviceName = `gemini-allowed-${randomBytes(4).toString( "hex" )}`; devicesToRemove.push(allowedDeviceName); try { await execFileAsync("lxc", [ "config", "device", "add", containerName, allowedDeviceName, "disk", `source=${hostPath}`, `path=${hostPath}`, "readonly=true" ]); debugLogger.log( `mounted allowed path '${hostPath}' into container as device '${allowedDeviceName}' (ro)` ); } catch (err) { debugLogger.warn( `Failed to mount allowed path '${hostPath}' into LXC container: ${err instanceof Error ? err.message : String(err)}` ); } } } } process.on("exit", removeDevices); const envArgs = []; const envVarsToForward = { GEMINI_API_KEY: process.env["GEMINI_API_KEY"], GOOGLE_API_KEY: process.env["GOOGLE_API_KEY"], GOOGLE_GEMINI_BASE_URL: process.env["GOOGLE_GEMINI_BASE_URL"], GOOGLE_VERTEX_BASE_URL: process.env["GOOGLE_VERTEX_BASE_URL"], GOOGLE_GENAI_USE_VERTEXAI: process.env["GOOGLE_GENAI_USE_VERTEXAI"], GOOGLE_GENAI_USE_GCA: process.env["GOOGLE_GENAI_USE_GCA"], GOOGLE_CLOUD_PROJECT: process.env["GOOGLE_CLOUD_PROJECT"], GOOGLE_CLOUD_LOCATION: process.env["GOOGLE_CLOUD_LOCATION"], GEMINI_MODEL: process.env["GEMINI_MODEL"], TERM: process.env["TERM"], COLORTERM: process.env["COLORTERM"], GEMINI_CLI_IDE_SERVER_PORT: process.env["GEMINI_CLI_IDE_SERVER_PORT"], GEMINI_CLI_IDE_WORKSPACE_PATH: process.env["GEMINI_CLI_IDE_WORKSPACE_PATH"], TERM_PROGRAM: process.env["TERM_PROGRAM"] }; for (const [key, value] of Object.entries(envVarsToForward)) { if (value) { envArgs.push("--env", `${key}=${value}`); } } if (process.env["SANDBOX_ENV"]) { for (let env2 of process.env["SANDBOX_ENV"].split(",")) { if (env2 = env2.trim()) { if (env2.includes("=")) { envArgs.push("--env", env2); } else { throw new FatalSandboxError( "SANDBOX_ENV must be a comma-separated list of key=value pairs" ); } } } } const existingNodeOptions = process.env["NODE_OPTIONS"] || ""; const allNodeOptions = [ ...existingNodeOptions ? [existingNodeOptions] : [], ...nodeArgs ].join(" "); if (allNodeOptions.length > 0) { envArgs.push("--env", `NODE_OPTIONS=${allNodeOptions}`); } envArgs.push("--env", `SANDBOX=${containerName}`); const finalEntrypoint = entrypoint(workdir, cliArgs); const args = [ "exec", containerName, "--cwd", workdir, ...envArgs, "--", ...finalEntrypoint ]; debugLogger.log(`lxc exec args: ${args.join(" ")}`); process.stdin.pause(); const sandboxProcess = spawn("lxc", args, { stdio: "inherit" }); return await new Promise((resolve9, reject) => { sandboxProcess.on("error", (err) => { coreEvents.emitFeedback("error", "LXC sandbox process error", err); reject(err); }); sandboxProcess.on("close", (code, signal) => { process.stdin.resume(); if (code !== 0 && code !== null) { debugLogger.log( `LXC sandbox process exited with code: ${code}, signal: ${signal}` ); } resolve9(code ?? 1); }); }); } finally { process.off("exit", removeDevices); removeDevices(); } } async function imageExists(sandbox, image) { return new Promise((resolve9) => { const args = ["images", "-q", image]; const checkProcess = spawn(sandbox, args); let stdoutData = ""; if (checkProcess.stdout) { checkProcess.stdout.on("data", (data) => { stdoutData += data.toString(); }); } checkProcess.on("error", (err) => { debugLogger.warn( `Failed to start '${sandbox}' command for image check: ${err.message}` ); resolve9(false); }); checkProcess.on("close", (code) => { if (code !== 0) { } resolve9(stdoutData.trim() !== ""); }); }); } async function pullImage(sandbox, image, cliConfig) { debugLogger.debug(`Attempting to pull image ${image} using ${sandbox}...`); return new Promise((resolve9) => { const args = ["pull", image]; const pullProcess = spawn(sandbox, args, { stdio: "pipe" }); let stderrData = ""; const onStdoutData = (data) => { if (cliConfig?.getDebugMode() || process.env["DEBUG"]) { debugLogger.log(data.toString().trim()); } }; const onStderrData = (data) => { stderrData += data.toString(); console.error(data.toString().trim()); }; const onError = (err) => { debugLogger.warn( `Failed to start '${sandbox} pull ${image}' command: ${err.message}` ); cleanup(); resolve9(false); }; const onClose = (code) => { if (code === 0) { debugLogger.log(`Successfully pulled image ${image}.`); cleanup(); resolve9(true); } else { debugLogger.warn( `Failed to pull image ${image}. '${sandbox} pull ${image}' exited with code ${code}.` ); if (stderrData.trim()) { } cleanup(); resolve9(false); } }; const cleanup = () => { if (pullProcess.stdout) { pullProcess.stdout.removeListener("data", onStdoutData); } if (pullProcess.stderr) { pullProcess.stderr.removeListener("data", onStderrData); } pullProcess.removeListener("error", onError); pullProcess.removeListener("close", onClose); if (pullProcess.connected) { pullProcess.disconnect(); } }; if (pullProcess.stdout) { pullProcess.stdout.on("data", onStdoutData); } if (pullProcess.stderr) { pullProcess.stderr.on("data", onStderrData); } pullProcess.on("error", onError); pullProcess.on("close", onClose); }); } async function ensureSandboxImageIsPresent(sandbox, image, cliConfig) { debugLogger.log(`Checking for sandbox image: ${image}`); if (await imageExists(sandbox, image)) { debugLogger.log(`Sandbox image ${image} found locally.`); return true; } debugLogger.log(`Sandbox image ${image} not found locally.`); if (image === LOCAL_DEV_SANDBOX_IMAGE_NAME) { return false; } if (await pullImage(sandbox, image, cliConfig)) { if (await imageExists(sandbox, image)) { debugLogger.log(`Sandbox image ${image} is now available after pulling.`); return true; } else { debugLogger.warn( `Sandbox image ${image} still not found after a pull attempt. This might indicate an issue with the image name or registry, or the pull command reported success but failed to make the image available.` ); return false; } } coreEvents.emitFeedback( "error", `Failed to obtain sandbox image ${image} after check and pull attempt.` ); return false; } // packages/cli/src/utils/startupWarnings.ts import fs5 from "node:fs/promises"; import os4 from "node:os"; import { join as pathJoin } from "node:path"; var warningsFilePath = pathJoin(os4.tmpdir(), "gemini-cli-warnings.txt"); async function getStartupWarnings() { try { await fs5.access(warningsFilePath); const warningsContent = await fs5.readFile(warningsFilePath, "utf-8"); const warnings = warningsContent.split("\n").filter((line) => line.trim() !== ""); try { await fs5.unlink(warningsFilePath); } catch { warnings.push("Warning: Could not delete temporary warnings file."); } return warnings; } catch (err) { if (err instanceof Error && "code" in err && err.code === "ENOENT") { return []; } return [`Error checking/reading warnings file: ${getErrorMessage(err)}`]; } } // packages/cli/src/utils/userStartupWarnings.ts import fs6 from "node:fs/promises"; import path8 from "node:path"; import process4 from "node:process"; var homeDirectoryCheck = { id: "home-directory", priority: WarningPriority.Low, check: async (workspaceRoot, settings) => { if (settings.ui?.showHomeDirectoryWarning === false) { return null; } try { const [workspaceRealPath, homeRealPath] = await Promise.all([ fs6.realpath(workspaceRoot), fs6.realpath(homedir()) ]); if (workspaceRealPath === homeRealPath) { if (isFolderTrustEnabled(settings) && isWorkspaceTrusted(settings).isTrusted) { return null; } return "Warning you are running Gemini CLI in your home directory.\nThis warning can be disabled in /settings"; } return null; } catch (_err) { return "Could not verify the current directory due to a file system error."; } } }; var rootDirectoryCheck = { id: "root-directory", priority: WarningPriority.High, check: async (workspaceRoot, _settings) => { try { const workspaceRealPath = await fs6.realpath(workspaceRoot); const errorMessage = "Warning: You are running Gemini CLI in the root directory. Your entire folder structure will be used for context. It is strongly recommended to run in a project-specific directory."; if (path8.dirname(workspaceRealPath) === workspaceRealPath) { return errorMessage; } return null; } catch (_err) { return "Could not verify the current directory due to a file system error."; } } }; var WARNING_CHECKS = [ homeDirectoryCheck, rootDirectoryCheck ]; async function getUserStartupWarnings(settings, workspaceRoot = process4.cwd(), options) { const results = await Promise.all( WARNING_CHECKS.map(async (check) => { const message = await check.check(workspaceRoot, settings); if (message) { return { id: check.id, message, priority: check.priority }; } return null; }) ); const warnings = results.filter((w) => w !== null); if (settings.ui?.showCompatibilityWarnings !== false) { warnings.push( ...getCompatibilityWarnings({ isAlternateBuffer: options?.isAlternateBuffer }) ); } return warnings; } // packages/cli/src/nonInteractiveCli.ts import readline from "node:readline"; // packages/cli/src/ui/noninteractive/nonInteractiveUi.ts function createNonInteractiveUI() { return { addItem: (item, _timestamp) => { if ("text" in item && item.text) { if (item.type === "error") { process.stderr.write(`Error: ${item.text} `); } else if (item.type === "warning") { process.stderr.write(`Warning: ${item.text} `); } else if (item.type === "info") { process.stdout.write(`${item.text} `); } } return 0; }, clear: () => { }, setDebugMessage: (_message) => { }, loadHistory: (_newHistory) => { }, pendingItem: null, setPendingItem: (_item) => { }, toggleCorgiMode: () => { }, toggleDebugProfiler: () => { }, toggleVimEnabled: async () => false, reloadCommands: () => { }, openAgentConfigDialog: () => { }, extensionsUpdateState: /* @__PURE__ */ new Map(), dispatchExtensionStateUpdate: (_action) => { }, addConfirmUpdateExtensionRequest: (_request) => { }, setConfirmationRequest: (_request) => { }, removeComponent: () => { }, toggleBackgroundShell: () => { }, toggleShortcutsHelp: () => { } }; } // packages/cli/src/nonInteractiveCliCommands.ts var handleSlashCommand = async (rawQuery, abortController, config, settings) => { const trimmed = rawQuery.trim(); if (!trimmed.startsWith("/")) { return; } const commandService = await CommandService.create( [ new BuiltinCommandLoader(config), new McpPromptLoader(config), new FileCommandLoader(config) ], abortController.signal ); const commands = commandService.getCommands(); const { commandToExecute, args } = parseSlashCommand(rawQuery, commands); if (commandToExecute) { if (commandToExecute.action) { const sessionStats = { sessionId: config?.getSessionId(), sessionStartTime: /* @__PURE__ */ new Date(), metrics: uiTelemetryService.getMetrics(), lastPromptTokenCount: 0, promptCount: 1 }; const logger = new Logger(config?.getSessionId() || "", config?.storage); const commandContext = { services: { agentContext: config, settings, git: void 0, logger }, ui: createNonInteractiveUI(), session: { stats: sessionStats, sessionShellAllowlist: /* @__PURE__ */ new Set() }, invocation: { raw: trimmed, name: commandToExecute.name, args } }; const result = await commandToExecute.action(commandContext, args); if (result) { switch (result.type) { case "submit_prompt": return result.content; case "confirm_shell_commands": throw new FatalInputError( "Exiting due to a confirmation prompt requested by the command." ); default: throw new FatalInputError( "Exiting due to command result that is not supported in non-interactive mode." ); } } } } return; }; // packages/cli/src/utils/errors.ts function extractErrorCode(error) { const errorWithCode = error; if (typeof errorWithCode.exitCode === "number") { return errorWithCode.exitCode; } if (errorWithCode.code !== void 0) { return errorWithCode.code; } if (errorWithCode.status !== void 0) { return errorWithCode.status; } return 1; } function getNumericExitCode(errorCode) { return typeof errorCode === "number" ? errorCode : 1; } function handleError(error, config, customErrorCode) { const errorMessage = parseAndFormatApiError( error, config.getContentGeneratorConfig()?.authType ); if (config.getOutputFormat() === OutputFormat.STREAM_JSON) { const streamFormatter = new StreamJsonFormatter(); const errorCode = customErrorCode ?? extractErrorCode(error); const metrics = uiTelemetryService.getMetrics(); streamFormatter.emitEvent({ type: JsonStreamEventType.RESULT, timestamp: (/* @__PURE__ */ new Date()).toISOString(), status: "error", error: { type: error instanceof Error ? error.constructor.name : "Error", message: errorMessage }, stats: streamFormatter.convertToStreamStats(metrics, 0) }); runSyncCleanup(); process.exit(getNumericExitCode(errorCode)); } else if (config.getOutputFormat() === OutputFormat.JSON) { const formatter = new JsonFormatter(); const errorCode = customErrorCode ?? extractErrorCode(error); const formattedError = formatter.formatError( error instanceof Error ? error : new Error(getErrorMessage(error)), errorCode, config.getSessionId() ); coreEvents.emitFeedback("error", formattedError); runSyncCleanup(); process.exit(getNumericExitCode(errorCode)); } else { throw error; } } function handleToolError(toolName, toolError, config, errorType, resultDisplay) { const errorMessage = `Error executing tool ${toolName}: ${resultDisplay || toolError.message}`; const isFatal = isFatalToolError(errorType); if (isFatal) { const toolExecutionError = new FatalToolExecutionError(errorMessage); if (config.getOutputFormat() === OutputFormat.STREAM_JSON) { const streamFormatter = new StreamJsonFormatter(); const metrics = uiTelemetryService.getMetrics(); streamFormatter.emitEvent({ type: JsonStreamEventType.RESULT, timestamp: (/* @__PURE__ */ new Date()).toISOString(), status: "error", error: { type: errorType ?? "FatalToolExecutionError", message: toolExecutionError.message }, stats: streamFormatter.convertToStreamStats(metrics, 0) }); } else if (config.getOutputFormat() === OutputFormat.JSON) { const formatter = new JsonFormatter(); const formattedError = formatter.formatError( toolExecutionError, errorType ?? toolExecutionError.exitCode, config.getSessionId() ); coreEvents.emitFeedback("error", formattedError); } else { coreEvents.emitFeedback("error", errorMessage); } runSyncCleanup(); process.exit(toolExecutionError.exitCode); } debugLogger.warn(errorMessage); } function handleCancellationError(config) { const cancellationError = new FatalCancellationError("Operation cancelled."); if (config.getOutputFormat() === OutputFormat.STREAM_JSON) { const streamFormatter = new StreamJsonFormatter(); const metrics = uiTelemetryService.getMetrics(); streamFormatter.emitEvent({ type: JsonStreamEventType.RESULT, timestamp: (/* @__PURE__ */ new Date()).toISOString(), status: "error", error: { type: "FatalCancellationError", message: cancellationError.message }, stats: streamFormatter.convertToStreamStats(metrics, 0) }); runSyncCleanup(); process.exit(cancellationError.exitCode); } else if (config.getOutputFormat() === OutputFormat.JSON) { const formatter = new JsonFormatter(); const formattedError = formatter.formatError( cancellationError, cancellationError.exitCode, config.getSessionId() ); coreEvents.emitFeedback("error", formattedError); runSyncCleanup(); process.exit(cancellationError.exitCode); } else { coreEvents.emitFeedback("error", cancellationError.message); runSyncCleanup(); process.exit(cancellationError.exitCode); } } function handleMaxTurnsExceededError(config) { const maxTurnsError = new FatalTurnLimitedError( "Reached max session turns for this session. Increase the number of turns by specifying maxSessionTurns in settings.json." ); if (config.getOutputFormat() === OutputFormat.STREAM_JSON) { const streamFormatter = new StreamJsonFormatter(); const metrics = uiTelemetryService.getMetrics(); streamFormatter.emitEvent({ type: JsonStreamEventType.RESULT, timestamp: (/* @__PURE__ */ new Date()).toISOString(), status: "error", error: { type: "FatalTurnLimitedError", message: maxTurnsError.message }, stats: streamFormatter.convertToStreamStats(metrics, 0) }); runSyncCleanup(); process.exit(maxTurnsError.exitCode); } else if (config.getOutputFormat() === OutputFormat.JSON) { const formatter = new JsonFormatter(); const formattedError = formatter.formatError( maxTurnsError, maxTurnsError.exitCode, config.getSessionId() ); coreEvents.emitFeedback("error", formattedError); runSyncCleanup(); process.exit(maxTurnsError.exitCode); } else { coreEvents.emitFeedback("error", maxTurnsError.message); runSyncCleanup(); process.exit(maxTurnsError.exitCode); } } // packages/cli/src/ui/utils/textOutput.ts var TextOutput = class { atStartOfLine = true; outputStream; constructor(outputStream = process.stdout) { this.outputStream = outputStream; } /** * Writes a string to stdout. * @param str The string to write. */ write(str) { if (str.length === 0) { return; } this.outputStream.write(str); const strippedStr = stripAnsi(str); if (strippedStr.length > 0) { this.atStartOfLine = strippedStr.endsWith("\n"); } } /** * Writes a string to stdout, ensuring it starts on a new line. * If the previous output did not end with a newline, one will be added. * This prevents adding extra blank lines if a newline already exists. * @param str The string to write. */ writeOnNewLine(str) { if (!this.atStartOfLine) { this.write("\n"); } this.write(str); } /** * Ensures that the output ends with a newline. If the last character * written was not a newline, one will be added. */ ensureTrailingNewline() { if (!this.atStartOfLine) { this.write("\n"); } } }; // packages/cli/src/nonInteractiveCli.ts async function runNonInteractive({ config, settings, input, prompt_id, resumedSessionData }) { return promptIdContext.run(prompt_id, async () => { const consolePatcher = new ConsolePatcher({ stderr: true, debugMode: config.getDebugMode(), onNewMessage: (msg) => { coreEvents.emitConsoleLog(msg.type, msg.content); } }); if (process.env["GEMINI_CLI_ACTIVITY_LOG_TARGET"]) { const { setupInitialActivityLogger } = await import("./devtoolsService-ZKU2HLK2.js"); await setupInitialActivityLogger(config); } const { stdout: workingStdout } = createWorkingStdio(); const textOutput = new TextOutput(workingStdout); const handleUserFeedback = (payload) => { const prefix = payload.severity.toUpperCase(); process.stderr.write(`[${prefix}] ${payload.message} `); if (payload.error && config.getDebugMode()) { const errorToLog = payload.error instanceof Error ? payload.error.stack || payload.error.message : String(payload.error); process.stderr.write(`${errorToLog} `); } }; const startTime = Date.now(); const streamFormatter = config.getOutputFormat() === OutputFormat.STREAM_JSON ? new StreamJsonFormatter() : null; const abortController = new AbortController(); let isAborting = false; let cancelMessageTimer = null; let stdinWasRaw = false; let rl = null; const setupStdinCancellation = () => { if (!process.stdin.isTTY) { return; } stdinWasRaw = process.stdin.isRaw || false; process.stdin.setRawMode(true); process.stdin.resume(); rl = readline.createInterface({ input: process.stdin, escapeCodeTimeout: 0 }); readline.emitKeypressEvents(process.stdin, rl); const keypressHandler = (str, key) => { if (key && key.ctrl && key.name === "c" || str === "") { if (isAborting) { return; } isAborting = true; cancelMessageTimer = setTimeout(() => { process.stderr.write("\nCancelling...\n"); }, 200); abortController.abort(); } }; process.stdin.on("keypress", keypressHandler); }; const cleanupStdinCancellation = () => { if (cancelMessageTimer) { clearTimeout(cancelMessageTimer); cancelMessageTimer = null; } if (rl) { rl.close(); rl = null; } process.stdin.removeAllListeners("keypress"); if (process.stdin.isTTY) { process.stdin.setRawMode(stdinWasRaw); process.stdin.pause(); } }; let errorToHandle; try { consolePatcher.patch(); if (config.getRawOutput() && !config.getAcceptRawOutputRisk() && config.getOutputFormat() === OutputFormat.TEXT) { process.stderr.write( "[WARNING] --raw-output is enabled. Model output is not sanitized and may contain harmful ANSI sequences (e.g. for phishing or command injection). Use --accept-raw-output-risk to suppress this warning.\n" ); } setupStdinCancellation(); coreEvents.on(CoreEvent.UserFeedback, handleUserFeedback); coreEvents.drainBacklogs(); process.stdout.on("error", (err) => { if (err.code === "EPIPE") { process.exit(0); } }); const geminiClient = config.getGeminiClient(); const scheduler = new Scheduler({ context: config, messageBus: config.getMessageBus(), getPreferredEditor: () => void 0, schedulerId: ROOT_SCHEDULER_ID }); if (resumedSessionData) { await geminiClient.resumeChat( convertSessionToClientHistory( resumedSessionData.conversation.messages ), resumedSessionData ); } if (streamFormatter) { streamFormatter.emitEvent({ type: JsonStreamEventType.INIT, timestamp: (/* @__PURE__ */ new Date()).toISOString(), session_id: config.getSessionId(), model: config.getModel() }); } let query; if (isSlashCommand(input)) { const slashCommandResult = await handleSlashCommand( input, abortController, config, settings ); if (slashCommandResult) { query = slashCommandResult; } } if (!query) { const { processedQuery, error } = await handleAtCommand({ query: input, config, addItem: (_item, _timestamp) => 0, onDebugMessage: () => { }, messageId: Date.now(), signal: abortController.signal, escapePastedAtSymbols: false }); if (error || !processedQuery) { throw new FatalInputError( error || "Exiting due to an error processing the @ command." ); } query = processedQuery; } if (streamFormatter) { streamFormatter.emitEvent({ type: JsonStreamEventType.MESSAGE, timestamp: (/* @__PURE__ */ new Date()).toISOString(), role: "user", content: input }); } let currentMessages = [{ role: "user", parts: query }]; let turnCount = 0; while (true) { turnCount++; if (config.getMaxSessionTurns() >= 0 && turnCount > config.getMaxSessionTurns()) { handleMaxTurnsExceededError(config); } const toolCallRequests = []; const responseStream = geminiClient.sendMessageStream( currentMessages[0]?.parts || [], abortController.signal, prompt_id, void 0, false, turnCount === 1 ? input : void 0 ); let responseText = ""; for await (const event of responseStream) { if (abortController.signal.aborted) { handleCancellationError(config); } if (event.type === GeminiEventType.Content) { const isRaw = config.getRawOutput() || config.getAcceptRawOutputRisk(); const output = isRaw ? event.value : stripAnsi(event.value); if (streamFormatter) { streamFormatter.emitEvent({ type: JsonStreamEventType.MESSAGE, timestamp: (/* @__PURE__ */ new Date()).toISOString(), role: "assistant", content: output, delta: true }); } else if (config.getOutputFormat() === OutputFormat.JSON) { responseText += output; } else { if (event.value) { textOutput.write(output); } } } else if (event.type === GeminiEventType.ToolCallRequest) { if (streamFormatter) { streamFormatter.emitEvent({ type: JsonStreamEventType.TOOL_USE, timestamp: (/* @__PURE__ */ new Date()).toISOString(), tool_name: event.value.name, tool_id: event.value.callId, parameters: event.value.args }); } toolCallRequests.push(event.value); } else if (event.type === GeminiEventType.LoopDetected) { if (streamFormatter) { streamFormatter.emitEvent({ type: JsonStreamEventType.ERROR, timestamp: (/* @__PURE__ */ new Date()).toISOString(), severity: "warning", message: "Loop detected, stopping execution" }); } } else if (event.type === GeminiEventType.MaxSessionTurns) { if (streamFormatter) { streamFormatter.emitEvent({ type: JsonStreamEventType.ERROR, timestamp: (/* @__PURE__ */ new Date()).toISOString(), severity: "error", message: "Maximum session turns exceeded" }); } } else if (event.type === GeminiEventType.Error) { throw event.value.error; } else if (event.type === GeminiEventType.AgentExecutionStopped) { const stopMessage = `Agent execution stopped: ${event.value.systemMessage?.trim() || event.value.reason}`; if (config.getOutputFormat() === OutputFormat.TEXT) { process.stderr.write(`${stopMessage} `); } if (streamFormatter) { const metrics = uiTelemetryService.getMetrics(); const durationMs = Date.now() - startTime; streamFormatter.emitEvent({ type: JsonStreamEventType.RESULT, timestamp: (/* @__PURE__ */ new Date()).toISOString(), status: "success", stats: streamFormatter.convertToStreamStats( metrics, durationMs ) }); } return; } else if (event.type === GeminiEventType.AgentExecutionBlocked) { const blockMessage = `Agent execution blocked: ${event.value.systemMessage?.trim() || event.value.reason}`; if (config.getOutputFormat() === OutputFormat.TEXT) { process.stderr.write(`[WARNING] ${blockMessage} `); } } } if (toolCallRequests.length > 0) { textOutput.ensureTrailingNewline(); const completedToolCalls = await scheduler.schedule( toolCallRequests, abortController.signal ); const toolResponseParts = []; for (const completedToolCall of completedToolCalls) { const toolResponse = completedToolCall.response; const requestInfo = completedToolCall.request; if (streamFormatter) { streamFormatter.emitEvent({ type: JsonStreamEventType.TOOL_RESULT, timestamp: (/* @__PURE__ */ new Date()).toISOString(), tool_id: requestInfo.callId, status: completedToolCall.status === "error" ? "error" : "success", output: typeof toolResponse.resultDisplay === "string" ? toolResponse.resultDisplay : void 0, error: toolResponse.error ? { type: toolResponse.errorType || "TOOL_EXECUTION_ERROR", message: toolResponse.error.message } : void 0 }); } if (toolResponse.error) { handleToolError( requestInfo.name, toolResponse.error, config, toolResponse.errorType || "TOOL_EXECUTION_ERROR", typeof toolResponse.resultDisplay === "string" ? toolResponse.resultDisplay : void 0 ); } if (toolResponse.responseParts) { toolResponseParts.push(...toolResponse.responseParts); } } try { const currentModel = geminiClient.getCurrentSequenceModel() ?? config.getModel(); geminiClient.getChat().recordCompletedToolCalls(currentModel, completedToolCalls); await recordToolCallInteractions(config, completedToolCalls); } catch (error) { debugLogger.error( `Error recording completed tool call information: ${error}` ); } const stopExecutionTool = completedToolCalls.find( (tc) => tc.response.errorType === ToolErrorType.STOP_EXECUTION ); if (stopExecutionTool && stopExecutionTool.response.error) { const stopMessage = `Agent execution stopped: ${stopExecutionTool.response.error.message}`; if (config.getOutputFormat() === OutputFormat.TEXT) { process.stderr.write(`${stopMessage} `); } if (streamFormatter) { const metrics = uiTelemetryService.getMetrics(); const durationMs = Date.now() - startTime; streamFormatter.emitEvent({ type: JsonStreamEventType.RESULT, timestamp: (/* @__PURE__ */ new Date()).toISOString(), status: "success", stats: streamFormatter.convertToStreamStats( metrics, durationMs ) }); } else if (config.getOutputFormat() === OutputFormat.JSON) { const formatter = new JsonFormatter(); const stats = uiTelemetryService.getMetrics(); textOutput.write( formatter.format(config.getSessionId(), responseText, stats) ); } else { textOutput.ensureTrailingNewline(); } return; } currentMessages = [{ role: "user", parts: toolResponseParts }]; } else { if (streamFormatter) { const metrics = uiTelemetryService.getMetrics(); const durationMs = Date.now() - startTime; streamFormatter.emitEvent({ type: JsonStreamEventType.RESULT, timestamp: (/* @__PURE__ */ new Date()).toISOString(), status: "success", stats: streamFormatter.convertToStreamStats(metrics, durationMs) }); } else if (config.getOutputFormat() === OutputFormat.JSON) { const formatter = new JsonFormatter(); const stats = uiTelemetryService.getMetrics(); textOutput.write( formatter.format(config.getSessionId(), responseText, stats) ); } else { textOutput.ensureTrailingNewline(); } return; } } } catch (error) { errorToHandle = error; } finally { cleanupStdinCancellation(); consolePatcher.cleanup(); coreEvents.off(CoreEvent.UserFeedback, handleUserFeedback); } if (errorToHandle) { handleError(errorToHandle, config); } }); } // packages/cli/src/utils/worktreeSetup.ts async function setupWorktree(worktreeName) { if (process.env["GEMINI_CLI_WORKTREE_HANDLED"] === "1") { return void 0; } try { const projectRoot = await getProjectRootForWorktree(process.cwd()); const service = await createWorktreeService(projectRoot); const worktreeInfo = await service.setup(worktreeName || void 0); process.chdir(worktreeInfo.path); process.env["GEMINI_CLI_WORKTREE_HANDLED"] = "1"; return worktreeInfo; } catch (error) { const errorMessage = error instanceof Error ? error.message : String(error); writeToStderr(`Failed to create or switch to worktree: ${errorMessage} `); process.exit(1); } } // node_modules/@agentclientprotocol/sdk/dist/schema/index.js var AGENT_METHODS = { authenticate: "authenticate", initialize: "initialize", session_cancel: "session/cancel", session_close: "session/close", session_fork: "session/fork", session_list: "session/list", session_load: "session/load", session_new: "session/new", session_prompt: "session/prompt", session_resume: "session/resume", session_set_config_option: "session/set_config_option", session_set_mode: "session/set_mode", session_set_model: "session/set_model" }; var CLIENT_METHODS = { fs_read_text_file: "fs/read_text_file", fs_write_text_file: "fs/write_text_file", session_request_permission: "session/request_permission", session_update: "session/update", terminal_create: "terminal/create", terminal_kill: "terminal/kill", terminal_output: "terminal/output", terminal_release: "terminal/release", terminal_wait_for_exit: "terminal/wait_for_exit" }; var PROTOCOL_VERSION = 1; // node_modules/@agentclientprotocol/sdk/dist/schema/zod.gen.js var zAuthCapabilities = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), terminal: external_exports2.boolean().optional().default(false) }); var zAuthEnvVar = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), label: external_exports2.string().nullish(), name: external_exports2.string(), optional: external_exports2.boolean().optional().default(false), secret: external_exports2.boolean().optional().default(true) }); var zAuthMethodAgent = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), description: external_exports2.string().nullish(), id: external_exports2.string(), name: external_exports2.string() }); var zAuthMethodEnvVar = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), description: external_exports2.string().nullish(), id: external_exports2.string(), link: external_exports2.string().nullish(), name: external_exports2.string(), vars: external_exports2.array(zAuthEnvVar) }); var zAuthMethodTerminal = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), args: external_exports2.array(external_exports2.string()).optional(), description: external_exports2.string().nullish(), env: external_exports2.record(external_exports2.string(), external_exports2.string()).optional(), id: external_exports2.string(), name: external_exports2.string() }); var zAuthMethod = external_exports2.union([ zAuthMethodEnvVar.and(external_exports2.object({ type: external_exports2.literal("env_var") })), zAuthMethodTerminal.and(external_exports2.object({ type: external_exports2.literal("terminal") })), zAuthMethodAgent ]); var zAuthenticateRequest = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), methodId: external_exports2.string() }); var zAuthenticateResponse = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish() }); var zBlobResourceContents = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), blob: external_exports2.string(), mimeType: external_exports2.string().nullish(), uri: external_exports2.string() }); var zCloseSessionResponse = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish() }); var zCost = external_exports2.object({ amount: external_exports2.number(), currency: external_exports2.string() }); var zCreateTerminalResponse = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), terminalId: external_exports2.string() }); var zDiff = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), newText: external_exports2.string(), oldText: external_exports2.string().nullish(), path: external_exports2.string() }); var zEnvVariable = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), name: external_exports2.string(), value: external_exports2.string() }); var zErrorCode = external_exports2.union([ external_exports2.literal(-32700), external_exports2.literal(-32600), external_exports2.literal(-32601), external_exports2.literal(-32602), external_exports2.literal(-32603), external_exports2.literal(-32800), external_exports2.literal(-32e3), external_exports2.literal(-32002), external_exports2.number().int().min(-2147483648, { message: "Invalid value: Expected int32 to be >= -2147483648" }).max(2147483647, { message: "Invalid value: Expected int32 to be <= 2147483647" }) ]); var zError = external_exports2.object({ code: zErrorCode, data: external_exports2.unknown().optional(), message: external_exports2.string() }); var zExtNotification = external_exports2.unknown(); var zExtRequest = external_exports2.unknown(); var zExtResponse = external_exports2.unknown(); var zFileSystemCapabilities = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), readTextFile: external_exports2.boolean().optional().default(false), writeTextFile: external_exports2.boolean().optional().default(false) }); var zClientCapabilities = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), auth: zAuthCapabilities.optional().default({ terminal: false }), fs: zFileSystemCapabilities.optional().default({ readTextFile: false, writeTextFile: false }), terminal: external_exports2.boolean().optional().default(false) }); var zHttpHeader = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), name: external_exports2.string(), value: external_exports2.string() }); var zImplementation = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), name: external_exports2.string(), title: external_exports2.string().nullish(), version: external_exports2.string() }); var zKillTerminalResponse = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish() }); var zListSessionsRequest = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), cursor: external_exports2.string().nullish(), cwd: external_exports2.string().nullish() }); var zMcpCapabilities = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), http: external_exports2.boolean().optional().default(false), sse: external_exports2.boolean().optional().default(false) }); var zMcpServerHttp = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), headers: external_exports2.array(zHttpHeader), name: external_exports2.string(), url: external_exports2.string() }); var zMcpServerSse = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), headers: external_exports2.array(zHttpHeader), name: external_exports2.string(), url: external_exports2.string() }); var zMcpServerStdio = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), args: external_exports2.array(external_exports2.string()), command: external_exports2.string(), env: external_exports2.array(zEnvVariable), name: external_exports2.string() }); var zMcpServer = external_exports2.union([ zMcpServerHttp.and(external_exports2.object({ type: external_exports2.literal("http") })), zMcpServerSse.and(external_exports2.object({ type: external_exports2.literal("sse") })), zMcpServerStdio ]); var zModelId = external_exports2.string(); var zModelInfo = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), description: external_exports2.string().nullish(), modelId: zModelId, name: external_exports2.string() }); var zNewSessionRequest = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), cwd: external_exports2.string(), mcpServers: external_exports2.array(zMcpServer) }); var zPermissionOptionId = external_exports2.string(); var zPermissionOptionKind = external_exports2.union([ external_exports2.literal("allow_once"), external_exports2.literal("allow_always"), external_exports2.literal("reject_once"), external_exports2.literal("reject_always") ]); var zPermissionOption = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), kind: zPermissionOptionKind, name: external_exports2.string(), optionId: zPermissionOptionId }); var zPlanEntryPriority = external_exports2.union([ external_exports2.literal("high"), external_exports2.literal("medium"), external_exports2.literal("low") ]); var zPlanEntryStatus = external_exports2.union([ external_exports2.literal("pending"), external_exports2.literal("in_progress"), external_exports2.literal("completed") ]); var zPlanEntry = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), content: external_exports2.string(), priority: zPlanEntryPriority, status: zPlanEntryStatus }); var zPlan = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), entries: external_exports2.array(zPlanEntry) }); var zPromptCapabilities = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), audio: external_exports2.boolean().optional().default(false), embeddedContext: external_exports2.boolean().optional().default(false), image: external_exports2.boolean().optional().default(false) }); var zProtocolVersion = external_exports2.number().int().gte(0).lte(65535); var zInitializeRequest = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), clientCapabilities: zClientCapabilities.optional().default({ auth: { terminal: false }, fs: { readTextFile: false, writeTextFile: false }, terminal: false }), clientInfo: zImplementation.nullish(), protocolVersion: zProtocolVersion }); var zReadTextFileResponse = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), content: external_exports2.string() }); var zReleaseTerminalResponse = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish() }); var zRequestId = external_exports2.union([external_exports2.number(), external_exports2.string()]).nullable(); var zCancelRequestNotification = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), requestId: zRequestId }); var zRole = external_exports2.enum(["assistant", "user"]); var zAnnotations = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), audience: external_exports2.array(zRole).nullish(), lastModified: external_exports2.string().nullish(), priority: external_exports2.number().nullish() }); var zAudioContent = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), annotations: zAnnotations.nullish(), data: external_exports2.string(), mimeType: external_exports2.string() }); var zImageContent = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), annotations: zAnnotations.nullish(), data: external_exports2.string(), mimeType: external_exports2.string(), uri: external_exports2.string().nullish() }); var zResourceLink = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), annotations: zAnnotations.nullish(), description: external_exports2.string().nullish(), mimeType: external_exports2.string().nullish(), name: external_exports2.string(), size: external_exports2.number().nullish(), title: external_exports2.string().nullish(), uri: external_exports2.string() }); var zSelectedPermissionOutcome = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), optionId: zPermissionOptionId }); var zRequestPermissionOutcome = external_exports2.union([ external_exports2.object({ outcome: external_exports2.literal("cancelled") }), zSelectedPermissionOutcome.and(external_exports2.object({ outcome: external_exports2.literal("selected") })) ]); var zRequestPermissionResponse = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), outcome: zRequestPermissionOutcome }); var zSessionCloseCapabilities = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish() }); var zSessionConfigBoolean = external_exports2.object({ currentValue: external_exports2.boolean() }); var zSessionConfigGroupId = external_exports2.string(); var zSessionConfigId = external_exports2.string(); var zSessionConfigOptionCategory = external_exports2.union([ external_exports2.literal("mode"), external_exports2.literal("model"), external_exports2.literal("thought_level"), external_exports2.string() ]); var zSessionConfigValueId = external_exports2.string(); var zSessionConfigSelectOption = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), description: external_exports2.string().nullish(), name: external_exports2.string(), value: zSessionConfigValueId }); var zSessionConfigSelectGroup = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), group: zSessionConfigGroupId, name: external_exports2.string(), options: external_exports2.array(zSessionConfigSelectOption) }); var zSessionConfigSelectOptions = external_exports2.union([ external_exports2.array(zSessionConfigSelectOption), external_exports2.array(zSessionConfigSelectGroup) ]); var zSessionConfigSelect = external_exports2.object({ currentValue: zSessionConfigValueId, options: zSessionConfigSelectOptions }); var zSessionConfigOption = external_exports2.intersection(external_exports2.union([ zSessionConfigSelect.and(external_exports2.object({ type: external_exports2.literal("select") })), zSessionConfigBoolean.and(external_exports2.object({ type: external_exports2.literal("boolean") })) ]), external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), category: zSessionConfigOptionCategory.nullish(), description: external_exports2.string().nullish(), id: zSessionConfigId, name: external_exports2.string() })); var zConfigOptionUpdate = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), configOptions: external_exports2.array(zSessionConfigOption) }); var zSessionForkCapabilities = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish() }); var zSessionId = external_exports2.string(); var zCancelNotification = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), sessionId: zSessionId }); var zClientNotification = external_exports2.object({ method: external_exports2.string(), params: external_exports2.union([zCancelNotification, zExtNotification]).nullish() }); var zCloseSessionRequest = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), sessionId: zSessionId }); var zCreateTerminalRequest = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), args: external_exports2.array(external_exports2.string()).optional(), command: external_exports2.string(), cwd: external_exports2.string().nullish(), env: external_exports2.array(zEnvVariable).optional(), outputByteLimit: external_exports2.number().nullish(), sessionId: zSessionId }); var zForkSessionRequest = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), cwd: external_exports2.string(), mcpServers: external_exports2.array(zMcpServer).optional(), sessionId: zSessionId }); var zKillTerminalRequest = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), sessionId: zSessionId, terminalId: external_exports2.string() }); var zLoadSessionRequest = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), cwd: external_exports2.string(), mcpServers: external_exports2.array(zMcpServer), sessionId: zSessionId }); var zReadTextFileRequest = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), limit: external_exports2.number().int().gte(0).max(4294967295, { message: "Invalid value: Expected uint32 to be <= 4294967295" }).nullish(), line: external_exports2.number().int().gte(0).max(4294967295, { message: "Invalid value: Expected uint32 to be <= 4294967295" }).nullish(), path: external_exports2.string(), sessionId: zSessionId }); var zReleaseTerminalRequest = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), sessionId: zSessionId, terminalId: external_exports2.string() }); var zResumeSessionRequest = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), cwd: external_exports2.string(), mcpServers: external_exports2.array(zMcpServer).optional(), sessionId: zSessionId }); var zSessionInfo = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), cwd: external_exports2.string(), sessionId: zSessionId, title: external_exports2.string().nullish(), updatedAt: external_exports2.string().nullish() }); var zListSessionsResponse = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), nextCursor: external_exports2.string().nullish(), sessions: external_exports2.array(zSessionInfo) }); var zSessionInfoUpdate = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), title: external_exports2.string().nullish(), updatedAt: external_exports2.string().nullish() }); var zSessionListCapabilities = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish() }); var zSessionModeId = external_exports2.string(); var zCurrentModeUpdate = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), currentModeId: zSessionModeId }); var zSessionMode = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), description: external_exports2.string().nullish(), id: zSessionModeId, name: external_exports2.string() }); var zSessionModeState = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), availableModes: external_exports2.array(zSessionMode), currentModeId: zSessionModeId }); var zSessionModelState = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), availableModels: external_exports2.array(zModelInfo), currentModelId: zModelId }); var zForkSessionResponse = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), configOptions: external_exports2.array(zSessionConfigOption).nullish(), models: zSessionModelState.nullish(), modes: zSessionModeState.nullish(), sessionId: zSessionId }); var zLoadSessionResponse = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), configOptions: external_exports2.array(zSessionConfigOption).nullish(), models: zSessionModelState.nullish(), modes: zSessionModeState.nullish() }); var zNewSessionResponse = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), configOptions: external_exports2.array(zSessionConfigOption).nullish(), models: zSessionModelState.nullish(), modes: zSessionModeState.nullish(), sessionId: zSessionId }); var zResumeSessionResponse = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), configOptions: external_exports2.array(zSessionConfigOption).nullish(), models: zSessionModelState.nullish(), modes: zSessionModeState.nullish() }); var zSessionResumeCapabilities = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish() }); var zSessionCapabilities = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), close: zSessionCloseCapabilities.nullish(), fork: zSessionForkCapabilities.nullish(), list: zSessionListCapabilities.nullish(), resume: zSessionResumeCapabilities.nullish() }); var zAgentCapabilities = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), loadSession: external_exports2.boolean().optional().default(false), mcpCapabilities: zMcpCapabilities.optional().default({ http: false, sse: false }), promptCapabilities: zPromptCapabilities.optional().default({ audio: false, embeddedContext: false, image: false }), sessionCapabilities: zSessionCapabilities.optional().default({}) }); var zInitializeResponse = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), agentCapabilities: zAgentCapabilities.optional().default({ loadSession: false, mcpCapabilities: { http: false, sse: false }, promptCapabilities: { audio: false, embeddedContext: false, image: false }, sessionCapabilities: {} }), agentInfo: zImplementation.nullish(), authMethods: external_exports2.array(zAuthMethod).optional().default([]), protocolVersion: zProtocolVersion }); var zSetSessionConfigOptionRequest = external_exports2.intersection(external_exports2.union([ external_exports2.object({ type: external_exports2.literal("boolean"), value: external_exports2.boolean() }), external_exports2.object({ value: zSessionConfigValueId }) ]), external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), configId: zSessionConfigId, sessionId: zSessionId })); var zSetSessionConfigOptionResponse = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), configOptions: external_exports2.array(zSessionConfigOption) }); var zSetSessionModeRequest = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), modeId: zSessionModeId, sessionId: zSessionId }); var zSetSessionModeResponse = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish() }); var zSetSessionModelRequest = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), modelId: zModelId, sessionId: zSessionId }); var zSetSessionModelResponse = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish() }); var zStopReason = external_exports2.union([ external_exports2.literal("end_turn"), external_exports2.literal("max_tokens"), external_exports2.literal("max_turn_requests"), external_exports2.literal("refusal"), external_exports2.literal("cancelled") ]); var zTerminal = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), terminalId: external_exports2.string() }); var zTerminalExitStatus = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), exitCode: external_exports2.number().int().gte(0).max(4294967295, { message: "Invalid value: Expected uint32 to be <= 4294967295" }).nullish(), signal: external_exports2.string().nullish() }); var zTerminalOutputRequest = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), sessionId: zSessionId, terminalId: external_exports2.string() }); var zTerminalOutputResponse = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), exitStatus: zTerminalExitStatus.nullish(), output: external_exports2.string(), truncated: external_exports2.boolean() }); var zTextContent = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), annotations: zAnnotations.nullish(), text: external_exports2.string() }); var zTextResourceContents = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), mimeType: external_exports2.string().nullish(), text: external_exports2.string(), uri: external_exports2.string() }); var zEmbeddedResourceResource = external_exports2.union([ zTextResourceContents, zBlobResourceContents ]); var zEmbeddedResource = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), annotations: zAnnotations.nullish(), resource: zEmbeddedResourceResource }); var zContentBlock = external_exports2.union([ zTextContent.and(external_exports2.object({ type: external_exports2.literal("text") })), zImageContent.and(external_exports2.object({ type: external_exports2.literal("image") })), zAudioContent.and(external_exports2.object({ type: external_exports2.literal("audio") })), zResourceLink.and(external_exports2.object({ type: external_exports2.literal("resource_link") })), zEmbeddedResource.and(external_exports2.object({ type: external_exports2.literal("resource") })) ]); var zContent = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), content: zContentBlock }); var zContentChunk = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), content: zContentBlock, messageId: external_exports2.string().nullish() }); var zPromptRequest = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), messageId: external_exports2.string().nullish(), prompt: external_exports2.array(zContentBlock), sessionId: zSessionId }); var zClientRequest = external_exports2.object({ id: zRequestId, method: external_exports2.string(), params: external_exports2.union([ zInitializeRequest, zAuthenticateRequest, zNewSessionRequest, zLoadSessionRequest, zListSessionsRequest, zForkSessionRequest, zResumeSessionRequest, zCloseSessionRequest, zSetSessionModeRequest, zSetSessionConfigOptionRequest, zPromptRequest, zSetSessionModelRequest, zExtRequest ]).nullish() }); var zToolCallContent = external_exports2.union([ zContent.and(external_exports2.object({ type: external_exports2.literal("content") })), zDiff.and(external_exports2.object({ type: external_exports2.literal("diff") })), zTerminal.and(external_exports2.object({ type: external_exports2.literal("terminal") })) ]); var zToolCallId = external_exports2.string(); var zToolCallLocation = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), line: external_exports2.number().int().gte(0).max(4294967295, { message: "Invalid value: Expected uint32 to be <= 4294967295" }).nullish(), path: external_exports2.string() }); var zToolCallStatus = external_exports2.union([ external_exports2.literal("pending"), external_exports2.literal("in_progress"), external_exports2.literal("completed"), external_exports2.literal("failed") ]); var zToolKind = external_exports2.union([ external_exports2.literal("read"), external_exports2.literal("edit"), external_exports2.literal("delete"), external_exports2.literal("move"), external_exports2.literal("search"), external_exports2.literal("execute"), external_exports2.literal("think"), external_exports2.literal("fetch"), external_exports2.literal("switch_mode"), external_exports2.literal("other") ]); var zToolCall = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), content: external_exports2.array(zToolCallContent).optional(), kind: zToolKind.optional(), locations: external_exports2.array(zToolCallLocation).optional(), rawInput: external_exports2.unknown().optional(), rawOutput: external_exports2.unknown().optional(), status: zToolCallStatus.optional(), title: external_exports2.string(), toolCallId: zToolCallId }); var zToolCallUpdate = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), content: external_exports2.array(zToolCallContent).nullish(), kind: zToolKind.nullish(), locations: external_exports2.array(zToolCallLocation).nullish(), rawInput: external_exports2.unknown().optional(), rawOutput: external_exports2.unknown().optional(), status: zToolCallStatus.nullish(), title: external_exports2.string().nullish(), toolCallId: zToolCallId }); var zRequestPermissionRequest = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), options: external_exports2.array(zPermissionOption), sessionId: zSessionId, toolCall: zToolCallUpdate }); var zUnstructuredCommandInput = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), hint: external_exports2.string() }); var zAvailableCommandInput = zUnstructuredCommandInput; var zAvailableCommand = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), description: external_exports2.string(), input: zAvailableCommandInput.nullish(), name: external_exports2.string() }); var zAvailableCommandsUpdate = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), availableCommands: external_exports2.array(zAvailableCommand) }); var zUsage = external_exports2.object({ cachedReadTokens: external_exports2.number().nullish(), cachedWriteTokens: external_exports2.number().nullish(), inputTokens: external_exports2.number(), outputTokens: external_exports2.number(), thoughtTokens: external_exports2.number().nullish(), totalTokens: external_exports2.number() }); var zPromptResponse = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), stopReason: zStopReason, usage: zUsage.nullish(), userMessageId: external_exports2.string().nullish() }); var zAgentResponse = external_exports2.union([ external_exports2.object({ id: zRequestId, result: external_exports2.union([ zInitializeResponse, zAuthenticateResponse, zNewSessionResponse, zLoadSessionResponse, zListSessionsResponse, zForkSessionResponse, zResumeSessionResponse, zCloseSessionResponse, zSetSessionModeResponse, zSetSessionConfigOptionResponse, zPromptResponse, zSetSessionModelResponse, zExtResponse ]) }), external_exports2.object({ error: zError, id: zRequestId }) ]); var zUsageUpdate = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), cost: zCost.nullish(), size: external_exports2.number(), used: external_exports2.number() }); var zSessionUpdate = external_exports2.union([ zContentChunk.and(external_exports2.object({ sessionUpdate: external_exports2.literal("user_message_chunk") })), zContentChunk.and(external_exports2.object({ sessionUpdate: external_exports2.literal("agent_message_chunk") })), zContentChunk.and(external_exports2.object({ sessionUpdate: external_exports2.literal("agent_thought_chunk") })), zToolCall.and(external_exports2.object({ sessionUpdate: external_exports2.literal("tool_call") })), zToolCallUpdate.and(external_exports2.object({ sessionUpdate: external_exports2.literal("tool_call_update") })), zPlan.and(external_exports2.object({ sessionUpdate: external_exports2.literal("plan") })), zAvailableCommandsUpdate.and(external_exports2.object({ sessionUpdate: external_exports2.literal("available_commands_update") })), zCurrentModeUpdate.and(external_exports2.object({ sessionUpdate: external_exports2.literal("current_mode_update") })), zConfigOptionUpdate.and(external_exports2.object({ sessionUpdate: external_exports2.literal("config_option_update") })), zSessionInfoUpdate.and(external_exports2.object({ sessionUpdate: external_exports2.literal("session_info_update") })), zUsageUpdate.and(external_exports2.object({ sessionUpdate: external_exports2.literal("usage_update") })) ]); var zSessionNotification = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), sessionId: zSessionId, update: zSessionUpdate }); var zAgentNotification = external_exports2.object({ method: external_exports2.string(), params: external_exports2.union([zSessionNotification, zExtNotification]).nullish() }); var zWaitForTerminalExitRequest = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), sessionId: zSessionId, terminalId: external_exports2.string() }); var zWaitForTerminalExitResponse = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), exitCode: external_exports2.number().int().gte(0).max(4294967295, { message: "Invalid value: Expected uint32 to be <= 4294967295" }).nullish(), signal: external_exports2.string().nullish() }); var zWriteTextFileRequest = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish(), content: external_exports2.string(), path: external_exports2.string(), sessionId: zSessionId }); var zAgentRequest = external_exports2.object({ id: zRequestId, method: external_exports2.string(), params: external_exports2.union([ zWriteTextFileRequest, zReadTextFileRequest, zRequestPermissionRequest, zCreateTerminalRequest, zTerminalOutputRequest, zReleaseTerminalRequest, zWaitForTerminalExitRequest, zKillTerminalRequest, zExtRequest ]).nullish() }); var zWriteTextFileResponse = external_exports2.object({ _meta: external_exports2.record(external_exports2.string(), external_exports2.unknown()).nullish() }); var zClientResponse = external_exports2.union([ external_exports2.object({ id: zRequestId, result: external_exports2.union([ zWriteTextFileResponse, zReadTextFileResponse, zRequestPermissionResponse, zCreateTerminalResponse, zTerminalOutputResponse, zReleaseTerminalResponse, zWaitForTerminalExitResponse, zKillTerminalResponse, zExtResponse ]) }), external_exports2.object({ error: zError, id: zRequestId }) ]); // node_modules/@agentclientprotocol/sdk/dist/stream.js function ndJsonStream(output, input) { const textEncoder = new TextEncoder(); const textDecoder = new TextDecoder(); const readable = new ReadableStream({ async start(controller) { let content = ""; const reader = input.getReader(); try { while (true) { const { value, done } = await reader.read(); if (done) { break; } if (!value) { continue; } content += textDecoder.decode(value, { stream: true }); const lines = content.split("\n"); content = lines.pop() || ""; for (const line of lines) { const trimmedLine = line.trim(); if (trimmedLine) { try { const message = JSON.parse(trimmedLine); controller.enqueue(message); } catch (err) { console.error("Failed to parse JSON message:", trimmedLine, err); } } } } } finally { reader.releaseLock(); controller.close(); } } }); const writable = new WritableStream({ async write(message) { const content = JSON.stringify(message) + "\n"; const writer = output.getWriter(); try { await writer.write(textEncoder.encode(content)); } finally { writer.releaseLock(); } } }); return { readable, writable }; } // node_modules/@agentclientprotocol/sdk/dist/acp.js var AgentSideConnection = class { #connection; /** * Creates a new agent-side connection to a client. * * This establishes the communication channel from the agent's perspective * following the ACP specification. * * @param toAgent - A function that creates an Agent handler to process incoming client requests * @param stream - The bidirectional message stream for communication. Typically created using * {@link ndJsonStream} for stdio-based connections. * * See protocol docs: [Communication Model](https://agentclientprotocol.com/protocol/overview#communication-model) */ constructor(toAgent, stream) { const agent = toAgent(this); const requestHandler = async (method, params) => { switch (method) { case AGENT_METHODS.initialize: { const validatedParams = zInitializeRequest.parse(params); return agent.initialize(validatedParams); } case AGENT_METHODS.session_new: { const validatedParams = zNewSessionRequest.parse(params); return agent.newSession(validatedParams); } case AGENT_METHODS.session_load: { if (!agent.loadSession) { throw RequestError.methodNotFound(method); } const validatedParams = zLoadSessionRequest.parse(params); return agent.loadSession(validatedParams); } case AGENT_METHODS.session_list: { if (!agent.listSessions) { throw RequestError.methodNotFound(method); } const validatedParams = zListSessionsRequest.parse(params); return agent.listSessions(validatedParams); } case AGENT_METHODS.session_fork: { if (!agent.unstable_forkSession) { throw RequestError.methodNotFound(method); } const validatedParams = zForkSessionRequest.parse(params); return agent.unstable_forkSession(validatedParams); } case AGENT_METHODS.session_resume: { if (!agent.unstable_resumeSession) { throw RequestError.methodNotFound(method); } const validatedParams = zResumeSessionRequest.parse(params); return agent.unstable_resumeSession(validatedParams); } case AGENT_METHODS.session_close: { if (!agent.unstable_closeSession) { throw RequestError.methodNotFound(method); } const validatedParams = zCloseSessionRequest.parse(params); return agent.unstable_closeSession(validatedParams); } case AGENT_METHODS.session_set_mode: { if (!agent.setSessionMode) { throw RequestError.methodNotFound(method); } const validatedParams = zSetSessionModeRequest.parse(params); const result = await agent.setSessionMode(validatedParams); return result ?? {}; } case AGENT_METHODS.authenticate: { const validatedParams = zAuthenticateRequest.parse(params); const result = await agent.authenticate(validatedParams); return result ?? {}; } case AGENT_METHODS.session_prompt: { const validatedParams = zPromptRequest.parse(params); return agent.prompt(validatedParams); } case AGENT_METHODS.session_set_model: { if (!agent.unstable_setSessionModel) { throw RequestError.methodNotFound(method); } const validatedParams = zSetSessionModelRequest.parse(params); const result = await agent.unstable_setSessionModel(validatedParams); return result ?? {}; } case AGENT_METHODS.session_set_config_option: { if (!agent.setSessionConfigOption) { throw RequestError.methodNotFound(method); } const validatedParams = zSetSessionConfigOptionRequest.parse(params); return agent.setSessionConfigOption(validatedParams); } default: if (agent.extMethod) { return agent.extMethod(method, params); } throw RequestError.methodNotFound(method); } }; const notificationHandler = async (method, params) => { switch (method) { case AGENT_METHODS.session_cancel: { const validatedParams = zCancelNotification.parse(params); return agent.cancel(validatedParams); } default: if (agent.extNotification) { return agent.extNotification(method, params); } throw RequestError.methodNotFound(method); } }; this.#connection = new Connection(requestHandler, notificationHandler, stream); } /** * Handles session update notifications from the agent. * * This is a notification endpoint (no response expected) that sends * real-time updates about session progress, including message chunks, * tool calls, and execution plans. * * Note: Clients SHOULD continue accepting tool call updates even after * sending a `session/cancel` notification, as the agent may send final * updates before responding with the cancelled stop reason. * * See protocol docs: [Agent Reports Output](https://agentclientprotocol.com/protocol/prompt-turn#3-agent-reports-output) */ async sessionUpdate(params) { return await this.#connection.sendNotification(CLIENT_METHODS.session_update, params); } /** * Requests permission from the user for a tool call operation. * * Called by the agent when it needs user authorization before executing * a potentially sensitive operation. The client should present the options * to the user and return their decision. * * If the client cancels the prompt turn via `session/cancel`, it MUST * respond to this request with `RequestPermissionOutcome::Cancelled`. * * See protocol docs: [Requesting Permission](https://agentclientprotocol.com/protocol/tool-calls#requesting-permission) */ async requestPermission(params) { return await this.#connection.sendRequest(CLIENT_METHODS.session_request_permission, params); } /** * Reads content from a text file in the client's file system. * * Only available if the client advertises the `fs.readTextFile` capability. * Allows the agent to access file contents within the client's environment. * * See protocol docs: [Client](https://agentclientprotocol.com/protocol/overview#client) */ async readTextFile(params) { return await this.#connection.sendRequest(CLIENT_METHODS.fs_read_text_file, params); } /** * Writes content to a text file in the client's file system. * * Only available if the client advertises the `fs.writeTextFile` capability. * Allows the agent to create or modify files within the client's environment. * * See protocol docs: [Client](https://agentclientprotocol.com/protocol/overview#client) */ async writeTextFile(params) { return await this.#connection.sendRequest(CLIENT_METHODS.fs_write_text_file, params) ?? {}; } /** * Executes a command in a new terminal. * * Returns a `TerminalHandle` that can be used to get output, wait for exit, * kill the command, or release the terminal. * * The terminal can also be embedded in tool calls by using its ID in * `ToolCallContent` with type "terminal". * * @param params - The terminal creation parameters * @returns A handle to control and monitor the terminal */ async createTerminal(params) { const response = await this.#connection.sendRequest(CLIENT_METHODS.terminal_create, params); return new TerminalHandle(response.terminalId, params.sessionId, this.#connection); } /** * Extension method * * Allows the Agent to send an arbitrary request that is not part of the ACP spec. */ async extMethod(method, params) { return await this.#connection.sendRequest(method, params); } /** * Extension notification * * Allows the Agent to send an arbitrary notification that is not part of the ACP spec. */ async extNotification(method, params) { return await this.#connection.sendNotification(method, params); } /** * AbortSignal that aborts when the connection closes. * * This signal can be used to: * - Listen for connection closure: `connection.signal.addEventListener('abort', () => {...})` * - Check connection status synchronously: `if (connection.signal.aborted) {...}` * - Pass to other APIs (fetch, setTimeout) for automatic cancellation * * The connection closes when the underlying stream ends, either normally or due to an error. * * @example * ```typescript * const connection = new AgentSideConnection(agent, stream); * * // Listen for closure * connection.signal.addEventListener('abort', () => { * console.log('Connection closed - performing cleanup'); * }); * * // Check status * if (connection.signal.aborted) { * console.log('Connection is already closed'); * } * * // Pass to other APIs * fetch(url, { signal: connection.signal }); * ``` */ get signal() { return this.#connection.signal; } /** * Promise that resolves when the connection closes. * * The connection closes when the underlying stream ends, either normally or due to an error. * Once closed, the connection cannot send or receive any more messages. * * This is useful for async/await style cleanup: * * @example * ```typescript * const connection = new AgentSideConnection(agent, stream); * await connection.closed; * console.log('Connection closed - performing cleanup'); * ``` */ get closed() { return this.#connection.closed; } }; var TerminalHandle = class { id; #sessionId; #connection; constructor(id, sessionId2, conn) { this.id = id; this.#sessionId = sessionId2; this.#connection = conn; } /** * Gets the current terminal output without waiting for the command to exit. */ async currentOutput() { return await this.#connection.sendRequest(CLIENT_METHODS.terminal_output, { sessionId: this.#sessionId, terminalId: this.id }); } /** * Waits for the terminal command to complete and returns its exit status. */ async waitForExit() { return await this.#connection.sendRequest(CLIENT_METHODS.terminal_wait_for_exit, { sessionId: this.#sessionId, terminalId: this.id }); } /** * Kills the terminal command without releasing the terminal. * * The terminal remains valid after killing, allowing you to: * - Get the final output with `currentOutput()` * - Check the exit status * - Release the terminal when done * * Useful for implementing timeouts or cancellation. */ async kill() { return await this.#connection.sendRequest(CLIENT_METHODS.terminal_kill, { sessionId: this.#sessionId, terminalId: this.id }) ?? {}; } /** * Releases the terminal and frees all associated resources. * * If the command is still running, it will be killed. * After release, the terminal ID becomes invalid and cannot be used * with other terminal methods. * * Tool calls that already reference this terminal will continue to * display its output. * * **Important:** Always call this method when done with the terminal. */ async release() { return await this.#connection.sendRequest(CLIENT_METHODS.terminal_release, { sessionId: this.#sessionId, terminalId: this.id }) ?? {}; } async [Symbol.asyncDispose]() { await this.release(); } }; var Connection = class { #pendingResponses = /* @__PURE__ */ new Map(); #nextRequestId = 0; #requestHandler; #notificationHandler; #stream; #writeQueue = Promise.resolve(); #abortController = new AbortController(); #closedPromise; constructor(requestHandler, notificationHandler, stream) { this.#requestHandler = requestHandler; this.#notificationHandler = notificationHandler; this.#stream = stream; this.#closedPromise = new Promise((resolve9) => { this.#abortController.signal.addEventListener("abort", () => resolve9()); }); this.#receive(); } /** * AbortSignal that aborts when the connection closes. * * This signal can be used to: * - Listen for connection closure via event listeners * - Check connection status synchronously with `signal.aborted` * - Pass to other APIs (fetch, setTimeout) for automatic cancellation */ get signal() { return this.#abortController.signal; } /** * Promise that resolves when the connection closes. * * The connection closes when the underlying stream ends, either normally * or due to an error. Once closed, the connection cannot send or receive * any more messages. * * @example * ```typescript * const connection = new ClientSideConnection(client, stream); * await connection.closed; * console.log('Connection closed - performing cleanup'); * ``` */ get closed() { return this.#closedPromise; } async #receive() { const reader = this.#stream.readable.getReader(); try { while (true) { const { value: message, done } = await reader.read(); if (done) { break; } if (!message) { continue; } try { this.#processMessage(message); } catch (err) { console.error("Unexpected error during message processing:", message, err); if ("id" in message && message.id !== void 0) { this.#sendMessage({ jsonrpc: "2.0", id: message.id, error: { code: -32700, message: "Parse error" } }); } } } } finally { reader.releaseLock(); this.#abortController.abort(); } } async #processMessage(message) { if ("method" in message && "id" in message) { const response = await this.#tryCallRequestHandler(message.method, message.params); if ("error" in response) { console.error("Error handling request", message, response.error); } await this.#sendMessage({ jsonrpc: "2.0", id: message.id, ...response }); } else if ("method" in message) { const response = await this.#tryCallNotificationHandler(message.method, message.params); if ("error" in response) { console.error("Error handling notification", message, response.error); } } else if ("id" in message) { this.#handleResponse(message); } else { console.error("Invalid message", { message }); } } async #tryCallRequestHandler(method, params) { try { const result = await this.#requestHandler(method, params); return { result: result ?? null }; } catch (error) { if (error instanceof RequestError) { return error.toResult(); } if (error instanceof external_exports.ZodError) { return RequestError.invalidParams(error.format()).toResult(); } let details; if (error instanceof Error) { details = error.message; } else if (typeof error === "object" && error != null && "message" in error && typeof error.message === "string") { details = error.message; } try { return RequestError.internalError(details ? JSON.parse(details) : {}).toResult(); } catch { return RequestError.internalError({ details }).toResult(); } } } async #tryCallNotificationHandler(method, params) { try { await this.#notificationHandler(method, params); return { result: null }; } catch (error) { if (error instanceof RequestError) { return error.toResult(); } if (error instanceof external_exports.ZodError) { return RequestError.invalidParams(error.format()).toResult(); } let details; if (error instanceof Error) { details = error.message; } else if (typeof error === "object" && error != null && "message" in error && typeof error.message === "string") { details = error.message; } try { return RequestError.internalError(details ? JSON.parse(details) : {}).toResult(); } catch { return RequestError.internalError({ details }).toResult(); } } } #handleResponse(response) { const pendingResponse = this.#pendingResponses.get(response.id); if (pendingResponse) { if ("result" in response) { pendingResponse.resolve(response.result); } else if ("error" in response) { pendingResponse.reject(response.error); } this.#pendingResponses.delete(response.id); } else { console.error("Got response to unknown request", response.id); } } async sendRequest(method, params) { const id = this.#nextRequestId++; const responsePromise = new Promise((resolve9, reject) => { this.#pendingResponses.set(id, { resolve: resolve9, reject }); }); await this.#sendMessage({ jsonrpc: "2.0", id, method, params }); return responsePromise; } async sendNotification(method, params) { await this.#sendMessage({ jsonrpc: "2.0", method, params }); } async #sendMessage(message) { this.#writeQueue = this.#writeQueue.then(async () => { const writer = this.#stream.writable.getWriter(); try { await writer.write(message); } finally { writer.releaseLock(); } }).catch((error) => { console.error("ACP write error:", error); }); return this.#writeQueue; } }; var RequestError = class _RequestError extends Error { code; data; constructor(code, message, data) { super(message); this.code = code; this.name = "RequestError"; this.data = data; } /** * Invalid JSON was received by the server. An error occurred on the server while parsing the JSON text. */ static parseError(data, additionalMessage) { return new _RequestError(-32700, `Parse error${additionalMessage ? `: ${additionalMessage}` : ""}`, data); } /** * The JSON sent is not a valid Request object. */ static invalidRequest(data, additionalMessage) { return new _RequestError(-32600, `Invalid request${additionalMessage ? `: ${additionalMessage}` : ""}`, data); } /** * The method does not exist / is not available. */ static methodNotFound(method) { return new _RequestError(-32601, `"Method not found": ${method}`, { method }); } /** * Invalid method parameter(s). */ static invalidParams(data, additionalMessage) { return new _RequestError(-32602, `Invalid params${additionalMessage ? `: ${additionalMessage}` : ""}`, data); } /** * Internal JSON-RPC error. */ static internalError(data, additionalMessage) { return new _RequestError(-32603, `Internal error${additionalMessage ? `: ${additionalMessage}` : ""}`, data); } /** * Authentication required. */ static authRequired(data, additionalMessage) { return new _RequestError(-32e3, `Authentication required${additionalMessage ? `: ${additionalMessage}` : ""}`, data); } /** * Resource, such as a file, was not found */ static resourceNotFound(uri) { return new _RequestError(-32002, `Resource not found${uri ? `: ${uri}` : ""}`, uri && { uri }); } toResult() { return { error: { code: this.code, message: this.message, data: this.data } }; } toErrorResponse() { return { code: this.code, message: this.message, data: this.data }; } }; // packages/cli/src/acp/fileSystemService.ts import os5 from "node:os"; import path9 from "node:path"; var AcpFileSystemService = class { constructor(connection, sessionId2, capabilities, fallback, root) { this.connection = connection; this.sessionId = sessionId2; this.capabilities = capabilities; this.fallback = fallback; this.root = root; } geminiDir = path9.join(os5.homedir(), ".gemini"); shouldUseFallback(filePath) { return !isWithinRoot(filePath, this.root) || isWithinRoot(filePath, this.geminiDir); } normalizeFileSystemError(err) { const errorMessage = err instanceof Error ? err.message : String(err); if (errorMessage.includes("Resource not found") || errorMessage.includes("ENOENT") || errorMessage.includes("does not exist") || errorMessage.includes("No such file")) { const newErr = new Error(errorMessage); newErr.code = "ENOENT"; throw newErr; } throw err; } async readTextFile(filePath) { if (!this.capabilities.readTextFile || this.shouldUseFallback(filePath)) { return this.fallback.readTextFile(filePath); } try { const response = await this.connection.readTextFile({ path: filePath, sessionId: this.sessionId }); return response.content; } catch (err) { this.normalizeFileSystemError(err); } } async writeTextFile(filePath, content) { if (!this.capabilities.writeTextFile || this.shouldUseFallback(filePath)) { return this.fallback.writeTextFile(filePath, content); } try { await this.connection.writeTextFile({ path: filePath, content, sessionId: this.sessionId }); } catch (err) { this.normalizeFileSystemError(err); } } }; // packages/cli/src/acp/acpErrors.ts function getAcpErrorMessage(error) { const coreMessage = getErrorMessage(error); return extractRecursiveMessage(coreMessage); } function extractRecursiveMessage(input) { const trimmed = input.trim(); if (trimmed.startsWith("{") && trimmed.endsWith("}") || trimmed.startsWith("[") && trimmed.endsWith("]")) { try { const parsed = JSON.parse(trimmed); const next = parsed?.error?.message || parsed?.[0]?.error?.message || parsed?.message; if (next && typeof next === "string" && next !== input) { return extractRecursiveMessage(next); } } catch { } } return input; } // packages/cli/src/acp/acpClient.ts import { Readable, Writable } from "node:stream"; import * as fs9 from "node:fs/promises"; import * as path12 from "node:path"; import { randomUUID } from "node:crypto"; // packages/cli/src/acp/commands/commandRegistry.ts var CommandRegistry = class { commands = /* @__PURE__ */ new Map(); register(command2) { if (this.commands.has(command2.name)) { debugLogger.warn(`Command ${command2.name} already registered. Skipping.`); return; } this.commands.set(command2.name, command2); for (const subCommand of command2.subCommands ?? []) { this.register(subCommand); } } get(commandName) { return this.commands.get(commandName); } getAllCommands() { return [...this.commands.values()]; } }; // packages/cli/src/acp/commands/memory.ts var DEFAULT_SANITIZATION_CONFIG = { allowedEnvironmentVariables: [], blockedEnvironmentVariables: [], enableEnvironmentVariableRedaction: false }; var MemoryCommand = class { name = "memory"; description = "Manage memory."; subCommands = [ new ShowMemoryCommand(), new RefreshMemoryCommand(), new ListMemoryCommand(), new AddMemoryCommand() ]; requiresWorkspace = true; async execute(context, _) { return new ShowMemoryCommand().execute(context, _); } }; var ShowMemoryCommand = class { name = "memory show"; description = "Shows the current memory contents."; async execute(context, _) { const result = showMemory(context.agentContext.config); return { name: this.name, data: result.content }; } }; var RefreshMemoryCommand = class { name = "memory refresh"; aliases = ["memory reload"]; description = "Refreshes the memory from the source."; async execute(context, _) { const result = await refreshMemory(context.agentContext.config); return { name: this.name, data: result.content }; } }; var ListMemoryCommand = class { name = "memory list"; description = "Lists the paths of the GEMINI.md files in use."; async execute(context, _) { const result = listMemoryFiles(context.agentContext.config); return { name: this.name, data: result.content }; } }; var AddMemoryCommand = class { name = "memory add"; description = "Add content to the memory."; async execute(context, args) { const textToAdd = args.join(" ").trim(); const result = addMemory(textToAdd); if (result.type === "message") { return { name: this.name, data: result.content }; } const toolRegistry = context.agentContext.toolRegistry; const tool = toolRegistry.getTool(result.toolName); if (tool) { const abortController = new AbortController(); const signal = abortController.signal; await context.sendMessage(`Saving memory via ${result.toolName}...`); await tool.buildAndExecute(result.toolArgs, signal, void 0, { shellExecutionConfig: { sanitizationConfig: DEFAULT_SANITIZATION_CONFIG, sandboxManager: context.agentContext.sandboxManager } }); await refreshMemory(context.agentContext.config); return { name: this.name, data: `Added memory: "${textToAdd}"` }; } else { return { name: this.name, data: `Error: Tool ${result.toolName} not found.` }; } } }; // packages/cli/src/acp/commands/extensions.ts import { stat } from "node:fs/promises"; var ExtensionsCommand = class { name = "extensions"; description = "Manage extensions."; subCommands = [ new ListExtensionsCommand(), new ExploreExtensionsCommand(), new EnableExtensionCommand(), new DisableExtensionCommand(), new InstallExtensionCommand(), new LinkExtensionCommand(), new UninstallExtensionCommand(), new RestartExtensionCommand(), new UpdateExtensionCommand() ]; async execute(context, _) { return new ListExtensionsCommand().execute(context, _); } }; var ListExtensionsCommand = class { name = "extensions list"; description = "Lists all installed extensions."; async execute(context, _) { const extensions = listExtensions(context.agentContext.config); const data = extensions.length ? extensions : "No extensions installed."; return { name: this.name, data }; } }; var ExploreExtensionsCommand = class { name = "extensions explore"; description = "Explore available extensions."; async execute(_context, _) { const extensionsUrl = "https://geminicli.com/extensions/"; return { name: this.name, data: `View or install available extensions at ${extensionsUrl}` }; } }; function getEnableDisableContext(config, args, invocationName) { const extensionManager = config.getExtensionLoader(); if (!(extensionManager instanceof ExtensionManager)) { return { error: `Cannot ${invocationName} extensions in this environment.` }; } if (args.length === 0) { return { error: `Usage: /extensions ${invocationName} [--scope=]` }; } let scope = "User" /* User */; if (args.includes("--scope=workspace") || args.includes("workspace")) { scope = "Workspace" /* Workspace */; } else if (args.includes("--scope=session") || args.includes("session")) { scope = "Session" /* Session */; } const name = args.filter( (a) => !a.startsWith("--scope") && !["user", "workspace", "session"].includes(a) )[0]; let names = []; if (name === "--all") { let extensions = extensionManager.getExtensions(); if (invocationName === "enable") { extensions = extensions.filter((ext) => !ext.isActive); } if (invocationName === "disable") { extensions = extensions.filter((ext) => ext.isActive); } names = extensions.map((ext) => ext.name); } else if (name) { names = [name]; } else { return { error: "No extension name provided." }; } return { extensionManager, names, scope }; } var EnableExtensionCommand = class { name = "extensions enable"; description = "Enable an extension."; async execute(context, args) { const enableContext = getEnableDisableContext( context.agentContext.config, args, "enable" ); if ("error" in enableContext) { return { name: this.name, data: enableContext.error }; } const { names, scope, extensionManager } = enableContext; const output = []; for (const name of names) { try { await extensionManager.enableExtension(name, scope); output.push(`Extension "${name}" enabled for scope "${scope}".`); const extension = extensionManager.getExtensions().find((e) => e.name === name); if (extension?.mcpServers) { const mcpEnablementManager = McpServerEnablementManager.getInstance(); const mcpClientManager = context.agentContext.config.getMcpClientManager(); const enabledServers = await mcpEnablementManager.autoEnableServers( Object.keys(extension.mcpServers) ); if (mcpClientManager && enabledServers.length > 0) { const restartPromises = enabledServers.map( (serverName) => mcpClientManager.restartServer(serverName).catch((error) => { output.push( `Failed to restart MCP server '${serverName}': ${getErrorMessage(error)}` ); }) ); await Promise.all(restartPromises); output.push(`Re-enabled MCP servers: ${enabledServers.join(", ")}`); } } } catch (e) { output.push(`Failed to enable "${name}": ${getErrorMessage(e)}`); } } return { name: this.name, data: output.join("\n") || "No action taken." }; } }; var DisableExtensionCommand = class { name = "extensions disable"; description = "Disable an extension."; async execute(context, args) { const enableContext = getEnableDisableContext( context.agentContext.config, args, "disable" ); if ("error" in enableContext) { return { name: this.name, data: enableContext.error }; } const { names, scope, extensionManager } = enableContext; const output = []; for (const name of names) { try { await extensionManager.disableExtension(name, scope); output.push(`Extension "${name}" disabled for scope "${scope}".`); } catch (e) { output.push(`Failed to disable "${name}": ${getErrorMessage(e)}`); } } return { name: this.name, data: output.join("\n") || "No action taken." }; } }; var InstallExtensionCommand = class { name = "extensions install"; description = "Install an extension from a git repo or local path."; async execute(context, args) { const extensionLoader = context.agentContext.config.getExtensionLoader(); if (!(extensionLoader instanceof ExtensionManager)) { return { name: this.name, data: "Cannot install extensions in this environment." }; } const source = args.join(" ").trim(); if (!source) { return { name: this.name, data: `Usage: /extensions install ` }; } if (/[;&|`'"]/.test(source)) { return { name: this.name, data: `Invalid source: contains disallowed characters.` }; } try { const installMetadata = await inferInstallMetadata(source); const extension = await extensionLoader.installOrUpdateExtension(installMetadata); return { name: this.name, data: `Extension "${extension.name}" installed successfully.` }; } catch (error) { return { name: this.name, data: `Failed to install extension from "${source}": ${getErrorMessage(error)}` }; } } }; var LinkExtensionCommand = class { name = "extensions link"; description = "Link an extension from a local path."; async execute(context, args) { const extensionLoader = context.agentContext.config.getExtensionLoader(); if (!(extensionLoader instanceof ExtensionManager)) { return { name: this.name, data: "Cannot link extensions in this environment." }; } const sourceFilepath = args.join(" ").trim(); if (!sourceFilepath) { return { name: this.name, data: `Usage: /extensions link ` }; } try { await stat(sourceFilepath); } catch (_error) { return { name: this.name, data: `Invalid source: ${sourceFilepath}` }; } try { const extension = await extensionLoader.installOrUpdateExtension({ source: sourceFilepath, type: "link" }); return { name: this.name, data: `Extension "${extension.name}" linked successfully.` }; } catch (error) { return { name: this.name, data: `Failed to link extension: ${getErrorMessage(error)}` }; } } }; var UninstallExtensionCommand = class { name = "extensions uninstall"; description = "Uninstall an extension."; async execute(context, args) { const extensionLoader = context.agentContext.config.getExtensionLoader(); if (!(extensionLoader instanceof ExtensionManager)) { return { name: this.name, data: "Cannot uninstall extensions in this environment." }; } const all = args.includes("--all"); const names = args.filter((a) => !a.startsWith("--")).map((a) => a.trim()); if (!all && names.length === 0) { return { name: this.name, data: `Usage: /extensions uninstall |--all` }; } let namesToUninstall = []; if (all) { namesToUninstall = extensionLoader.getExtensions().map((ext) => ext.name); } else { namesToUninstall = names; } if (namesToUninstall.length === 0) { return { name: this.name, data: all ? "No extensions installed." : "No extension name provided." }; } const output = []; for (const extensionName of namesToUninstall) { try { await extensionLoader.uninstallExtension(extensionName, false); output.push(`Extension "${extensionName}" uninstalled successfully.`); } catch (error) { output.push( `Failed to uninstall extension "${extensionName}": ${getErrorMessage(error)}` ); } } return { name: this.name, data: output.join("\n") }; } }; var RestartExtensionCommand = class { name = "extensions restart"; description = "Restart an extension."; async execute(context, args) { const extensionLoader = context.agentContext.config.getExtensionLoader(); if (!(extensionLoader instanceof ExtensionManager)) { return { name: this.name, data: "Cannot restart extensions." }; } const all = args.includes("--all"); const names = all ? null : args.filter((a) => !!a); if (!all && names?.length === 0) { return { name: this.name, data: "Usage: /extensions restart |--all" }; } let extensionsToRestart = extensionLoader.getExtensions().filter((e) => e.isActive); if (names) { extensionsToRestart = extensionsToRestart.filter( (e) => names.includes(e.name) ); } if (extensionsToRestart.length === 0) { return { name: this.name, data: "No active extensions matched the request." }; } const output = []; for (const extension of extensionsToRestart) { try { await extensionLoader.restartExtension(extension); output.push(`Restarted "${extension.name}".`); } catch (e) { output.push( `Failed to restart "${extension.name}": ${getErrorMessage(e)}` ); } } return { name: this.name, data: output.join("\n") }; } }; var UpdateExtensionCommand = class { name = "extensions update"; description = "Update an extension."; async execute(context, args) { const extensionLoader = context.agentContext.config.getExtensionLoader(); if (!(extensionLoader instanceof ExtensionManager)) { return { name: this.name, data: "Cannot update extensions." }; } const all = args.includes("--all"); const names = all ? null : args.filter((a) => !!a); if (!all && names?.length === 0) { return { name: this.name, data: "Usage: /extensions update |--all" }; } return { name: this.name, data: "Headless extension updating requires internal UI dispatches. Please use `gemini extensions update` directly in the terminal." }; } }; // packages/cli/src/acp/commands/init.ts import * as fs7 from "node:fs"; import * as path10 from "node:path"; var InitCommand = class { name = "init"; description = "Analyzes the project and creates a tailored GEMINI.md file"; requiresWorkspace = true; async execute(context, _args = []) { const targetDir = context.agentContext.config.getTargetDir(); if (!targetDir) { throw new Error("Command requires a workspace."); } const geminiMdPath = path10.join(targetDir, "GEMINI.md"); const result = performInit(fs7.existsSync(geminiMdPath)); switch (result.type) { case "message": return { name: this.name, data: result }; case "submit_prompt": fs7.writeFileSync(geminiMdPath, "", "utf8"); if (typeof result.content !== "string") { throw new Error("Init command content must be a string."); } return { name: this.name, data: { type: "message", messageType: "info", content: `A template GEMINI.md has been created at ${geminiMdPath}. To populate it with project context, you can run the following prompt in a new chat: ${result.content}` } }; default: throw new Error("Unknown result type from performInit"); } } }; // packages/cli/src/acp/commands/restore.ts import * as fs8 from "node:fs/promises"; import * as path11 from "node:path"; var RestoreCommand = class { name = "restore"; description = "Restore to a previous checkpoint, or list available checkpoints to restore. This will reset the conversation and file history to the state it was in when the checkpoint was created"; requiresWorkspace = true; subCommands = [new ListCheckpointsCommand()]; async execute(context, args) { const { agentContext, git: gitService } = context; const { config } = agentContext; const argsStr = args.join(" "); try { if (!argsStr) { return await new ListCheckpointsCommand().execute(context); } if (!config.getCheckpointingEnabled()) { return { name: this.name, data: "Checkpointing is not enabled. Please enable it in your settings (`general.checkpointing.enabled: true`) to use /restore." }; } const selectedFile = argsStr.endsWith(".json") ? argsStr : `${argsStr}.json`; const checkpointDir = config.storage.getProjectTempCheckpointsDir(); const filePath = path11.join(checkpointDir, selectedFile); let data; try { data = await fs8.readFile(filePath, "utf-8"); } catch (error) { if (isNodeError(error) && error.code === "ENOENT") { return { name: this.name, data: `File not found: ${selectedFile}` }; } throw error; } const toolCallData = JSON.parse(data); const ToolCallDataSchema = getToolCallDataSchema(); const parseResult = ToolCallDataSchema.safeParse(toolCallData); if (!parseResult.success) { return { name: this.name, data: "Checkpoint file is invalid or corrupted." }; } const restoreResultGenerator = performRestore( parseResult.data, gitService ); const restoreResult = []; for await (const result of restoreResultGenerator) { restoreResult.push(result); } const formattedResult = restoreResult.map((r) => { if (r.type === "message") { return `[${r.messageType.toUpperCase()}] ${r.content}`; } else if (r.type === "load_history") { return `Loaded history with ${r.clientHistory.length} messages.`; } return `Restored: ${JSON.stringify(r)}`; }).join("\n"); return { name: this.name, data: formattedResult }; } catch (error) { return { name: this.name, data: `An unexpected error occurred during restore: ${error}` }; } } }; var ListCheckpointsCommand = class { name = "restore list"; description = "Lists all available checkpoints."; async execute(context) { const { config } = context.agentContext; try { if (!config.getCheckpointingEnabled()) { return { name: this.name, data: "Checkpointing is not enabled. Please enable it in your settings (`general.checkpointing.enabled: true`) to use /restore." }; } const checkpointDir = config.storage.getProjectTempCheckpointsDir(); try { await fs8.mkdir(checkpointDir, { recursive: true }); } catch (_e) { } const files = await fs8.readdir(checkpointDir); const jsonFiles = files.filter((file) => file.endsWith(".json")); if (jsonFiles.length === 0) { return { name: this.name, data: "No checkpoints found." }; } const checkpointFiles = /* @__PURE__ */ new Map(); for (const file of jsonFiles) { const filePath = path11.join(checkpointDir, file); const data = await fs8.readFile(filePath, "utf-8"); checkpointFiles.set(file, data); } const checkpointInfoList = getCheckpointInfoList(checkpointFiles); const formatted = checkpointInfoList.map((info) => { const i = info; const fileName = String(i["fileName"] || "Unknown"); const toolName = String(i["toolName"] || "Unknown"); const status = String(i["status"] || "Unknown"); const timestamp = new Date( Number(i["timestamp"]) || 0 ).toLocaleString(); return `- **${fileName}**: ${toolName} (Status: ${status}) [${timestamp}]`; }).join("\n"); return { name: this.name, data: `Available Checkpoints: ${formatted}` }; } catch (_error) { return { name: this.name, data: "An unexpected error occurred while listing checkpoints." }; } } }; // packages/cli/src/acp/commandHandler.ts var CommandHandler = class _CommandHandler { registry; constructor() { this.registry = _CommandHandler.createRegistry(); } static createRegistry() { const registry = new CommandRegistry(); registry.register(new MemoryCommand()); registry.register(new ExtensionsCommand()); registry.register(new InitCommand()); registry.register(new RestoreCommand()); return registry; } getAvailableCommands() { return this.registry.getAllCommands().map((cmd) => ({ name: cmd.name, description: cmd.description })); } /** * Parses and executes a command string if it matches a registered command. * Returns true if a command was handled, false otherwise. */ async handleCommand(commandText, context) { const { commandToExecute, args } = this.parseSlashCommand(commandText); if (commandToExecute) { await this.runCommand(commandToExecute, args, context); return true; } return false; } async runCommand(commandToExecute, args, context) { try { const result = await commandToExecute.execute( context, args ? args.split(/\s+/) : [] ); let messageContent = ""; if (typeof result.data === "string") { messageContent = result.data; } else if (typeof result.data === "object" && result.data !== null && "content" in result.data) { messageContent = result.data["content"]; } else { messageContent = JSON.stringify(result.data, null, 2); } await context.sendMessage(messageContent); } catch (error) { const errorMessage = error instanceof Error ? error.message : String(error); await context.sendMessage(`Error: ${errorMessage}`); } } /** * Parses a raw slash command string into its matching headless command and arguments. * Mirrors `packages/cli/src/utils/commands.ts` logic. */ parseSlashCommand(query) { const trimmed = query.trim(); const parts = trimmed.substring(1).trim().split(/\s+/); const commandPath = parts.filter((p) => p); let currentCommands = this.registry.getAllCommands(); let commandToExecute; let pathIndex = 0; for (const part of commandPath) { const foundCommand = currentCommands.find((cmd) => { const expectedName = commandPath.slice(0, pathIndex + 1).join(" "); return cmd.name === part || cmd.name === expectedName || cmd.aliases?.includes(part) || cmd.aliases?.includes(expectedName); }); if (foundCommand) { commandToExecute = foundCommand; pathIndex++; if (foundCommand.subCommands) { currentCommands = foundCommand.subCommands; } else { break; } } else { break; } } const args = parts.slice(pathIndex).join(" "); return { commandToExecute, args }; } }; // packages/cli/src/acp/acpClient.ts function hasMeta(obj) { return typeof obj === "object" && obj !== null && "_meta" in obj; } async function runAcpClient(config, settings, argv) { const { stdout: workingStdout } = createWorkingStdio(); const stdout = Writable.toWeb(workingStdout); const stdin = Readable.toWeb(process.stdin); const stream = ndJsonStream(stdout, stdin); const connection = new AgentSideConnection( (connection2) => new GeminiAgent(config, settings, argv, connection2), stream ); await connection.closed.finally(runExitCleanup); } var GeminiAgent = class _GeminiAgent { constructor(context, settings, argv, connection) { this.context = context; this.settings = settings; this.argv = argv; this.connection = connection; } static callIdCounter = 0; static generateCallId(name) { return `${name}-${Date.now()}-${++_GeminiAgent.callIdCounter}`; } sessions = /* @__PURE__ */ new Map(); clientCapabilities; apiKey; baseUrl; customHeaders; async initialize(args) { this.clientCapabilities = args.clientCapabilities; const authMethods = [ { id: AuthType.LOGIN_WITH_GOOGLE, name: "Log in with Google", description: "Log in with your Google account" }, { id: AuthType.USE_GEMINI, name: "Gemini API key", description: "Use an API key with Gemini Developer API", _meta: { "api-key": { provider: "google" } } }, { id: AuthType.USE_VERTEX_AI, name: "Vertex AI", description: "Use an API key with Vertex AI GenAI API" }, { id: AuthType.GATEWAY, name: "AI API Gateway", description: "Use a custom AI API Gateway", _meta: { gateway: { protocol: "google", restartRequired: "false" } } } ]; await this.context.config.initialize(); const version = await getVersion(); return { protocolVersion: PROTOCOL_VERSION, authMethods, agentInfo: { name: "gemini-cli", title: "Gemini CLI", version }, agentCapabilities: { loadSession: true, promptCapabilities: { image: true, audio: true, embeddedContext: true }, mcpCapabilities: { http: true, sse: true } } }; } async authenticate(req) { const { methodId } = req; const method = external_exports.nativeEnum(AuthType).parse(methodId); const selectedAuthType = this.settings.merged.security.auth.selectedType; if (selectedAuthType && selectedAuthType !== method) { await clearCachedCredentialFile(); } const meta = hasMeta(req) ? req._meta : void 0; const apiKey = typeof meta?.["api-key"] === "string" ? meta["api-key"] : void 0; try { if (apiKey) { this.apiKey = apiKey; } const gatewaySchema = external_exports.object({ baseUrl: external_exports.string().optional(), headers: external_exports.record(external_exports.string()).optional() }); let baseUrl; let headers; if (meta?.["gateway"]) { const result = gatewaySchema.safeParse(meta["gateway"]); if (result.success) { baseUrl = result.data.baseUrl; headers = result.data.headers; } else { throw new RequestError( -32602, `Malformed gateway payload: ${result.error.message}` ); } } this.baseUrl = baseUrl; this.customHeaders = headers; await this.context.config.refreshAuth( method, apiKey ?? this.apiKey, baseUrl, headers ); } catch (e) { throw new RequestError(-32e3, getAcpErrorMessage(e)); } this.settings.setValue( "User" /* User */, "security.auth.selectedType", method ); } async newSession({ cwd, mcpServers }) { const sessionId2 = randomUUID(); const loadedSettings = loadSettings(cwd); const config = await this.newSessionConfig( sessionId2, cwd, mcpServers, loadedSettings ); const authType = loadedSettings.merged.security.auth.selectedType || AuthType.USE_GEMINI; let isAuthenticated = false; let authErrorMessage = ""; try { await config.refreshAuth( authType, this.apiKey, this.baseUrl, this.customHeaders ); isAuthenticated = true; const contentGeneratorConfig = config.getContentGeneratorConfig(); if (authType === AuthType.USE_GEMINI && (!contentGeneratorConfig || !contentGeneratorConfig.apiKey)) { isAuthenticated = false; authErrorMessage = "Gemini API key is missing or not configured."; } } catch (e) { isAuthenticated = false; authErrorMessage = getAcpErrorMessage(e); debugLogger.error( `Authentication failed: ${e instanceof Error ? e.stack : e}` ); } if (!isAuthenticated) { throw new RequestError( -32e3, authErrorMessage || "Authentication required." ); } if (this.clientCapabilities?.fs) { const acpFileSystemService = new AcpFileSystemService( this.connection, sessionId2, this.clientCapabilities.fs, config.getFileSystemService(), cwd ); config.setFileSystemService(acpFileSystemService); } await config.initialize(); startupProfiler.flush(config); const geminiClient = config.getGeminiClient(); const chat = await geminiClient.startChat(); const session = new Session( sessionId2, chat, config, this.connection, this.settings ); this.sessions.set(sessionId2, session); setTimeout(() => { session.sendAvailableCommands(); }, 0); const { availableModels, currentModelId } = buildAvailableModels( config, loadedSettings ); const response = { sessionId: sessionId2, modes: { availableModes: buildAvailableModes(config.isPlanEnabled()), currentModeId: config.getApprovalMode() }, models: { availableModels, currentModelId } }; return response; } async loadSession({ sessionId: sessionId2, cwd, mcpServers }) { const config = await this.initializeSessionConfig( sessionId2, cwd, mcpServers ); const sessionSelector = new SessionSelector(config); const { sessionData, sessionPath } = await sessionSelector.resolveSession(sessionId2); const clientHistory = convertSessionToClientHistory(sessionData.messages); const geminiClient = config.getGeminiClient(); await geminiClient.initialize(); await geminiClient.resumeChat(clientHistory, { conversation: sessionData, filePath: sessionPath }); const session = new Session( sessionId2, geminiClient.getChat(), config, this.connection, this.settings ); this.sessions.set(sessionId2, session); session.streamHistory(sessionData.messages); setTimeout(() => { session.sendAvailableCommands(); }, 0); const { availableModels, currentModelId } = buildAvailableModels( config, this.settings ); const response = { modes: { availableModes: buildAvailableModes(config.isPlanEnabled()), currentModeId: config.getApprovalMode() }, models: { availableModels, currentModelId } }; return response; } async initializeSessionConfig(sessionId2, cwd, mcpServers) { const selectedAuthType = this.settings.merged.security.auth.selectedType; if (!selectedAuthType) { throw RequestError.authRequired(); } const config = await this.newSessionConfig(sessionId2, cwd, mcpServers); try { await config.refreshAuth( selectedAuthType, this.apiKey, this.baseUrl, this.customHeaders ); } catch (e) { debugLogger.error(`Authentication failed: ${e}`); throw RequestError.authRequired(); } if (this.clientCapabilities?.fs) { const acpFileSystemService = new AcpFileSystemService( this.connection, sessionId2, this.clientCapabilities.fs, config.getFileSystemService(), cwd ); config.setFileSystemService(acpFileSystemService); } await config.initialize(); startupProfiler.flush(config); return config; } async newSessionConfig(sessionId2, cwd, mcpServers, loadedSettings) { const currentSettings = loadedSettings || this.settings; const mergedMcpServers = { ...currentSettings.merged.mcpServers }; for (const server of mcpServers) { if ("type" in server && (server.type === "sse" || server.type === "http")) { const headers = Object.fromEntries( server.headers.map(({ name, value }) => [name, value]) ); mergedMcpServers[server.name] = new MCPServerConfig( void 0, // command void 0, // args void 0, // env void 0, // cwd server.type === "sse" ? server.url : void 0, // url (sse) server.type === "http" ? server.url : void 0, // httpUrl headers ); } else if ("command" in server) { const env2 = {}; for (const { name: envName, value } of server.env) { env2[envName] = value; } mergedMcpServers[server.name] = new MCPServerConfig( server.command, server.args, env2, cwd ); } } const settings = { ...currentSettings.merged, mcpServers: mergedMcpServers }; const config = await loadCliConfig(settings, sessionId2, this.argv, { cwd }); return config; } async cancel(params) { const session = this.sessions.get(params.sessionId); if (!session) { throw new Error(`Session not found: ${params.sessionId}`); } await session.cancelPendingPrompt(); } async prompt(params) { const session = this.sessions.get(params.sessionId); if (!session) { throw new Error(`Session not found: ${params.sessionId}`); } return session.prompt(params); } async setSessionMode(params) { const session = this.sessions.get(params.sessionId); if (!session) { throw new Error(`Session not found: ${params.sessionId}`); } return session.setMode(params.modeId); } async unstable_setSessionModel(params) { const session = this.sessions.get(params.sessionId); if (!session) { throw new Error(`Session not found: ${params.sessionId}`); } return session.setModel(params.modelId); } }; var Session = class { constructor(id, chat, context, connection, settings) { this.id = id; this.chat = chat; this.context = context; this.connection = connection; this.settings = settings; } pendingPrompt = null; commandHandler = new CommandHandler(); async cancelPendingPrompt() { if (!this.pendingPrompt) { throw new Error("Not currently generating"); } this.pendingPrompt.abort(); this.pendingPrompt = null; } setMode(modeId) { const availableModes = buildAvailableModes( this.context.config.isPlanEnabled() ); const mode = availableModes.find((m) => m.id === modeId); if (!mode) { throw new Error(`Invalid or unavailable mode: ${modeId}`); } this.context.config.setApprovalMode(mode.id); return {}; } getAvailableCommands() { return this.commandHandler.getAvailableCommands(); } async sendAvailableCommands() { const availableCommands = this.getAvailableCommands().map((command2) => ({ name: command2.name, description: command2.description })); await this.sendUpdate({ sessionUpdate: "available_commands_update", availableCommands }); } setModel(modelId) { this.context.config.setModel(modelId); return {}; } async streamHistory(messages) { for (const msg of messages) { const contentString = partListUnionToString(msg.content); if (msg.type === "user") { if (contentString.trim()) { await this.sendUpdate({ sessionUpdate: "user_message_chunk", content: { type: "text", text: contentString } }); } } else if (msg.type === "gemini") { if (msg.thoughts) { for (const thought of msg.thoughts) { const thoughtText = `**${thought.subject}** ${thought.description}`; await this.sendUpdate({ sessionUpdate: "agent_thought_chunk", content: { type: "text", text: thoughtText } }); } } if (contentString.trim()) { await this.sendUpdate({ sessionUpdate: "agent_message_chunk", content: { type: "text", text: contentString } }); } if (msg.toolCalls) { for (const toolCall of msg.toolCalls) { const toolCallContent = []; if (toolCall.resultDisplay) { if (typeof toolCall.resultDisplay === "string") { toolCallContent.push({ type: "content", content: { type: "text", text: toolCall.resultDisplay } }); } else if ("fileName" in toolCall.resultDisplay) { toolCallContent.push({ type: "diff", path: toolCall.resultDisplay.fileName, oldText: toolCall.resultDisplay.originalContent, newText: toolCall.resultDisplay.newContent }); } } const tool = this.context.toolRegistry.getTool(toolCall.name); await this.sendUpdate({ sessionUpdate: "tool_call", toolCallId: toolCall.id, status: toolCall.status === CoreToolCallStatus.Success ? "completed" : "failed", title: toolCall.displayName || toolCall.name, content: toolCallContent, kind: tool ? toAcpToolKind(tool.kind) : "other" }); } } } } } async prompt(params) { this.pendingPrompt?.abort(); const pendingSend = new AbortController(); this.pendingPrompt = pendingSend; await this.context.config.waitForMcpInit(); const promptId = Math.random().toString(16).slice(2); const chat = this.chat; const parts = await this.#resolvePrompt(params.prompt, pendingSend.signal); let commandText = ""; for (const part of parts) { if (typeof part === "object" && part !== null) { if ("text" in part) { const text = part.text; if (typeof text === "string") { commandText += text; } } else { break; } } } commandText = commandText.trim(); if (commandText && (commandText.startsWith("/") || commandText.startsWith("$"))) { const handled = await this.handleCommand(commandText, parts); if (handled) { return { stopReason: "end_turn", _meta: { quota: { token_count: { input_tokens: 0, output_tokens: 0 }, model_usage: [] } } }; } } let totalInputTokens = 0; let totalOutputTokens = 0; const modelUsageMap = /* @__PURE__ */ new Map(); let nextMessage = { role: "user", parts }; while (nextMessage !== null) { if (pendingSend.signal.aborted) { chat.addHistory(nextMessage); return { stopReason: CoreToolCallStatus.Cancelled }; } const functionCalls = []; try { const model = resolveModel( this.context.config.getModel(), await this.context.config.getGemini31Launched?.() ?? false ); const responseStream = await chat.sendMessageStream( { model }, nextMessage?.parts ?? [], promptId, pendingSend.signal, LlmRole.MAIN ); nextMessage = null; let turnInputTokens = 0; let turnOutputTokens = 0; let turnModelId = model; for await (const resp of responseStream) { if (pendingSend.signal.aborted) { return { stopReason: CoreToolCallStatus.Cancelled }; } if (resp.type === StreamEventType.CHUNK && resp.value.usageMetadata) { turnInputTokens = resp.value.usageMetadata.promptTokenCount ?? turnInputTokens; turnOutputTokens = resp.value.usageMetadata.candidatesTokenCount ?? turnOutputTokens; if (resp.value.modelVersion) { turnModelId = resp.value.modelVersion; } } if (resp.type === StreamEventType.CHUNK && resp.value.candidates && resp.value.candidates.length > 0) { const candidate = resp.value.candidates[0]; for (const part of candidate.content?.parts ?? []) { if (!part.text) { continue; } const content = { type: "text", text: part.text }; this.sendUpdate({ sessionUpdate: part.thought ? "agent_thought_chunk" : "agent_message_chunk", content }); } } if (resp.type === StreamEventType.CHUNK && resp.value.functionCalls) { functionCalls.push(...resp.value.functionCalls); } } totalInputTokens += turnInputTokens; totalOutputTokens += turnOutputTokens; if (turnInputTokens > 0 || turnOutputTokens > 0) { const existing = modelUsageMap.get(turnModelId) ?? { input: 0, output: 0 }; existing.input += turnInputTokens; existing.output += turnOutputTokens; modelUsageMap.set(turnModelId, existing); } if (pendingSend.signal.aborted) { return { stopReason: CoreToolCallStatus.Cancelled }; } } catch (error) { if (getErrorStatus(error) === 429) { throw new RequestError( 429, "Rate limit exceeded. Try again later." ); } if (pendingSend.signal.aborted || error instanceof Error && error.name === "AbortError") { return { stopReason: CoreToolCallStatus.Cancelled }; } throw new RequestError( getErrorStatus(error) || 500, getAcpErrorMessage(error) ); } if (functionCalls.length > 0) { const toolResponseParts = []; for (const fc of functionCalls) { const response = await this.runTool(pendingSend.signal, promptId, fc); toolResponseParts.push(...response); } nextMessage = { role: "user", parts: toolResponseParts }; } } const modelUsageArray = Array.from(modelUsageMap.entries()).map( ([modelName, counts]) => ({ model: modelName, token_count: { input_tokens: counts.input, output_tokens: counts.output } }) ); return { stopReason: "end_turn", _meta: { quota: { token_count: { input_tokens: totalInputTokens, output_tokens: totalOutputTokens }, model_usage: modelUsageArray } } }; } async handleCommand(commandText, parts) { const gitService = await this.context.config.getGitService(); const commandContext = { agentContext: this.context, settings: this.settings, git: gitService, sendMessage: async (text) => { await this.sendUpdate({ sessionUpdate: "agent_message_chunk", content: { type: "text", text } }); } }; return this.commandHandler.handleCommand(commandText, commandContext); } async sendUpdate(update) { const params = { sessionId: this.id, update }; await this.connection.sessionUpdate(params); } async runTool(abortSignal, promptId, fc) { const callId = fc.id ?? GeminiAgent.generateCallId(fc.name || "unknown"); const args = fc.args ?? {}; const startTime = Date.now(); const errorResponse = (error) => { const durationMs = Date.now() - startTime; logToolCall( this.context.config, new ToolCallEvent( void 0, fc.name ?? "", args, durationMs, false, promptId, typeof tool !== "undefined" && tool instanceof DiscoveredMCPTool ? "mcp" : "native", error.message ) ); return [ { functionResponse: { id: callId, name: fc.name ?? "", response: { error: error.message } } } ]; }; if (!fc.name) { return errorResponse(new Error("Missing function name")); } const toolRegistry = this.context.toolRegistry; const tool = toolRegistry.getTool(fc.name); if (!tool) { return errorResponse( new Error(`Tool "${fc.name}" not found in registry.`) ); } try { const invocation = tool.build(args); const displayTitle = typeof invocation.getDisplayTitle === "function" ? invocation.getDisplayTitle() : invocation.getDescription(); const explanation = typeof invocation.getExplanation === "function" ? invocation.getExplanation() : ""; if (explanation) { await this.sendUpdate({ sessionUpdate: "agent_thought_chunk", content: { type: "text", text: explanation } }); } const confirmationDetails = await invocation.shouldConfirmExecute(abortSignal); if (confirmationDetails) { const content2 = []; if (confirmationDetails.type === "edit") { content2.push({ type: "diff", path: confirmationDetails.filePath, oldText: confirmationDetails.originalContent, newText: confirmationDetails.newContent, _meta: { kind: !confirmationDetails.originalContent ? "add" : confirmationDetails.newContent === "" ? "delete" : "modify" } }); } const params = { sessionId: this.id, options: toPermissionOptions( confirmationDetails, this.context.config ), toolCall: { toolCallId: callId, status: "pending", title: displayTitle, content: content2, locations: invocation.toolLocations(), kind: toAcpToolKind(tool.kind) } }; const output = await this.connection.requestPermission(params); const outcome = output.outcome.outcome === CoreToolCallStatus.Cancelled ? ToolConfirmationOutcome.Cancel : external_exports.nativeEnum(ToolConfirmationOutcome).parse(output.outcome.optionId); await confirmationDetails.onConfirm(outcome); switch (outcome) { case ToolConfirmationOutcome.Cancel: return errorResponse( new Error(`Tool "${fc.name}" was canceled by the user.`) ); case ToolConfirmationOutcome.ProceedOnce: case ToolConfirmationOutcome.ProceedAlways: case ToolConfirmationOutcome.ProceedAlwaysAndSave: case ToolConfirmationOutcome.ProceedAlwaysServer: case ToolConfirmationOutcome.ProceedAlwaysTool: case ToolConfirmationOutcome.ModifyWithEditor: break; default: { const resultOutcome = outcome; throw new Error(`Unexpected: ${resultOutcome}`); } } } else { const content2 = []; await this.sendUpdate({ sessionUpdate: "tool_call", toolCallId: callId, status: "in_progress", title: displayTitle, content: content2, locations: invocation.toolLocations(), kind: toAcpToolKind(tool.kind) }); } const toolResult = await invocation.execute(abortSignal); const content = toToolCallContent(toolResult); const updateContent = content ? [content] : []; await this.sendUpdate({ sessionUpdate: "tool_call_update", toolCallId: callId, status: "completed", title: displayTitle, content: updateContent, locations: invocation.toolLocations(), kind: toAcpToolKind(tool.kind) }); const durationMs = Date.now() - startTime; logToolCall( this.context.config, new ToolCallEvent( void 0, fc.name ?? "", args, durationMs, true, promptId, typeof tool !== "undefined" && tool instanceof DiscoveredMCPTool ? "mcp" : "native" ) ); this.chat.recordCompletedToolCalls(this.context.config.getActiveModel(), [ { status: CoreToolCallStatus.Success, request: { callId, name: fc.name, args, isClientInitiated: false, prompt_id: promptId }, tool, invocation, response: { callId, responseParts: convertToFunctionResponse( fc.name, callId, toolResult.llmContent, this.context.config.getActiveModel(), this.context.config ), resultDisplay: toolResult.returnDisplay, error: void 0, errorType: void 0 } } ]); return convertToFunctionResponse( fc.name, callId, toolResult.llmContent, this.context.config.getActiveModel(), this.context.config ); } catch (e) { const error = e instanceof Error ? e : new Error(String(e)); await this.sendUpdate({ sessionUpdate: "tool_call_update", toolCallId: callId, status: "failed", content: [ { type: "content", content: { type: "text", text: error.message } } ], kind: toAcpToolKind(tool.kind) }); this.chat.recordCompletedToolCalls(this.context.config.getActiveModel(), [ { status: CoreToolCallStatus.Error, request: { callId, name: fc.name, args, isClientInitiated: false, prompt_id: promptId }, tool, response: { callId, responseParts: [ { functionResponse: { id: callId, name: fc.name ?? "", response: { error: error.message } } } ], resultDisplay: error.message, error, errorType: void 0 } } ]); return errorResponse(error); } } async #resolvePrompt(message, abortSignal) { const FILE_URI_SCHEME = "file://"; const embeddedContext = []; const parts = message.map((part) => { switch (part.type) { case "text": return { text: part.text }; case "image": case "audio": return { inlineData: { mimeType: part.mimeType, data: part.data } }; case "resource_link": { if (part.uri.startsWith(FILE_URI_SCHEME)) { return { fileData: { mimeData: part.mimeType, name: part.name, fileUri: part.uri.slice(FILE_URI_SCHEME.length) } }; } else { return { text: `@${part.uri}` }; } } case "resource": { embeddedContext.push(part.resource); return { text: `@${part.resource.uri}` }; } default: { const unreachable = part; throw new Error(`Unexpected chunk type: '${unreachable}'`); } } }); const atPathCommandParts = parts.filter((part) => "fileData" in part); if (atPathCommandParts.length === 0 && embeddedContext.length === 0) { return parts; } const atPathToResolvedSpecMap = /* @__PURE__ */ new Map(); const fileDiscovery = this.context.config.getFileService(); const fileFilteringOptions = this.context.config.getFileFilteringOptions(); const pathSpecsToRead = []; const contentLabelsForDisplay = []; const ignoredPaths = []; const toolRegistry = this.context.toolRegistry; const readManyFilesTool = new ReadManyFilesTool( this.context.config, this.context.messageBus ); const globTool = toolRegistry.getTool("glob"); if (!readManyFilesTool) { throw new Error("Error: read_many_files tool not found."); } for (const atPathPart of atPathCommandParts) { const pathName = atPathPart.fileData.fileUri; if (fileDiscovery.shouldIgnoreFile(pathName, fileFilteringOptions)) { ignoredPaths.push(pathName); debugLogger.warn(`Path ${pathName} is ignored and will be skipped.`); continue; } let currentPathSpec = pathName; let resolvedSuccessfully = false; try { const absolutePath = path12.resolve( this.context.config.getTargetDir(), pathName ); if (isWithinRoot(absolutePath, this.context.config.getTargetDir())) { const stats = await fs9.stat(absolutePath); if (stats.isDirectory()) { currentPathSpec = pathName.endsWith("/") ? `${pathName}**` : `${pathName}/**`; this.debug( `Path ${pathName} resolved to directory, using glob: ${currentPathSpec}` ); } else { this.debug(`Path ${pathName} resolved to file: ${currentPathSpec}`); } resolvedSuccessfully = true; } else { this.debug( `Path ${pathName} is outside the project directory. Skipping.` ); } } catch (error) { if (isNodeError(error) && error.code === "ENOENT") { if (this.context.config.getEnableRecursiveFileSearch() && globTool) { this.debug( `Path ${pathName} not found directly, attempting glob search.` ); try { const globResult = await globTool.buildAndExecute( { pattern: `**/*${pathName}*`, path: this.context.config.getTargetDir() }, abortSignal ); if (globResult.llmContent && typeof globResult.llmContent === "string" && !globResult.llmContent.startsWith("No files found") && !globResult.llmContent.startsWith("Error:")) { const lines = globResult.llmContent.split("\n"); if (lines.length > 1 && lines[1]) { const firstMatchAbsolute = lines[1].trim(); currentPathSpec = path12.relative( this.context.config.getTargetDir(), firstMatchAbsolute ); this.debug( `Glob search for ${pathName} found ${firstMatchAbsolute}, using relative path: ${currentPathSpec}` ); resolvedSuccessfully = true; } else { this.debug( `Glob search for '**/*${pathName}*' did not return a usable path. Path ${pathName} will be skipped.` ); } } else { this.debug( `Glob search for '**/*${pathName}*' found no files or an error. Path ${pathName} will be skipped.` ); } } catch (globError) { debugLogger.error( `Error during glob search for ${pathName}: ${getErrorMessage(globError)}` ); } } else { this.debug( `Glob tool not found. Path ${pathName} will be skipped.` ); } } else { debugLogger.error( `Error stating path ${pathName}. Path ${pathName} will be skipped.` ); } } if (resolvedSuccessfully) { pathSpecsToRead.push(currentPathSpec); atPathToResolvedSpecMap.set(pathName, currentPathSpec); contentLabelsForDisplay.push(pathName); } } let initialQueryText = ""; for (let i = 0; i < parts.length; i++) { const chunk = parts[i]; if ("text" in chunk) { initialQueryText += chunk.text; } else { const resolvedSpec = chunk.fileData && atPathToResolvedSpecMap.get(chunk.fileData.fileUri); if (i > 0 && initialQueryText.length > 0 && !initialQueryText.endsWith(" ") && resolvedSpec) { const prevPart = parts[i - 1]; if ("text" in prevPart || "fileData" in prevPart && atPathToResolvedSpecMap.has(prevPart.fileData.fileUri)) { initialQueryText += " "; } } if (resolvedSpec) { initialQueryText += `@${resolvedSpec}`; } else { if (i > 0 && initialQueryText.length > 0 && !initialQueryText.endsWith(" ") && !chunk.fileData?.fileUri.startsWith(" ")) { initialQueryText += " "; } if (chunk.fileData?.fileUri) { initialQueryText += `@${chunk.fileData.fileUri}`; } } } } initialQueryText = initialQueryText.trim(); if (ignoredPaths.length > 0) { this.debug( `Ignored ${ignoredPaths.length} files: ${ignoredPaths.join(", ")}` ); } const processedQueryParts = [{ text: initialQueryText }]; if (pathSpecsToRead.length === 0 && embeddedContext.length === 0) { debugLogger.warn("No valid file paths found in @ commands to read."); return [{ text: initialQueryText }]; } if (pathSpecsToRead.length > 0) { const toolArgs = { include: pathSpecsToRead }; const callId = GeminiAgent.generateCallId(readManyFilesTool.name); try { const invocation = readManyFilesTool.build(toolArgs); await this.sendUpdate({ sessionUpdate: "tool_call", toolCallId: callId, status: "in_progress", title: invocation.getDescription(), content: [], locations: invocation.toolLocations(), kind: toAcpToolKind(readManyFilesTool.kind) }); const result = await invocation.execute(abortSignal); const content = toToolCallContent(result) || { type: "content", content: { type: "text", text: `Successfully read: ${contentLabelsForDisplay.join(", ")}` } }; await this.sendUpdate({ sessionUpdate: "tool_call_update", toolCallId: callId, status: "completed", title: invocation.getDescription(), content: content ? [content] : [], locations: invocation.toolLocations(), kind: toAcpToolKind(readManyFilesTool.kind) }); if (Array.isArray(result.llmContent)) { const fileContentRegex = /^--- (.*?) ---\n\n([\s\S]*?)\n\n$/; processedQueryParts.push({ text: ` ${REFERENCE_CONTENT_START}` }); for (const part of result.llmContent) { if (typeof part === "string") { const match = fileContentRegex.exec(part); if (match) { const filePathSpecInContent = match[1]; const fileActualContent = match[2].trim(); processedQueryParts.push({ text: ` Content from @${filePathSpecInContent}: ` }); processedQueryParts.push({ text: fileActualContent }); } else { processedQueryParts.push({ text: part }); } } else { processedQueryParts.push(part); } } } else { debugLogger.warn( "read_many_files tool returned no content or empty content." ); } } catch (error) { await this.sendUpdate({ sessionUpdate: "tool_call_update", toolCallId: callId, status: "failed", content: [ { type: "content", content: { type: "text", text: `Error reading files (${contentLabelsForDisplay.join(", ")}): ${getErrorMessage(error)}` } } ], kind: toAcpToolKind(readManyFilesTool.kind) }); throw error; } } if (embeddedContext.length > 0) { processedQueryParts.push({ text: "\n--- Content from referenced context ---" }); for (const contextPart of embeddedContext) { processedQueryParts.push({ text: ` Content from @${contextPart.uri}: ` }); if ("text" in contextPart) { processedQueryParts.push({ text: contextPart.text }); } else { processedQueryParts.push({ inlineData: { mimeType: contextPart.mimeType ?? "application/octet-stream", data: contextPart.blob } }); } } } return processedQueryParts; } debug(msg) { if (this.context.config.getDebugMode()) { debugLogger.warn(msg); } } }; function toToolCallContent(toolResult) { if (toolResult.error?.message) { throw new Error(toolResult.error.message); } if (toolResult.returnDisplay) { if (typeof toolResult.returnDisplay === "string") { return { type: "content", content: { type: "text", text: toolResult.returnDisplay } }; } else { if ("fileName" in toolResult.returnDisplay) { return { type: "diff", path: toolResult.returnDisplay.filePath ?? toolResult.returnDisplay.fileName, oldText: toolResult.returnDisplay.originalContent, newText: toolResult.returnDisplay.newContent, _meta: { kind: !toolResult.returnDisplay.originalContent ? "add" : toolResult.returnDisplay.newContent === "" ? "delete" : "modify" } }; } return null; } } else { return null; } } var basicPermissionOptions = [ { optionId: ToolConfirmationOutcome.ProceedOnce, name: "Allow", kind: "allow_once" }, { optionId: ToolConfirmationOutcome.Cancel, name: "Reject", kind: "reject_once" } ]; function toPermissionOptions(confirmation, config) { const disableAlwaysAllow = config.getDisableAlwaysAllow(); const options = []; if (!disableAlwaysAllow) { switch (confirmation.type) { case "edit": options.push({ optionId: ToolConfirmationOutcome.ProceedAlways, name: "Allow All Edits", kind: "allow_always" }); break; case "exec": options.push({ optionId: ToolConfirmationOutcome.ProceedAlways, name: `Always Allow ${confirmation.rootCommand}`, kind: "allow_always" }); break; case "mcp": options.push( { optionId: ToolConfirmationOutcome.ProceedAlwaysServer, name: `Always Allow ${confirmation.serverName}`, kind: "allow_always" }, { optionId: ToolConfirmationOutcome.ProceedAlwaysTool, name: `Always Allow ${confirmation.toolName}`, kind: "allow_always" } ); break; case "info": options.push({ optionId: ToolConfirmationOutcome.ProceedAlways, name: `Always Allow`, kind: "allow_always" }); break; case "ask_user": case "exit_plan_mode": break; default: break; } } options.push(...basicPermissionOptions); switch (confirmation.type) { case "edit": case "exec": case "mcp": case "info": case "ask_user": case "exit_plan_mode": case "sandbox_expansion": break; default: { const unreachable = confirmation; throw new Error(`Unexpected: ${unreachable}`); } } return options; } function toAcpToolKind(kind) { switch (kind) { case Kind.Read: case Kind.Edit: case Kind.Execute: case Kind.Search: case Kind.Delete: case Kind.Move: case Kind.Think: case Kind.Fetch: case Kind.SwitchMode: case Kind.Other: return kind; case Kind.Agent: return "think"; case Kind.Plan: case Kind.Communicate: default: return "other"; } } function buildAvailableModes(isPlanEnabled) { const modes = [ { id: ApprovalMode.DEFAULT, name: "Default", description: "Prompts for approval" }, { id: ApprovalMode.AUTO_EDIT, name: "Auto Edit", description: "Auto-approves edit tools" }, { id: ApprovalMode.YOLO, name: "YOLO", description: "Auto-approves all tools" } ]; if (isPlanEnabled) { modes.push({ id: ApprovalMode.PLAN, name: "Plan", description: "Read-only mode" }); } return modes; } function buildAvailableModels(config, settings) { const preferredModel = config.getModel() || DEFAULT_GEMINI_MODEL_AUTO; const shouldShowPreviewModels = config.getHasAccessToPreviewModel(); const useGemini31 = config.getGemini31LaunchedSync?.() ?? false; const selectedAuthType = settings.merged.security.auth.selectedType; const useCustomToolModel = useGemini31 && selectedAuthType === AuthType.USE_GEMINI; const mainOptions = [ { value: DEFAULT_GEMINI_MODEL_AUTO, title: getDisplayString(DEFAULT_GEMINI_MODEL_AUTO), description: "Let Gemini CLI decide the best model for the task: gemini-2.5-pro, gemini-2.5-flash" } ]; if (shouldShowPreviewModels) { mainOptions.unshift({ value: PREVIEW_GEMINI_MODEL_AUTO, title: getDisplayString(PREVIEW_GEMINI_MODEL_AUTO), description: useGemini31 ? "Let Gemini CLI decide the best model for the task: gemini-3.1-pro, gemini-3-flash" : "Let Gemini CLI decide the best model for the task: gemini-3-pro, gemini-3-flash" }); } const manualOptions = [ { value: DEFAULT_GEMINI_MODEL, title: getDisplayString(DEFAULT_GEMINI_MODEL) }, { value: DEFAULT_GEMINI_FLASH_MODEL, title: getDisplayString(DEFAULT_GEMINI_FLASH_MODEL) }, { value: DEFAULT_GEMINI_FLASH_LITE_MODEL, title: getDisplayString(DEFAULT_GEMINI_FLASH_LITE_MODEL) } ]; if (shouldShowPreviewModels) { const previewProModel = useGemini31 ? PREVIEW_GEMINI_3_1_MODEL : PREVIEW_GEMINI_MODEL; const previewProValue = useCustomToolModel ? PREVIEW_GEMINI_3_1_CUSTOM_TOOLS_MODEL : previewProModel; manualOptions.unshift( { value: previewProValue, title: getDisplayString(previewProModel) }, { value: PREVIEW_GEMINI_FLASH_MODEL, title: getDisplayString(PREVIEW_GEMINI_FLASH_MODEL) } ); } const scaleOptions = (options) => options.map((o) => ({ modelId: o.value, name: o.title, description: o.description })); return { availableModels: [ ...scaleOptions(mainOptions), ...scaleOptions(manualOptions) ], currentModelId: preferredModel }; } // packages/cli/src/validateNonInterActiveAuth.ts async function validateNonInteractiveAuth(configuredAuthType, useExternalAuth, nonInteractiveConfig, settings) { try { const effectiveAuthType = configuredAuthType || getAuthTypeFromEnv(); const enforcedType = settings.merged.security.auth.enforcedType; if (enforcedType && effectiveAuthType !== enforcedType) { const message = effectiveAuthType ? `The enforced authentication type is '${enforcedType}', but the current type is '${effectiveAuthType}'. Please re-authenticate with the correct type.` : `The auth type '${enforcedType}' is enforced, but no authentication is configured.`; throw new Error(message); } if (!effectiveAuthType) { const message = `Please set an Auth method in your ${USER_SETTINGS_PATH} or specify one of the following environment variables before running: GEMINI_API_KEY, GOOGLE_GENAI_USE_VERTEXAI, GOOGLE_GENAI_USE_GCA`; throw new Error(message); } const authType = effectiveAuthType; if (!useExternalAuth) { const err = validateAuthMethod(String(authType)); if (err != null) { throw new Error(err); } } return authType; } catch (error) { if (nonInteractiveConfig.getOutputFormat() === OutputFormat.JSON) { handleError( error instanceof Error ? error : new Error(String(error)), nonInteractiveConfig, ExitCodes.FATAL_AUTHENTICATION_ERROR ); } else { debugLogger.error(error instanceof Error ? error.message : String(error)); await runExitCleanup(); process.exit(ExitCodes.FATAL_AUTHENTICATION_ERROR); } } } // packages/cli/src/utils/relaunch.ts import { spawn as spawn2 } from "node:child_process"; async function relaunchOnExitCode(runner) { while (true) { try { const exitCode = await runner(); if (exitCode !== RELAUNCH_EXIT_CODE) { process.exit(exitCode); } } catch (error) { process.stdin.resume(); const errorMessage = error instanceof Error ? error.stack ?? error.message : String(error); writeToStderr( `Fatal error: Failed to relaunch the CLI process. ${errorMessage} ` ); process.exit(1); } } } async function relaunchAppInChildProcess(additionalNodeArgs, additionalScriptArgs, remoteAdminSettings) { if (process.env["GEMINI_CLI_NO_RELAUNCH"]) { return; } let latestAdminSettings = remoteAdminSettings; const runner = () => { const script = process.argv[1]; const scriptArgs = process.argv.slice(2); const nodeArgs = [ ...process.execArgv, ...additionalNodeArgs, script, ...additionalScriptArgs, ...scriptArgs ]; const newEnv = { ...process.env, GEMINI_CLI_NO_RELAUNCH: "true" }; process.stdin.pause(); const child = spawn2(process.execPath, nodeArgs, { stdio: ["inherit", "inherit", "inherit", "ipc"], env: newEnv }); if (latestAdminSettings) { child.send({ type: "admin-settings", settings: latestAdminSettings }); } child.on("message", (msg) => { if (msg.type === "admin-settings-update" && msg.settings) { latestAdminSettings = msg.settings; } }); return new Promise((resolve9, reject) => { child.on("error", reject); child.on("close", (code) => { process.stdin.resume(); resolve9(code ?? 1); }); }); }; await relaunchOnExitCode(runner); } // packages/cli/src/utils/sessions.ts async function listSessions(config) { await generateSummary(config); const sessionSelector = new SessionSelector(config); const sessions = await sessionSelector.listSessions(); if (sessions.length === 0) { writeToStdout("No previous sessions found for this project."); return; } writeToStdout( ` Available sessions for this project (${sessions.length}): ` ); sessions.sort( (a, b) => new Date(a.startTime).getTime() - new Date(b.startTime).getTime() ).forEach((session, index) => { const current = session.isCurrentSession ? ", current" : ""; const time = formatRelativeTime(session.lastUpdated); const title = session.displayName.length > 100 ? session.displayName.slice(0, 97) + "..." : session.displayName; writeToStdout( ` ${index + 1}. ${title} (${time}${current}) [${session.id}] ` ); }); } async function deleteSession(config, sessionIndex) { const sessionSelector = new SessionSelector(config); const sessions = await sessionSelector.listSessions(); if (sessions.length === 0) { writeToStderr("No sessions found for this project."); return; } const sortedSessions = sessions.sort( (a, b) => new Date(a.startTime).getTime() - new Date(b.startTime).getTime() ); let sessionToDelete; const sessionByUuid = sortedSessions.find( (session) => session.id === sessionIndex ); if (sessionByUuid) { sessionToDelete = sessionByUuid; } else { const index = parseInt(sessionIndex, 10); if (isNaN(index) || index < 1 || index > sessions.length) { writeToStderr( `Invalid session identifier "${sessionIndex}". Use --list-sessions to see available sessions.` ); return; } sessionToDelete = sortedSessions[index - 1]; } if (sessionToDelete.isCurrentSession) { writeToStderr("Cannot delete the current active session."); return; } try { const chatRecordingService = new ChatRecordingService(config); chatRecordingService.deleteSession(sessionToDelete.file); const time = formatRelativeTime(sessionToDelete.lastUpdated); writeToStdout( `Deleted session ${sessionToDelete.index}: ${sessionToDelete.firstUserMessage} (${time})` ); } catch (error) { writeToStderr( `Failed to delete session: ${error instanceof Error ? error.message : "Unknown error"}` ); } } // packages/cli/src/utils/terminalTheme.ts async function setupTerminalAndTheme(config, settings) { let terminalBackground = void 0; if (config.isInteractive() && process.stdin.isTTY) { await terminalCapabilityManager.detectCapabilities(); terminalBackground = terminalCapabilityManager.getTerminalBackgroundColor(); } themeManager.loadCustomThemes(settings.merged.ui.customThemes); if (settings.merged.ui.theme) { if (!themeManager.setActiveTheme(settings.merged.ui.theme)) { debugLogger.warn( `Warning: Theme "${settings.merged.ui.theme}" not found.` ); } } else { const themeName = pickDefaultThemeName( terminalBackground, themeManager.getAllThemes(), DEFAULT_THEME.name, "Default Light" ); themeManager.setActiveTheme(themeName); } config.setTerminalBackground(terminalBackground); themeManager.setTerminalBackground(terminalBackground); if (terminalBackground !== void 0) { const currentTheme = themeManager.getActiveTheme(); if (!themeManager.isThemeCompatible(currentTheme, terminalBackground)) { const backgroundType = getThemeTypeFromBackgroundColor(terminalBackground); coreEvents.emitFeedback( "warning", `Theme '${currentTheme.name}' (${currentTheme.type}) might look incorrect on your ${backgroundType} terminal background. Type /theme to change theme.` ); } } return terminalBackground; } // packages/cli/src/utils/logCleanup.ts import { promises as fs10 } from "node:fs"; import * as path13 from "node:path"; var RETENTION_PERIOD_MS = 7 * 24 * 60 * 60 * 1e3; async function cleanupBackgroundLogs(debugMode = false) { try { const logDir = ShellExecutionService.getLogDir(); try { await fs10.access(logDir); } catch { return; } const entries = await fs10.readdir(logDir, { withFileTypes: true }); const now = Date.now(); let deletedCount = 0; for (const entry of entries) { if (entry.isFile() && entry.name.endsWith(".log")) { const filePath = path13.join(logDir, entry.name); try { const stats = await fs10.stat(filePath); if (now - stats.mtime.getTime() > RETENTION_PERIOD_MS) { await fs10.unlink(filePath); deletedCount++; } } catch (error) { if (debugMode) { debugLogger.debug( `Failed to process log file ${entry.name}:`, error ); } } } } if (deletedCount > 0 && debugMode) { debugLogger.debug(`Cleaned up ${deletedCount} expired background logs.`); } } catch (error) { if (debugMode) { debugLogger.warn("Background log cleanup failed:", error); } } } // packages/cli/src/services/SlashCommandConflictHandler.ts var SlashCommandConflictHandler = class { notifiedConflicts = /* @__PURE__ */ new Set(); pendingConflicts = []; flushTimeout = null; constructor() { this.handleConflicts = this.handleConflicts.bind(this); } start() { coreEvents.on(CoreEvent.SlashCommandConflicts, this.handleConflicts); } stop() { coreEvents.off(CoreEvent.SlashCommandConflicts, this.handleConflicts); if (this.flushTimeout) { clearTimeout(this.flushTimeout); this.flushTimeout = null; } } handleConflicts(payload) { const newConflicts = payload.conflicts.filter((c) => { const sourceId = c.loserExtensionName || c.loserMcpServerName || c.loserKind; const key = `${c.name}:${sourceId}:${c.renamedTo}`; if (this.notifiedConflicts.has(key)) { return false; } this.notifiedConflicts.add(key); return true; }); if (newConflicts.length > 0) { this.pendingConflicts.push(...newConflicts); this.scheduleFlush(); } } scheduleFlush() { if (this.flushTimeout) { clearTimeout(this.flushTimeout); } this.flushTimeout = setTimeout(() => this.flush(), 500); } flush() { this.flushTimeout = null; const conflicts = [...this.pendingConflicts]; this.pendingConflicts = []; if (conflicts.length === 0) { return; } const grouped = /* @__PURE__ */ new Map(); for (const c of conflicts) { const list = grouped.get(c.name) ?? []; list.push(c); grouped.set(c.name, list); } for (const [name, commandConflicts] of grouped) { if (commandConflicts.length > 1) { this.emitGroupedFeedback(name, commandConflicts); } else { this.emitSingleFeedback(commandConflicts[0]); } } } /** * Emits a grouped notification for multiple conflicts sharing the same name. */ emitGroupedFeedback(name, conflicts) { const messages = conflicts.map((c) => { const source = this.getSourceDescription( c.loserExtensionName, c.loserKind, c.loserMcpServerName ); return `- ${this.capitalize(source)} '/${c.name}' was renamed to '/${c.renamedTo}'`; }).join("\n"); coreEvents.emitFeedback( "info", `Conflicts detected for command '/${name}': ${messages}` ); } /** * Emits a descriptive notification for a single command conflict. */ emitSingleFeedback(c) { const loserSource = this.getSourceDescription( c.loserExtensionName, c.loserKind, c.loserMcpServerName ); const winnerSource = this.getSourceDescription( c.winnerExtensionName, c.winnerKind, c.winnerMcpServerName ); coreEvents.emitFeedback( "info", `${this.capitalize(loserSource)} '/${c.name}' was renamed to '/${c.renamedTo}' because it conflicts with ${winnerSource}.` ); } capitalize(s) { return s.charAt(0).toUpperCase() + s.slice(1); } /** * Returns a human-readable description of a command's source. */ getSourceDescription(extensionName, kind, mcpServerName) { switch (kind) { case "extension-file" /* EXTENSION_FILE */: return extensionName ? `extension '${extensionName}' command` : "extension command"; case "skill" /* SKILL */: return extensionName ? `extension '${extensionName}' skill` : "skill command"; case "mcp-prompt" /* MCP_PROMPT */: return mcpServerName ? `MCP server '${mcpServerName}' command` : "MCP server command"; case "user-file" /* USER_FILE */: return "user command"; case "workspace-file" /* WORKSPACE_FILE */: return "workspace command"; case "built-in" /* BUILT_IN */: return "built-in command"; default: return "existing command"; } } }; // packages/cli/src/gemini.tsx function validateDnsResolutionOrder(order) { const defaultValue = "ipv4first"; if (order === void 0) { return defaultValue; } if (order === "ipv4first" || order === "verbatim") { return order; } debugLogger.warn( `Invalid value for dnsResolutionOrder in settings: "${order}". Using default "${defaultValue}".` ); return defaultValue; } function getNodeMemoryArgs(isDebugMode2) { const totalMemoryMB = os6.totalmem() / (1024 * 1024); const heapStats = v8.getHeapStatistics(); const currentMaxOldSpaceSizeMb = Math.floor( heapStats.heap_size_limit / 1024 / 1024 ); const targetMaxOldSpaceSizeInMB = Math.floor(totalMemoryMB * 0.5); if (isDebugMode2) { debugLogger.debug( `Current heap size ${currentMaxOldSpaceSizeMb.toFixed(2)} MB` ); } if (process.env["GEMINI_CLI_NO_RELAUNCH"]) { return []; } if (targetMaxOldSpaceSizeInMB > currentMaxOldSpaceSizeMb) { if (isDebugMode2) { debugLogger.debug( `Need to relaunch with more memory: ${targetMaxOldSpaceSizeInMB.toFixed(2)} MB` ); } return [`--max-old-space-size=${targetMaxOldSpaceSizeInMB}`]; } return []; } function setupUnhandledRejectionHandler() { let unhandledRejectionOccurred = false; process.on("unhandledRejection", (reason, _promise) => { const errorMessage = `========================================= This is an unexpected error. Please file a bug report using the /bug tool. CRITICAL: Unhandled Promise Rejection! ========================================= Reason: ${reason}${reason instanceof Error && reason.stack ? ` Stack trace: ${reason.stack}` : ""}`; debugLogger.error(errorMessage); if (!unhandledRejectionOccurred) { unhandledRejectionOccurred = true; appEvents.emit("open-debug-console" /* OpenDebugConsole */); } }); } async function startInteractiveUI(config, settings, startupWarnings, workspaceRoot = process.cwd(), resumedSessionData, initializationResult) { const { startInteractiveUI: doStartUI } = await import("./interactiveCli-VLQHRXHU.js"); await doStartUI( config, settings, startupWarnings, workspaceRoot, resumedSessionData, initializationResult ); } async function main() { const cliStartupHandle = startupProfiler.start("cli_startup"); const adminControlsListner = setupAdminControlsListener(); registerCleanup(adminControlsListner.cleanup); const cleanupStdio = patchStdio(); registerSyncCleanup(() => { initializeOutputListenersAndFlush(); cleanupStdio(); }); setupUnhandledRejectionHandler(); setupSignalHandlers(); const slashCommandConflictHandler = new SlashCommandConflictHandler(); slashCommandConflictHandler.start(); registerCleanup(() => slashCommandConflictHandler.stop()); const loadSettingsHandle = startupProfiler.start("load_settings"); const settings = loadSettings(); loadSettingsHandle?.end(); const requestedWorktree = getRequestedWorktreeName(settings); let worktreeInfo; if (requestedWorktree !== void 0) { const worktreeHandle = startupProfiler.start("setup_worktree"); worktreeInfo = await setupWorktree(requestedWorktree || void 0); worktreeHandle?.end(); } const cleanupOpsHandle = startupProfiler.start("cleanup_ops"); Promise.all([ cleanupCheckpoints(), cleanupToolOutputFiles(settings.merged), cleanupBackgroundLogs() ]).catch((e) => { debugLogger.error("Early cleanup failed:", e); }).finally(() => { cleanupOpsHandle?.end(); }); const parseArgsHandle = startupProfiler.start("parse_arguments"); const argvPromise = parseArguments(settings.merged).finally(() => { parseArgsHandle?.end(); }); const rawStartupWarningsPromise = getStartupWarnings(); settings.errors.forEach((error) => { coreEvents.emitFeedback("warning", error.message); }); const trustedFolders = loadTrustedFolders(); trustedFolders.errors.forEach((error) => { coreEvents.emitFeedback( "warning", `Error in ${error.path}: ${error.message}` ); }); const argv = await argvPromise; if (argv.allowedTools && argv.allowedTools.length > 0 || settings.merged.tools?.allowed && settings.merged.tools.allowed.length > 0) { coreEvents.emitFeedback( "warning", "Warning: --allowed-tools cli argument and tools.allowed in settings.json are deprecated and will be removed in 1.0: Migrate to Policy Engine: https://geminicli.com/docs/core/policy-engine/" ); } if (settings.merged.tools?.exclude && settings.merged.tools.exclude.length > 0) { coreEvents.emitFeedback( "warning", "Warning: tools.exclude in settings.json is deprecated and will be removed in 1.0. Migrate to Policy Engine: https://geminicli.com/docs/core/policy-engine/" ); } if (argv.startupMessages) { argv.startupMessages.forEach((msg) => { coreEvents.emitFeedback("info", msg); }); } if (argv.promptInteractive && !process.stdin.isTTY) { writeToStderr( "Error: The --prompt-interactive flag cannot be used when input is piped from stdin.\n" ); await runExitCleanup(); process.exit(ExitCodes.FATAL_INPUT_ERROR); } const isDebugMode2 = isDebugMode(argv); const consolePatcher = new ConsolePatcher({ stderr: true, debugMode: isDebugMode2, onNewMessage: (msg) => { coreEvents.emitConsoleLog(msg.type, msg.content); } }); consolePatcher.patch(); registerCleanup(consolePatcher.cleanup); dns.setDefaultResultOrder( validateDnsResolutionOrder(settings.merged.advanced.dnsResolutionOrder) ); if (!settings.merged.security.auth.selectedType || settings.merged.security.auth.selectedType === AuthType.LEGACY_CLOUD_SHELL) { if (process.env["CLOUD_SHELL"] === "true" || process.env["GEMINI_CLI_USE_COMPUTE_ADC"] === "true") { settings.setValue( "User" /* User */, "security.auth.selectedType", AuthType.COMPUTE_ADC ); } } const partialConfig = await loadCliConfig(settings.merged, sessionId, argv, { projectHooks: settings.workspace.settings.hooks }); adminControlsListner.setConfig(partialConfig); let initialAuthFailed = false; if (!settings.merged.security.auth.useExternal && !argv.isCommand) { try { if (partialConfig.isInteractive() && settings.merged.security.auth.selectedType) { const err = validateAuthMethod( settings.merged.security.auth.selectedType ); if (err) { throw new Error(err); } await partialConfig.refreshAuth( settings.merged.security.auth.selectedType ); } else if (!partialConfig.isInteractive()) { const authType = await validateNonInteractiveAuth( settings.merged.security.auth.selectedType, settings.merged.security.auth.useExternal, partialConfig, settings ); await partialConfig.refreshAuth(authType); } } catch (err) { if (err instanceof ValidationCancelledError) { await runExitCleanup(); process.exit(ExitCodes.SUCCESS); } if (!(err instanceof ValidationRequiredError)) { debugLogger.error("Error authenticating:", err); initialAuthFailed = true; } } } const remoteAdminSettings = partialConfig.getRemoteAdminSettings(); if (remoteAdminSettings) { settings.setRemoteAdminSettings(remoteAdminSettings); } await runDeferredCommand(settings.merged); if (!process.env["SANDBOX"] && !argv.isCommand) { const memoryArgs = settings.merged.advanced.autoConfigureMemory ? getNodeMemoryArgs(isDebugMode2) : []; const sandboxConfig = await loadSandboxConfig(settings.merged, argv); if (sandboxConfig) { if (initialAuthFailed) { await runExitCleanup(); process.exit(ExitCodes.FATAL_AUTHENTICATION_ERROR); } let stdinData = ""; if (!process.stdin.isTTY) { stdinData = await readStdin(); } const injectStdinIntoArgs = (args, stdinData2) => { const finalArgs = [...args]; if (stdinData2) { const promptIndex = finalArgs.findIndex( (arg) => arg === "--prompt" || arg === "-p" ); if (promptIndex > -1 && finalArgs.length > promptIndex + 1) { finalArgs[promptIndex + 1] = `${stdinData2} ${finalArgs[promptIndex + 1]}`; } else { finalArgs.push("--prompt", stdinData2); } } return finalArgs; }; const sandboxArgs = injectStdinIntoArgs(process.argv, stdinData); await relaunchOnExitCode( () => start_sandbox(sandboxConfig, memoryArgs, partialConfig, sandboxArgs) ); await runExitCleanup(); process.exit(ExitCodes.SUCCESS); } else { await relaunchAppInChildProcess(memoryArgs, [], remoteAdminSettings); } } { const loadConfigHandle = startupProfiler.start("load_cli_config"); const config = await loadCliConfig(settings.merged, sessionId, argv, { projectHooks: settings.workspace.settings.hooks, worktreeSettings: worktreeInfo }); loadConfigHandle?.end(); await config.storage.initialize(); adminControlsListner.setConfig(config); if (config.isInteractive() && settings.merged.general.devtools) { const { setupInitialActivityLogger } = await import("./devtoolsService-ZKU2HLK2.js"); await setupInitialActivityLogger(config); } registerTelemetryConfig(config); const policyEngine = config.getPolicyEngine(); const messageBus = config.getMessageBus(); createPolicyUpdater2(policyEngine, messageBus, config.storage); registerCleanup(async () => { await config.getHookSystem()?.fireSessionEndEvent(SessionEndReason.Exit); }); cleanupExpiredSessions(config, settings.merged).catch((e) => { debugLogger.error("Failed to cleanup expired sessions:", e); }); if (config.getListExtensions()) { debugLogger.log("Installed extensions:"); for (const extension of config.getExtensions()) { debugLogger.log(`- ${extension.name}`); } await runExitCleanup(); process.exit(ExitCodes.SUCCESS); } if (config.getListSessions()) { const authType2 = settings.merged.security.auth.selectedType; if (authType2) { try { await config.refreshAuth(authType2); } catch (e) { debugLogger.debug( "Auth failed for --list-sessions, summaries may not be generated:", e ); } } await listSessions(config); await runExitCleanup(); process.exit(ExitCodes.SUCCESS); } const sessionToDelete = config.getDeleteSession(); if (sessionToDelete) { await deleteSession(config, sessionToDelete); await runExitCleanup(); process.exit(ExitCodes.SUCCESS); } const wasRaw = process.stdin.isRaw; if (config.isInteractive() && !wasRaw && process.stdin.isTTY) { process.stdin.setRawMode(true); registerSyncCleanup(() => { process.stdin.setRawMode(wasRaw); }); } const terminalHandle = startupProfiler.start("setup_terminal"); await setupTerminalAndTheme(config, settings); terminalHandle?.end(); const initAppHandle = startupProfiler.start("initialize_app"); const initializationResult = await initializeApp(config, settings); initAppHandle?.end(); if (settings.merged.security.auth.selectedType === AuthType.LOGIN_WITH_GOOGLE && config.isBrowserLaunchSuppressed()) { await getOauthClient(settings.merged.security.auth.selectedType, config); } if (config.getAcpMode()) { return runAcpClient(config, settings, argv); } let input = config.getQuestion(); const useAlternateBuffer = shouldEnterAlternateScreen( isAlternateBufferEnabled(config), config.getScreenReader() ); const rawStartupWarnings = await rawStartupWarningsPromise; const startupWarnings = [ ...rawStartupWarnings.map((message) => ({ id: `startup-${createHash("sha256").update(message).digest("hex").substring(0, 16)}`, message, priority: WarningPriority.High })), ...await getUserStartupWarnings(settings.merged, void 0, { isAlternateBuffer: useAlternateBuffer }) ]; let resumedSessionData = void 0; if (argv.resume) { const sessionSelector = new SessionSelector(config); try { const result = await sessionSelector.resolveSession(argv.resume); resumedSessionData = { conversation: result.sessionData, filePath: result.sessionPath }; config.setSessionId(resumedSessionData.conversation.sessionId); } catch (error) { if (error instanceof SessionError && error.code === "NO_SESSIONS_FOUND") { startupWarnings.push({ id: "resume-no-sessions", message: error.message, priority: WarningPriority.High }); } else { coreEvents.emitFeedback( "error", `Error resuming session: ${error instanceof Error ? error.message : "Unknown error"}` ); await runExitCleanup(); process.exit(ExitCodes.FATAL_INPUT_ERROR); } } } cliStartupHandle?.end(); if (config.isInteractive()) { await startInteractiveUI( config, settings, startupWarnings, process.cwd(), resumedSessionData, initializationResult ); return; } await config.initialize(); startupProfiler.flush(config); let stdinData = void 0; if (!process.stdin.isTTY) { stdinData = await readStdin(); if (stdinData) { input = input ? `${stdinData} ${input}` : stdinData; } } const sessionStartSource = resumedSessionData ? SessionStartSource.Resume : SessionStartSource.Startup; const hookSystem = config?.getHookSystem(); if (hookSystem) { const result = await hookSystem.fireSessionStartEvent(sessionStartSource); if (result) { if (result.systemMessage) { writeToStderr(result.systemMessage + "\n"); } const additionalContext = result.getAdditionalContext(); if (additionalContext) { const wrappedContext = `${additionalContext}`; input = input ? `${wrappedContext} ${input}` : wrappedContext; } } } registerCleanup(async () => { await config.getHookSystem()?.fireSessionEndEvent(SessionEndReason.Exit); }); if (!input) { debugLogger.error( `No input provided via stdin. Input can be provided by piping data into gemini or using the --prompt option.` ); await runExitCleanup(); process.exit(ExitCodes.FATAL_INPUT_ERROR); } const prompt_id = sessionId; logUserPrompt( config, new UserPromptEvent( input.length, prompt_id, config.getContentGeneratorConfig()?.authType, input ) ); const authType = await validateNonInteractiveAuth( settings.merged.security.auth.selectedType, settings.merged.security.auth.useExternal, config, settings ); await config.refreshAuth(authType); if (config.getDebugMode()) { debugLogger.log("Session ID: %s", sessionId); } initializeOutputListenersAndFlush(); await runNonInteractive({ config, settings, input, prompt_id, resumedSessionData }); await runExitCleanup(); process.exit(ExitCodes.SUCCESS); } } function initializeOutputListenersAndFlush() { if (coreEvents.listenerCount(CoreEvent.Output) === 0) { coreEvents.on(CoreEvent.Output, (payload) => { if (payload.isStderr) { writeToStderr(payload.chunk, payload.encoding); } else { writeToStdout(payload.chunk, payload.encoding); } }); if (coreEvents.listenerCount(CoreEvent.ConsoleLog) === 0) { coreEvents.on(CoreEvent.ConsoleLog, (payload) => { if (payload.type === "error" || payload.type === "warn") { writeToStderr(payload.content); } else { writeToStdout(payload.content); } }); } if (coreEvents.listenerCount(CoreEvent.UserFeedback) === 0) { coreEvents.on(CoreEvent.UserFeedback, (payload) => { if (payload.severity === "error" || payload.severity === "warning") { writeToStderr(payload.message); } else { writeToStdout(payload.message); } }); } } coreEvents.drainBacklogs(); } function setupAdminControlsListener() { let pendingSettings; let config; const messageHandler = (msg) => { const message = msg; if (message?.type === "admin-settings" && message.settings) { if (config) { config.setRemoteAdminSettings(message.settings); } else { pendingSettings = message.settings; } } }; process.on("message", messageHandler); return { setConfig: (newConfig) => { config = newConfig; if (pendingSettings) { config.setRemoteAdminSettings(pendingSettings); } }, cleanup: () => { process.off("message", messageHandler); } }; } // packages/cli/index.ts process.on("uncaughtException", (error) => { if (process.platform === "win32" && error instanceof Error && error.message === "Cannot resize a pty that has already exited") { return; } if (error instanceof Error) { writeToStderr(error.stack + "\n"); } else { writeToStderr(String(error) + "\n"); } process.exit(1); }); main().catch(async (error) => { const cleanupTimeout = setTimeout(() => { writeToStderr("Cleanup timed out, forcing exit...\n"); process.exit(1); }, 5e3); try { await runExitCleanup(); } catch (cleanupError) { writeToStderr( `Error during final cleanup: ${cleanupError instanceof Error ? cleanupError.message : String(cleanupError)} ` ); } finally { clearTimeout(cleanupTimeout); } if (error instanceof FatalError) { let errorMessage = error.message; if (!process.env["NO_COLOR"]) { errorMessage = `\x1B[31m${errorMessage}\x1B[0m`; } writeToStderr(errorMessage + "\n"); process.exit(error.exitCode); } writeToStderr("An unexpected critical error occurred:"); if (error instanceof Error) { writeToStderr(error.stack + "\n"); } else { writeToStderr(String(error) + "\n"); } process.exit(1); }); /** * @license * Copyright 2025 Google LLC * SPDX-License-Identifier: Apache-2.0 */ /** * @license * Copyright 2026 Google LLC * SPDX-License-Identifier: Apache-2.0 */ /*! Bundled license information: yargs-parser/build/lib/string-utils.js: yargs-parser/build/lib/tokenize-arg-string.js: yargs-parser/build/lib/yargs-parser-types.js: yargs-parser/build/lib/yargs-parser.js: (** * @license * Copyright (c) 2016, Contributors * SPDX-License-Identifier: ISC *) yargs-parser/build/lib/index.js: (** * @fileoverview Main entrypoint for libraries using yargs-parser in Node.js * CJS and ESM environments. * * @license * Copyright (c) 2016, Contributors * SPDX-License-Identifier: ISC *) */