AutomationFlowsData & Sheets › Automate Blog Post Publishing From Airtable to Hashnode with API Integration

Automate Blog Post Publishing From Airtable to Hashnode with API Integration

ByFabioInTech @fabiointech on n8n.io

This workflow streamlines your content publishing process by automatically creating draft blog posts on Hashnode from content stored in Airtable. Perfect for content creators, marketing teams, and developers who want to maintain a consistent publishing schedule while managing…

Event trigger★★★★☆ complexity16 nodesHTTP RequestAirtable
Data & Sheets Trigger: Event Nodes: 16 Complexity: ★★★★☆ Added:

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

This workflow follows the Airtable → HTTP Request recipe pattern — see all workflows that pair these two integrations.

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
{
  "id": "NKH75Yw8BamfkKSH",
  "meta": {
    "templateCredsSetupCompleted": true
  },
  "name": "Airtable-to-HashNode",
  "tags": [
    {
      "id": "fouVh2Y0OYqejpLm",
      "name": "Template_shared",
      "createdAt": "2025-07-29T14:31:26.567Z",
      "updatedAt": "2025-07-29T14:31:26.567Z"
    }
  ],
  "nodes": [
    {
      "id": "7e5e97e9-f9b4-451c-8f0d-796da1e9c5e2",
      "name": "Sticky Note9",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        4592,
        720
      ],
      "parameters": {
        "color": 7,
        "width": 288,
        "height": 272,
        "content": "## 5. Post Draft\n- Using [HTTP Request Node](https://docs.n8n.io/integrations/builtin/core-nodes/n8n-nodes-base.httprequest/)"
      },
      "typeVersion": 1
    },
    {
      "id": "2594eda3-f5cd-4fdd-b9ab-5630c852e164",
      "name": "Sticky Note10",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        3232,
        720
      ],
      "parameters": {
        "color": 7,
        "width": 324,
        "height": 260,
        "content": "## 1. Get Blog Posts\n- Using [Airtable Node](https://docs.n8n.io/integrations/builtin/app-nodes/n8n-nodes-base.airtable/)"
      },
      "typeVersion": 1
    },
    {
      "id": "a872841f-48bc-4548-91bc-634fd352e876",
      "name": "Get Publication ID",
      "type": "n8n-nodes-base.httpRequest",
      "position": [
        4000,
        832
      ],
      "parameters": {
        "url": "https://gql.hashnode.com",
        "method": "POST",
        "options": {},
        "jsonBody": "={\n  \"query\": \"query GetPublication($host: String!) { publication(host: $host) { id title } }\",\n  \"variables\": {\n    \"host\": \"{{ $json.HashNode_Publication_Domain }}\"\n  }\n}",
        "sendBody": true,
        "sendHeaders": true,
        "specifyBody": "json",
        "headerParameters": {
          "parameters": [
            {
              "name": "Authorization",
              "value": "=Bearer {{ $json.Hashnode_Token }}"
            }
          ]
        }
      },
      "typeVersion": 4.2
    },
    {
      "id": "280f1bdb-a467-44dc-896f-c6cf23a6724b",
      "name": "Sticky Note",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        3920,
        720
      ],
      "parameters": {
        "color": 7,
        "width": 272,
        "height": 272,
        "content": "## 3. Get Publication_ID\n- Using [HTTP Request Node](https://docs.n8n.io/integrations/builtin/core-nodes/n8n-nodes-base.httprequest/)"
      },
      "typeVersion": 1
    },
    {
      "id": "f4cd172e-3dd4-45f6-b021-04ab76f92a31",
      "name": "Get Posts",
      "type": "n8n-nodes-base.airtable",
      "position": [
        3344,
        816
      ],
      "parameters": {
        "base": {
          "__rl": true,
          "mode": "list",
          "value": "appWkeQWqFgNbvHuB",
          "cachedResultUrl": "https://airtable.com/appWkeQWqFgNbvHuB",
          "cachedResultName": "ATO_AESA"
        },
        "table": {
          "__rl": true,
          "mode": "list",
          "value": "tbluWDZPDOsCs39aS",
          "cachedResultUrl": "https://airtable.com/appWkeQWqFgNbvHuB/tbluWDZPDOsCs39aS",
          "cachedResultName": "HashNode"
        },
        "options": {},
        "operation": "search",
        "filterByFormula": "={Status} = \"Not Published\""
      },
      "typeVersion": 2.1
    },
    {
      "id": "bbba998f-64ff-4374-9483-ad3a5087f6c2",
      "name": "When clicking \u2018Execute workflow\u2019",
      "type": "n8n-nodes-base.manualTrigger",
      "position": [
        3024,
        816
      ],
      "parameters": {},
      "typeVersion": 1
    },
    {
      "id": "3ca28839-f6ed-48b7-9a60-2c5d49cdb8ea",
      "name": "If Exists Publication_ID",
      "type": "n8n-nodes-base.if",
      "position": [
        4352,
        832
      ],
      "parameters": {
        "options": {},
        "conditions": {
          "options": {
            "version": 2,
            "leftValue": "",
            "caseSensitive": true,
            "typeValidation": "strict"
          },
          "combinator": "and",
          "conditions": [
            {
              "id": "19bb7e3a-2988-4722-bc0e-c63bbf3d34cb",
              "operator": {
                "type": "string",
                "operation": "exists",
                "singleValue": true
              },
              "leftValue": "={{ $json.data.publication.id }}",
              "rightValue": ""
            }
          ]
        }
      },
      "typeVersion": 2.2
    },
    {
      "id": "1a5f8592-9f33-41fe-9c91-d09c4ece0507",
      "name": "Sticky Note1",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        4240,
        720
      ],
      "parameters": {
        "color": 7,
        "width": 304,
        "height": 272,
        "content": "## 4. Publication_ID Exists? \n- Using [IF Node](https://docs.n8n.io/integrations/builtin/core-nodes/n8n-nodes-base.if/)"
      },
      "typeVersion": 1
    },
    {
      "id": "f908dc80-185c-43a2-aee9-6b87a60f5402",
      "name": "Sticky Note11",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        4928,
        752
      ],
      "parameters": {
        "color": 7,
        "width": 292,
        "height": 260,
        "content": "## 6. Update Blog Posts\n- Using [Airtable Node](https://docs.n8n.io/integrations/builtin/app-nodes/n8n-nodes-base.airtable/)"
      },
      "typeVersion": 1
    },
    {
      "id": "1dcca5e8-928b-49e1-940a-105e2a6bba81",
      "name": "Loop Over Items",
      "type": "n8n-nodes-base.splitInBatches",
      "position": [
        3680,
        816
      ],
      "parameters": {
        "options": {}
      },
      "typeVersion": 3
    },
    {
      "id": "acc6a156-392b-4ff1-b13c-862c23657819",
      "name": "Sticky Note2",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        3600,
        720
      ],
      "parameters": {
        "color": 7,
        "width": 272,
        "height": 272,
        "content": "## 2. Item process\n- Using [Loop over Itens Node](https://docs.n8n.io/integrations/builtin/core-nodes/n8n-nodes-base.splitinbatches/)"
      },
      "typeVersion": 1
    },
    {
      "id": "dea6549a-c554-4194-a55b-be7dbe1d4bf4",
      "name": "HashNode Post Draft",
      "type": "n8n-nodes-base.httpRequest",
      "position": [
        4688,
        816
      ],
      "parameters": {
        "url": "https://gql.hashnode.com",
        "method": "POST",
        "options": {},
        "jsonBody": "={\n  \"query\": \"mutation CreateDraft($input: CreateDraftInput!) { createDraft(input: $input) { draft { id } } }\",\n  \"variables\": {\n    \"input\": {\n      \"title\": {{ JSON.stringify($('Get Posts').item.json.Title) }},\n      \"contentMarkdown\": {{ JSON.stringify($('Get Posts').item.json.Content_markdown) }},\n      \"publicationId\": \"{{ $('Get Publication ID').item.json.data.publication.id }}\"\n    }\n  }\n}",
        "sendBody": true,
        "sendHeaders": true,
        "specifyBody": "json",
        "headerParameters": {
          "parameters": [
            {
              "name": "Authorization",
              "value": "=Bearer {{ $('Get Posts').item.json.Hashnode_Token }}"
            }
          ]
        }
      },
      "typeVersion": 4.2
    },
    {
      "id": "f72171cd-ef2c-45ec-939e-e9f378e52154",
      "name": "Update Post",
      "type": "n8n-nodes-base.airtable",
      "position": [
        5024,
        848
      ],
      "parameters": {
        "base": {
          "__rl": true,
          "mode": "list",
          "value": "appWkeQWqFgNbvHuB",
          "cachedResultUrl": "https://airtable.com/appWkeQWqFgNbvHuB",
          "cachedResultName": "ATO_AESA"
        },
        "table": {
          "__rl": true,
          "mode": "list",
          "value": "tbluWDZPDOsCs39aS",
          "cachedResultUrl": "https://airtable.com/appWkeQWqFgNbvHuB/tbluWDZPDOsCs39aS",
          "cachedResultName": "HashNode"
        },
        "columns": {
          "value": {
            "id": "={{ $('Get Posts').item.json.id }}",
            "Status": "Published"
          },
          "schema": [
            {
              "id": "id",
              "type": "string",
              "display": true,
              "removed": false,
              "readOnly": true,
              "required": false,
              "displayName": "id",
              "defaultMatch": true
            },
            {
              "id": "Post_name",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Post_name",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Title",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Title",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Content_markdown",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Content_markdown",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Hashnode_Token",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Hashnode_Token",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "HashNode_Publication_Domain",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "HashNode_Publication_Domain",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Status",
              "type": "options",
              "display": true,
              "options": [
                {
                  "name": "Not Published",
                  "value": "Not Published"
                },
                {
                  "name": "Published",
                  "value": "Published"
                },
                {
                  "name": "Error",
                  "value": "Error"
                },
                {
                  "name": "",
                  "value": ""
                }
              ],
              "removed": false,
              "readOnly": false,
              "required": false,
              "displayName": "Status",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            }
          ],
          "mappingMode": "defineBelow",
          "matchingColumns": [
            "id"
          ],
          "attemptToConvertTypes": false,
          "convertFieldsToString": false
        },
        "options": {
          "updateAllMatches": false
        },
        "operation": "update"
      },
      "typeVersion": 2.1
    },
    {
      "id": "6a8c2896-5300-41af-bcc9-b70dce159025",
      "name": "Update Error",
      "type": "n8n-nodes-base.airtable",
      "position": [
        4352,
        1152
      ],
      "parameters": {
        "base": {
          "__rl": true,
          "mode": "list",
          "value": "appWkeQWqFgNbvHuB",
          "cachedResultUrl": "https://airtable.com/appWkeQWqFgNbvHuB",
          "cachedResultName": "ATO_AESA"
        },
        "table": {
          "__rl": true,
          "mode": "list",
          "value": "tbluWDZPDOsCs39aS",
          "cachedResultUrl": "https://airtable.com/appWkeQWqFgNbvHuB/tbluWDZPDOsCs39aS",
          "cachedResultName": "HashNode"
        },
        "columns": {
          "value": {
            "id": "={{ $('Get Posts').item.json.id }}",
            "Status": "Error"
          },
          "schema": [
            {
              "id": "id",
              "type": "string",
              "display": true,
              "removed": false,
              "readOnly": true,
              "required": false,
              "displayName": "id",
              "defaultMatch": true
            },
            {
              "id": "Post_name",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Post_name",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Title",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Title",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Content_markdown",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Content_markdown",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Hashnode_Token",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Hashnode_Token",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "HashNode_Publication_Domain",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "HashNode_Publication_Domain",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Status",
              "type": "options",
              "display": true,
              "options": [
                {
                  "name": "Not Published",
                  "value": "Not Published"
                },
                {
                  "name": "Published",
                  "value": "Published"
                },
                {
                  "name": "Error",
                  "value": "Error"
                },
                {
                  "name": "",
                  "value": ""
                }
              ],
              "removed": false,
              "readOnly": false,
              "required": false,
              "displayName": "Status",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            }
          ],
          "mappingMode": "defineBelow",
          "matchingColumns": [
            "id"
          ],
          "attemptToConvertTypes": false,
          "convertFieldsToString": false
        },
        "options": {
          "updateAllMatches": false
        },
        "operation": "update"
      },
      "typeVersion": 2.1
    },
    {
      "id": "ed0ea527-4672-4a35-a073-1836e9e71454",
      "name": "Sticky Note12",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        4224,
        1056
      ],
      "parameters": {
        "color": 7,
        "width": 356,
        "height": 260,
        "content": "## 7. Error - No Publication_ID\n- Using [Airtable Node](https://docs.n8n.io/integrations/builtin/app-nodes/n8n-nodes-base.airtable/)"
      },
      "typeVersion": 1
    },
    {
      "id": "fd32a6ae-50a7-4a65-ab13-64f8ac954127",
      "name": "Sticky Note3",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        2064,
        640
      ],
      "parameters": {
        "width": 848,
        "height": 1376,
        "content": "## \ud83d\udcdd Automated Blog Post Publishing from Airtable to Hashnode\n\nThis workflow streamlines your content publishing process by automatically creating draft blog posts on Hashnode from content stored in Airtable. Perfect for content creators, marketing teams, and developers who want to maintain a consistent publishing schedule while managing multiple Hashnode publications from a centralized database.\n\n## \ud83c\udfaf Who's it for\n- **Content creators** managing multiple blog publications\n- **Marketing teams** coordinating content across different Hashnode accounts\n- **Developers** looking to automate their technical blog publishing workflow\n- **Agencies** managing content for multiple clients on Hashnode\n\n## \u2699\ufe0f How it works\nThe workflow operates in a simple 7-step process:\n\n1. **Retrieves unpublished posts** from your Airtable database (filtered by \"Not Published\" status)\n2. **Processes each post individually** using a loop to handle multiple posts\n3. **Fetches the publication ID** from Hashnode using the provided domain\n4. **Validates the publication exists** before proceeding with post creation\n5. **Creates draft posts** on Hashnode with the title and markdown content\n6. **Updates post status** to \"Published\" in Airtable upon successful creation\n7. **Handles errors** by marking failed posts with \"Error\" status for easy troubleshooting\n\n## \ud83d\udccb Requirements\n**Airtable Setup:**\nYour Airtable table must include these columns:\n- `Title` - The blog post title\n- `Content_markdown` - Full blog post content in Markdown format\n- `Hashnode_Token` - Your Hashnode API authentication token\n- `HashNode_Publication_Domain` - Your publication's domain (e.g., \"yourblog.hashnode.dev\")\n- `Status` - Publication status (\"Not Published\", \"Published\", or \"Error\")\n\n**Hashnode Requirements:**\n- Valid Hashnode account with API access\n- Publication domain configured\n- API token with draft creation permissions\n\n## \ud83d\udd27 How to set up\n1. **Configure Airtable credentials** in the \"Get Posts\" and \"Update Post\" nodes\n2. **Set your Airtable base and table IDs** to match your setup\n3. **Ensure your Airtable table** contains all required columns listed above\n4. **Add your content** with status \"Not Published\" to trigger the workflow\n5. **Test the workflow** with a single post before processing multiple items\n\n## \ud83c\udfa8 How to customize the workflow\n- **Modify the filter criteria** in the \"Get Posts\" node to target different post statuses\n- **Add content validation** before posting (word count, required fields, etc.)\n- **Include post scheduling** by adding date/time conditions\n- **Extend with notifications** using Slack, Discord, or email nodes\n- **Add SEO optimization** by including meta descriptions and tags\n- **Create published post tracking** by storing Hashnode draft IDs in Airtable\n\n## \ud83d\udca1 Need Help?\nJoin the [Discord](https://discord.com/invite/XPKeKXeB7d) or ask in the [Forum](https://community.n8n.io/)!"
      },
      "typeVersion": 1
    }
  ],
  "active": false,
  "settings": {
    "executionOrder": "v1"
  },
  "versionId": "16c19ea4-f275-4474-b1d9-368602766d47",
  "connections": {
    "Get Posts": {
      "main": [
        [
          {
            "node": "Loop Over Items",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Update Post": {
      "main": [
        [
          {
            "node": "Loop Over Items",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Update Error": {
      "main": [
        [
          {
            "node": "Loop Over Items",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Loop Over Items": {
      "main": [
        [],
        [
          {
            "node": "Get Publication ID",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Get Publication ID": {
      "main": [
        [
          {
            "node": "If Exists Publication_ID",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "HashNode Post Draft": {
      "main": [
        [
          {
            "node": "Update Post",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "If Exists Publication_ID": {
      "main": [
        [
          {
            "node": "HashNode Post Draft",
            "type": "main",
            "index": 0
          }
        ],
        [
          {
            "node": "Update Error",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "When clicking \u2018Execute workflow\u2019": {
      "main": [
        [
          {
            "node": "Get Posts",
            "type": "main",
            "index": 0
          }
        ]
      ]
    }
  }
}
Pro

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

About this workflow

This workflow streamlines your content publishing process by automatically creating draft blog posts on Hashnode from content stored in Airtable. Perfect for content creators, marketing teams, and developers who want to maintain a consistent publishing schedule while managing…

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

More Data & Sheets workflows → · Browse all categories →

Related workflows

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

Data & Sheets

Lmchatopenai Workflow. Uses noOp, stickyNote, executeWorkflowTrigger, airtable. Event-driven trigger; 41 nodes.

Execute Workflow Trigger, Airtable, HTTP Request
Data & Sheets

This n8n workflow retrieves an Airtable record along with its related child records in a hierarchical structure. It can fetch up to 3 levels of linked records and assembles them into a comprehensive J

Execute Workflow Trigger, Airtable, HTTP Request
Data & Sheets

How it works

Airtable Trigger, Sendinblue, Airtable +1
Data & Sheets

This workflow automatically pulls SERP rankings, competitor keywords, and related keyword ideas from DataForSEO and stores structured results in Airtable — making SEO tracking and keyword research str

Airtable, HTTP Request
Data & Sheets

d16-Web-Scraper-Data-Flow. Uses httpRequest, airtable, executeWorkflowTrigger. Event-driven trigger; 20 nodes.

HTTP Request, Airtable, Execute Workflow Trigger