update_entry
Edit a timeline entry's content or subject; only supplied fields are changed. Use to correct or extend previous notes.
Instructions
Edit an existing timeline entry — typically a note. Provide the entry id plus the fields you want to change (content, subject). Only the fields you supply are modified; other fields keep their current values. Cannot change the entry's type. Use this to correct or extend a note added previously.
Input Schema
| Name | Required | Description | Default |
|---|---|---|---|
| id | Yes | Entry ID to update | |
| content | No | New body text for the entry. For notes, this is the markdown content; for emails, the body. Provide only if you want to change it. | |
| subject | No | New subject line. Mostly meaningful on email-type entries; on plain notes Capsule accepts the call (HTTP 200) but **does not store the subject and does not advance `updatedAt`** — a true no-op for inapplicable fields. `entryAt` (when the note was authored) is preserved across edits; `updatedAt` advances only when an applicable field actually changes. To sort/filter by 'when did this happen', use `entryAt`; for 'last touched', use `updatedAt`. |
Implementation Reference
- src/tools/entries.ts:165-176 (handler)The handler function that executes the update_entry logic. Extracts id and remaining fields (content, subject), builds a partial body object, and calls capsulePut to PATCH /entries/{id}.
export async function updateEntry(input: z.infer<typeof updateEntrySchema>) { const { id, ...rest } = input; const body: Record<string, unknown> = {}; if (rest.content !== undefined) body["content"] = rest.content; if (rest.subject !== undefined) body["subject"] = rest.subject; if (Object.keys(body).length === 0) { throw new Error("update_entry: provide at least one field to update (content or subject)"); } return capsulePut<{ entry: unknown }>(`/entries/${id}`, { entry: body }); } - src/tools/entries.ts:148-163 (schema)Zod schema for update_entry. Defines required id (positive integer), optional content (string min 1), and optional subject (string).
export const updateEntrySchema = z.object({ id: z.number().int().positive().describe("Entry ID to update"), content: z .string() .min(1) .optional() .describe( "New body text for the entry. For notes, this is the markdown content; for emails, the body. Provide only if you want to change it.", ), subject: z .string() .optional() .describe( "New subject line. Mostly meaningful on email-type entries; on plain notes Capsule accepts the call (HTTP 200) but **does not store the subject and does not advance `updatedAt`** — a true no-op for inapplicable fields. `entryAt` (when the note was authored) is preserved across edits; `updatedAt` advances only when an applicable field actually changes. To sort/filter by 'when did this happen', use `entryAt`; for 'last touched', use `updatedAt`.", ), }); - src/server.ts:812-818 (registration)Registration of the 'update_entry' tool on the MCP server with its description, schema, and handler via registerTool helper.
registerTool( server, "update_entry", "Edit an existing timeline entry — typically a note. Provide the entry id plus the fields you want to change (content, subject). Only the fields you supply are modified; other fields keep their current values. Cannot change the entry's type. Use this to correct or extend a note added previously.", updateEntrySchema, updateEntry, ); - src/server/register-tool.ts:39-59 (helper)The registerTool helper that wraps the handler and registers it with the MCP server (handles JSON-stringify response wrapping).
export function registerTool<Schema extends z.ZodObject<ZodRawShape>>( server: McpServer, name: string, description: string, schema: Schema, handler: (input: z.infer<Schema>) => Promise<unknown>, ): void { // Use the SDK config-form registerTool with the full Zod schema. The // deprecated shape overload rebuilds z.object(schema.shape), which drops // object-level refinements such as superRefine. const registerWithSchema = server.registerTool.bind(server) as ( toolName: string, config: { description: string; inputSchema: Schema }, callback: (input: z.infer<Schema>) => Promise<CallToolResult>, ) => void; registerWithSchema(name, { description, inputSchema: schema }, async (input) => { const result = await handler(input); return wrapAsText(result); }); }