This workflow corresponds to n8n.io template #13596 — we link there as the canonical source.
This workflow follows the Google Sheets → 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 →
{
"id": "JdpB1DL6CoVRuGB3",
"meta": {
"templateCredsSetupCompleted": true
},
"name": "Jasper AI Content Creator",
"tags": [],
"nodes": [
{
"id": "89a3fcb6-4395-4632-8036-02f28902c482",
"name": "README",
"type": "n8n-nodes-base.stickyNote",
"position": [
-448,
-320
],
"parameters": {
"width": 800,
"height": 848,
"content": "# Jasper AI Content Creator\n\nGenerates SEO blog posts, ad copy, email sequences, and social captions using Claude AI.\n\n## Setup\n1. Add your ANTHROPIC_API_KEY in the Set Config node\n2. Configure Serper API key for SEO data (optional)\n3. Set your WordPress, Mailchimp, Airtable credentials\n4. POST to the webhook URL\n\n## Webhook Payload\n```\n{\n \"topic\": \"Best AI Tools 2025\",\n \"contentType\": \"blog_post\",\n \"keyword\": \"ai tools for marketing\",\n \"tone\": \"professional\",\n \"audience\": \"SMB marketers\",\n \"wordCount\": 1500,\n \"brand\": \"YourBrand\",\n \"clientEmail\": \"client@email.com\"\n}\n```\n\n## Content Types\n- blog_post\n- ad_copy\n- email_sequence\n- social_captions\n\n## Flow\nWebhook -> Config -> SEO Fetch -> Build Prompt -> Claude AI -> Parse Response -> Save to Sheet -> Send Email -> Respond"
},
"typeVersion": 1
},
{
"id": "075ca433-b1cf-4fc8-9fab-7445bb31ee30",
"name": "Stage 1",
"type": "n8n-nodes-base.stickyNote",
"position": [
416,
-128
],
"parameters": {
"color": 4,
"width": 584,
"height": 452,
"content": "## Stage 1 - Intake\nWebhook receives brief, Set node stores config values, HTTP node fetches top Google results for the keyword to give Claude competitor context."
},
"typeVersion": 1
},
{
"id": "f3654273-1853-4318-b0af-a504e9e13bb1",
"name": "Stage 2",
"type": "n8n-nodes-base.stickyNote",
"position": [
1024,
-128
],
"parameters": {
"color": 3,
"width": 552,
"height": 532,
"content": "## Stage 2 - Generate\nCode node builds the Claude prompt based on content type. HTTP Request calls Anthropic API. Another Code node parses the response and extracts clean content + SEO metadata."
},
"typeVersion": 1
},
{
"id": "b3c5e80a-1155-4db1-aac5-fcc2cd71bc18",
"name": "Stage 3",
"type": "n8n-nodes-base.stickyNote",
"position": [
1616,
-128
],
"parameters": {
"color": 6,
"width": 520,
"height": 564,
"content": "## Stage 3 - Publish\nGoogle Sheets logs every job. HTTP Request sends delivery email via SendGrid. Webhook responds with JSON summary including SEO score, meta title, and content preview."
},
"typeVersion": 1
},
{
"id": "d047e225-8069-484a-af0f-7c94592830ea",
"name": "Receive Brief",
"type": "n8n-nodes-base.webhook",
"position": [
464,
144
],
"parameters": {
"path": "content-brief",
"options": {},
"httpMethod": "POST",
"responseMode": "responseNode"
},
"typeVersion": 2
},
{
"id": "80a1438d-c755-4574-92c1-4c104bc6a8c6",
"name": "Set Config",
"type": "n8n-nodes-base.set",
"position": [
656,
144
],
"parameters": {
"options": {},
"assignments": {
"assignments": [
{
"id": "a1",
"name": "topic",
"type": "string",
"value": "={{ $json.body.topic || $json.topic || 'AI Tools for Marketing' }}"
},
{
"id": "a2",
"name": "contentType",
"type": "string",
"value": "={{ $json.body.contentType || $json.contentType || 'blog_post' }}"
},
{
"id": "a3",
"name": "keyword",
"type": "string",
"value": "={{ $json.body.keyword || $json.keyword || $json.body.topic || 'ai tools' }}"
},
{
"id": "a4",
"name": "tone",
"type": "string",
"value": "={{ $json.body.tone || $json.tone || 'professional' }}"
},
{
"id": "a5",
"name": "audience",
"type": "string",
"value": "={{ $json.body.audience || $json.audience || 'business owners' }}"
},
{
"id": "a6",
"name": "wordCount",
"type": "number",
"value": "={{ $json.body.wordCount || $json.wordCount || 1200 }}"
},
{
"id": "a7",
"name": "brand",
"type": "string",
"value": "={{ $json.body.brand || $json.brand || 'YourBrand' }}"
},
{
"id": "a8",
"name": "clientEmail",
"type": "string",
"value": "={{ $json.body.clientEmail || $json.clientEmail || '' }}"
},
{
"id": "a9",
"name": "jobId",
"type": "string",
"value": "={{ 'JAS-' + Date.now() }}"
},
{
"id": "a10",
"name": "anthropicKey",
"type": "string",
"value": "YOUR_ANTHROPIC_API_KEY"
},
{
"id": "a11",
"name": "serperKey",
"type": "string",
"value": "YOUR_SERPER_API_KEY"
},
{
"id": "a12",
"name": "sendgridKey",
"type": "string",
"value": "YOUR_SENDGRID_API_KEY"
}
]
}
},
"typeVersion": 3.4
},
{
"id": "2fee290b-02e2-4f44-bc28-eb1deaed7709",
"name": "Fetch SERP Data",
"type": "n8n-nodes-base.httpRequest",
"position": [
864,
144
],
"parameters": {
"url": "https://google.serper.dev/search",
"method": "POST",
"options": {},
"jsonBody": "={{ JSON.stringify({ q: $json.keyword, num: 5 }) }}",
"sendBody": true,
"sendHeaders": true,
"specifyBody": "json",
"headerParameters": {
"parameters": [
{
"name": "X-API-KEY",
"value": "={{ $json.serperKey }}"
},
{
"name": "Content-Type",
"value": "application/json"
}
]
}
},
"typeVersion": 4.2,
"continueOnFail": true
},
{
"id": "eac2193f-2cb9-440d-baaf-91ce2bb5a448",
"name": "Build Claude Prompt",
"type": "n8n-nodes-base.code",
"position": [
1056,
144
],
"parameters": {
"jsCode": "\nvar cfg = $('Set Config').first().json;\nvar serp = $('Fetch SERP Data').first().json;\n\nvar competitors = '';\ntry {\n var organic = serp.organic || [];\n competitors = organic.slice(0,4).map(function(r){ return '- ' + r.title; }).join('\\n');\n} catch(e) { competitors = 'No competitor data'; }\n\nvar type = cfg.contentType || 'blog_post';\nvar prompts = {};\n\nprompts['blog_post'] = 'Write a ' + cfg.wordCount + '-word SEO blog post.\\nTopic: ' + cfg.topic + '\\nKeyword (use 3-5 times): ' + cfg.keyword + '\\nTone: ' + cfg.tone + '\\nAudience: ' + cfg.audience + '\\nBrand: ' + cfg.brand + '\\nCompetitor titles to beat:\\n' + competitors + '\\n\\nStructure: H1 with keyword > intro hook > 4-5 H2 sections > FAQ (3 questions) > conclusion with CTA.\\n\\nEnd with:\\nMETA_TITLE: (max 55 chars)\\nMETA_DESC: (max 155 chars)\\nSEO_SCORE: (0-100 number only)';\n\nprompts['ad_copy'] = 'Write high-converting ad copy.\\nProduct/Topic: ' + cfg.topic + '\\nKeyword: ' + cfg.keyword + '\\nBrand: ' + cfg.brand + '\\nAudience: ' + cfg.audience + '\\n\\nProvide:\\n1. GOOGLE ADS - 3 sets of (Headline 1 max30, Headline 2 max30, Headline 3 max30, Desc 1 max90, Desc 2 max90)\\n2. META ADS - 3 variations of (Primary text max125, Headline max40, Description max30)\\n3. EMAIL SUBJECTS - 3 subject lines with preview text\\n\\nEnd with:\\nMETA_TITLE: best headline as meta title\\nMETA_DESC: best description\\nSEO_SCORE: 65';\n\nprompts['email_sequence'] = 'Write a 4-email drip sequence.\\nTopic: ' + cfg.topic + '\\nBrand: ' + cfg.brand + '\\nAudience: ' + cfg.audience + '\\nTone: ' + cfg.tone + '\\n\\nEmail 1 (send immediately): Welcome - subject, preview, body 180 words, CTA\\nEmail 2 (day 2): Value Nurture - subject, preview, body 200 words, CTA\\nEmail 3 (day 4): Social Proof - subject, preview, body 200 words, CTA\\nEmail 4 (day 7): Sales Close - subject, preview, body 250 words, CTA\\n\\nUse {{first_name}} for personalization.\\n\\nEnd with:\\nMETA_TITLE: Email sequence title\\nMETA_DESC: Sequence description\\nSEO_SCORE: 70';\n\nprompts['social_captions'] = 'Write social media content.\\nTopic: ' + cfg.topic + '\\nBrand: ' + cfg.brand + '\\nAudience: ' + cfg.audience + '\\nTone: ' + cfg.tone + '\\n\\n1. LINKEDIN POST (1000-1300 chars, professional, line breaks, CTA, 3 hashtags)\\n2. TWITTER THREAD (5 tweets max 280 chars each, hook first, end with CTA)\\n3. TWITTER STANDALONE (1 viral tweet max 280 chars)\\n4. INSTAGRAM CAPTION (with emoji, storytelling, CTA, 25 hashtags at end)\\n5. INSTAGRAM CAROUSEL (5 slides: slide headline + 2 bullet points each)\\n\\nEnd with:\\nMETA_TITLE: Best headline from above\\nMETA_DESC: Best caption summary\\nSEO_SCORE: 72';\n\nvar prompt = prompts[type] || prompts['blog_post'];\n\nreturn [{ json: {\n topic: cfg.topic,\n contentType: cfg.contentType,\n keyword: cfg.keyword,\n tone: cfg.tone,\n audience: cfg.audience,\n wordCount: cfg.wordCount,\n brand: cfg.brand,\n clientEmail: cfg.clientEmail,\n jobId: cfg.jobId,\n anthropicKey: cfg.anthropicKey,\n sendgridKey: cfg.sendgridKey,\n claudePrompt: prompt,\n competitors: competitors\n}}];\n"
},
"typeVersion": 2
},
{
"id": "1a314124-cb2c-4196-b0ae-542f51762824",
"name": "Call Claude AI",
"type": "n8n-nodes-base.httpRequest",
"position": [
1264,
144
],
"parameters": {
"url": "https://api.anthropic.com/v1/messages",
"method": "POST",
"options": {},
"jsonBody": "={{ JSON.stringify({ model: \"claude-sonnet-4-20250514\", max_tokens: 4000, system: \"You are a world-class marketing copywriter and SEO expert. Always follow the exact format requested.\", messages: [{ role: \"user\", content: $json.claudePrompt }] }) }}",
"sendBody": true,
"sendHeaders": true,
"specifyBody": "json",
"headerParameters": {
"parameters": [
{
"name": "x-api-key",
"value": "={{ $json.anthropicKey }}"
},
{
"name": "anthropic-version",
"value": "2023-06-01"
},
{
"name": "content-type",
"value": "application/json"
}
]
}
},
"typeVersion": 4.2
},
{
"id": "d2a2d489-1d69-477a-ab1b-9043ed8e4624",
"name": "Parse Claude Response",
"type": "n8n-nodes-base.code",
"position": [
1456,
144
],
"parameters": {
"jsCode": "\nvar claudeRaw = $('Call Claude AI').first().json;\nvar brief = $('Build Claude Prompt').first().json;\n\nvar content = '';\ntry {\n if (claudeRaw.content && Array.isArray(claudeRaw.content)) {\n content = claudeRaw.content.map(function(b){ return b.text || ''; }).join('\\n');\n } else if (claudeRaw.text) {\n content = claudeRaw.text;\n } else {\n content = JSON.stringify(claudeRaw);\n }\n} catch(e) {\n content = 'Error extracting content: ' + e.message;\n}\n\nvar metaTitle = '';\nvar metaDesc = '';\nvar seoScore = 0;\n\ntry {\n var mtMatch = content.match(/META_TITLE:\\s*(.+)/);\n if (mtMatch) metaTitle = mtMatch[1].trim();\n var mdMatch = content.match(/META_DESC:\\s*(.+)/);\n if (mdMatch) metaDesc = mdMatch[1].trim();\n var ssMatch = content.match(/SEO_SCORE:\\s*(\\d+)/);\n if (ssMatch) seoScore = parseInt(ssMatch[1]);\n} catch(e) {}\n\nif (!metaTitle) metaTitle = brief.topic;\nif (!metaDesc) metaDesc = 'Read our guide on ' + brief.topic;\nif (!seoScore) seoScore = 72;\n\nvar slug = (brief.keyword || brief.topic).toLowerCase().replace(/[^a-z0-9]+/g, '-').replace(/^-|-$/g, '');\n\nvar valueMap = { blog_post: 250, ad_copy: 150, email_sequence: 350, social_captions: 120 };\n\nreturn [{ json: {\n jobId: brief.jobId,\n contentType: brief.contentType,\n topic: brief.topic,\n keyword: brief.keyword,\n brand: brief.brand,\n clientEmail: brief.clientEmail,\n sendgridKey: brief.sendgridKey,\n generatedContent: content,\n contentLength: content.length,\n metaTitle: metaTitle,\n metaDesc: metaDesc,\n seoScore: seoScore,\n slug: slug,\n estimatedValue: valueMap[brief.contentType] || 200,\n generatedAt: new Date().toISOString()\n}}];\n"
},
"typeVersion": 2
},
{
"id": "e576fa4e-3082-468b-add4-8c4eb0cb13ac",
"name": "Save to Google Sheets",
"type": "n8n-nodes-base.googleSheets",
"position": [
1664,
48
],
"parameters": {
"columns": {
"value": {},
"schema": [],
"mappingMode": "autoMapInputData",
"matchingColumns": [],
"attemptToConvertTypes": false,
"convertFieldsToString": false
},
"options": {},
"operation": "append",
"sheetName": {
"__rl": true,
"mode": "name",
"value": "Content Log"
},
"documentId": {
"__rl": true,
"mode": "id",
"value": "YOUR_GOOGLE_SHEET_ID"
},
"authentication": "serviceAccount"
},
"credentials": {
"googleApi": {
"name": "<your credential>"
}
},
"typeVersion": 4.5,
"continueOnFail": true
},
{
"id": "703a38b4-3015-498d-8b66-ca4a299c86f3",
"name": "Send Delivery Email",
"type": "n8n-nodes-base.httpRequest",
"position": [
1664,
240
],
"parameters": {
"url": "https://api.sendgrid.com/v3/mail/send",
"method": "POST",
"options": {},
"jsonBody": "={{ JSON.stringify({ personalizations: [{ to: [{ email: $json.clientEmail || \"client@example.com\" }] }], from: { email: \"noreply@youragency.com\", name: \"Content Engine\" }, subject: \"Content ready: \" + $json.topic, content: [{ type: \"text/plain\", value: \"Your content is ready!\\n\\nJob: \" + $json.jobId + \"\\nType: \" + $json.contentType + \"\\nTopic: \" + $json.topic + \"\\nSEO Score: \" + $json.seoScore + \"/100\\nMeta Title: \" + $json.metaTitle + \"\\n\\nContent Preview:\\n\" + ($json.generatedContent || \"\").substring(0, 500) + \"...\" }] }) }}",
"sendBody": true,
"sendHeaders": true,
"specifyBody": "json",
"headerParameters": {
"parameters": [
{
"name": "Authorization",
"value": "={{ 'Bearer ' + $json.sendgridKey }}"
},
{
"name": "Content-Type",
"value": "application/json"
}
]
}
},
"typeVersion": 4.2,
"continueOnFail": true
},
{
"id": "bbbaeaeb-d8a5-461d-988d-2a204c56eeef",
"name": "Send Response",
"type": "n8n-nodes-base.respondToWebhook",
"position": [
1856,
144
],
"parameters": {
"options": {
"responseCode": 200
},
"respondWith": "json",
"responseBody": "={{ JSON.stringify({ success: true, jobId: $json.jobId, contentType: $json.contentType, topic: $json.topic, seoScore: $json.seoScore, metaTitle: $json.metaTitle, metaDesc: $json.metaDesc, slug: $json.slug, estimatedValue: $json.estimatedValue, contentLength: $json.contentLength, generatedAt: $json.generatedAt }) }}"
},
"typeVersion": 1.1
}
],
"active": false,
"settings": {
"executionOrder": "v1"
},
"versionId": "0696ac8a-e4cf-4806-8ae7-b13c45b77838",
"connections": {
"Set Config": {
"main": [
[
{
"node": "Fetch SERP Data",
"type": "main",
"index": 0
}
]
]
},
"Receive Brief": {
"main": [
[
{
"node": "Set Config",
"type": "main",
"index": 0
}
]
]
},
"Call Claude AI": {
"main": [
[
{
"node": "Parse Claude Response",
"type": "main",
"index": 0
}
]
]
},
"Fetch SERP Data": {
"main": [
[
{
"node": "Build Claude Prompt",
"type": "main",
"index": 0
}
]
]
},
"Build Claude Prompt": {
"main": [
[
{
"node": "Call Claude AI",
"type": "main",
"index": 0
}
]
]
},
"Send Delivery Email": {
"main": [
[
{
"node": "Send Response",
"type": "main",
"index": 0
}
]
]
},
"Parse Claude Response": {
"main": [
[
{
"node": "Save to Google Sheets",
"type": "main",
"index": 0
},
{
"node": "Send Delivery Email",
"type": "main",
"index": 0
}
]
]
},
"Save to Google Sheets": {
"main": [
[
{
"node": "Send Response",
"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.
googleApi
For the full experience including quality scoring and batch install features for each workflow upgrade to Pro
About this workflow
Generates SEO blog posts, ad copy, email sequences, and social captions using Claude AI. Add your ANTHROPICAPIKEY in the Set Config node Configure Serper API key for SEO data (optional) Set your WordPress, Mailchimp, Airtable credentials POST to the webhook URL blog_post ad_copy…
Source: https://n8n.io/workflows/13596/ — original creator credit. Request a take-down →
Related workflows
Workflows that share integrations, category, or trigger type with this one. All free to copy and import.
This template automates the enrichment of business leads from a Google Sheet by: Triggering when a row is activated Searching for company information with Serper.dev Generating and validating potentia
The automation starts by retreiving the unused queries from a sheet, executes queries in the web using Serper API and extracts linkedin profiles of decision makers.
This workflow helps you automatically collect verified business leads from Google Search using SerpAPI — no coding required. It extracts company names, websites, emails, and phone numbers directly fro
This workflow automates comprehensive SEO reporting by: Extracting keyword rankings and page performance from Google Search Console. Gathering organic reach metrics from Google Analytics. Analyzing in
Automatically qualify, score, and route inbound B2B leads using GPT-4o-mini — no manual review needed.