This workflow corresponds to n8n.io template #15655 — we link there as the canonical source.
This workflow follows the Agent → Google Sheets 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 →
{
"meta": {
"templateCredsSetupCompleted": true
},
"nodes": [
{
"id": "f39e3db1-7434-4c32-99a5-504ee242e96e",
"name": "Overview",
"type": "n8n-nodes-base.stickyNote",
"position": [
-752,
-272
],
"parameters": {
"color": 4,
"width": 556,
"height": 1172,
"content": "## YouTube Video to Weekly Email Newsletter Generator \u2014 WayinVideo Summarization + GPT-4o-mini + Google Sheets\n\nFor content creators, media brands, newsletter writers, and marketing teams who publish YouTube videos and want to automatically convert each one into a ready-to-send email newsletter every Monday morning \u2014 without manually watching videos or writing from scratch. Every Monday at 7AM this workflow reads pending YouTube video URLs from your Google Sheet Video Queue tab. For each video, WayinVideo Summarization API generates a structured summary with numbered highlights and tags. GPT-4o-mini reads the summary and writes a complete newsletter issue \u2014 subject line (45\u201355 chars), preview text (85\u2013100 chars), hook intro, three content sections each with an H2 heading and body, a featured quote, a CTA button text, and hashtags. A Code node parses all 12 labeled sections, assembles the full newsletter body in Markdown format with H2 headings and a blockquote, and computes word count. Google Sheets appends the draft to Newsletter Drafts tab and marks the video as Processed in the Video Queue tab.\n\n## How it works\n- **1. Schedule \u2014 Every Monday 7AM** triggers the pipeline automatically each week\n- **2. Google Sheets \u2014 Read Pending Videos** reads all rows from the Video Queue tab\n- **3. IF \u2014 Any Pending Videos Today?** stops the workflow cleanly if the queue is empty\n- **4\u20136. WayinVideo Summarization** submits each URL, waits 90 seconds, polls until SUCCEEDED\n- **7. IF \u2014 Summary Complete?** checks status \u2014 retries via 30-second wait if not ready\n- **9. Code \u2014 Extract Summary Data** extracts summary, highlights, tags, sheet metadata, and computes the week-number issue label\n- **10. AI Agent \u2014 Write Newsletter** uses GPT-4o-mini with 12 labeled output sections to write the full newsletter\n- **11. OpenAI \u2014 GPT-4o-mini Model** language model attached to the AI Agent\n- **12. Code \u2014 Parse Newsletter Output** extracts all 12 sections via regex, builds full Markdown newsletter body, validates required fields\n- **13. Google Sheets \u2014 Save Newsletter Draft** appends 14 columns to Newsletter Drafts tab with Status set to Draft\n- **14. Google Sheets \u2014 Mark Video Processed** updates the Video Queue row with Processed status and date\n\n## Set up steps\n1. In **4** and **6** \u2014 replace `YOUR_WAYINVIDEO_API_KEY`\n2. In **11. OpenAI \u2014 GPT-4o-mini Model** \u2014 connect your OpenAI credential\n3. In **2** and **14** \u2014 connect Google Sheets OAuth2 and replace `YOUR_VIDEO_QUEUE_SHEET_ID`\n4. In **13** \u2014 connect Google Sheets OAuth2 and replace `YOUR_NEWSLETTER_SHEET_ID`\n5. Create a Google Sheet named Newsletter Pipeline with tab Video Queue (columns: Video URL, Video Title, Newsletter Niche / Brand, Target Audience, Newsletter Tone, CTA Link, Status, Processed Date) and tab Newsletter Drafts (columns: Video URL, Video Title, Newsletter Niche, Issue Number, Subject Line, Preview Text, Newsletter Body, Featured Quote, CTA Text, CTA Link, Hashtags, Word Count, Generated On, Status)"
},
"typeVersion": 1
},
{
"id": "e88766a2-c13e-4e3a-9e52-0442c2f05d2b",
"name": "Section \u2014 Schedule Trigger",
"type": "n8n-nodes-base.stickyNote",
"position": [
-160,
0
],
"parameters": {
"color": 5,
"width": 292,
"height": 356,
"content": "## Schedule Trigger\nFires every Monday at 7AM automatically. Can also be triggered manually to process the current week's queue on demand."
},
"typeVersion": 1
},
{
"id": "f82c5809-e822-4714-83a2-29512b64a82e",
"name": "Section \u2014 Sheet Read and Empty Queue Check",
"type": "n8n-nodes-base.stickyNote",
"position": [
144,
-112
],
"parameters": {
"color": 5,
"width": 452,
"height": 692,
"content": "## Sheet Read and Empty Queue Check\nReads all rows from the Video Queue tab. IF no pending videos exist the workflow stops cleanly. IF videos are found each one is processed sequentially through the summarization and newsletter pipeline."
},
"typeVersion": 1
},
{
"id": "b49d0747-443e-41d5-9989-f18bf7a29eac",
"name": "Section \u2014 WayinVideo Summarization Submit and Poll",
"type": "n8n-nodes-base.stickyNote",
"position": [
624,
32
],
"parameters": {
"color": 6,
"width": 676,
"height": 308,
"content": "## WayinVideo Summarization Submit and Poll\nSubmits each YouTube video URL to the Summarization API. Waits 90 seconds for initial processing. Polls the results endpoint until status equals SUCCEEDED."
},
"typeVersion": 1
},
{
"id": "174651fc-bea2-46f2-a7a8-3c6f13b6a26d",
"name": "Section \u2014 Summary Status Check and Retry Loop",
"type": "n8n-nodes-base.stickyNote",
"position": [
1312,
-32
],
"parameters": {
"color": 6,
"width": 308,
"height": 596,
"content": "## Summary Status Check and Retry Loop\nIF checks for SUCCEEDED status. TRUE proceeds to summary extraction. FALSE waits 30 seconds and polls again. Loop continues until summary is ready."
},
"typeVersion": 1
},
{
"id": "3e46d6fd-a784-4945-aabb-c211476c2ac9",
"name": "Section \u2014 Summary Extraction and AI Newsletter Writing",
"type": "n8n-nodes-base.stickyNote",
"position": [
1664,
-128
],
"parameters": {
"color": 6,
"width": 532,
"height": 692,
"content": "## Summary Extraction and AI Newsletter Writing\nExtracts summary, highlights, tags, and sheet metadata. Computes the week-number issue label. GPT-4o-mini writes a complete newsletter with 12 labeled sections \u2014 subject, preview, intro, three H2 sections, featured quote, CTA, and hashtags."
},
"typeVersion": 1
},
{
"id": "b83456ab-e99c-4352-bb29-0fcde1903e56",
"name": "Section \u2014 Newsletter Parse, Draft Save, and Video Queue Update",
"type": "n8n-nodes-base.stickyNote",
"position": [
2240,
-16
],
"parameters": {
"color": 4,
"width": 708,
"height": 356,
"content": "## Newsletter Parse, Draft Save, and Video Queue Update\nParses all 12 labeled sections via regex. Assembles full Markdown newsletter body. Appends 14-column draft row to Newsletter Drafts tab. Updates Video Queue row to Processed."
},
"typeVersion": 1
},
{
"id": "6c905dc2-8947-4b4a-9400-29cd1d8ac11a",
"name": "1. Schedule \u2014 Every Monday 7AM",
"type": "n8n-nodes-base.scheduleTrigger",
"position": [
-64,
144
],
"parameters": {
"rule": {
"interval": [
{
"field": "cronExpression",
"expression": "0 7 * * 1"
}
]
}
},
"typeVersion": 1.2
},
{
"id": "b90cf8ba-698e-4ca0-b72f-e531104160ea",
"name": "2. Google Sheets \u2014 Read Pending Videos",
"type": "n8n-nodes-base.googleSheets",
"position": [
192,
144
],
"parameters": {
"operation": "getAll",
"documentId": {
"__rl": true,
"mode": "id",
"value": "YOUR_VIDEO_QUEUE_SHEET_ID"
}
},
"typeVersion": 4.5
},
{
"id": "280a6f9b-5639-4e3f-85e7-162c7e6ad8e5",
"name": "3. IF \u2014 Any Pending Videos Today?",
"type": "n8n-nodes-base.if",
"position": [
432,
144
],
"parameters": {
"options": {},
"conditions": {
"options": {
"version": 3,
"leftValue": "",
"caseSensitive": true,
"typeValidation": "loose"
},
"combinator": "and",
"conditions": [
{
"id": "has-videos",
"operator": {
"type": "number",
"operation": "gt"
},
"leftValue": "={{ $items().length }}",
"rightValue": 0
}
]
}
},
"typeVersion": 2.3
},
{
"id": "8c3cc609-ece4-4172-8d40-c7b342e8ccf4",
"name": "4. WayinVideo \u2014 Submit Summarization",
"type": "n8n-nodes-base.httpRequest",
"position": [
688,
128
],
"parameters": {
"url": "https://wayinvideo-api.wayin.ai/api/v2/summaries",
"method": "POST",
"options": {},
"jsonBody": "={\n \"video_url\": \"{{ $json['Video URL'] }}\",\n \"target_lang\": \"en\"\n}",
"sendBody": true,
"sendHeaders": true,
"specifyBody": "json",
"headerParameters": {
"parameters": [
{
"name": "Authorization",
"value": "Bearer YOUR_TOKEN_HERE"
},
{
"name": "x-wayinvideo-api-version",
"value": "v2"
},
{
"name": "Content-Type",
"value": "application/json"
}
]
}
},
"typeVersion": 4.2
},
{
"id": "a7591d07-4c26-4700-9200-07ae3f7ccd01",
"name": "5. Wait \u2014 90 Seconds",
"type": "n8n-nodes-base.wait",
"position": [
928,
128
],
"parameters": {
"amount": 90
},
"typeVersion": 1.1
},
{
"id": "b86e558d-96bb-49ab-8681-16435c8ab458",
"name": "6. WayinVideo \u2014 Get Summary Results",
"type": "n8n-nodes-base.httpRequest",
"position": [
1168,
128
],
"parameters": {
"url": "=https://wayinvideo-api.wayin.ai/api/v2/summaries/results/{{ $('4. WayinVideo \u2014 Submit Summarization').item.json.data.id }}",
"options": {},
"sendHeaders": true,
"headerParameters": {
"parameters": [
{
"name": "Authorization",
"value": "Bearer YOUR_TOKEN_HERE"
},
{
"name": "x-wayinvideo-api-version",
"value": "v2"
},
{
"name": "Content-Type",
"value": "application/json"
}
]
}
},
"typeVersion": 4.2
},
{
"id": "5cdc040e-df43-40b8-a316-c30c5d6696a5",
"name": "7. IF \u2014 Summary Complete?",
"type": "n8n-nodes-base.if",
"position": [
1408,
144
],
"parameters": {
"options": {},
"conditions": {
"options": {
"version": 3,
"leftValue": "",
"caseSensitive": true,
"typeValidation": "loose"
},
"combinator": "and",
"conditions": [
{
"id": "summary-status",
"operator": {
"type": "string",
"operation": "equals"
},
"leftValue": "={{ $json.data.status }}",
"rightValue": "SUCCEEDED"
}
]
}
},
"typeVersion": 2.3
},
{
"id": "59fb08bd-55d5-4250-926d-a67015404264",
"name": "8. Wait \u2014 30 Seconds Retry",
"type": "n8n-nodes-base.wait",
"position": [
1408,
352
],
"parameters": {
"amount": 30
},
"typeVersion": 1.1
},
{
"id": "7e07cec7-68ef-4005-8231-fa104816e86c",
"name": "9. Code \u2014 Extract Summary Data",
"type": "n8n-nodes-base.code",
"position": [
1712,
128
],
"parameters": {
"jsCode": "// Extract summary data\nconst summaryData = $('6. WayinVideo \u2014 Get Summary Results').item.json.data;\n\nconst summary = summaryData.summary || '';\nconst highlights = Array.isArray(summaryData.highlights)\n ? summaryData.highlights.map((h, i) => `${i + 1}. ${h.desc}`).join('\\n')\n : '';\nconst tags = Array.isArray(summaryData.tags)\n ? summaryData.tags.join(', ')\n : '';\n\n// Get sheet data\nconst videoUrl = $('2. Google Sheets \u2014 Read Pending Videos').item.json['Video URL'];\nconst videoTitle = $('2. Google Sheets \u2014 Read Pending Videos').item.json['Video Title'] || 'Untitled';\nconst newsletterNiche = $('2. Google Sheets \u2014 Read Pending Videos').item.json['Newsletter Niche / Brand'] || 'General';\nconst targetAudience = $('2. Google Sheets \u2014 Read Pending Videos').item.json['Target Audience'] || 'General audience';\nconst newsletterTone = $('2. Google Sheets \u2014 Read Pending Videos').item.json['Newsletter Tone'] || 'Educational';\nconst ctaLink = $('2. Google Sheets \u2014 Read Pending Videos').item.json['CTA Link'] || 'YOUR_LINK_HERE';\n\n// Get current week number for issue numbering\nconst now = new Date();\nconst startOfYear = new Date(now.getFullYear(), 0, 1);\nconst weekNumber = Math.ceil(((now - startOfYear) / 86400000 + startOfYear.getDay() + 1) / 7);\n\nreturn [{\n json: {\n summary,\n highlights,\n tags,\n videoUrl,\n videoTitle,\n newsletterNiche,\n targetAudience,\n newsletterTone,\n ctaLink,\n issueNumber: `Issue #${weekNumber} \u2014 ${now.getFullYear()}`\n }\n}];"
},
"typeVersion": 2
},
{
"id": "f7fe0147-59e6-410c-bc98-fc2c2950cf0b",
"name": "10. AI Agent \u2014 Write Newsletter",
"type": "@n8n/n8n-nodes-langchain.agent",
"position": [
1904,
128
],
"parameters": {
"text": "={{ $json.summary }}\n\nKey Highlights from video:\n{{ $json.highlights }}\n\nTags: {{ $json.tags }}",
"options": {
"systemMessage": "=You are an expert email newsletter writer who specializes in writing engaging, high-open-rate newsletters for content creators and media brands.\n\nRead this video summary and highlights, then write a complete email newsletter issue based ONLY on what was covered in the video.\n\n---\n\n## NEWSLETTER DETAILS\n- Video Title: {{ $json.videoTitle }}\n- Newsletter Niche: {{ $json.newsletterNiche }}\n- Target Audience: {{ $json.targetAudience }}\n- Tone: {{ $json.newsletterTone }}\n- Issue: {{ $json.issueNumber }}\n- CTA Link: {{ $json.ctaLink }}\n- Video URL: {{ $json.videoUrl }}\n\n---\n\n## NEWSLETTER WRITING RULES\n1. Write ONLY from the video summary and highlights provided \u2014 no invented content\n2. Match the specified tone throughout\n3. Subject line must create curiosity or promise clear value \u2014 45-55 characters\n4. Preview text must complement subject line \u2014 never repeat it \u2014 85-100 characters\n5. Newsletter body: 350-500 words total \u2014 short punchy paragraphs\n6. Include exactly 3 content sections \u2014 each with a bold H2 heading and 2-3 short paragraphs\n7. Featured quote: extract the most interesting or insightful statement from the highlights\n8. CTA must be specific and action-oriented \u2014 not generic\n9. End with 4-6 relevant hashtags\n\n---\n\n## OUTPUT FORMAT\nReturn in this exact structure:\n\nSUBJECT_LINE:\n[Subject line \u2014 45-55 characters]\n\nPREVIEW_TEXT:\n[Preview text \u2014 85-100 characters \u2014 never repeats subject]\n\nNEWSLETTER_INTRO:\n[2-3 sentence opening \u2014 hook the reader immediately \u2014 no generic greetings]\n\nSECTION_1_HEADING:\n[Bold heading for section 1 \u2014 4-7 words]\n\nSECTION_1_BODY:\n[2-3 short paragraphs from highlight 1-2 \u2014 80-120 words]\n\nSECTION_2_HEADING:\n[Bold heading for section 2 \u2014 4-7 words]\n\nSECTION_2_BODY:\n[2-3 short paragraphs from highlight 3-4 \u2014 80-120 words]\n\nSECTION_3_HEADING:\n[Bold heading for section 3 \u2014 4-7 words]\n\nSECTION_3_BODY:\n[2-3 short paragraphs from highlight 5-6 \u2014 80-120 words]\n\nFEATURED_QUOTE:\n[Most insightful quote or statement from the highlights \u2014 1-2 sentences]\n\nCTA_TEXT:\n[Button text \u2014 3-5 words \u2014 action oriented]\n\nHASHTAGS:\n[4-6 hashtags \u2014 lowercase \u2014 relevant to niche and content]\n\n---\n\nNow write the complete newsletter issue:"
},
"promptType": "define"
},
"typeVersion": 3.1
},
{
"id": "c83d27fe-bdf5-4861-b747-cedacea6ac84",
"name": "11. OpenAI \u2014 GPT-4o-mini Model",
"type": "@n8n/n8n-nodes-langchain.lmChatOpenAi",
"position": [
1904,
368
],
"parameters": {
"model": {
"__rl": true,
"mode": "list",
"value": "gpt-4o-mini"
},
"options": {},
"builtInTools": {}
},
"typeVersion": 1.3
},
{
"id": "9b43417d-f80d-4340-b9f1-9bbac7e36b04",
"name": "12. Code \u2014 Parse Newsletter Output",
"type": "n8n-nodes-base.code",
"position": [
2288,
128
],
"parameters": {
"jsCode": "// Parse AI newsletter output\nconst output = $input.first().json.output || '';\n\n// Extract each section\nconst subjectMatch = output.match(/SUBJECT_LINE:\\s*([\\s\\S]*?)(?=\\nPREVIEW_TEXT:|$)/);\nconst previewMatch = output.match(/PREVIEW_TEXT:\\s*([\\s\\S]*?)(?=\\nNEWSLETTER_INTRO:|$)/);\nconst introMatch = output.match(/NEWSLETTER_INTRO:\\s*([\\s\\S]*?)(?=\\nSECTION_1_HEADING:|$)/);\nconst s1HeadMatch = output.match(/SECTION_1_HEADING:\\s*([\\s\\S]*?)(?=\\nSECTION_1_BODY:|$)/);\nconst s1BodyMatch = output.match(/SECTION_1_BODY:\\s*([\\s\\S]*?)(?=\\nSECTION_2_HEADING:|$)/);\nconst s2HeadMatch = output.match(/SECTION_2_HEADING:\\s*([\\s\\S]*?)(?=\\nSECTION_2_BODY:|$)/);\nconst s2BodyMatch = output.match(/SECTION_2_BODY:\\s*([\\s\\S]*?)(?=\\nSECTION_3_HEADING:|$)/);\nconst s3HeadMatch = output.match(/SECTION_3_HEADING:\\s*([\\s\\S]*?)(?=\\nSECTION_3_BODY:|$)/);\nconst s3BodyMatch = output.match(/SECTION_3_BODY:\\s*([\\s\\S]*?)(?=\\nFEATURED_QUOTE:|$)/);\nconst quoteMatch = output.match(/FEATURED_QUOTE:\\s*([\\s\\S]*?)(?=\\nCTA_TEXT:|$)/);\nconst ctaTextMatch = output.match(/CTA_TEXT:\\s*([\\s\\S]*?)(?=\\nHASHTAGS:|$)/);\nconst hashtagsMatch = output.match(/HASHTAGS:\\s*([\\s\\S]*)$/);\n\nconst subjectLine = subjectMatch ? subjectMatch[1].trim() : '';\nconst previewText = previewMatch ? previewMatch[1].trim() : '';\nconst intro = introMatch ? introMatch[1].trim() : '';\nconst s1Heading = s1HeadMatch ? s1HeadMatch[1].trim() : '';\nconst s1Body = s1BodyMatch ? s1BodyMatch[1].trim() : '';\nconst s2Heading = s2HeadMatch ? s2HeadMatch[1].trim() : '';\nconst s2Body = s2BodyMatch ? s2BodyMatch[1].trim() : '';\nconst s3Heading = s3HeadMatch ? s3HeadMatch[1].trim() : '';\nconst s3Body = s3BodyMatch ? s3BodyMatch[1].trim() : '';\nconst featuredQuote = quoteMatch ? quoteMatch[1].trim() : '';\nconst ctaText = ctaTextMatch ? ctaTextMatch[1].trim() : 'Watch Now';\nconst hashtags = hashtagsMatch ? hashtagsMatch[1].trim() : '';\n\n// Build full newsletter body\nconst newsletterBody = [\n intro,\n '',\n `## ${s1Heading}`,\n s1Body,\n '',\n `## ${s2Heading}`,\n s2Body,\n '',\n `## ${s3Heading}`,\n s3Body,\n '',\n `> \"${featuredQuote}\"`,\n '',\n `[${ctaText}](${$('9. Code \u2014 Extract Summary Data').item.json.ctaLink})`\n].join('\\n');\n\nconst wordCount = newsletterBody.split(/\\s+/).filter(w => w.length > 0).length;\n\nif (!subjectLine || !intro) {\n throw new Error('Could not parse newsletter from AI output. Check the AI prompt format.');\n}\n\nconst videoData = $('9. Code \u2014 Extract Summary Data').item.json;\n\nreturn [{\n json: {\n subjectLine,\n previewText,\n newsletterBody,\n featuredQuote,\n ctaText,\n hashtags,\n wordCount,\n videoUrl: videoData.videoUrl,\n videoTitle: videoData.videoTitle,\n newsletterNiche: videoData.newsletterNiche,\n issueNumber: videoData.issueNumber,\n ctaLink: videoData.ctaLink\n }\n}];"
},
"typeVersion": 2
},
{
"id": "13cb67b9-76cb-4906-9e1d-63adfed18ca3",
"name": "13. Google Sheets \u2014 Save Newsletter Draft",
"type": "n8n-nodes-base.googleSheets",
"position": [
2528,
128
],
"parameters": {
"columns": {
"value": {
"Status": "Draft",
"CTA Link": "={{ $json.ctaLink }}",
"CTA Text": "={{ $json.ctaText }}",
"Hashtags": "={{ $json.hashtags }}",
"Video URL": "={{ $json.videoUrl }}",
"Word Count": "={{ $json.wordCount }}",
"Video Title": "={{ $json.videoTitle }}",
"Generated On": "={{ $now.toFormat('dd MMMM yyyy HH:mm') }}",
"Issue Number": "={{ $json.issueNumber }}",
"Preview Text": "={{ $json.previewText }}",
"Subject Line": "={{ $json.subjectLine }}",
"Featured Quote": "={{ $json.featuredQuote }}",
"Newsletter Body": "={{ $json.newsletterBody }}",
"Newsletter Niche": "={{ $json.newsletterNiche }}"
},
"schema": [],
"mappingMode": "defineBelow",
"matchingColumns": []
},
"options": {},
"operation": "append",
"sheetName": {
"__rl": true,
"mode": "name",
"value": "Newsletter Drafts"
},
"documentId": {
"__rl": true,
"mode": "id",
"value": "YOUR_NEWSLETTER_SHEET_ID"
}
},
"typeVersion": 4.5
},
{
"id": "1c9a2d83-8464-4108-9347-f84fbfd39d49",
"name": "14. Google Sheets \u2014 Mark Video Processed",
"type": "n8n-nodes-base.googleSheets",
"position": [
2768,
128
],
"parameters": {
"columns": {
"value": {
"Status": "Processed",
"Video URL": "={{ $('9. Code \u2014 Extract Summary Data').item.json.videoUrl }}",
"Processed Date": "={{ $now.toFormat('dd MMMM yyyy') }}"
},
"schema": [],
"mappingMode": "defineBelow",
"matchingColumns": [
"Video URL"
]
},
"options": {},
"operation": "update",
"sheetName": {
"__rl": true,
"mode": "name",
"value": "Video Queue"
},
"documentId": {
"__rl": true,
"mode": "id",
"value": "YOUR_VIDEO_QUEUE_SHEET_ID"
}
},
"typeVersion": 4.5
}
],
"connections": {
"5. Wait \u2014 90 Seconds": {
"main": [
[
{
"node": "6. WayinVideo \u2014 Get Summary Results",
"type": "main",
"index": 0
}
]
]
},
"7. IF \u2014 Summary Complete?": {
"main": [
[
{
"node": "9. Code \u2014 Extract Summary Data",
"type": "main",
"index": 0
}
],
[
{
"node": "8. Wait \u2014 30 Seconds Retry",
"type": "main",
"index": 0
}
]
]
},
"8. Wait \u2014 30 Seconds Retry": {
"main": [
[
{
"node": "6. WayinVideo \u2014 Get Summary Results",
"type": "main",
"index": 0
}
]
]
},
"1. Schedule \u2014 Every Monday 7AM": {
"main": [
[
{
"node": "2. Google Sheets \u2014 Read Pending Videos",
"type": "main",
"index": 0
}
]
]
},
"11. OpenAI \u2014 GPT-4o-mini Model": {
"ai_languageModel": [
[
{
"node": "10. AI Agent \u2014 Write Newsletter",
"type": "ai_languageModel",
"index": 0
}
]
]
},
"9. Code \u2014 Extract Summary Data": {
"main": [
[
{
"node": "10. AI Agent \u2014 Write Newsletter",
"type": "main",
"index": 0
}
]
]
},
"10. AI Agent \u2014 Write Newsletter": {
"main": [
[
{
"node": "12. Code \u2014 Parse Newsletter Output",
"type": "main",
"index": 0
}
]
]
},
"3. IF \u2014 Any Pending Videos Today?": {
"main": [
[
{
"node": "4. WayinVideo \u2014 Submit Summarization",
"type": "main",
"index": 0
}
]
]
},
"12. Code \u2014 Parse Newsletter Output": {
"main": [
[
{
"node": "13. Google Sheets \u2014 Save Newsletter Draft",
"type": "main",
"index": 0
}
]
]
},
"6. WayinVideo \u2014 Get Summary Results": {
"main": [
[
{
"node": "7. IF \u2014 Summary Complete?",
"type": "main",
"index": 0
}
]
]
},
"4. WayinVideo \u2014 Submit Summarization": {
"main": [
[
{
"node": "5. Wait \u2014 90 Seconds",
"type": "main",
"index": 0
}
]
]
},
"2. Google Sheets \u2014 Read Pending Videos": {
"main": [
[
{
"node": "3. IF \u2014 Any Pending Videos Today?",
"type": "main",
"index": 0
}
]
]
},
"13. Google Sheets \u2014 Save Newsletter Draft": {
"main": [
[
{
"node": "14. Google Sheets \u2014 Mark Video Processed",
"type": "main",
"index": 0
}
]
]
}
}
}
For the full experience including quality scoring and batch install features for each workflow upgrade to Pro
About this workflow
Add your YouTube video URLs to a Google Sheet once and every Monday at 7AM the workflow automatically converts each pending video into a complete newsletter draft. WayinVideo summarizes each video and extracts numbered highlights and tags, then GPT-4o-mini reads the summary and…
Source: https://n8n.io/workflows/15655/ — 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 n8n automation workflow automates the creation, scripting, production, and posting of YouTube videos. It leverages AI (OpenAI), image generation (PIAPI), video rendering (Shotstack), and platform
This workflow is designed for: Content creators and marketers E-commerce and product-based businesses Agencies producing social media visuals and videos Automation builders looking for AI-powered crea
Generate product images with NanoBanana Pro to Veo videos and Blotato - vide 2 ok. Uses httpRequest, editImage, googleDrive, googleSheets. Scheduled trigger; 76 nodes.
Created by: Peyton Leveillee Last updated: October 2025
The Multi-Model Agency Content Engine is a high-performance editorial system designed for agencies. It solves the "blank page" problem by alternating between real-world social proof and strategic expe