mirror of
https://github.com/openclaw/openclaw.git
synced 2026-05-09 17:20:43 +00:00
perf: fast-path gateway foreground startup
This commit is contained in:
@@ -10,6 +10,7 @@ import {
|
||||
defineImportedProgramCommandGroupSpecs,
|
||||
type CommandGroupDescriptorSpec,
|
||||
} from "./command-group-descriptors.js";
|
||||
import { removeCommandByName } from "./command-tree.js";
|
||||
import { loadPrivateQaCliModule } from "./private-qa-cli.js";
|
||||
import {
|
||||
registerCommandGroupByName,
|
||||
@@ -26,6 +27,28 @@ export { getSubCliCommandsWithSubcommands };
|
||||
|
||||
type SubCliRegistrar = (program: Command) => Promise<void> | void;
|
||||
|
||||
function shouldRegisterGatewayRunOnly(name: string, argv: string[]): boolean {
|
||||
if (name !== "gateway") {
|
||||
return false;
|
||||
}
|
||||
const invocation = resolveCliArgvInvocation(argv);
|
||||
if (invocation.hasHelpOrVersion || invocation.commandPath[0] !== "gateway") {
|
||||
return false;
|
||||
}
|
||||
return invocation.commandPath.length === 1 || invocation.commandPath[1] === "run";
|
||||
}
|
||||
|
||||
async function registerGatewayRunOnly(program: Command): Promise<void> {
|
||||
const { addGatewayRunCommand } = await import("../gateway-cli/run.js");
|
||||
removeCommandByName(program, "gateway");
|
||||
const gateway = addGatewayRunCommand(
|
||||
program.command("gateway").description("Run, inspect, and query the WebSocket Gateway"),
|
||||
);
|
||||
addGatewayRunCommand(
|
||||
gateway.command("run").description("Run the WebSocket Gateway (foreground)"),
|
||||
);
|
||||
}
|
||||
|
||||
async function registerSubCliWithPluginCommands(
|
||||
program: Command,
|
||||
registerSubCli: () => Promise<void>,
|
||||
@@ -241,7 +264,15 @@ export function getSubCliEntries(): ReadonlyArray<SubCliDescriptor> {
|
||||
return getSubCliEntryDescriptors();
|
||||
}
|
||||
|
||||
export async function registerSubCliByName(program: Command, name: string): Promise<boolean> {
|
||||
export async function registerSubCliByName(
|
||||
program: Command,
|
||||
name: string,
|
||||
argv: string[] = process.argv,
|
||||
): Promise<boolean> {
|
||||
if (shouldRegisterGatewayRunOnly(name, argv)) {
|
||||
await registerGatewayRunOnly(program);
|
||||
return true;
|
||||
}
|
||||
return registerCommandGroupByName(program, resolveSubCliCommandGroups(), name);
|
||||
}
|
||||
|
||||
|
||||
@@ -47,8 +47,25 @@ const { registerPluginsCli, registerPluginCliCommandsFromValidatedConfig } = vi.
|
||||
}),
|
||||
registerPluginCliCommandsFromValidatedConfig: vi.fn(async () => null),
|
||||
}));
|
||||
const { addGatewayRunCommand, gatewayRunAction, registerGatewayCli } = vi.hoisted(() => {
|
||||
const runAction = vi.fn();
|
||||
return {
|
||||
addGatewayRunCommand: vi.fn((command: Command) =>
|
||||
command.option("--force", "force", false).action(runAction),
|
||||
),
|
||||
gatewayRunAction: runAction,
|
||||
registerGatewayCli: vi.fn((program: Command) => {
|
||||
program
|
||||
.command("gateway")
|
||||
.command("call")
|
||||
.action(() => undefined);
|
||||
}),
|
||||
};
|
||||
});
|
||||
|
||||
vi.mock("../acp-cli.js", () => ({ registerAcpCli }));
|
||||
vi.mock("../gateway-cli.js", () => ({ registerGatewayCli }));
|
||||
vi.mock("../gateway-cli/run.js", () => ({ addGatewayRunCommand }));
|
||||
vi.mock("../nodes-cli.js", () => ({ registerNodesCli }));
|
||||
vi.mock("../capability-cli.js", () => ({ registerCapabilityCli }));
|
||||
vi.mock("../plugins-cli.js", () => ({ registerPluginsCli }));
|
||||
@@ -93,6 +110,9 @@ describe("registerSubCliCommands", () => {
|
||||
inferAction.mockClear();
|
||||
registerPluginsCli.mockClear();
|
||||
registerPluginCliCommandsFromValidatedConfig.mockClear();
|
||||
addGatewayRunCommand.mockClear();
|
||||
gatewayRunAction.mockClear();
|
||||
registerGatewayCli.mockClear();
|
||||
});
|
||||
|
||||
afterEach(() => {
|
||||
@@ -174,6 +194,30 @@ describe("registerSubCliCommands", () => {
|
||||
expect(acpAction).toHaveBeenCalledTimes(1);
|
||||
});
|
||||
|
||||
it("registers only the gateway run surface for gateway startup", async () => {
|
||||
const argv = ["node", "openclaw", "gateway", "--force"];
|
||||
process.argv = argv;
|
||||
const program = new Command().name("openclaw");
|
||||
|
||||
await registerSubCliByName(program, "gateway", argv);
|
||||
|
||||
expect(addGatewayRunCommand).toHaveBeenCalledTimes(2);
|
||||
expect(registerGatewayCli).not.toHaveBeenCalled();
|
||||
await program.parseAsync(["gateway", "--force"], { from: "user" });
|
||||
expect(gatewayRunAction).toHaveBeenCalledTimes(1);
|
||||
});
|
||||
|
||||
it("keeps the full gateway CLI for non-run gateway subcommands", async () => {
|
||||
const argv = ["node", "openclaw", "gateway", "call", "health"];
|
||||
process.argv = argv;
|
||||
const program = new Command().name("openclaw");
|
||||
|
||||
await registerSubCliByName(program, "gateway", argv);
|
||||
|
||||
expect(addGatewayRunCommand).not.toHaveBeenCalled();
|
||||
expect(registerGatewayCli).toHaveBeenCalledTimes(1);
|
||||
});
|
||||
|
||||
it.each([
|
||||
["plugins update", ["plugins", "update", "lossless-claw"]],
|
||||
["plugins update --all", ["plugins", "update", "--all"]],
|
||||
|
||||
@@ -46,8 +46,12 @@ export function getSubCliEntries(): ReadonlyArray<SubCliDescriptor> {
|
||||
return getSubCliEntryDescriptors();
|
||||
}
|
||||
|
||||
export async function registerSubCliByName(program: Command, name: string): Promise<boolean> {
|
||||
if (await registerSubCliByNameCore(program, name)) {
|
||||
export async function registerSubCliByName(
|
||||
program: Command,
|
||||
name: string,
|
||||
argv: string[] = process.argv,
|
||||
): Promise<boolean> {
|
||||
if (await registerSubCliByNameCore(program, name, argv)) {
|
||||
return true;
|
||||
}
|
||||
return registerCommandGroupByName(program, resolveSubCliCommandGroups(), name);
|
||||
|
||||
Reference in New Issue
Block a user