On this page
Guides / Tasks

Tasks

Workspace checklists that split work between people, with steps, comments, views and activity.

Updated View .md

A task is a workspace checklist: a piece of work with an owner, an optional deadline and steps that the person they are assigned to checks off. The API lets you create them, fill them in and read where they stand, so work that starts in your system shows up on Meteor's task board and the other way around.

Use the tasks:read and tasks:write scopes.

The API no longer runs tasks. Until August 31, 2026 (contract 3.0.0) a task could be triggered, run step by step by a Met and stop to ask for approval. That was retired: tasks.execute(), the execution history, approveStep(), rejectStep(), completeHumanStep(), cancelExecution(), tasks.triggers and met tasks run no longer exist, and their endpoints return 404. Anything that runs on its own is built today in Functions and flows, and to have a Met do the work you use a Run. The task.completed event is no longer emitted (see Webhooks).

Create a task

A task has one owner: a person (responsible_user_id) or a Met (responsible_met_id), never both.

const task = await met.tasks.create({
  name: 'Qualify new leads',
  description: 'Review contacts with no stage and leave a qualification.',
  responsible_user_id: 77,
  deadline: '2026-11-05T17:00:00-05:00',
});
// → { id, name, status, ... }
task = met.tasks.create(
    name="Qualify new leads",
    description="Review contacts with no stage and leave a qualification.",
    responsible_user_id=77,
    deadline="2026-11-05T17:00:00-05:00",
)

With contact_id the task becomes a follow-up of a CRM contact, and met.tasks.iterate({ contactId }) returns only that contact's tasks. list() stops at 100; iterate() walks all of them.

Steps

Steps are the checklist. They are created one at a time, go at the end (or right below another one with after_step_id) and are assigned to a person: a step is not assigned to a Met.

const step = await met.tasks.steps.create(task.id, {
  name: 'Pull contacts with no stage',
  assigned_to_user_id: 77,
});

// Whoever does the step checks it off; your system can do it too.
await met.tasks.steps.update(task.id, step.id, { status: 'completed' });

await met.tasks.steps.reorder(task.id, [stepB.id, stepA.id]);

A step is pending or completed. Tasks created before the executor was retired may keep running, failed or cancelled on some step; nothing writes them anymore.

steps.updateResult() replaces the step's result with content blocks. It is useful when the real work was done by your system and you want to leave the deliverable on the task:

await met.tasks.steps.updateResult(task.id, step.id, {
  blocks: [{ type: 'text', data: { html: '<p>42 contacts qualified</p>' } }],
});

It replaces, it does not append: the array you send becomes the full result.

Find out where it stands

const detail = await met.tasks.retrieve(task.id);   // the task with its steps
const steps = (detail.steps ?? []) as Array<{ id: string; name: string; status?: string }>;
const pending = steps.filter((s) => s.status !== 'completed');

There is no task event: to learn about a change, read the detail or the activity when you need it, not in a loop every few seconds.

Status

await met.tasks.setStatus(task.id, 'completed');

It accepts pending, running, paused, completed, failed and cancelled; what each one means day to day is defined by your workspace's board, not by the API. Changing the status does not run anything.

Comments and attachments

The task thread accepts files. Upload first, then send the metadata:

const attachment = await met.tasks.comments.upload(task.id, file, {
  filename: 'report.pdf',
  contentType: 'application/pdf',
});

await met.tasks.comments.create(task.id, {
  body: 'Attaching the closing report.',
  attachments: [attachment],
});

A comment needs body or attachments; an empty one returns 400.

Context and activity

const activity = await met.tasks.activity(task.id);            // one task
const all = await met.tasks.workspaceActivity({ limit: 50 });  // the whole workspace

const linked = await met.tasks.linkedItems(task.id);           // items the task lives in

linkedItems() returns the collection items that have the task embedded in their content: it is how you know which record the work was requested from. See Collections and items.

Saved views

Views belong to the workspace, not to a task: saved filters over the panel's list.

await met.tasks.views.create({
  name: 'Paused',
  filters: [{ field: 'status', operator: 'is', value: 'paused' }],
});

views.reorder() is deprecated and stops responding on 2027-04-08: it is the order of the panel's menu, not workspace data.