refactor: remove parseArgs value casts in subcommands (#1157)

This commit is contained in:
Devansh Jain
2026-02-25 20:15:15 -08:00
committed by GitHub
parent cca57b1759
commit 2c243151c6
4 changed files with 122 additions and 88 deletions

View File

@@ -38,23 +38,29 @@ function parseTags(value: unknown): string[] | undefined {
return tags.length > 0 ? tags : undefined;
}
const AGENTS_OPTIONS = {
help: { type: "boolean", short: "h" },
name: { type: "string" },
query: { type: "string" },
tags: { type: "string" },
"match-all-tags": { type: "boolean" },
"include-blocks": { type: "boolean" },
limit: { type: "string" },
} as const;
function parseAgentsArgs(argv: string[]) {
return parseArgs({
args: argv,
options: AGENTS_OPTIONS,
strict: true,
allowPositionals: true,
});
}
export async function runAgentsSubcommand(argv: string[]): Promise<number> {
let parsed: ReturnType<typeof parseArgs>;
let parsed: ReturnType<typeof parseAgentsArgs>;
try {
parsed = parseArgs({
args: argv,
options: {
help: { type: "boolean", short: "h" },
name: { type: "string" },
query: { type: "string" },
tags: { type: "string" },
"match-all-tags": { type: "boolean" },
"include-blocks": { type: "boolean" },
limit: { type: "string" },
},
strict: true,
allowPositionals: true,
});
parsed = parseAgentsArgs(argv);
} catch (error) {
const message = error instanceof Error ? error.message : String(error);
console.error(`Error: ${message}`);

View File

@@ -27,6 +27,26 @@ function getAgentId(agentFromArgs?: string, agentIdFromArgs?: string): string {
return agentFromArgs || agentIdFromArgs || process.env.LETTA_AGENT_ID || "";
}
const BLOCKS_OPTIONS = {
help: { type: "boolean", short: "h" },
agent: { type: "string" },
"agent-id": { type: "string" },
limit: { type: "string" },
"block-id": { type: "string" },
label: { type: "string" },
override: { type: "boolean" },
"read-only": { type: "boolean" },
} as const;
function parseBlocksArgs(argv: string[]) {
return parseArgs({
args: argv,
options: BLOCKS_OPTIONS,
strict: true,
allowPositionals: true,
});
}
type CopyBlockResult = {
sourceBlock: Awaited<
ReturnType<Awaited<ReturnType<typeof getClient>>["blocks"]["retrieve"]>
@@ -253,23 +273,9 @@ async function attachBlock(
}
export async function runBlocksSubcommand(argv: string[]): Promise<number> {
let parsed: ReturnType<typeof parseArgs>;
let parsed: ReturnType<typeof parseBlocksArgs>;
try {
parsed = parseArgs({
args: argv,
options: {
help: { type: "boolean", short: "h" },
agent: { type: "string" },
"agent-id": { type: "string" },
limit: { type: "string" },
"block-id": { type: "string" },
label: { type: "string" },
override: { type: "boolean" },
"read-only": { type: "boolean" },
},
strict: true,
allowPositionals: true,
});
parsed = parseBlocksArgs(argv);
} catch (error) {
const message = error instanceof Error ? error.message : String(error);
console.error(`Error: ${message}`);
@@ -306,8 +312,8 @@ export async function runBlocksSubcommand(argv: string[]): Promise<number> {
return 1;
}
const agentId = getAgentId(
parsed.values.agent as string | undefined,
parsed.values["agent-id"] as string | undefined,
parsed.values.agent,
parsed.values["agent-id"],
);
const result = await copyBlock(client, blockId, {
labelOverride:
@@ -328,8 +334,8 @@ export async function runBlocksSubcommand(argv: string[]): Promise<number> {
return 1;
}
const agentId = getAgentId(
parsed.values.agent as string | undefined,
parsed.values["agent-id"] as string | undefined,
parsed.values.agent,
parsed.values["agent-id"],
);
const result = await attachBlock(client, blockId, {
readOnly: parsed.values["read-only"] === true,

View File

@@ -40,6 +40,24 @@ function getAgentId(agentFromArgs?: string, agentIdFromArgs?: string): string {
return agentFromArgs || agentIdFromArgs || process.env.LETTA_AGENT_ID || "";
}
const MEMFS_OPTIONS = {
help: { type: "boolean", short: "h" },
agent: { type: "string" },
"agent-id": { type: "string" },
from: { type: "string" },
force: { type: "boolean" },
out: { type: "string" },
} as const;
function parseMemfsArgs(argv: string[]) {
return parseArgs({
args: argv,
options: MEMFS_OPTIONS,
strict: true,
allowPositionals: true,
});
}
function getMemoryRoot(agentId: string): string {
return join(homedir(), ".letta", "agents", agentId, "memory");
}
@@ -97,21 +115,9 @@ function resolveBackupPath(agentId: string, from: string): string {
}
export async function runMemfsSubcommand(argv: string[]): Promise<number> {
let parsed: ReturnType<typeof parseArgs>;
let parsed: ReturnType<typeof parseMemfsArgs>;
try {
parsed = parseArgs({
args: argv,
options: {
help: { type: "boolean", short: "h" },
agent: { type: "string" },
"agent-id": { type: "string" },
from: { type: "string" },
force: { type: "boolean" },
out: { type: "string" },
},
strict: true,
allowPositionals: true,
});
parsed = parseMemfsArgs(argv);
} catch (error) {
const message = error instanceof Error ? error.message : String(error);
console.error(`Error: ${message}`);
@@ -126,10 +132,7 @@ export async function runMemfsSubcommand(argv: string[]): Promise<number> {
return 0;
}
const agentId = getAgentId(
parsed.values.agent as string | undefined,
parsed.values["agent-id"] as string | undefined,
);
const agentId = getAgentId(parsed.values.agent, parsed.values["agent-id"]);
if (!agentId) {
console.error(
@@ -204,7 +207,7 @@ export async function runMemfsSubcommand(argv: string[]): Promise<number> {
}
if (action === "restore") {
const from = parsed.values.from as string | undefined;
const from = parsed.values.from;
if (!from) {
console.error("Missing --from <backup>.");
return 1;
@@ -231,7 +234,7 @@ export async function runMemfsSubcommand(argv: string[]): Promise<number> {
}
if (action === "export") {
const out = parsed.values.out as string | undefined;
const out = parsed.values.out;
if (!out) {
console.error("Missing --out <dir>.");
return 1;

View File

@@ -2,6 +2,7 @@ import { parseArgs } from "node:util";
import { getClient } from "../../agent/client";
type SearchMode = "vector" | "fts" | "hybrid";
type ListOrder = "asc" | "desc";
function printUsage(): void {
console.log(
@@ -52,32 +53,45 @@ function parseMode(value: unknown): SearchMode | undefined {
return undefined;
}
function parseOrder(value: unknown): ListOrder | undefined {
if (typeof value === "string" && (value === "asc" || value === "desc")) {
return value;
}
return undefined;
}
function getAgentId(agentFromArgs?: string, agentIdFromArgs?: string): string {
return agentFromArgs || agentIdFromArgs || process.env.LETTA_AGENT_ID || "";
}
const MESSAGES_OPTIONS = {
help: { type: "boolean", short: "h" },
query: { type: "string" },
mode: { type: "string" },
"start-date": { type: "string" },
"end-date": { type: "string" },
limit: { type: "string" },
"all-agents": { type: "boolean" },
agent: { type: "string" },
"agent-id": { type: "string" },
after: { type: "string" },
before: { type: "string" },
order: { type: "string" },
} as const;
function parseMessagesArgs(argv: string[]) {
return parseArgs({
args: argv,
options: MESSAGES_OPTIONS,
strict: true,
allowPositionals: true,
});
}
export async function runMessagesSubcommand(argv: string[]): Promise<number> {
let parsed: ReturnType<typeof parseArgs>;
let parsed: ReturnType<typeof parseMessagesArgs>;
try {
parsed = parseArgs({
args: argv,
options: {
help: { type: "boolean", short: "h" },
query: { type: "string" },
mode: { type: "string" },
"start-date": { type: "string" },
"end-date": { type: "string" },
limit: { type: "string" },
"all-agents": { type: "boolean" },
agent: { type: "string" },
"agent-id": { type: "string" },
after: { type: "string" },
before: { type: "string" },
order: { type: "string" },
},
strict: true,
allowPositionals: true,
});
parsed = parseMessagesArgs(argv);
} catch (error) {
const message = error instanceof Error ? error.message : String(error);
console.error(`Error: ${message}`);
@@ -103,8 +117,8 @@ export async function runMessagesSubcommand(argv: string[]): Promise<number> {
const allAgents = parsed.values["all-agents"] ?? false;
const agentId = getAgentId(
parsed.values.agent as string | undefined,
parsed.values["agent-id"] as string | undefined,
parsed.values.agent,
parsed.values["agent-id"],
);
if (!allAgents && !agentId) {
console.error(
@@ -117,8 +131,8 @@ export async function runMessagesSubcommand(argv: string[]): Promise<number> {
query,
agent_id: allAgents ? undefined : agentId,
search_mode: parseMode(parsed.values.mode) ?? "hybrid",
start_date: parsed.values["start-date"] as string | undefined,
end_date: parsed.values["end-date"] as string | undefined,
start_date: parsed.values["start-date"],
end_date: parsed.values["end-date"],
limit: parseLimit(parsed.values.limit, 10),
});
@@ -128,8 +142,8 @@ export async function runMessagesSubcommand(argv: string[]): Promise<number> {
if (action === "list") {
const agentId = getAgentId(
parsed.values.agent as string | undefined,
parsed.values["agent-id"] as string | undefined,
parsed.values.agent,
parsed.values["agent-id"],
);
if (!agentId) {
console.error(
@@ -138,11 +152,18 @@ export async function runMessagesSubcommand(argv: string[]): Promise<number> {
return 1;
}
const orderRaw = parsed.values.order;
const order = parseOrder(orderRaw);
if (orderRaw !== undefined && !order) {
console.error(`Invalid --order "${orderRaw}". Use "asc" or "desc".`);
return 1;
}
const response = await client.agents.messages.list(agentId, {
limit: parseLimit(parsed.values.limit, 20),
after: parsed.values.after as string | undefined,
before: parsed.values.before as string | undefined,
order: parsed.values.order as "asc" | "desc" | undefined,
after: parsed.values.after,
before: parsed.values.before,
order,
});
const messages = response.items ?? [];
@@ -151,11 +172,9 @@ export async function runMessagesSubcommand(argv: string[]): Promise<number> {
let filtered = messages;
if (startDate || endDate) {
const startTime = startDate
? new Date(startDate as string).getTime()
: 0;
const startTime = startDate ? new Date(startDate).getTime() : 0;
const endTime = endDate
? new Date(endDate as string).getTime()
? new Date(endDate).getTime()
: Number.POSITIVE_INFINITY;
filtered = messages.filter((msg) => {
if (!("date" in msg) || !msg.date) return true;