Skip to main content
Glama
kydycode

Enhanced Todoist MCP Server Extended

todoist_move_task

Move a Todoist task to a different project, section, or make it a subtask of another task, including all subtasks.

Instructions

Move a single task (and its subtasks, if any) to a different project, section, or make it a subtask of another task. Provide the taskId and exactly one of: projectId, sectionId, or parentId.

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault
taskIdYesThe ID of the task to move.
projectIdNoThe ID of the destination project. (Optional, use only one of projectId, sectionId, parentId)
sectionIdNoThe ID of the destination section. (Optional, use only one of projectId, sectionId, parentId)
parentIdNoThe ID of the parent task to move this task under. (Optional, use only one of projectId, sectionId, parentId)

Implementation Reference

  • Executes the tool logic: validates args with isMoveTaskArgs, constructs moveArgs, calls todoistClient.moveTasks([taskId], moveArgs), fetches updated task with getTask, formats and returns success response or error.
    if (name === "todoist_move_task") { if (!isMoveTaskArgs(args)) { return { content: [{ type: "text", text: "Invalid arguments for move_task. Provide taskId and exactly one of: projectId, sectionId, or parentId (must be a non-empty string)." }], isError: true }; } try { const moveArgs: { projectId?: string; sectionId?: string; parentId?: string } = {}; if (args.projectId) moveArgs.projectId = args.projectId; else if (args.sectionId) moveArgs.sectionId = args.sectionId; else if (args.parentId) moveArgs.parentId = args.parentId; // Use moveTasks from SDK v4+ await todoistClient.moveTasks([args.taskId], moveArgs as any); // Cast to any for MoveTaskArgs as it expects RequireExactlyOne const movedTask = await todoistClient.getTask(args.taskId); return { content: [{ type: "text", text: `Task ${args.taskId} moved successfully.\nNew details:\n${formatTask(movedTask)}` }], isError: false }; } catch (error: any) { return { content: [{ type: "text", text: `Error moving task: ${error.message}` }], isError: true }; } }
  • JSON schema defining the input parameters for the todoist_move_task tool: taskId (required), and exactly one optional destination: projectId, sectionId, or parentId.
    const MOVE_TASK_TOOL: Tool = { name: "todoist_move_task", description: "Move a single task (and its subtasks, if any) to a different project, section, or make it a subtask of another task. Provide the taskId and exactly one of: projectId, sectionId, or parentId.", inputSchema: { type: "object", properties: { taskId: { type: "string", description: "The ID of the task to move." }, projectId: { type: "string", description: "The ID of the destination project. (Optional, use only one of projectId, sectionId, parentId)" }, sectionId: { type: "string", description: "The ID of the destination section. (Optional, use only one of projectId, sectionId, parentId)" }, parentId: { type: "string", description: "The ID of the parent task to move this task under. (Optional, use only one of projectId, sectionId, parentId)" } }, required: ["taskId"] // Note: Validation for providing exactly one of projectId, sectionId, or parentId // is handled in the isMoveTaskArgs type guard and the tool handler. // A more complex JSON schema with oneOf could enforce this, but client support varies. } };
  • src/index.ts:1083-1121 (registration)
    Registers the todoist_move_task tool (as MOVE_TASK_TOOL) in the list of available tools returned by the ListToolsRequest handler.
    server.setRequestHandler(ListToolsRequestSchema, async () => ({ tools: [ // Task tools CREATE_TASK_TOOL, QUICK_ADD_TASK_TOOL, GET_TASKS_TOOL, GET_TASK_TOOL, UPDATE_TASK_TOOL, DELETE_TASK_TOOL, COMPLETE_TASK_TOOL, REOPEN_TASK_TOOL, SEARCH_TASKS_TOOL, MOVE_TASK_TOOL, BULK_MOVE_TASKS_TOOL, // Project tools GET_PROJECTS_TOOL, GET_PROJECT_TOOL, CREATE_PROJECT_TOOL, UPDATE_PROJECT_TOOL, DELETE_PROJECT_TOOL, // Section tools GET_SECTIONS_TOOL, CREATE_SECTION_TOOL, UPDATE_SECTION_TOOL, DELETE_SECTION_TOOL, // Label tools CREATE_LABEL_TOOL, GET_LABEL_TOOL, GET_LABELS_TOOL, UPDATE_LABEL_TOOL, DELETE_LABEL_TOOL, // Comment tools CREATE_COMMENT_TOOL, GET_COMMENT_TOOL, GET_COMMENTS_TOOL, UPDATE_COMMENT_TOOL, DELETE_COMMENT_TOOL, ], }));
  • Type guard helper that validates the input arguments for todoist_move_task, ensuring taskId is a string and exactly one non-empty destination (projectId, sectionId, or parentId) is provided.
    function isMoveTaskArgs(args: unknown): args is { taskId: string; projectId?: string; sectionId?: string; parentId?: string; } { if (typeof args !== 'object' || args === null || !('taskId' in args) || typeof (args as any).taskId !== 'string') { return false; } const { projectId, sectionId, parentId } = args as any; const destinations = [projectId, sectionId, parentId]; const providedDestinations = destinations.filter(dest => dest !== undefined && dest !== null && String(dest).trim() !== ''); // Exactly one destination must be provided and be a non-empty string return providedDestinations.length === 1 && providedDestinations.every(dest => typeof dest === 'string'); }

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/kydycode/todoist-mcp-server-ext'

If you have feedback or need assistance with the MCP directory API, please join our Discord server