Skip to main content
Glama

get_active_tasks

Retrieve a list of uncompleted tasks from OmniFocus to view current work items and manage ongoing activities.

Instructions

Call this tool to get a list of all active (uncompleted) tasks from the user's OmniFocus. Use it when the user asks for their 'active tasks', 'current tasks', or 'open tasks'.

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault

No arguments

Implementation Reference

  • Core handler function implementing the logic to fetch active tasks from OmniFocus by generating and executing a JXA script, parsing the JSON output.
    async getActiveTasks(filters: TaskFilters = {}): Promise<OmniFocusTask[]> { console.error('[DEBUG] getActiveTasks called with filters:', JSON.stringify(filters)); const jxaScript = buildJxaScriptForTasks(true); const output = this.executeScript(jxaScript); try { const tasks = JSON.parse(output); return tasks; } catch (e) { console.error('[DEBUG] Failed to parse OmniFocus JXA output:', output); throw new Error('Failed to parse OmniFocus output as JSON'); } }
  • src/server.ts:46-50 (registration)
    Tool registration in the MCP ListTools response, including name, description, and input schema (empty object since no parameters required).
    { name: 'get_active_tasks', description: "Call this tool to get a list of all active (uncompleted) tasks from the user's OmniFocus. Use it when the user asks for their 'active tasks', 'current tasks', or 'open tasks'.", inputSchema: { type: 'object', properties: {} } },
  • MCP CallToolRequest handler dispatch for 'get_active_tasks', invoking the OmniFocusClient method.
    case 'get_active_tasks': result = await this.client.getActiveTasks(); break;
  • TypeScript interface defining the structure of OmniFocusTask, used as the return type for getActiveTasks.
    export interface OmniFocusTask { id: string; name: string; note: string; completed: boolean; completionDate?: string | null; creationDate: string; modificationDate: string; dueDate?: string | null; deferDate?: string | null; estimatedMinutes?: number | null; flagged: boolean; repetitionRule?: string | null; sequential: boolean; project?: { id: string; name: string; } | null; context?: { id: string; name: string; } | null; containingProject?: { id: string; name: string; } | null; }
  • Helper function generating the JXA (JavaScript for Automation) script executed in OmniFocus to retrieve active tasks, including filtering logic.
    export function buildJxaScriptForTasks(activeOnly: boolean): string { return ` (() => { const app = Application('OmniFocus'); app.includeStandardAdditions = true; const ofDoc = app.defaultDocument; function safe(obj, method) { try { return obj && typeof obj[method] === 'function' ? obj[method]() : null; } catch { return null; } } function getContext(task) { const ctx = safe(task, 'context'); return ctx ? { id: safe(ctx, 'id'), name: safe(ctx, 'name') } : null; } function getProject(task) { const proj = safe(task, 'containingProject'); return proj ? { id: safe(proj, 'id'), name: safe(proj, 'name') } : null; } function isInTemplatesFolder(project) { let folder = safe(project, 'folder'); while (folder) { if (safe(folder, 'name') === 'Templates') return true; folder = safe(folder, 'parentFolder'); } return false; } function isExcludedTask(task) { const name = safe(task, 'name') || ''; const note = safe(task, 'note') || ''; if (name.includes('«') || name.includes('»') || note.includes('«') || note.includes('»')) return true; if (name.includes('⚙️') || note.includes('⚙️')) return true; const proj = safe(task, 'containingProject'); if (!proj) return false; return isInTemplatesFolder(proj); } function getTaskData(task) { return { id: safe(task, 'id'), name: safe(task, 'name'), note: safe(task, 'note'), completed: safe(task, 'completed'), status: safe(task, 'status'), completionDate: safe(task, 'completionDate') ? safe(task, 'completionDate').toISOString() : null, creationDate: safe(task, 'creationDate') ? safe(task, 'creationDate').toISOString() : null, modificationDate: safe(task, 'modificationDate') ? safe(task, 'modificationDate').toISOString() : null, dueDate: safe(task, 'dueDate') ? safe(task, 'dueDate').toISOString() : null, deferDate: safe(task, 'deferDate') ? safe(task, 'deferDate').toISOString() : null, estimatedMinutes: safe(task, 'estimatedMinutes'), flagged: safe(task, 'flagged'), repetitionRule: safe(task, 'repetitionRule'), sequential: safe(task, 'sequential'), project: safe(task, 'project'), context: getContext(task), containingProject: getProject(task) }; } const allTasks = Array.from(ofDoc.flattenedTasks()); const filteredTasks = allTasks.filter(task => { if (isExcludedTask(task)) return false; const statusObj = safe(task, 'status') ? task.status() : null; const statusName = statusObj ? safe(statusObj, 'name') : ''; if (${activeOnly ? 'true' : 'false'}) { // Exclude completed or dropped tasks return !task.completed() && !/dropped/i.test(statusName); } return true; }); const result = filteredTasks.map(getTaskData); return JSON.stringify(result); })(); `; }

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/mdoel/omnifocus-mcp'

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