AutomationFlowsGeneral › Convert Google Tasks to Google Calendar Events via Webhook Integration

Convert Google Tasks to Google Calendar Events via Webhook Integration

ByR4wd0G @r4wd0g on n8n.io

Operators and makers who capture tasks from custom forms, bots, or automations and want them to appear as time-boxed events in Google Calendar with minimal setup.

Webhook trigger★★★★☆ complexity16 nodesGoogle TasksGoogle Calendar
General Trigger: Webhook Nodes: 16 Complexity: ★★★★☆ Added:

This workflow corresponds to n8n.io template #7865 — we link there as the canonical source.

The workflow JSON

Copy or download the full n8n JSON below. Paste it into a new n8n workflow, add your credentials, activate. Full import guide →

Download .json
{
  "meta": {
    "templateCredsSetupCompleted": true
  },
  "nodes": [
    {
      "id": "e617195e-a1e2-4bb4-95b9-c7751ee8782c",
      "name": "Template Notes",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        272,
        0
      ],
      "parameters": {
        "color": 5,
        "width": 528,
        "height": 288,
        "content": "## What this template does\nCreate Google Calendar events from incoming task payloads.\n\n## How to set up\n1) Select Google credentials in Tasks & Calendar nodes.\n2) Configure `tasklistId` and `calendarId` in **Configuration**.\n3) POST `{ TaskName, DueDateTimeSeconds }` to the Webhook.\n4) Test, then activate.\n"
      },
      "typeVersion": 1
    },
    {
      "id": "8baf3bc2-affd-4427-ad8f-0a8eef5995e9",
      "name": "Configuration",
      "type": "n8n-nodes-base.set",
      "position": [
        320,
        480
      ],
      "parameters": {
        "values": {
          "number": [
            {
              "name": "defaultMinutes",
              "value": 30
            },
            {
              "name": "eventColor",
              "value": 8
            }
          ],
          "string": [
            {
              "name": "calendarId",
              "value": "primary"
            },
            {
              "name": "tasklistId",
              "value": "REPLACE_WITH_TASKLIST_ID"
            }
          ]
        },
        "options": {}
      },
      "typeVersion": 2
    },
    {
      "id": "6d90eb2d-3275-4525-b5d7-f7e761417683",
      "name": "Google Tasks",
      "type": "n8n-nodes-base.googleTasks",
      "position": [
        544,
        480
      ],
      "parameters": {
        "task": "={{ $('Configuration').item.json.tasklistId }}",
        "operation": "getAll",
        "additionalFields": {
          "showCompleted": false
        }
      },
      "credentials": {
        "googleTasksOAuth2Api": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 1
    },
    {
      "id": "668b1608-7a1b-4ac2-8570-fcbf8278cfaa",
      "name": "Date & Time",
      "type": "n8n-nodes-base.dateTime",
      "position": [
        752,
        480
      ],
      "parameters": {
        "date": "={{ $('Webhook').item.json.body.DueDateTimeSeconds.toDateTime(\"s\") }}",
        "format": "custom",
        "options": {},
        "operation": "formatDate",
        "customFormat": "=yyyy-MM-dd HH:mm:ss"
      },
      "typeVersion": 2
    },
    {
      "id": "0be0e8d0-b369-47e4-9419-90b3def746ad",
      "name": "Google Calendar",
      "type": "n8n-nodes-base.googleCalendar",
      "position": [
        1392,
        560
      ],
      "parameters": {
        "end": "={{ $('Date & Time').item.json.formattedDate.toDateTime().plus($('Configuration').item.json.defaultMinutes, 'minutes').format(\"yyyy-MM-dd HH:mm:ss\") }}",
        "start": "={{ $('Date & Time').item.json.formattedDate }}",
        "calendar": {
          "__rl": true,
          "mode": "id",
          "value": "={{ $('Configuration').item.json.calendarId }}"
        },
        "additionalFields": {
          "color": "={{ $('Configuration').item.json.eventColor }}",
          "summary": "={{ $('Google Tasks').item.json.title }}"
        }
      },
      "credentials": {
        "googleCalendarOAuth2Api": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 1.1
    },
    {
      "id": "530619d8-52f2-4bb6-9fed-4068e686127a",
      "name": "Google Tasks1",
      "type": "n8n-nodes-base.googleTasks",
      "position": [
        1616,
        560
      ],
      "parameters": {
        "task": "MTQ4MDk5NDE1Mjc2NjA5MTA5MjE6MDow",
        "taskId": "={{ $('Google Tasks').item.json.id }}",
        "operation": "delete"
      },
      "credentials": {
        "googleTasksOAuth2Api": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 1
    },
    {
      "id": "36a1682b-8390-4273-ac26-1c35ec932294",
      "name": "Webhook",
      "type": "n8n-nodes-base.webhook",
      "position": [
        112,
        480
      ],
      "parameters": {
        "path": "task-YOUR_OPENAI_KEY_HERE-calendar",
        "options": {},
        "httpMethod": "POST"
      },
      "typeVersion": 2
    },
    {
      "id": "0fde8152-49b5-49e5-b52e-23fdb8000d03",
      "name": "Google Calendar9",
      "type": "n8n-nodes-base.googleCalendar",
      "position": [
        960,
        480
      ],
      "parameters": {
        "limit": 3,
        "options": {
          "query": "={{ $('Webhook').item.json.body.TaskName }}",
          "updatedMin": "={{ $now.minus(5, 'minutes') }}",
          "showDeleted": "=false"
        },
        "calendar": {
          "__rl": true,
          "mode": "id",
          "value": "={{ $('Configuration').item.json.calendarId }}"
        },
        "operation": "getAll"
      },
      "credentials": {
        "googleCalendarOAuth2Api": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 1.1,
      "alwaysOutputData": true
    },
    {
      "id": "de1caa4c-f1fc-44cc-baf4-9522f72f2b8d",
      "name": "If1",
      "type": "n8n-nodes-base.if",
      "position": [
        1152,
        480
      ],
      "parameters": {
        "options": {},
        "conditions": {
          "options": {
            "leftValue": "",
            "caseSensitive": true,
            "typeValidation": "strict"
          },
          "combinator": "and",
          "conditions": [
            {
              "id": "f08129c7-f807-4915-9012-020c59db3629",
              "operator": {
                "type": "string",
                "operation": "exists",
                "singleValue": true
              },
              "leftValue": "={{ $json.summary }}",
              "rightValue": "={{ $json.summary }}"
            },
            {
              "id": "66c9e6d4-82bd-4e28-9456-4b9c9c1e54a3",
              "operator": {
                "name": "filter.operator.equals",
                "type": "string",
                "operation": "equals"
              },
              "leftValue": "{{ $('Webhook').item.json.body.TaskName }}",
              "rightValue": "{{ $json.summary }}"
            }
          ]
        }
      },
      "typeVersion": 2,
      "alwaysOutputData": false
    },
    {
      "id": "b6b89761-d9dd-4f41-b150-c3e1de4246b6",
      "name": "Step 1 \u2013 Trigger",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        96,
        736
      ],
      "parameters": {
        "color": "blue",
        "height": 288,
        "content": "## Step 1 \u2013 Trigger (Webhook)\nReceives a JSON payload and starts the flow.\n\n**Example payload**\n```json\n{ \"TaskName\": \"Pay invoice\", \"DueDateTimeSeconds\": 1735179600 }\n```\nTip: replace the Manual Trigger if you prefer scheduled imports."
      },
      "typeVersion": 1
    },
    {
      "id": "63bc5ca7-8930-434a-b293-6168a11f5881",
      "name": "Step 2 \u2013 Configuration",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        368,
        736
      ],
      "parameters": {
        "color": "blue",
        "height": 288,
        "content": "## Step 2 \u2013 Configuration\nSingle place to adjust variables:\n- `tasklistId` \u2013 Google Tasks list ID\n- `calendarId` \u2013 target Calendar (e.g., `primary`)\n- `defaultMinutes` \u2013 event duration\n- `eventColor` \u2013 Calendar color index"
      },
      "typeVersion": 1
    },
    {
      "id": "91d84006-1103-4686-877d-7135245db2a1",
      "name": "Step 3 \u2013 Date",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        640,
        736
      ],
      "parameters": {
        "color": "blue",
        "height": 176,
        "content": "## Step 3 \u2013 Date formatting\nBuilds a proper start datetime from `DueDateTimeSeconds`.\nEnd time = start + `defaultMinutes` (configurable)."
      },
      "typeVersion": 1
    },
    {
      "id": "d4b1604a-8d40-466b-b8a8-a8d7dcdf6f03",
      "name": "Step 4 \u2013 Dedupe",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        912,
        736
      ],
      "parameters": {
        "color": "blue",
        "height": 224,
        "content": "## Step 4 \u2013 Duplicate guard\nSearches recently updated events in the target calendar to prevent duplicates.\nAdjust the search window or title matching to fit your use case."
      },
      "typeVersion": 1
    },
    {
      "id": "c74b5b51-10c0-4a4f-ada8-450a25846258",
      "name": "Step 5 \u2013 Create Event",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        1184,
        736
      ],
      "parameters": {
        "color": "blue",
        "height": 192,
        "content": "## Step 5 \u2013 Create event\nCreates a Calendar event using the formatted start time.\nEnd time = start + `defaultMinutes`. Color taken from `eventColor`."
      },
      "typeVersion": 1
    },
    {
      "id": "680dfb47-1ef5-482b-a772-01ea49eb67f1",
      "name": "Step 6 \u2013 Cleanup",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        1456,
        736
      ],
      "parameters": {
        "color": "blue",
        "height": 192,
        "content": "## Step 6 \u2013 Cleanup (optional)\nDeletes the original Google Task after creating the Calendar event.\nDisable this if you prefer to keep tasks."
      },
      "typeVersion": 1
    },
    {
      "id": "ba3e90cf-b8ce-40d7-adfa-f8c8f48891b5",
      "name": "Flow Overview",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        832,
        0
      ],
      "parameters": {
        "color": "blue",
        "width": 400,
        "height": 192,
        "content": "## Flow overview\n1) **Webhook** receives task payload \u2192\n2) **Configuration** centralizes variables \u2192\n3) **Date & Time** formats schedule \u2192\n4) **Duplicate guard** checks recent events \u2192\n5) **Create event** on Google Calendar \u2192\n6) **Cleanup** optionally deletes original task."
      },
      "typeVersion": 1
    }
  ],
  "connections": {
    "If1": {
      "main": [
        [],
        [
          {
            "node": "Google Calendar",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Webhook": {
      "main": [
        [
          {
            "node": "Configuration",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Date & Time": {
      "main": [
        [
          {
            "node": "Google Calendar9",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Google Tasks": {
      "main": [
        [
          {
            "node": "Date & Time",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Configuration": {
      "main": [
        [
          {
            "node": "Google Tasks",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Google Calendar": {
      "main": [
        [
          {
            "node": "Google Tasks1",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Google Calendar9": {
      "main": [
        [
          {
            "node": "If1",
            "type": "main",
            "index": 0
          }
        ]
      ]
    }
  }
}

Credentials you'll need

Each integration node will prompt for credentials when you import. We strip credential IDs before publishing — you'll add your own.

Pro

For the full experience including quality scoring and batch install features for each workflow upgrade to Pro

About this workflow

Operators and makers who capture tasks from custom forms, bots, or automations and want them to appear as time-boxed events in Google Calendar with minimal setup.

Source: https://n8n.io/workflows/7865/ — original creator credit. Request a take-down →

More General workflows → · Browse all categories →

Related workflows

Workflows that share integrations, category, or trigger type with this one. All free to copy and import.

General

A clean, extensible REST-style API routing template for n8n webhooks with up to 3 path levels. Serves API routes via Webhooks with path variables Normalizes incoming requests into "global" REQUEST and

General

PUQ Docker NextCloud deploy. Uses respondToWebhook, stickyNote, httpRequest, ssh. Webhook trigger; 44 nodes.

HTTP Request, Ssh
General

puq-docker-immich-deploy. Uses respondToWebhook, ssh, stickyNote. Webhook trigger; 35 nodes.

Ssh
General

Analyze_email_headers_for_IPs_and_spoofing__3. Uses stickyNote, respondToWebhook, itemLists, httpRequest. Webhook trigger; 35 nodes.

Item Lists, HTTP Request
General

puq-docker-n8n-deploy. Uses respondToWebhook, ssh, stickyNote. Webhook trigger; 34 nodes.

Ssh