openclaw
Version:
Multi-channel AI gateway with extensible messaging integrations
257 lines (256 loc) • 12 kB
JavaScript
import { A as getCommanderSubcommandFact, D as getCommanderCommandPath, N as setCommanderErrorCommand, O as getCommanderErrorCommandNames, T as isModelsPlainMachineOutput, j as hasCommanderOptionToken, k as getCommanderErrorCommandPath, l as isHelpOrVersionInvocation, o as getVerboseFlag } from "./argv-DNjh_yaF.js";
import { t as resolveCliArgvInvocation } from "./argv-invocation-C1WhAkJL.js";
import { r as defaultRuntime } from "./runtime-CF2WjnNZ.js";
import { n as resolveCliName } from "./cli-name-CVj-3DWf.js";
import { r as setVerbose } from "./global-state-BAD7XgmL.js";
import { t as VERSION } from "./version-v1kuAkGj.js";
import { n as inheritOptionFromParent } from "./command-options-BDuSHeWG.js";
import "./globals-CTaGxEqj.js";
import { t as resolveCliCommandPathPolicy } from "./command-path-policy-CYBY98jZ.js";
import { r as isJsonOutputModeActive, t as applyResolvedCommandOutputMode } from "./json-output-mode-D0F07HLf.js";
import { n as resolvePluginInstallPreactionRequest, t as resolvePluginInstallInvalidConfigPolicy } from "./plugin-install-config-policy-BKE_FN73.js";
import { n as resolveCliChannelOptions } from "./channel-options-C63ZRUEe.js";
import { n as isParentDefaultHelpAction } from "./parent-default-help-DQUF3qKA.js";
import { n as ensureCliExecutionBootstrap, r as resolveCliExecutionStartupContext, t as applyCliExecutionStartupPresentation } from "./command-execution-startup-DGi7CCGi.js";
import { n as setProgramContext } from "./program-context-VEhF8JxS.js";
import { t as isCommandJsonOutputMode } from "./json-mode-jHy4Wzfh.js";
import { t as forceFreePort } from "./ports-DO5L-Eey.js";
import { t as registerProgramCommands } from "./command-registry-DsTQkra2.js";
import { t as configureProgramHelp } from "./help-DitEEZjx.js";
import { t as createCliParseError } from "./error-output-qfnKpM3A.js";
import process$1 from "node:process";
import { Command, CommanderError } from "commander";
//#region src/cli/program/context.ts
/** Create a program context that resolves channel options once on first use. */
function createProgramContext() {
let cachedChannelOptions;
const getChannelOptions = () => {
if (cachedChannelOptions === void 0) cachedChannelOptions = resolveCliChannelOptions();
return cachedChannelOptions;
};
return {
programVersion: VERSION,
get channelOptions() {
return getChannelOptions();
},
get messageChannelOptions() {
return getChannelOptions().join("|");
},
get agentChannelOptions() {
return ["last", ...getChannelOptions()].join("|");
}
};
}
//#endregion
//#region src/cli/program/openclaw-command.ts
var OpenClawCommand = class OpenClawCommand extends Command {
createCommand(name) {
return new OpenClawCommand(name);
}
error(message, errorOptions) {
const restoreErrorCommand = setCommanderErrorCommand(this);
try {
return super.error(message, errorOptions);
} catch (error) {
if (error instanceof CommanderError && error.exitCode !== 0 && (isJsonOutputModeActive(process.argv) || isCommandJsonOutputMode(this, process.argv))) {
if (!isCommandJsonOutputMode(this, process.argv) && !hasCommanderOptionToken(this, process.argv, /* @__PURE__ */ new Set(["--json"]), "flag")) {
applyResolvedCommandOutputMode(false);
throw error;
}
applyResolvedCommandOutputMode(true);
throw createCliParseError(message, {
argv: process.argv,
commandPath: getCommanderErrorCommandPath(this),
commandNames: getCommanderErrorCommandNames(this)
}, { humanOutputWritten: true });
}
throw error;
} finally {
restoreErrorCommand();
}
}
_outputHelpIfRequested(args) {
const subcommandFact = getCommanderSubcommandFact(this, args);
if (subcommandFact?.kind === "defer") return;
if (subcommandFact?.kind === "unknown") this.error(`error: unknown command '${subcommandFact.name}'`, { code: "commander.unknownCommand" });
super._outputHelpIfRequested(args);
}
};
//#endregion
//#region src/cli/program/preaction.ts
const HELP_OR_VERSION_FLAGS = /* @__PURE__ */ new Set([
"-h",
"--help",
"-V",
"--version"
]);
function setProcessTitleForCommand(actionCommand) {
let current = actionCommand;
while (current.parent && current.parent.parent) current = current.parent;
const name = current.name();
const cliName = resolveCliName();
if (!name || name === cliName) return;
process.title = `${cliName}-${name}`;
}
function shouldAllowInvalidConfigForAction(actionCommand, commandPath) {
return commandPath[0] === "update" || resolvePluginInstallInvalidConfigPolicy(resolvePluginInstallPreactionRequest({
actionCommand,
commandPath,
argv: process.argv
})) === "allow-plugin-recovery";
}
function getCliLogLevel(actionCommand) {
if (actionCommand.getOptionValueSourceWithGlobals("logLevel") !== "cli") return;
const logLevel = actionCommand.optsWithGlobals().logLevel;
return typeof logLevel === "string" ? logLevel : void 0;
}
function getStateMigrationAgentId(actionCommand) {
if (!actionCommand.options.some((option) => option.attributeName() === "agent")) return;
const value = actionCommand.getOptionValueSource("agent") === "cli" ? actionCommand.getOptionValue("agent") : inheritOptionFromParent(actionCommand, "agent", "cli");
return typeof value === "string" && value.trim() ? value.trim() : void 0;
}
function isBareParentDefaultHelpInvocation(actionCommand, argv) {
if (!isParentDefaultHelpAction(actionCommand)) return false;
const { commandPath } = resolveCliArgvInvocation(argv);
const [primary, extra] = commandPath;
if (extra !== void 0 || !primary) return false;
return primary === actionCommand.name() || actionCommand.aliases().includes(primary);
}
function isGuidedConfigAction(actionCommand) {
return actionCommand.name() === "config" && !actionCommand.parent?.parent;
}
function isGuidedConfigCommandPath(commandPath) {
const [primary, secondary, extra] = commandPath;
if (primary !== "config" || extra !== void 0) return false;
return secondary !== "get" && secondary !== "set" && secondary !== "patch" && secondary !== "unset" && secondary !== "file" && secondary !== "schema" && secondary !== "validate";
}
function isGatewayRunAction(actionCommand) {
if (actionCommand.name() === "gateway") return actionCommand.parent?.parent === null;
return actionCommand.name() === "run" && actionCommand.parent?.name() === "gateway" && actionCommand.parent.parent?.parent === null;
}
async function runStateStoreGuard(commandPath) {
if (resolveCliCommandPathPolicy(commandPath).stateStoreGuard !== "run") return;
let outcome;
try {
const { checkCliGatewayStateDir } = await import("./state-dir-gateway-check-D7-K0HhU.js");
outcome = await checkCliGatewayStateDir({ command: `openclaw ${commandPath.join(" ")}` });
} catch (error) {
const { formatErrorMessage } = await import("./infra/errors.js");
const { logDebug } = await import("./logger-O6tGyy_w.js");
logDebug(`state-store guard unavailable: ${formatErrorMessage(error)}`);
return;
}
if (outcome.kind === "warn") defaultRuntime.log(outcome.message);
else if (outcome.kind === "refuse") throw new Error(outcome.message);
}
/** Register global pre-action bootstrap hooks for every non-help command invocation. */
function registerPreActionHooks(program, programVersion) {
program.hook("preAction", async (_thisCommand, actionCommand) => {
setProcessTitleForCommand(actionCommand);
const argv = process.argv;
const helpOrVersionWasOptionValue = hasCommanderOptionToken(actionCommand, argv, HELP_OR_VERSION_FLAGS, "value");
if (isHelpOrVersionInvocation(argv) && !helpOrVersionWasOptionValue || isBareParentDefaultHelpInvocation(actionCommand, argv)) return;
const jsonOutputMode = isCommandJsonOutputMode(actionCommand, argv);
const machineOutputMode = jsonOutputMode || isModelsPlainMachineOutput(argv, actionCommand);
applyResolvedCommandOutputMode(jsonOutputMode, machineOutputMode);
const { commandPath, startupPolicy } = resolveCliExecutionStartupContext({
argv,
commandPath: getCommanderCommandPath(actionCommand),
jsonOutputMode,
machineOutputMode,
env: process.env
});
await applyCliExecutionStartupPresentation({
startupPolicy,
version: programVersion
});
const verbose = getVerboseFlag(argv, { includeDebug: true });
setVerbose(verbose);
const cliLogLevel = getCliLogLevel(actionCommand);
if (cliLogLevel) process.env.OPENCLAW_LOG_LEVEL = cliLogLevel;
if (!verbose) process.env.NODE_NO_WARNINGS ??= "1";
if (isGuidedConfigAction(actionCommand) || isGuidedConfigCommandPath(commandPath)) return;
await runStateStoreGuard(commandPath);
if (startupPolicy.skipConfigGuard) {
await ensureCliExecutionBootstrap({
runtime: defaultRuntime,
commandPath,
startupPolicy,
skipConfigGuard: true
});
return;
}
let beforeStateMigrations;
let skipPristineStartupStateMigrations = false;
let skipPristineCoreStateMigrations = false;
let allowInvalid = shouldAllowInvalidConfigForAction(actionCommand, commandPath);
if (isGatewayRunAction(actionCommand)) {
const { prepareGatewayRunBootstrap, recheckGatewayRunBootstrap, wasPreparedGatewayRunCoreStatePristine, wasPreparedGatewayRunStatePristine } = await import("./pre-bootstrap-CenrzAsB.js");
const { resolveGatewayRunOptions } = await import("./run-options-BM5MTMBe.js");
const resolvedOptions = resolveGatewayRunOptions(actionCommand.opts(), actionCommand);
allowInvalid ||= resolvedOptions.allowUnconfigured === true;
const opts = {
force: resolvedOptions.force === true,
reset: resolvedOptions.reset === true
};
if (!await prepareGatewayRunBootstrap({
opts,
runtime: defaultRuntime
})) return;
skipPristineStartupStateMigrations = wasPreparedGatewayRunStatePristine();
skipPristineCoreStateMigrations = wasPreparedGatewayRunCoreStatePristine();
beforeStateMigrations = (snapshot) => recheckGatewayRunBootstrap({
opts,
runtime: defaultRuntime,
...snapshot ? { snapshot } : {}
});
}
const stateMigrationAgentId = getStateMigrationAgentId(actionCommand);
if (stateMigrationAgentId) {
const existingGuard = beforeStateMigrations;
beforeStateMigrations = async (snapshot) => {
if (snapshot) {
const { isValidAgentId, normalizeAgentId } = await import("./normalization-core/agent-id.js");
if (isValidAgentId(stateMigrationAgentId)) {
const [{ listAgentIds }, { retainLegacyDefaultAgentId }] = await Promise.all([import("./agent-scope-config-K8hF78lq.js"), import("./legacy.default-agent-owner-C_b4jI0i.js")]);
const agentId = normalizeAgentId(stateMigrationAgentId);
if (listAgentIds(snapshot.sourceConfig).includes(agentId)) retainLegacyDefaultAgentId(snapshot.sourceConfig, agentId);
}
}
return await existingGuard?.(snapshot) ?? true;
};
}
await ensureCliExecutionBootstrap({
runtime: defaultRuntime,
commandPath,
startupPolicy,
allowInvalid,
...beforeStateMigrations ? { beforeStateMigrations } : {},
...skipPristineStartupStateMigrations ? { skipPristineStartupStateMigrations: true } : {},
...skipPristineCoreStateMigrations ? { skipPristineCoreStateMigrations: true } : {}
});
if (beforeStateMigrations && isGatewayRunAction(actionCommand)) {
const { reloadTrustedGatewayRunEnvironment } = await import("./pre-bootstrap-CenrzAsB.js");
await reloadTrustedGatewayRunEnvironment({ runtime: defaultRuntime });
}
});
}
//#endregion
//#region src/cli/program/build-program.ts
function buildProgram() {
const program = new OpenClawCommand();
program.enablePositionalOptions();
program.exitOverride((err) => {
process$1.exitCode = typeof err.exitCode === "number" ? err.exitCode : 1;
throw err;
});
const ctx = createProgramContext();
const argv = process$1.argv;
setProgramContext(program, ctx);
configureProgramHelp(program, ctx);
registerPreActionHooks(program, ctx.programVersion);
registerProgramCommands(program, ctx, argv);
return program;
}
//#endregion
export { buildProgram, forceFreePort };