Zie619/n8n-workflows · error · Error

No Todoist section found for status '${statusName}'

Error message

No Todoist section found for status '${statusName}'

What it means

Thrown by 'Map Notion to Todoist' (runOnceForEachItem) when a Notion task's Status name (properties['Status'].status.name) has no matching section in globals.sections — the section list fetched earlier from the Todoist project. Done and Obsolete are exempted (no section needed); every other status must exist as a Todoist section by exact name.

Source

Thrown at workflows/Webhook/1897_Webhook_Filter_Sync_Webhook.json:896

              "value": "={{ $json.section_id }}"
            }
          ]
        }
      },
      "typeVersion": 3.4,
      "notes": "This set node performs automated tasks as part of the workflow."
    },
    {
      "id": "283370f2-93ff-4272-82bf-ad45c54e47f7",
      "name": "Map Notion to Todoist",
      "type": "n8n-nodes-base.code",
      "position": [
        3200,
        400
      ],
      "parameters": {
        "mode": "runOnceForEachItem",
        "jsCode": "const globals = $('Globals').first().json;\nconst properties = $json.properties;\n\nlet output = {};\n\noutput.id = properties['Todoist ID'].rich_text.length > 0 ? \n  properties['Todoist ID'].rich_text[0].text.content : \n  null;\n\noutput.content = properties['Name'].title.length > 0 ? properties['Name'].title[0].text.content : '[empty]';\n\noutput.description = \"[↗ Open in Notion](\" + $json.url + \")\"\n\n// Map priority\nif (properties['Priority'].select === null) {\n  output.priority = \"1\"; // P4\n} else {\n  output.priority = {\n    \"do first\": \"4\", // P1\n    \"urgent\": \"3\", // P2\n    \"important\": \"2\" // P3\n  }[properties['Priority'].select.name] ?? \"1\"; // P4\n}\n\n// Map section\nconst statusName = properties['Status'].status.name;\noutput.section_id = null;\nif (!['Done', 'Obsolete'].includes(statusName)) {\n  const sectionMap = Object.fromEntries(\n      globals.sections.map(section => [section.name, section.id])\n  );\n  if (!sectionMap.hasOwnProperty(statusName)) {\n      throw new Error(\"No Todoist section found for status '\" + statusName + \"'\");\n  }\n  output.section_id = sectionMap[statusName];\n}\n\n// Set UTC if time is set\noutput.due_datetime = null;\nif (properties['Due'].date !== null) {\n  output.due_datetime = properties.Due.date.start;\n  if (properties.Due.date.start.length > 10) {\n    output.due_datetime = new Date(properties.Due.date.start).toISOString();\n  }\n}\n\nreturn { json: output };"
      },
      "typeVersion": 2,
      "notes": "This code node performs automated tasks as part of the workflow."
    },
    {
      "id": "ca33c90f-3204-45e1-9d66-20e7e740a4d7",
      "name": "Update task in Todoist before closing",
      "type": "n8n-nodes-base.httpRequest",
      "position": [
        4540,
        1120
      ],
      "parameters": {
        "url": "{{ $env.BASE_URL }}",
        "method": "POST",
        "options": {},
        "jsonQuery": "={{ $json.toJsonString() }}",
        "sendQuery": true,

View on GitHub (pinned to 94007c1445)

Solutions

  1. Compare the Notion status names with the Todoist project's sections and create the missing section in Todoist (exact name match).
  2. Add a fallback mapping in the code for known renames, or default to a catch-all section instead of throwing.
  3. Verify the Globals node's project_id and that its sections list is complete (check its pinned output).
  4. Include the available section names in the error message for instant diagnosis.

Example fix

// before
if (!sectionMap.hasOwnProperty(statusName)) {
    throw new Error("No Todoist section found for status '" + statusName + "'");
}
output.section_id = sectionMap[statusName];

// after - explicit fallback with visibility
const FALLBACK_SECTION = 'Backlog';
if (!sectionMap.hasOwnProperty(statusName)) {
  if (!sectionMap.hasOwnProperty(FALLBACK_SECTION)) {
    throw new Error(`No Todoist section for status '${statusName}' and no fallback '${FALLBACK_SECTION}'. Known sections: ${Object.keys(sectionMap).join(', ')}`);
  }
  console.warn(`Unknown status '${statusName}'; routing to '${FALLBACK_SECTION}'`);
  output.section_id = sectionMap[FALLBACK_SECTION];
} else {
  output.section_id = sectionMap[statusName];
}
Defensive patterns

Strategy: validation

Validate before calling

const sectionMap = Object.fromEntries(globals.sections.map(s => [s.name, s.id]));
const statusName = properties['Status'].status.name;
if (!['Done', 'Obsolete'].includes(statusName) && !(statusName in sectionMap)) {
  // policy choice: fail loudly with full context, or fall back
  const fallback = sectionMap['Backlog'];
  if (!fallback) {
    throw new Error(`No section for '${statusName}'. Known: ${Object.keys(sectionMap).join(', ')}`);
  }
  output.section_id = fallback;
} else {
  output.section_id = sectionMap[statusName] ?? null;
}

Type guard

const isKnownStatus = (name, sections) =>
  ['Done', 'Obsolete'].includes(name) ||
  sections.some(s => s.name === name);

Prevention

When it happens

Trigger: A new status added to the Notion database (e.g., 'In Review') without creating the same-named section in the Todoist project, a renamed Notion status ('In Progress' -> 'Doing'), or the Globals node having fetched sections from the wrong project / an incomplete list (pagination, API hiccup).

Common situations: Notion databases evolve faster than the Todoist project; teams rename statuses; the Todoist project ID changes so globals.sections is empty or foreign; case/whitespace mismatches ('backlog' vs 'Backlog').

Related errors


AI-assisted analysis of Zie619/n8n-workflows@94007c1445 (2026-08-15). Data as JSON: /api/errors/d157f7d1d0d45c5c. Report an issue: GitHub.