CherryHQ/cherry-studio · error · Error

Invalid arguments for write: ${parsed.error}

Error message

Invalid arguments for write: ${parsed.error}

What it means

Thrown by the write tool when WriteToolSchema.safeParse(args) fails. The schema (write.ts:8) requires file_path: string and content: string. Zod's default object mode does not reject unknown keys, so the failure is specifically about file_path or content being absent, undefined, or not a string. The full Zod issue tree is appended via parsed.error.

Source

Thrown at src/main/ai/mcp/servers/filesystem/tools/write.ts:31

// Tool definition with detailed description
export const writeToolDefinition = {
  name: 'write',
  description: `Writes a file to the local filesystem.

- This tool will overwrite the existing file if one exists at the path
- You MUST use the read tool first to understand what you're overwriting
- ALWAYS prefer using the 'edit' tool for existing files
- NEVER proactively create documentation files unless explicitly requested
- Parent directories will be created automatically if they don't exist
- The file_path must resolve within the configured workspace root`,
  inputSchema: z.toJSONSchema(WriteToolSchema)
}

// Handler implementation
export async function handleWriteTool(args: unknown, baseDir: string) {
  const parsed = WriteToolSchema.safeParse(args)
  if (!parsed.success) {
    throw new Error(`Invalid arguments for write: ${parsed.error}`)
  }

  const filePath = parsed.data.file_path
  const validPath = await validatePath(filePath, baseDir)

  // Create parent directory if it doesn't exist
  const parentDir = path.dirname(validPath)
  try {
    await fs.mkdir(parentDir, { recursive: true })
  } catch (error: any) {
    if (error.code !== 'EEXIST') {
      throw new Error(`Failed to create parent directory: ${error.message}`)
    }
  }

  // Check if file exists (for logging)
  let isOverwrite = false
  try {

View on GitHub (pinned to 726446b54c)

Solutions

  1. Ensure args is exactly { file_path: string, content: string } with both fields present and string-typed.
  2. Use the snake_case key names file_path and content as defined in WriteToolSchema, not camelCase aliases.
  3. Run WriteToolSchema.safeParse(args) on the caller side first and surface parsed.error before sending.

Example fix

// before
await handleWriteTool({ filePath: 'a.txt', content: 'hi' }, baseDir) // throws: Invalid arguments (file_path missing)

// after
await handleWriteTool({ file_path: 'a.txt', content: 'hi' }, baseDir)
Defensive patterns

Strategy: validation

Validate before calling

import { WriteToolSchema } from './write'
const parsed = WriteToolSchema.safeParse(args)
if (!parsed.success) {
  // report parsed.error to the user before calling handleWriteTool
}

Type guard

function isWriteArgs(a: unknown): a is { file_path: string; content: string } {
  return typeof a === 'object' && a !== null &&
    typeof (a as any).file_path === 'string' &&
    typeof (a as any).content === 'string'
}

Try / catch

try {
  await handleWriteTool(args, baseDir)
} catch (e) {
  if (e instanceof Error && e.message.startsWith('Invalid arguments for write')) {
    // fix args shape using the Zod error details
  } else throw e
}

Prevention

When it happens

Trigger: Calling handleWriteTool with missing file_path or content; passing content as a non-string (number, object, Buffer); passing an object whose keys are nested differently than {file_path, content}; args is undefined/null is caught earlier only if Zod receives it (safeParse handles it and reports type errors).

Common situations: Caller uses a camelCase key (filePath) instead of file_path; content omitted because the caller assumed an overwrite-from-empty default; args built dynamically where a field ended up undefined after a conditional; SDK/client that strips falsy strings sent content as '' which is actually valid (empty string passes).

Related errors


AI-assisted analysis of CherryHQ/cherry-studio@726446b54c (2026-08-12). Data as JSON: /api/errors/7beec02fa4fd8970. Report an issue: GitHub.