{
  "id": "qQFa5Haojd7MRgNw",
  "name": "Repurpose YouTube videos to short-form clips with AI",
  "tags": [],
  "nodes": [
    {
      "id": "24509caf-c92d-4d79-98e9-ef73fcdb3dba",
      "name": "Create a record",
      "type": "n8n-nodes-base.airtable",
      "position": [
        1328,
        128
      ],
      "parameters": {
        "base": {
          "__rl": true,
          "mode": "list",
          "value": "appFGF4qoyqn50KOz",
          "cachedResultUrl": "https://airtable.com/appFGF4qoyqn50KOz",
          "cachedResultName": "Content Factory"
        },
        "table": {
          "__rl": true,
          "mode": "list",
          "value": "tblUTxWrEJD5pUsV2",
          "cachedResultUrl": "https://airtable.com/appFGF4qoyqn50KOz/tblUTxWrEJD5pUsV2",
          "cachedResultName": "Table 1"
        },
        "columns": {
          "value": {
            "Video file name": "={{ $json.name }}",
            "Longform edited video": "={{ $json.webViewLink }}"
          },
          "schema": [
            {
              "id": "Video file name",
              "type": "string",
              "display": true,
              "removed": false,
              "readOnly": false,
              "required": false,
              "displayName": "Video file name",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Longform edited video",
              "type": "string",
              "display": true,
              "removed": false,
              "readOnly": false,
              "required": false,
              "displayName": "Longform edited video",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Video summary",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Video summary",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Reference image 1",
              "type": "array",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Reference image 1",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Reference image 2",
              "type": "array",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Reference image 2",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Reference image 3",
              "type": "array",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Reference image 3",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Title 1",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Title 1",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Title 2",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Title 2",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Title 3",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Title 3",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Thumbnail 1 prompt",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Thumbnail 1 prompt",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Thumbnail 2 prompt",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Thumbnail 2 prompt",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Thumbnail 3 prompt",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Thumbnail 3 prompt",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Clips",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Clips",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Calculation",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": true,
              "required": false,
              "displayName": "Calculation",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            }
          ],
          "mappingMode": "defineBelow",
          "matchingColumns": [],
          "attemptToConvertTypes": false,
          "convertFieldsToString": false
        },
        "options": {},
        "operation": "create"
      },
      "credentials": {
        "airtableTokenApi": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 2.1
    },
    {
      "id": "c8d179de-9ced-434a-9ba8-7049a0325f97",
      "name": "When video is added to drive folder",
      "type": "n8n-nodes-base.googleDriveTrigger",
      "position": [
        1136,
        128
      ],
      "parameters": {
        "event": "fileCreated",
        "options": {},
        "pollTimes": {
          "item": [
            {
              "mode": "everyMinute"
            }
          ]
        },
        "triggerOn": "specificFolder",
        "folderToWatch": {
          "__rl": true,
          "mode": "list",
          "value": "1Uv782L3VuaRi_T7vtTpLy3mieKiVYB2Q",
          "cachedResultUrl": "https://drive.google.com/drive/folders/1Uv782L3VuaRi_T7vtTpLy3mieKiVYB2Q",
          "cachedResultName": "Edited videos (pre upload)"
        }
      },
      "credentials": {
        "googleDriveOAuth2Api": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 1
    },
    {
      "id": "96c9238b-fb77-4061-bf10-fe21fe18fde9",
      "name": "Webhook",
      "type": "n8n-nodes-base.webhook",
      "position": [
        1600,
        128
      ],
      "parameters": {
        "path": "a03394e6-91e5-40a5-9104-98c025e14f69",
        "options": {}
      },
      "typeVersion": 2.1
    },
    {
      "id": "27f3d8ce-76cc-4dc4-bd44-caa283274c7f",
      "name": "Generate 3 titles",
      "type": "@n8n/n8n-nodes-langchain.openAi",
      "position": [
        1968,
        128
      ],
      "parameters": {
        "modelId": {
          "__rl": true,
          "mode": "list",
          "value": "gpt-4o-mini",
          "cachedResultName": "GPT-4O-MINI"
        },
        "options": {
          "textFormat": {
            "textOptions": {
              "type": "json_schema",
              "schema": "{\n  \"type\": \"object\",\n  \"properties\": {\n    \"title_1\": {\n      \"type\": \"string\"\n    },\n    \"title_2\": {\n      \"type\": \"string\"\n    },\n    \"title_3\": {\n      \"type\": \"string\"\n    }\n  },\n  \"required\": [\"title_1\", \"title_2\", \"title_3\"],\n  \"additionalProperties\": false\n}"
            }
          }
        },
        "responses": {
          "values": [
            {
              "role": "system",
              "content": "=You are an expert YouTube title strategist specializing in (YOUR CONTENT NICHE HERE HAVE CLAUDE TAILOR THIS TO YOUR NICHE) Your job is to generate 3 high-performing title options based on proven 2025 YouTube title best practices and data-backed strategies.\n\n# CONTEXT\n- Niche: AI automation, n8n workflows, no-code automation, business process automation\n- Target Audience: Mix of (1) agency builders learning to sell AI automation, and (2) business owners needing automation solutions\n- Goal: Drive clicks (high CTR), rank in search, and funnel viewers to free Skool community\n\n# TITLE REQUIREMENTS\n\n## Length & Structure\n- 40-60 characters total (optimal for CTR and mobile display)\n- Front-load the most important keyword in the first 3-5 words\n- Avoid truncation - keep critical info visible before the \"...\"\n\n## Keyword Integration\n- Primary keyword MUST appear in the first half of the title\n- Use natural, human-readable phrasing (no keyword stuffing)\n- Include secondary/LSI keywords when relevant (e.g., \"workflow,\" \"automation,\" \"AI,\" \"n8n\")\n\n## Proven Title Formulas (Use These)\n1. **How-To Formula**: \"How to [Achieve Outcome] with [Tool/Method]\"\n   - Example: \"How to Automate Lead Gen with n8n (Step-by-Step)\"\n\n2. **Number-Based Formula**: \"[Number] Ways to [Benefit] Using [Tool]\"\n   - Example: \"5 n8n Workflows That Save 10 Hours/Week\"\n   - Note: Odd numbers (3, 5, 7) perform better than even\n\n3. **Outcome + Time Formula**: \"How I [Result] in [Timeframe] with [Method]\"\n   - Example: \"How I Built 20 Automations in 1 Week (n8n)\"\n\n4. **Problem/Solution Formula**: \"[Problem] \u274c \u2192 [Solution] \u2705\"\n   - Example: \"Manual Data Entry \u274c \u2192 AI Automation \u2705\"\n\n5. **Curiosity + Benefit Formula**: \"[Intriguing Hook] + [Clear Value]\"\n   - Example: \"This n8n Workflow Changed Everything (Free Template)\"\n\n6. **Bracket Enhancement**: Use [brackets] for context, updates, or bonuses\n   - Example: \"Build AI Chatbots in n8n [2025 Update + Free Template]\"\n\n## Power Words & Emotional Triggers\n**Include 1-2 of these in each title:**\n\n**Curiosity:** Secret, Hidden, Surprising, Breakthrough, Discovery\n**Authority:** Proven, Expert, Ultimate, Complete, Professional\n**Urgency:** Now, Fast, Quick, Instantly, Today, 2025\n**Value:** Free, Easy, Simple, Step-by-Step, Blueprint\n**Achievement:** Build, Create, Master, Automate, Scale\n**Specificity:** Exact, Specific, Real, Actual, True\n\n## Critical Rules\n\u2705 DO:\n- Start with the keyword your target audience is searching for\n- Use specific numbers and outcomes (\"Save 10 Hours\" not \"Save Time\")\n- Create curiosity while setting clear expectations\n- Match title to video content (no clickbait)\n- Include year (2025) for recency when relevant\n- Use parentheses or brackets for bonus context\n- Make the benefit crystal clear\n\n\u274c DON'T:\n- Use all caps or excessive emojis\n- Create misleading clickbait (kills watch time)\n- Bury the keyword at the end\n- Be vague (\"Cool Automation\" vs \"AI Lead Gen Automation\")\n- Exceed 60 characters\n- Use industry jargon that confuses beginners\n\n## Title Testing Strategy\nGenerate 3 variations that test different angles:\n- **Title 1**: SEO-focused (keyword-heavy, search-optimized)\n- **Title 2**: Curiosity-driven (emotional hook, benefit-focused)\n- **Title 3**: Hybrid (balances SEO + curiosity)\n\n# INPUT\nYou will receive a detailed video summary. Analyze it to:\n1. Identify the core problem being solved\n2. Extract the main tool/method being taught\n3. Determine the key outcome/benefit\n4. Note any specific numbers, timeframes, or results\n\n# OUTPUT FORMAT\nReturn ONLY the 3 titles in this exact format:\n\nTitle 1 (SEO-Focused): [title here]\nTitle 2 (Curiosity-Driven): [title here]\nTitle 3 (Hybrid): [title here]\n\n# EXAMPLES FOR n8n/AI AUTOMATION NICHE\n\nVideo Summary: \"Tutorial showing how to build an n8n workflow that automatically transcribes YouTube videos, generates summaries, creates 3 title options, and generates thumbnails using AI.\"\n\nOutput:\nTitle 1 (SEO-Focused): n8n AI Workflow: Auto-Generate YouTube Titles & Thumbnails\nTitle 2 (Curiosity-Driven): This AI Workflow Creates My YouTube Content (Save 5 Hours)\nTitle 3 (Hybrid): How to Automate YouTube Titles with n8n [Free Template]\n\n---\n\nVideo Summary: \"Building a complete RAG system in n8n that allows businesses to query their documents using AI, includes setup, testing, and deployment.\"\n\nOutput:\nTitle 1 (SEO-Focused): Build a RAG System in n8n (Complete AI Document Query Setup)\nTitle 2 (Curiosity-Driven): Turn Your PDFs Into an AI Assistant (n8n Workflow)\nTitle 3 (Hybrid): How I Built a $5K RAG System with n8n [Step-by-Step]"
            },
            {
              "content": "=# VIDEO SUMMARY\n\n{{ $json['Video summary'] }}\n\nGenerate 3 optimized YouTube title options for this AI automation/n8n tutorial video following the title framework provided in your system instructions."
            }
          ]
        },
        "builtInTools": {}
      },
      "credentials": {
        "openAiApi": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 2.1
    },
    {
      "id": "fe601d09-7b4d-4119-a246-502dfb56bd1f",
      "name": "Add titles to record",
      "type": "n8n-nodes-base.airtable",
      "position": [
        2256,
        128
      ],
      "parameters": {
        "base": {
          "__rl": true,
          "mode": "list",
          "value": "appFGF4qoyqn50KOz",
          "cachedResultUrl": "https://airtable.com/appFGF4qoyqn50KOz",
          "cachedResultName": "Content Factory"
        },
        "table": {
          "__rl": true,
          "mode": "list",
          "value": "tblUTxWrEJD5pUsV2",
          "cachedResultUrl": "https://airtable.com/appFGF4qoyqn50KOz/tblUTxWrEJD5pUsV2",
          "cachedResultName": "Table 1"
        },
        "columns": {
          "value": {
            "Title 1": "={{ $json.output[0].content[0].text.title_1 }}",
            "Title 2": "={{ $json.output[0].content[0].text.title_2 }}",
            "Title 3": "={{ $json.output[0].content[0].text.title_3 }}",
            "Calculation": "={{ $('Get a record').item.json.Calculation }}"
          },
          "schema": [
            {
              "id": "id",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": true,
              "required": false,
              "displayName": "id",
              "defaultMatch": true
            },
            {
              "id": "Video file name",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Video file name",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Longform edited video",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Longform edited video",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Video summary",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Video summary",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Reference image 1",
              "type": "array",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Reference image 1",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Reference image 2",
              "type": "array",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Reference image 2",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Reference image 3",
              "type": "array",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Reference image 3",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Title 1",
              "type": "string",
              "display": true,
              "removed": false,
              "readOnly": false,
              "required": false,
              "displayName": "Title 1",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Title 2",
              "type": "string",
              "display": true,
              "removed": false,
              "readOnly": false,
              "required": false,
              "displayName": "Title 2",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Title 3",
              "type": "string",
              "display": true,
              "removed": false,
              "readOnly": false,
              "required": false,
              "displayName": "Title 3",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Thumbnail 1 prompt",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Thumbnail 1 prompt",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Thumbnail 2 prompt",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Thumbnail 2 prompt",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Thumbnail 3 prompt",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Thumbnail 3 prompt",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Clips",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Clips",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Calculation",
              "type": "string",
              "display": true,
              "removed": false,
              "readOnly": true,
              "required": false,
              "displayName": "Calculation",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            }
          ],
          "mappingMode": "defineBelow",
          "matchingColumns": [
            "Calculation"
          ],
          "attemptToConvertTypes": false,
          "convertFieldsToString": false
        },
        "options": {},
        "operation": "update"
      },
      "credentials": {
        "airtableTokenApi": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 2.1
    },
    {
      "id": "74a8d801-2d67-4ab0-a8c8-d9718c63f144",
      "name": "Webhook2",
      "type": "n8n-nodes-base.webhook",
      "position": [
        1104,
        448
      ],
      "parameters": {
        "path": "8bcc5357-97bc-4816-982d-fee8a591f66f",
        "options": {}
      },
      "typeVersion": 2.1
    },
    {
      "id": "db66fa8a-f872-42cb-8ded-6761b1317214",
      "name": "Get a record2",
      "type": "n8n-nodes-base.airtable",
      "position": [
        1280,
        448
      ],
      "parameters": {
        "id": "={{ $json.query.recordId }}",
        "base": {
          "__rl": true,
          "mode": "list",
          "value": "appFGF4qoyqn50KOz",
          "cachedResultUrl": "https://airtable.com/appFGF4qoyqn50KOz",
          "cachedResultName": "Content Factory"
        },
        "table": {
          "__rl": true,
          "mode": "list",
          "value": "tblUTxWrEJD5pUsV2",
          "cachedResultUrl": "https://airtable.com/appFGF4qoyqn50KOz/tblUTxWrEJD5pUsV2",
          "cachedResultName": "Table 1"
        },
        "options": {}
      },
      "credentials": {
        "airtableTokenApi": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 2.1
    },
    {
      "id": "ffcb2eb2-242c-4e44-85d2-51a8da1d66a2",
      "name": "Get image1",
      "type": "n8n-nodes-base.httpRequest",
      "position": [
        1264,
        608
      ],
      "parameters": {
        "url": "https://api.kie.ai/api/v1/jobs/recordInfo",
        "options": {},
        "sendQuery": true,
        "authentication": "genericCredentialType",
        "genericAuthType": "httpHeaderAuth",
        "queryParameters": {
          "parameters": [
            {
              "name": "taskId",
              "value": "={{ $json.data.taskId }}"
            }
          ]
        }
      },
      "credentials": {
        "httpHeaderAuth": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 4.3
    },
    {
      "id": "eaa251c2-ff2c-46fa-a167-655a4af50e22",
      "name": "Extract from File5",
      "type": "n8n-nodes-base.extractFromFile",
      "position": [
        1856,
        592
      ],
      "parameters": {
        "options": {},
        "operation": "binaryToPropery"
      },
      "typeVersion": 1.1
    },
    {
      "id": "27f66737-cfea-47cd-b923-ee18e5767a5e",
      "name": "Wait10",
      "type": "n8n-nodes-base.wait",
      "position": [
        1664,
        752
      ],
      "parameters": {},
      "typeVersion": 1.1
    },
    {
      "id": "19369361-63fd-4d1e-965f-230b8bc9630e",
      "name": "Switch4",
      "type": "n8n-nodes-base.switch",
      "position": [
        1488,
        608
      ],
      "parameters": {
        "rules": {
          "values": [
            {
              "conditions": {
                "options": {
                  "version": 2,
                  "leftValue": "",
                  "caseSensitive": true,
                  "typeValidation": "strict"
                },
                "combinator": "and",
                "conditions": [
                  {
                    "id": "31ada6d9-ba49-44fe-9897-4349a16154e0",
                    "operator": {
                      "type": "string",
                      "operation": "notEmpty",
                      "singleValue": true
                    },
                    "leftValue": "={{ $json.data.resultJson }}",
                    "rightValue": 200
                  }
                ]
              }
            },
            {
              "conditions": {
                "options": {
                  "version": 2,
                  "leftValue": "",
                  "caseSensitive": true,
                  "typeValidation": "strict"
                },
                "combinator": "and",
                "conditions": [
                  {
                    "id": "a14c7d84-31f9-4358-8815-746f806b58b7",
                    "operator": {
                      "type": "string",
                      "operation": "empty",
                      "singleValue": true
                    },
                    "leftValue": "={{ $json.data.resultJson }}",
                    "rightValue": 501
                  }
                ]
              }
            }
          ]
        },
        "options": {}
      },
      "typeVersion": 3.3
    },
    {
      "id": "589d76e7-2e56-4167-bb26-14cd56d64cd7",
      "name": "Download image",
      "type": "n8n-nodes-base.httpRequest",
      "position": [
        1680,
        592
      ],
      "parameters": {
        "url": "={{ JSON.parse($json.data.resultJson).resultUrls[0] }}",
        "options": {}
      },
      "typeVersion": 4.3
    },
    {
      "id": "6d37ca11-09fa-453c-bc88-59d9e3c74812",
      "name": "Code in JavaScript",
      "type": "n8n-nodes-base.code",
      "position": [
        1952,
        448
      ],
      "parameters": {
        "jsCode": "// Get all items from previous node\nconst items = $input.all();\n\n// Get the prompt\nlet prompt = items[0].json.thumbnailPrompt;\n\n// Check if prompt exists\nif (!prompt) {\n  throw new Error('thumbnailPrompt is empty or undefined');\n}\n\n// Remove leading and trailing quotes if present\nif (prompt.startsWith('\"') && prompt.endsWith('\"')) {\n  prompt = prompt.slice(1, -1);\n}\n\n// Clean up the prompt\nprompt = prompt\n  .replace(/\\n/g, ' ')\n  .replace(/\\r/g, ' ')\n  .replace(/\\s+/g, ' ')\n  .replace(/\\\\\"/g, '\"')\n  .trim();\n\n// Get image URLs from Airtable\nconst airtableData = $('Get a record2').first().json;\n\n// Try both possible field names\nconst image1 = airtableData[\"Reference image 1\"]?.[0]?.url || airtableData[\"Thumbnail reference 1\"]?.[0]?.url;\nconst image2 = airtableData[\"Reference image 2\"]?.[0]?.url || airtableData[\"Thumbnail reference 2\"]?.[0]?.url;\n\n// Debug: Log what we found\nconsole.log('Airtable fields:', Object.keys(airtableData));\nconsole.log('Image1:', image1);\nconsole.log('Image2:', image2);\n\n// Check if images were found\nif (!image1 || !image2) {\n  throw new Error(`Missing images. Image1: ${!!image1}, Image2: ${!!image2}. Available fields: ${Object.keys(airtableData).join(', ')}`);\n}\n\n// Build the JSON body with only 2 images\nconst bodyRaw = JSON.stringify({\n  model: \"nano-banana-pro\",\n  callBackUrl: $execution.resumeUrl,\n  input: {\n    prompt: prompt,\n    image_input: [image1, image2],\n    aspect_ratio: \"16:9\",\n    resolution: \"1K\",\n    output_format: \"png\"\n  }\n});\n\n// Return the stringified JSON\nreturn [{\n  json: {\n    bodyRaw: bodyRaw\n  }\n}];"
      },
      "typeVersion": 2
    },
    {
      "id": "f9da1276-52fa-4232-be1f-71aa8a47d8f9",
      "name": "Thumbnail prompt optimizer",
      "type": "@n8n/n8n-nodes-langchain.openAi",
      "position": [
        1440,
        448
      ],
      "parameters": {
        "modelId": {
          "__rl": true,
          "mode": "list",
          "value": "gpt-5-mini",
          "cachedResultName": "GPT-5-MINI"
        },
        "options": {},
        "responses": {
          "values": [
            {
              "role": "system",
              "content": "=You are an expert at optimizing image generation prompts for Nano Banana Pro to create high-performing YouTube thumbnails.\n\n# YOUR TASK\n\nThe user provides a rough thumbnail idea. You optimize it into a single-paragraph Nano Banana Pro prompt that:\n1. Keeps their core concept\n2. Adds missing YouTube thumbnail essentials (text, lighting, effects, colors)\n3. Makes it visually appealing and high-converting\n4. Uses 2 reference images (Image 1 and Image 2)\n\n# YOUTUBE THUMBNAIL ESSENTIALS TO ADD\n\n**Text Overlay (add if missing):**\n- 1-3 words maximum\n- Bold Impact or sans-serif font\n- High contrast (white with colored glow, or bright yellow/orange)\n- Top center or top-left placement\n- Example words: \"AI Tool\", \"Watch This\", \"Free Method\", \"Secret Trick\"\n\n**Visual Effects:**\n- Glows on key elements (cyan, orange, neon green)\n- Rim lighting on people\n- Drop shadows for depth\n- High contrast colors\n- Blur background, sharp foreground\n\n**Colors:**\n- Vibrant, saturated colors (electric blue, neon green, orange, yellow)\n- Deep backgrounds (purple, navy, black gradients)\n- Avoid red/black/white (blends with YouTube)\n\n**Composition:**\n- Clear foreground/background separation\n- Mobile-optimized (70% watch on phones)\n- Face visible if person included\n- Rule of thirds\n\n# REFERENCE IMAGES\n\nUser will provide 2 images:\n- **Image 1**: Usually the person/creator\n- **Image 2**: Usually workflow/screenshot/content\n\n# CRITICAL RULES\n\n\u2705 DO:\n- Output ONLY the prompt (one paragraph)\n- Preserve user's core idea\n- Add text overlay if missing\n- Add lighting, glows, effects\n- Specify 16:9, high resolution, mobile-optimized\n- Use natural, flowing language\n\n\u274c DON'T:\n- Add preamble or analysis\n- Change their creative vision\n- Use section headers or labels\n- Reference \"Image 3\" (only 2 images available)\n- Explain your reasoning\n\n# EXAMPLES\n\n**Input:** \"workflow as background, me on the left\"\n\n**Output:** \"Create a 16:9 high-resolution YouTube thumbnail using the two provided reference images. Use Image 2 (workflow screenshot) as the full-width background, applying a strong Gaussian blur and deep purple to navy gradient overlay (#2D1B69 to #071029, 40% opacity) to create depth while keeping workflow elements recognizable. Extract and position Image 1 (person) as a clean cutout on the left third of frame with background removed, add dramatic cyan-tinted rim lighting on the edges and a soft drop shadow beneath for separation. Apply vibrant cyan glows (#00D9FF) to key workflow nodes and orange accents (#FF6B35) to connection lines in the blurred background. Place bold text 'AI WORKFLOW' in extra-large white Impact font at top center with bright orange outer glow (20px blur) and thin black stroke for maximum mobile readability. Ensure high contrast, sharp details on person, cinematic color grading, and professional YouTube thumbnail aesthetic optimized for small screens.\"\n\n**Input:** \"AI creating videos, phone showing result\"\n\n**Output:** \"Create a vibrant 16:9 YouTube thumbnail composition using the two reference images. Center Image 2 (phone/screen showing AI-generated video) as the dominant element angled toward viewer, with high saturation and contrast on the displayed content. Extract Image 1 (person) with background removed and place as a circular or angled cutout in the left or bottom corner at 30% size with neon green border (#00FF00) and drop shadow. Add electric blue background (#0080FF) with neon green and bright yellow accent elements suggesting AI processing or data flow. Apply screen glare effect on phone, cyan and magenta light rays emanating from screen, and dramatic lighting. Place bold text 'FREE AI' at top-left in extra-large bright yellow font (#FFFF00) with neon green glow for maximum visibility. Ensure eye-catching colors, high contrast, sharp phone details, cinematic lighting, and mobile-optimized composition with modern tech YouTube aesthetic.\"\n\n# OUTPUT FORMAT\n\nReturn ONLY the optimized prompt. No analysis, no preamble, no explanation. Just the prompt as one flowing paragraph ready to send to Nano Banana Pro."
            },
            {
              "content": "=Convert this YouTube thumbnail concept into an optimized Nano Banana Pro image generation prompt:\n{{ $json[\"Thumbnail prompt\"] }}"
            }
          ]
        },
        "builtInTools": {}
      },
      "credentials": {
        "openAiApi": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 2.1
    },
    {
      "id": "0c951080-8528-461a-a29b-a5432b56611c",
      "name": "clean up prompt",
      "type": "n8n-nodes-base.set",
      "position": [
        1760,
        448
      ],
      "parameters": {
        "options": {},
        "assignments": {
          "assignments": [
            {
              "id": "280ce518-be14-4bba-afa1-64e8e042a8f3",
              "name": "thumbnailPrompt",
              "type": "string",
              "value": "={{ JSON.stringify($json.output[0].content[0].text.replace(/\\n/g, ' ').replace(/\\r/g, ' ').replace(/\\s+/g, ' ').trim()) }}"
            }
          ]
        }
      },
      "typeVersion": 3.4
    },
    {
      "id": "21b60b2b-d25a-44c4-ba8b-e335bd43d1c7",
      "name": "Create thumbnail",
      "type": "n8n-nodes-base.httpRequest",
      "position": [
        2112,
        448
      ],
      "parameters": {
        "url": "https://api.kie.ai/api/v1/jobs/createTask",
        "method": "POST",
        "options": {},
        "jsonBody": "={{ $json.bodyRaw }}",
        "sendBody": true,
        "specifyBody": "json",
        "authentication": "genericCredentialType",
        "genericAuthType": "httpHeaderAuth"
      },
      "credentials": {
        "httpHeaderAuth": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 4.3
    },
    {
      "id": "e96cc769-2161-4007-bea8-17b31431a1cc",
      "name": "Add thumbnail to airtable",
      "type": "n8n-nodes-base.httpRequest",
      "position": [
        2032,
        592
      ],
      "parameters": {
        "url": "=https://content.airtable.com/v0/YOUR_BASE_ID/{{ $('Get a record2').item.json.id }}/Thumbnail/uploadAttachment",
        "method": "POST",
        "options": {},
        "jsonBody": "={\n  \"contentType\": \"image/png\",\n  \"file\": \"{{ $json.data }}\",\n  \"filename\": \"generated_image.png\"\n}\n",
        "sendBody": true,
        "specifyBody": "json",
        "authentication": "predefinedCredentialType",
        "nodeCredentialType": "airtableTokenApi"
      },
      "credentials": {
        "airtableApi": {
          "name": "<your credential>"
        },
        "airtableTokenApi": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 4.3
    },
    {
      "id": "9714391f-af38-40ca-bf43-0a73bf7aca2a",
      "name": "Sticky Note",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        1056,
        0
      ],
      "parameters": {
        "width": 480,
        "height": 304,
        "content": "## When edited video is added to google drive folder create the record with our video in airtable"
      },
      "typeVersion": 1
    },
    {
      "id": "f3c1d119-4824-41f8-ba73-e394e959115a",
      "name": "Sticky Note1",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        1536,
        0
      ],
      "parameters": {
        "color": 2,
        "width": 1072,
        "height": 304,
        "content": "## When Video summary is added this system is triggered to then generate 3 optimized titles to A/B test based on the video summary"
      },
      "typeVersion": 1
    },
    {
      "id": "0bdd2e76-0ace-4228-b034-26ba9dfb8c37",
      "name": "Sticky Note2",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        1056,
        304
      ],
      "parameters": {
        "color": 3,
        "width": 1552,
        "height": 656,
        "content": "## This system is manually triggered once you want to generate the thumbnail based on the idea you typed in the airtable \"thumbnail idea\" field. This system then sends that idea into our image prompt optimizer that then sends the image prompt to kie.ai to access nano banana pro"
      },
      "typeVersion": 1
    },
    {
      "id": "5c7940bb-ffdc-41e2-9b40-0a256feb431f",
      "name": "Sticky Note4",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        0,
        0
      ],
      "parameters": {
        "color": 7,
        "width": 1072,
        "height": 2304,
        "content": "# \ud83c\udfac AI REPURPOSING SYSTEM (READ THIS FIRST)\n\n# Created by: [Jordan Austin](https://www.skool.com/ai-growth-lab-4394/about?ref=5065ab28874b4325b44ef3ead8105722)\n\n# \ud83d\udca1 System Overview\n## This is a **fully automated YouTube content processing pipeline**. Upload a video to Google Drive and it automatically transcribes, generates 3 A/B-testable titles, creates an AI thumbnail with your reference style, identifies 3-8 elite clips with captions, and writes a YouTube description with chapters. Processing time: ~10-15 minutes per video.\n\n# Automated Steps:\n## * **Transcription:** Uses via Apify to transcribe with H:MM:SS.mmm timestamps.\n## * **Title Generation:** Creates 3 title variations for A/B testing using GPT-4o-mini.\n## * **Thumbnail Creation:** Generates photorealistic thumbnail with 2 reference images via Kie.ai Nano Banana Pro.\n## * **Clip Identification:** Uses Grok 4.1 Fast to find 3-8 elite clips (45+ seconds) with action-oriented captions and timestamps.\n## * **Description Generation:** Creates YouTube description with chapter timestamps.\n## * **Database Storage:** Saves all outputs to Airtable for easy access and workflow management.\n\n# \u2699\ufe0f Critical Setup & Configuration\n## * **Estimated Setup Time:** ~15-20 minutes.\n## * **Webhook Setup:** After activating workflow, copy Webhook URLs from Webhook1 and Webhook2 nodes and place into your Airtable button formulas and the 2 airtable automations\n## * **Make sure you look through the prompts where it says (HVE CLAUDE TAILOR THIS TO YOUR NICHE) and paste the prompt into claude telling it to not change the prompt but just to tailor it to what you make content about\n## * **Towards the end of the video I show you an error that we ran into and how to fix them. Instead of uploading the video to private we upload it as unlisted so that way we can access the video.\n## * **Another thing we added was a video id field into airtable which is required to paste in before you check the box saying the video was uploaded to youtube which then triggers the clip generator and description genrator\n\n# \u26a0\ufe0f Mandatory Steps (Do This First!)\n## 1. **Duplicate Airtable Base:** Copy the base structure into your account (buttons and fields are pre-configured).\n   ## * [AIRTABLE BASE](https://airtable.com/appGXKQcCn8bf8wyq/shrIf6F9GfnYZNp79)\n## 2. **Update Webhook URLs:** After activating the workflow in n8n:\n   ## * Copy Production URL from **Webhook2** node \u2192 Paste into \"Generate thumbnail\" button formula\n   ## * Update `YOUR_WEBHOOK_URL` in both Airtable automations \n## 3. **Credential Setup:** Connect your accounts for **every service** listed below via the Credentials panel.\n## 4. **Create drive folder** You need to create a drive folder that you can put your edited video into so the system can trigger\n## 5. **Anywhere that says YOUR_API in a node you need to paste in your API key (check the apify node)\n## 6. **In the add thumbnail to airtable node you need to add in your airtable base ID where it says YOUR_BASE_ID \n\n# \ud83d\udd11 Required Services (APIs & Credentials)\n## * [AIRTABLE](https://docs.n8n.io/integrations/builtin/credentials/airtable/?utm_source=n8n_app&utm_medium=credential_settings&utm_campaign=create_new_credentials_modal) - For database storage and workflow triggers.\n## * [GOOGLE DRIVE](https://docs.n8n.io/integrations/builtin/credentials/google/?utm_source=n8n_app&utm_medium=credential_settings&utm_campaign=create_new_credentials_modal) - For video upload monitoring.\n## * [APIFY](https://docs.apify.com/platform/integrations/api) - For video transcription via AssemblyAI actor.\n## * [OPENAI](https://docs.n8n.io/integrations/builtin/credentials/openai/?utm_source=n8n_app&utm_medium=credential_settings&utm_campaign=create_new_credentials_modal) - For title/description generation (GPT-4o-mini).\n## * [OPENROUTER](https://docs.n8n.io/integrations/builtin/credentials/openrouter/?utm_source=n8n_app&utm_medium=credential_settings&utm_campaign=create_new_credentials_modal) - For clip identification (Grok 4.1 Fast).\n## * Kie.ai\n## * [GOOGLE API SETUP VIDEO](https://youtube.com/shorts/FBRQNmCN0F8?feature=share)"
      },
      "typeVersion": 1
    },
    {
      "id": "5be766c2-2ffe-4179-976d-b9e529fd93cd",
      "name": "Sticky Note5",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        2624,
        -160
      ],
      "parameters": {
        "color": 6,
        "width": 1936,
        "height": 1104,
        "content": "@[Youtube](EEBaCA3XvUs)"
      },
      "typeVersion": 1
    },
    {
      "id": "00d5b7e4-b911-4f62-88b0-0c4cf4da6a8c",
      "name": "Get a record",
      "type": "n8n-nodes-base.airtable",
      "position": [
        1792,
        128
      ],
      "parameters": {
        "id": "={{ $json.query.recordId }}",
        "base": {
          "__rl": true,
          "mode": "list",
          "value": "appFGF4qoyqn50KOz",
          "cachedResultUrl": "https://airtable.com/appFGF4qoyqn50KOz",
          "cachedResultName": "Content Factory"
        },
        "table": {
          "__rl": true,
          "mode": "list",
          "value": "tblUTxWrEJD5pUsV2",
          "cachedResultUrl": "https://airtable.com/appFGF4qoyqn50KOz/tblUTxWrEJD5pUsV2",
          "cachedResultName": "Table 1"
        },
        "options": {}
      },
      "credentials": {
        "airtableTokenApi": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 2.1
    },
    {
      "id": "6c504471-38fc-496f-bd1f-2d4d31f7f48a",
      "name": "Wait 2 mins",
      "type": "n8n-nodes-base.wait",
      "position": [
        1104,
        608
      ],
      "parameters": {
        "unit": "minutes",
        "amount": 2
      },
      "typeVersion": 1.1
    },
    {
      "id": "5668f6df-1609-4d89-8210-6d37c8c73879",
      "name": "Sticky Note6",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        1344,
        1984
      ],
      "parameters": {
        "width": 1056,
        "height": 1392,
        "content": "# \u26a0\ufe0f YouTube Captions Polling Loop (Not in Video)\n\n## Why This Wasn't in the Original Video\nWhen I recorded the tutorial, I was testing with videos that already had captions available. I didn't realize YouTube takes 10-60 minutes AFTER upload to generate auto-captions.\n\n## **The Problem:** If you click \"Generate clips\" immediately after upload, there's no transcript available yet.\n\n## **The Solution:** When you click \"Generate clips,\" these 3 nodes automatically poll YouTube's API every 5 minutes until captions are ready, then the workflow continues to clip identification automatically.\n\n---\n\n## What These Nodes Do\n\n### **Node 1: Check YouTube Captions API**\n- Calls `captions.list` endpoint to check if auto-generated captions exist\n- Returns empty array if not ready, or caption data if ready\n\n### **Node 2: IF - Captions Ready?**\n- Checks if `items.length > 0`\n- **TRUE** \u2192 Captions ready, continue to clip identification\n- **FALSE** \u2192 Not ready, loop back to wait node\n\n### **Node 3: Wait 5 Minutes**\n- Pauses workflow for 5 minutes before checking again\n- Prevents API rate limiting\n\n---\n\n## How It Works\n\n## 1. Click \"Generate clips\" button in Airtable\n## 2. Workflow checks YouTube: Are captions ready?\n  ### - **YES** \u2192 Proceed to clip identification (rest of workflow)\n  ### - **NO** \u2192 Wait 5 minutes, check again\n## 3. Automatically continues when captions are available\n\n## **No manual checking required - the workflow handles everything automatically.**\n\n---\n\n## **Added:** December 9, 2025  \n## **Why:** Discovered caption processing delay when testing with freshly uploaded video"
      },
      "typeVersion": 1
    },
    {
      "id": "b3f31b8f-4398-4d8d-9f49-2c86ee7045f4",
      "name": "Wait 5 mins",
      "type": "n8n-nodes-base.wait",
      "position": [
        1952,
        1712
      ],
      "parameters": {
        "unit": "minutes"
      },
      "typeVersion": 1.1
    },
    {
      "id": "3f6e0d99-9626-4672-acba-46f9c710535e",
      "name": "Check to see if transcript is ready",
      "type": "n8n-nodes-base.httpRequest",
      "position": [
        1600,
        1680
      ],
      "parameters": {
        "url": "https://www.googleapis.com/youtube/v3/captions",
        "options": {},
        "sendQuery": true,
        "sendHeaders": true,
        "authentication": "predefinedCredentialType",
        "queryParameters": {
          "parameters": [
            {
              "name": "videoId",
              "value": "={{ $json.id }}"
            },
            {
              "name": "part",
              "value": "=snippet"
            }
          ]
        },
        "headerParameters": {
          "parameters": [
            {
              "name": "Accept",
              "value": "application/json"
            },
            {
              "name": "Content-Type",
              "value": "application/json"
            }
          ]
        },
        "nodeCredentialType": "youTubeOAuth2Api"
      },
      "credentials": {
        "youTubeOAuth2Api": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 4.3
    },
    {
      "id": "3ebe53cb-429d-49cd-9743-06a98c9c8a41",
      "name": "Is transcript ready?",
      "type": "n8n-nodes-base.switch",
      "position": [
        1792,
        1680
      ],
      "parameters": {
        "rules": {
          "values": [
            {
              "conditions": {
                "options": {
                  "version": 2,
                  "leftValue": "",
                  "caseSensitive": true,
                  "typeValidation": "strict"
                },
                "combinator": "and",
                "conditions": [
                  {
                    "id": "97ef1f9c-2247-4517-9f18-568d5986a182",
                    "operator": {
                      "type": "boolean",
                      "operation": "true",
                      "singleValue": true
                    },
                    "leftValue": "={{ $json.items.length > 0 }}",
                    "rightValue": ""
                  }
                ]
              }
            },
            {
              "conditions": {
                "options": {
                  "version": 2,
                  "leftValue": "",
                  "caseSensitive": true,
                  "typeValidation": "strict"
                },
                "combinator": "and",
                "conditions": [
                  {
                    "id": "7e5309db-9776-43d0-8cac-0e053d5deb35",
                    "operator": {
                      "type": "boolean",
                      "operation": "false",
                      "singleValue": true
                    },
                    "leftValue": "={{ $json.items.length > 0 }}",
                    "rightValue": ""
                  }
                ]
              }
            }
          ]
        },
        "options": {}
      },
      "typeVersion": 3.3
    },
    {
      "id": "c4a06c00-5ea9-4a6a-a103-32fd503c0275",
      "name": "Webhook3",
      "type": "n8n-nodes-base.webhook",
      "position": [
        1088,
        1296
      ],
      "parameters": {
        "path": "5df46517-cec1-4563-93f3-dc51948f3551",
        "options": {}
      },
      "typeVersion": 2.1
    },
    {
      "id": "d1ff3fab-12c8-4705-8755-1705afe71477",
      "name": "Get a record4",
      "type": "n8n-nodes-base.airtable",
      "position": [
        1232,
        1296
      ],
      "parameters": {
        "id": "={{ $json.query.recordId }}",
        "base": {
          "__rl": true,
          "mode": "list",
          "value": "appFGF4qoyqn50KOz",
          "cachedResultUrl": "https://airtable.com/appFGF4qoyqn50KOz",
          "cachedResultName": "Content Factory"
        },
        "table": {
          "__rl": true,
          "mode": "list",
          "value": "tblUTxWrEJD5pUsV2",
          "cachedResultUrl": "https://airtable.com/appFGF4qoyqn50KOz/tblUTxWrEJD5pUsV2",
          "cachedResultName": "Table 1"
        },
        "options": {}
      },
      "credentials": {
        "airtableTokenApi": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 2.1
    },
    {
      "id": "63e5a59d-fe0a-4c9c-a99c-1cf2019c3ab3",
      "name": " Get transcript from video1",
      "type": "n8n-nodes-base.httpRequest",
      "position": [
        2000,
        1280
      ],
      "parameters": {
        "url": "https://api.apify.com/v2/acts/pintostudio~youtube-transcript-scraper/run-sync-get-dataset-items?token=YOUR_TOKEN_HERE",
        "method": "POST",
        "options": {
          "redirect": {
            "redirect": {}
          }
        },
        "jsonBody": "={\n    \"videoUrl\": \"https://www.youtube.com/watch?v={{ $('Get a video1').item.json.id }}\"\n}",
        "sendBody": true,
        "sendHeaders": true,
        "specifyBody": "json",
        "headerParameters": {
          "parameters": [
            {
              "name": "Accept",
              "value": "application/json"
            },
            {
              "name": "Authorization",
              "value": "Bearer YOUR_TOKEN_HERE"
            }
          ]
        }
      },
      "typeVersion": 4.3
    },
    {
      "id": "730508c3-d6a9-486b-bb5a-06b401729bfa",
      "name": "Formatt transcript1",
      "type": "n8n-nodes-base.code",
      "position": [
        2208,
        1280
      ],
      "parameters": {
        "jsCode": "// Get the transcript array from Apify\nconst transcriptData = $json.data;\n\n// Check if it's an array\nif (!Array.isArray(transcriptData)) {\n  throw new Error(\"Transcript data is not an array\");\n}\n\n// Convert seconds to HH:MM:SS.mmm format\nfunction formatTimestamp(seconds) {\n  const totalSeconds = parseFloat(seconds);\n  const hrs = Math.floor(totalSeconds / 3600);\n  const mins = Math.floor((totalSeconds % 3600) / 60);\n  const secs = Math.floor(totalSeconds % 60);\n  const ms = Math.floor((totalSeconds % 1) * 1000);\n  \n  return `${String(hrs).padStart(2, '0')}:${String(mins).padStart(2, '0')}:${String(secs).padStart(2, '0')}.${String(ms).padStart(3, '0')}`;\n}\n\n// Build clean, readable transcript\nlet cleanTranscript = \"\";\n\nfor (let i = 0; i < transcriptData.length; i++) {\n  const item = transcriptData[i];\n  if (item.text && item.text.trim()) {\n    cleanTranscript += formatTimestamp(item.start) + \" - \" + item.text.trim() + \"\\n\\n\";\n  }\n}\n\n// Return formatted transcript\nreturn {\n  json: {\n    Transcript: cleanTranscript.trim()\n  }\n};"
      },
      "typeVersion": 2
    },
    {
      "id": "d520640d-adb4-438b-b5e4-c55d526e6506",
      "name": " Description agent1",
      "type": "@n8n/n8n-nodes-langchain.openAi",
      "position": [
        2464,
        1392
      ],
      "parameters": {
        "modelId": {
          "__rl": true,
          "mode": "list",
          "value": "gpt-5-mini",
          "cachedResultName": "GPT-5-MINI"
        },
        "options": {},
        "responses": {
          "values": [
            {
              "role": "system",
              "content": "=You are a YouTube description generator. Your job is to take a template and fill in the chapter timestamps based on the video transcript.\n\n# YOUR TASK\n\nFill in the YouTube description template with properly formatted chapter timestamps. Keep ALL other text in the template EXACTLY as provided.\n\n# TIMESTAMP REQUIREMENTS\n\n## Format Rules\n- Use MM:SS format for videos under 1 hour (example: 05:34)\n- Use HH:MM:SS format for videos over 1 hour (example: 1:05:34)\n- MUST start with 00:00 (YouTube requirement)\n- NO milliseconds (00:00:00.000 is WRONG)\n- Format must be EXACT: MM:SS or HH:MM:SS with leading zeros\n\n## Chapter Title Requirements\n- Keep titles clear and descriptive (5-10 words max)\n- Use title case (capitalize first letter of major words)\n- Be specific about what happens in that section\n- Make it scannable and valuable to viewers\n\nGOOD CHAPTER TITLES:\n\u2705 \"Introduction: What We're Building Today\"\n\u2705 \"Setting Up the n8n Webhook Trigger\"\n\u2705 \"Configuring the HTTP Request Node\"\n\u2705 \"Testing the Complete Workflow\"\n\u2705 \"Outro & Free Template Download\"\n\nBAD CHAPTER TITLES:\n\u274c \"Intro\" (too vague)\n\u274c \"Node breakdown starts here\" (not descriptive)\n\u274c \"Next part\" (doesn't tell viewer anything)\n\n## Chapter Placement Strategy\n- First chapter MUST be at 00:00\n- Create chapters at natural section breaks (every 2-5 minutes ideal)\n- Aim for 5-15 chapters total depending on video length\n- Don't create chapters for segments under 30 seconds\n- Align chapters with when new topics/steps begin\n\n# OUTPUT RULES\n\n- Return ONLY the completed description template\n- Do NOT add any preamble like \"Here's the description:\" or explanations\n- Do NOT add markdown formatting (no code blocks)\n- Keep ALL original text from the template unchanged\n- ONLY replace the [TIMESTAMPS SECTION] placeholder with generated timestamps\n- The output should be ready to copy/paste directly into YouTube"
            },
            {
              "content": "=Fill in this YouTube description template with chapter timestamps based on the transcript.\n\n**Template:**\n\n[VIDEO TITLE RESTATED WITH KEYWORDS]\nLearn how to [MAIN BENEFIT] using [TOOLS MENTIONED]. In this tutorial, I'll show you [KEY TAKEAWAY 1], [KEY TAKEAWAY 2], and [KEY TAKEAWAY 3].\n\n\ud83d\udc65 Join My Free Skool Community: https://www.skool.com/ai-growth-lab-4394/about?ref=5065ab28874b4325b44ef3ead8105722\n\nGet the full n8n template, Airtable base, and exclusive AI automation resources.\n\n\ud83e\udd16 Need Custom AI Solutions? Work with me: https://zangflow.com\n\n---\n\n\u23f1\ufe0f TIMESTAMPS\n00:00 - Introduction: What We're Building\n[AUTO-GENERATED TIMESTAMPS WITH DESCRIPTIVE TITLES]\n\n---\n\n\ud83d\udc47 TOOLS & RESOURCES\n\n\ud83d\ude80 Cold Email Engine (Instantly.ai): https://instantly.ai/?via=jordan-austin\n\ud83e\udd16 n8n Automation Platform: https://n8n.partnerlinks.io/77ys2bwb9k9c\n\n---\n\n\ud83d\udca1 Don't forget to like, subscribe, and turn on notifications for weekly AI automation tutorials, n8n workflows, and no-code AI agent builds!\n\n\n**Video Title:** {{ $('Get a record4').item.json['Title 1'] }}\n\n**Video Summary:** {{ $('Get a record4').item.json['Video summary'] }}\n\n**Full Transcript with Timestamps:**\n{{ $json[\"Transcript\"] }}\n\nReturn ONLY the completed description template ready to paste into YouTube. No preamble, no explanation, no markdown formatting.\n\nDO NOT CHANGE ANY OF THE LINKS "
            }
          ]
        },
        "builtInTools": {}
      },
      "credentials": {
        "openAiApi": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 2.1
    },
    {
      "id": "1babfed9-c0de-42a3-8a73-e7bb9cb942c3",
      "name": "OpenRouter Chat Model1",
      "type": "@n8n/n8n-nodes-langchain.lmChatOpenRouter",
      "position": [
        2304,
        1136
      ],
      "parameters": {
        "model": "x-ai/grok-4.1-fast",
        "options": {}
      },
      "credentials": {
        "openRouterApi": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 1
    },
    {
      "id": "cafddad4-37af-481f-8c96-284c12c55ce3",
      "name": "Key value pair clips",
      "type": "n8n-nodes-base.code",
      "position": [
        2704,
        1184
      ],
      "parameters": {
        "jsCode": "// Get the AI response\nconst items = $input.all();\n\n// Handle different possible structures\nlet rawOutput;\nif (items[0].json.output) {\n  // Anthropic/Claude structure\n  rawOutput = items[0].json.output[0].content[0].text;\n} else if (items[0].json.text) {\n  // Direct text field\n  rawOutput = items[0].json.text;\n} else if (items[0].json.choices) {\n  // OpenAI structure\n  rawOutput = items[0].json.choices[0].message.content;\n} else {\n  // Fallback - try to stringify and parse\n  rawOutput = JSON.stringify(items[0].json);\n}\n\n// Remove markdown code fences if present\nrawOutput = rawOutput\n  .replace(/```json\\s*/g, '')  // Remove ```json\n  .replace(/```\\s*/g, '')       // Remove closing ```\n  .trim();\n\n// Parse the JSON string\nconst clips = JSON.parse(rawOutput);\n\n// Return each clip as a separate item for Airtable\nreturn clips.map(clip => ({\n  json: clip\n}));"
      },
      "typeVersion": 2
    },
    {
      "id": "edb586a1-2d56-46e0-be62-20d4e3cfd9c9",
      "name": "cleanly formatt clips",
      "type": "n8n-nodes-base.code",
      "position": [
        2880,
        1184
      ],
      "parameters": {
        "jsCode": "// Get the input\nconst items = $input.all();\n\n// The input is already an array of clips\nconst clips = items.map(item => item.json);\n\n// Format each clip as readable text\nconst formattedClips = clips.map(clip => {\n  return `CLIP ${clip.clip_number}\n\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\n\ud83d\udccd Start: ${clip.start_timestamp}\n\ud83d\udccd End: ${clip.end_timestamp}\n\ud83d\udccd CTA Start: ${clip.cta_start_timestamp}\n\ud83d\udccd CTA End: ${clip.cta_end_timestamp}\n\n\ud83d\udcfa Title: ${clip.youtube_title}\n\n\ud83d\udcdd Caption:\n${clip.caption}\n`;\n}).join('\\n\\n');\n\n// Create summary\nconst summary = `\ud83c\udfac TOTAL CLIPS IDENTIFIED: ${clips.length}\n\n${formattedClips}`;\n\n// Return just what you need\nreturn [{\n  json: {\n    clips_formatted: summary\n  }\n}];"
      },
      "typeVersion": 2
    },
    {
      "id": "bcd6de1c-caa4-415c-8f99-f79bee7d5915",
      "name": "Update record",
      "type": "n8n-nodes-base.airtable",
      "position": [
        3024,
        1184
      ],
      "parameters": {
        "base": {
          "__rl": true,
          "mode": "list",
          "value": "appFGF4qoyqn50KOz",
          "cachedResultUrl": "https://airtable.com/appFGF4qoyqn50KOz",
          "cachedResultName": "Content Factory"
        },
        "table": {
          "__rl": true,
          "mode": "list",
          "value": "tblUTxWrEJD5pUsV2",
          "cachedResultUrl": "https://airtable.com/appFGF4qoyqn50KOz/tblUTxWrEJD5pUsV2",
          "cachedResultName": "Table 1"
        },
        "columns": {
          "value": {
            "Clips": "={{ $json.clips_formatted }}",
            "Select": "Complete",
            "Calculation": "={{ $('Get a record4').first().json.Calculation }}"
          },
          "schema": [
            {
              "id": "id",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": true,
              "required": false,
              "displayName": "id",
              "defaultMatch": true
            },
            {
              "id": "Video file name",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Video file name",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Select",
              "type": "options",
              "display": true,
              "options": [
                {
                  "name": "In progress",
                  "value": "In progress"
                },
                {
                  "name": "Complete",
                  "value": "Complete"
                }
              ],
              "removed": false,
              "readOnly": false,
              "required": false,
              "displayName": "Select",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Longform edited video",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Longform edited video",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Video summary",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Video summary",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Title 1",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Title 1",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Title 2",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Title 2",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Title 3",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Title 3",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Thumbnail prompt",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Thumbnail prompt",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Thumbnail reference 1",
              "type": "array",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Thumbnail reference 1",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Thumbnail reference 2",
              "type": "array",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Thumbnail reference 2",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Thumbnail",
              "type": "array",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Thumbnail",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "generate thumbnail (once reference images are added)",
              "type": "string",
              "display": true,
              "removed": true,
              "readOnly": true,
              "required": false,
              "displayName": "generate thumbnail (once reference images are added)",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Uploaded to YouTube? (on private for now)",
              "type": "boolean",
              "display": true,
              "removed": true,
              "readOnly": false,
              "required": false,
              "displayName": "Uploaded to YouTube? (on private for now)",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Clips",
              "type": "string",
              "display": true,
              "removed": false,
              "readOnly": false,
              "required": false,
              "displayName": "Clips",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Calculation",
              "type": "string",
              "display": true,
              "removed": false,
              "readOnly": true,
              "required": false,
              "displayName": "Calculation",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            }
          ],
          "mappingMode": "defineBelow",
          "matchingColumns": [
            "Calculation"
          ],
          "attemptToConvertTypes": false,
          "convertFieldsToString": false
        },
        "options": {},
        "operation": "update"
      },
      "credentials": {
        "airtableTokenApi": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 2.1
    },
    {
      "id": "cb0da050-f7dc-4caf-889e-b660a7aaa2fd",
      "name": "Clipping agent1",
      "type": "@n8n/n8n-nodes-langchain.chainLlm",
      "position": [
        2448,
        1184
      ],
      "parameters": {
        "text": "=Analyze this video transcript and identify ONLY the ELITE clips worthy of posting as short-form content (TikTok, Instagram Reels, YouTube Shorts).\n\n**Video Title:** {{ $('Get a record4').item.json['Title 1'] }}\n\n**Video Summary:** {{ $('Get a record4').item.json['Video summary'] }}\n\n**Full Transcript with Timestamps:**\n{{ $json.Transcript }}\n\n**CRITICAL:** Quality over quantity. Only select clips that meet ALL criteria and would genuinely perform well. If you only find 1-2 elite clips, that's perfectly fine. If you find zero clips that meet the standards, return an empty array.\n\nDo NOT force clips that don't meet the criteria. Every clip you identify must be excellent and self-contained.\n\nReturn your response as a JSON array of clips.\n",
        "batching": {},
        "messages": {
          "messageValues": [
            {
              "message": "=# Clip Identification System Prompt\n\nYou are an expert short-form content strategist specializing in identifying high-performing video clips from long-form YouTube content for TikTok, Instagram Reels, and YouTube Shorts.\n\n## BEFORE YOU START - CRITICAL MINDSET\n\nYou are NOT just extracting clips - you are creating STANDALONE VIDEOS that will be posted to TikTok/Instagram/YouTube.\n\nEach clip you identify will become a COMPLETE video that someone discovers while scrolling.\n\nAsk yourself for EVERY clip:\n1. If I saw this while scrolling, would I IMMEDIATELY understand what's happening within 3 seconds?\n2. Does this deliver COMPLETE value, or does it feel like a teaser that requires watching the full video?\n3. Would I watch this entire clip, or would I scroll away halfway through?\n4. Does the ending feel SATISFYING with a clear conclusion, or does it leave me hanging?\n5. Does the clip have proper CONTEXT at the start, or am I joining mid-explanation?\n\nIf you answer NO to any of these \u2192 the clip boundaries are WRONG. Adjust them.\n\n**Default to LONGER clips with MORE context rather than shorter clips that feel rushed.**\n\nBetter to have a 90-second clip that delivers complete value than a 50-second clip that feels incomplete.\n\n## PRIORITY ORDER (READ THIS FIRST)\n\nWhen criteria conflict, follow this priority:\n1. **Complete value delivery** (most important)\n2. **Natural idea boundaries** (proper start/end points with full context)\n3. **Includes full Skool CTA segment** (15-30 seconds)\n4. **Minimum 45 seconds duration** (unless truly exceptional)\n5. **Self-contained and understandable** (no prior context needed)\n\n## YOUR TASK\n\nAnalyze the provided video transcript with timestamps and identify ONLY the ELITE clips worthy of posting as short-form content. Focus on QUALITY over QUANTITY - only select clips that meet ALL criteria.\n\n## CRITICAL CLIP CRITERIA\n\nEvery clip you identify MUST meet ALL of these requirements:\n\n### 1. Minimum Duration Requirement\n\n**ABSOLUTE RULE:**\n- Clips MUST be at least 45 seconds long\n- Exception: Only clips 30-45 seconds if they deliver complete, high-impact value\n- NEVER create clips under 30 seconds\n\n**Why this matters:**\n- Under 45 seconds rarely allows for proper context + value delivery\n- Viewers need time to understand what they're watching\n- Short clips feel like teasers, not standalone content\n\n**If a potential clip is too short:**\n- Extend the start to include more context\n- Extend the end to include the full conclusion and result\n- Better to be 90 seconds with breathing room than 40 seconds rushed\n\n### 2. Complete Idea Boundaries\n\n**START POINT - THE \"COLD OPEN\" TEST:**\nRead the EXACT first words spoken. Ask yourself:\n- Would someone scrolling TikTok with NO context understand what this is about within 3 seconds?\n- Is this the TRUE beginning of an idea, or are we joining mid-thought?\n- Do the first words set clear context about what's about to happen?\n\n**GOOD START EXAMPLES:**\n- \u2705 \"Let me show you exactly how to set this up\"\n- \u2705 \"Here's the biggest mistake people make\"\n- \u2705 \"So the first thing you need to do is...\"\n- \u2705 \"In today's video, I'm going to show you\"\n- \u2705 \"Alright, so what we're building here is...\"\n\n**BAD START EXAMPLES:**\n- \u274c \"...and that's why you need to use this tool\" (starts with \"and\")\n- \u274c \"the second step is to click here\" (what was step one?)\n- \u274c \"it's actually really simple\" (what is \"it\"?)\n- \u274c \"so then you just paste it in\" (paste what? from where?)\n- \u274c \"Obviously, the more detailed you get...\" (obviously to who? what are we talking about?)\n\n**END POINT - THE \"SATISFACTION\" TEST:**\nRead the EXACT last words spoken. Ask yourself:\n- Does this thought feel complete?\n- Would a viewer feel satisfied or left hanging?\n- Is there a natural pause or conclusion?\n- Did we show the RESULT or OUTCOME, not just explain the process?\n\n**GOOD END EXAMPLES:**\n- \u2705 \"...and that's how you automate the entire process\"\n- \u2705 \"...and boom, you're done\"\n- \u2705 \"That's the secret that most people miss\"\n- \u2705 \"...now you have a fully working system\"\n- \u2705 \"Perfect, that's exactly what we were going for\"\n\n**BAD END EXAMPLES:**\n- \u274c \"...and then you need to...\" (incomplete)\n- \u274c \"...so the next step is...\" (implies more coming)\n- \u274c \"...which brings us to...\" (transition, not ending)\n- \u274c \"Now that we have this set up, we need to...\" (you just started the NEXT thing!)\n\n## HOW TO IDENTIFY PROPER START AND END POINTS\n\n### STEP-BY-STEP START IDENTIFICATION:\n\n**Step 1: Find a potential starting point**\n\n**Step 2: Read the 3-5 sentences BEFORE that point**\n- If those sentences provide essential context, your start is too late\n- If they're setting up the problem or explaining what's about to happen, INCLUDE THEM\n- Move the start earlier to capture the full setup\n\n**Step 3: Read the EXACT first sentence of your clip**\n- Does it have words like \"and\", \"so\", \"then\", \"also\", \"next\", \"obviously\"? \u2192 Start is probably too late\n- Does it reference \"this\", \"that\", \"it\" without explaining what it is? \u2192 Start is too late\n- Does it say \"step 2\" or \"the next thing\"? \u2192 Start is too late\n- Does it assume prior knowledge? \u2192 Start is too late\n\n**Step 4: Apply the \"Show to a stranger\" test**\n- Imagine showing just this clip to someone who has NEVER seen your content\n- Within 5 seconds, do they know: (1) What this is about, (2) Why they should care, (3) What they're about to learn?\n- If NO to any \u2192 move start earlier\n\n**EXAMPLE - WRONG START:**\n```\nStart timestamp: 0:11:05.519\nFirst words: \"Obviously, the more detailed you get, the better the character generation is going to be.\"\n```\n**Problem:** \"Obviously\" implies prior context. \"The character generation\" - which one? What are we generating? This is MID-EXPLANATION.\n\n**CORRECT START (moved earlier):**\n```\nStart timestamp: 0:10:40.000\nFirst words: \"So we have our product image and our product name, but we don't have an AI influencer to market that product. I'm going to click the plus sign over here, and I'm just going to give a character idea.\"\n```\n**Why it works:** Sets up the problem (need an influencer), explains what's about to happen (create one), clear action being taken.\n\n### STEP-BY-STEP END IDENTIFICATION:\n\n**Step 1: Find a potential ending point**\n\n**Step 2: Read the EXACT last sentence**\n- Does it end with \"and then...\", \"next...\", \"so now...\"? \u2192 End is too early\n- Does it feel complete or does it feel like a cliffhanger? \u2192 If cliffhanger, end is too early\n- Is there an unresolved question or incomplete demonstration? \u2192 End is too early\n- Did we SEE the result, or just hear the explanation? \u2192 If just explanation, end is too early\n\n**Step 3: Read the 2-3 sentences AFTER your end point**\n- Are those sentences wrapping up the same idea? \u2192 Your end is too early, include them\n- Do they show the final result or give a conclusion? \u2192 Your end is too early, include them\n- Do they give an assessment like \"Perfect, that worked\"? \u2192 Include them!\n- Are they starting a completely NEW topic? \u2192 Your end is correct\n\n**Step 4: Apply the \"Satisfaction\" test**\n- Would a viewer feel satisfied or frustrated at this ending?\n- Did they get the full value, or does it feel cut off?\n- Is there a natural pause or transition after this point?\n- Would they say \"oh cool, I learned something complete\" or \"wait, what happened?\"\n\n**EXAMPLE - WRONG END:**\n```\nEnd timestamp: 0:11:45.000\nLast words: \"Now that we have our character idea set up, we need to create our character.\"\n```\n**Problem:** \"we need to create\" - you haven't created it yet! This is setting up the NEXT step, not concluding. End is way too early.\n\n**CORRECT END (moved later):**\n```\nEnd timestamp: 0:12:08.639\nLast words: \"Perfect. That will work for exactly what we were going for. I think it fits the product pretty good.\"\n```\n**Why it works:** Shows the RESULT (character was generated), gives assessment (\"perfect\", \"fits the product\"), natural conclusion, viewer feels satisfied.\n\n### COMMON MISTAKES TO AVOID:\n\n**MISTAKE 1: Starting when the action begins, not when context is set**\n- \u274c Starting at: \"You're going to click these three dots\"\n- \u2705 Starting at: \"The way you're going to import it is you're just going to click these three dots\"\n- **Why:** Second version sets up WHAT we're importing and WHY\n\n**MISTAKE 2: Ending when the explanation finishes, but before showing the result**\n- \u274c Ending at: \"And that's how you set it up\"\n- \u2705 Ending at: \"And that's how you set it up. [shows result] Perfect, it worked exactly as expected.\"\n- **Why:** Viewers want to see the OUTCOME, not just hear the explanation\n\n**MISTAKE 3: Starting at a transition word**\n- \u274c Starting at: \"So the next thing...\"\n- \u274c Starting at: \"Now we're going to...\"\n- \u274c Starting at: \"Alright, so then...\"\n- \u274c Starting at: \"Obviously...\"\n- These words often mean you're joining MID-FLOW\n\n**MISTAKE 4: Ending at a transition word or setup phrase**\n- \u274c Ending at: \"...which brings us to...\"\n- \u274c Ending at: \"...and then the next step is...\"\n- \u274c Ending at: \"...so now we need to...\"\n- \u274c Ending at: \"Now that we have this set up...\"\n- These words mean the idea is NOT complete yet\n\n**MISTAKE 5: Not including the result/outcome**\n- \u274c Ending after explaining HOW to do something, but before showing it WORKED\n- \u2705 Always include the moment where you see/confirm the result\n\n### THE \"READ IT OUT LOUD\" TEST:\n\nBefore finalizing start/end timestamps:\n1. Copy the EXACT text from start to end\n2. Read it out loud as if you're explaining to a friend who knows nothing about this\n3. Does it sound complete? Or does it sound like you cut off mid-sentence?\n4. Would your friend say \"wait, what happened next?\" or \"oh cool, I get it\"?\n5. Did you show them the RESULT, or just tell them how to do it?\n\nIf they'd say \"wait, what?\" \u2192 Your boundaries are wrong\n\n### SPECIFIC INSTRUCTION FOR THIS WORKFLOW:\n\nWhen you identify a clip:\n1. Write down your initial start/end timestamps\n2. Go back and read 5 sentences BEFORE your start\n3. Go forward and read 3 sentences AFTER your end\n4. Ask: \"Should I include those sentences for better context or conclusion?\"\n5. Adjust accordingly - err on the side of MORE context\n6. ONLY THEN finalize the clip\n\n**Default to slightly LONGER clips rather than shorter**\n- A 90-second clip that feels complete > 60-second clip that feels rushed\n- A 2-minute clip with full context > 90-second clip missing setup\n- Better to include 15 extra seconds of context than cut off too early\n\n### 3. Must Include Full SKOOL CTA Segment (CRITICAL)\n\n**UNDERSTANDING THE CTA:**\n- The Skool CTA is typically a 15-30 second SEGMENT, not a single moment\n- It includes multiple related statements about accessing resources\n- ALL clips reference THE SAME CTA start and end timestamps\n- The CTA does NOT need to be within the clip's duration\n\n**FINDING THE FULL CTA SEGMENT:**\n\nStep 1: Find where the creator FIRST mentions Skool/community/template\nStep 2: Continue reading until they COMPLETELY FINISH all CTA instructions\nStep 3: The CTA includes ALL of these elements:\n- Mentioning the community/template\n- \"Link in description\"\n- \"Head to the classroom\"\n- \"Download the file\"\n- \"Import it\"\n- Any other access instructions\n\n**CTA DURATION RULE:**\n- CTA should be 15-30 seconds minimum\n- If your CTA is under 15 seconds, you cut it off too early\n- Keep reading until the creator moves to a completely NEW topic\n\n**EXAMPLE - CORRECT CTA IDENTIFICATION:**\n\nTranscript excerpt:\n```\n0:00:52.878 - \"first thing I advise you to do is import this template for yourself\"\n0:00:58.719 - \"because I do give this away for free in my free school community\"\n0:01:03.840 - \"if you just click the link in my description, it'll bring you to my free school community\"\n0:01:10.400 - \"the AI growth lab, where you can head over to the classroom\"\n0:01:16.240 - \"and then you can download this file, the JSON file for yourself\"\n0:01:21.520 - \"The way you're going to import it is you're just going to click these three dots\"\n```\n\n**CORRECT CTA Timestamps:**\n- cta_start_timestamp: \"0:00:52.878\" (starts mentioning template)\n- cta_end_timestamp: \"0:01:21.520\" (finishes explaining how to access)\n- Duration: ~28 seconds \u2705\n\n**WRONG CTA Timestamps (too short):**\n- cta_start_timestamp: \"0:00:52.878\"\n- cta_end_timestamp: \"0:01:10.400\"\n- Duration: ~17 seconds \u274c (cuts off before complete instructions)\n\n**SPELLING RULE:**\n- In your output, ALWAYS spell it as \"Skool\" (capital S, two o's)\n- Even if transcript says \"school\" or \"School\", you output \"Skool\"\n\n**WHAT COUNTS AS SKOOL CTA:**\n- \u2705 \"free school community\" (output as \"Skool\")\n- \u2705 \"my school\" (output as \"Skool\")\n- \u2705 \"link in description\" (when referring to template)\n- \u2705 \"grab the template\"\n- \u2705 \"AI growth lab\"\n- \u2705 \"download the file\"\n- \u2705 \"import the template\"\n\n**CTA POSITIONING:**\n- The CTA timestamps can be BEFORE, DURING, or AFTER the clip content\n- Example: Clip runs 0:05:00 to 0:07:00, CTA is at 0:01:03 to 0:01:21 (totally fine!)\n- The editor will overlay the CTA during that timestamp range\n\n**ALL CLIPS USE THE SAME CTA TIMESTAMPS:**\n- There's typically ONE Skool CTA in the video\n- Every clip you identify should reference those SAME start/end timestamps\n\n### 4. Self-Contained Value\n\n**THE 5-SECOND RULE:**\nWithin 5 seconds of the clip starting, a viewer should:\n- \u2705 Know what this clip is about\n- \u2705 Understand the value being offered\n- \u2705 Be able to follow along without prior context\n\n**ACCEPTABLE:**\n- \u2705 \"Let me show you how to import this template...\" (shows template, explains)\n- \u2705 \"Here's how this AI system works...\" (demonstrates system)\n- \u2705 \"The biggest mistake people make is...\" (sets up problem/solution)\n\n**UNACCEPTABLE:**\n- \u274c \"Now for step 3...\" (what were steps 1 and 2?)\n- \u274c \"That workflow we built earlier...\" (which workflow?)\n- \u274c \"As I mentioned before...\" (viewer didn't see \"before\")\n\n### 5. High-Value Content Types (Prioritize These)\n\n**BEST CLIP TYPES:**\n- **System Overviews** - \"Here's what we built\" with demonstration\n- **Setup Tutorials** - How to configure a specific tool/feature  \n- **How-To Demonstrations** - Step-by-step walkthroughs\n- **Tool Showcases** - Showing what a tool can create\n- **Aha Moments** - Key insights or revelations\n- **Problem to Solution** - Pain point + how to solve it\n- **Quick Wins** - Fast, actionable tips\n- **Before/After** - Transformation or results\n\n**AVOID:**\n- Long setup without payoff\n- Pure technical explanations without demonstration\n- Filler content or rambling\n- Content requiring deep prior context\n\n### 6. Length Guidelines\n\n**TARGET LENGTH:**\n- **Ideal:** 60-120 seconds (1-2 minutes)\n- **Acceptable minimum:** 45 seconds\n- **Absolute minimum:** 30 seconds (only if exceptional)\n- **Maximum:** 180 seconds (3 minutes)\n\n**LENGTH PRIORITY:**\n1. Complete value delivery (most important)\n2. Natural boundaries (proper start/end)\n3. Shorter is better ONLY if quality maintained\n\n**If choosing between two options:**\n- A 90-second clip with complete value > 45-second clip that feels rushed\n- A 120-second clip with natural ending > 60-second clip cut off abruptly\n- A 2-minute clip with full setup and result > 90-second clip missing context\n\n### 7. Platform Suitability\n\nAll clips should work for:\n- **TikTok** - up to 10 minutes allowed, 60-90s ideal\n- **Instagram Reels** - up to 90 seconds ideal\n- **YouTube Shorts** - up to 3 minutes, 60-90s ideal\n\n## OUTPUT FORMAT\n\nFor each clip you identify, provide ONLY these fields:\n```json\n{\n  \"clip_number\": 1,\n  \"start_timestamp\": \"0:00:52.878\",\n  \"end_timestamp\": \"0:03:01.039\",\n  \"cta_start_timestamp\": \"0:01:03.840\",\n  \"cta_end_timestamp\": \"0:01:30.400\",\n  \"youtube_title\": \"How to Import the AI UGC Template in n8n\",\n  \"caption\": \"Turn a 10-word character idea into a photorealistic AI influencer - one button in n8n generates the image, creates a name, and saves everything to Airtable automatically (grab the free template in my Skool).\"\n}\n```\n\n### Field Requirements\n\n- **clip_number**: Sequential number (integer)\n- **start_timestamp**: Format H:MM:SS.mmm (e.g., \"0:00:52.878\", \"1:15:30.500\")\n- **end_timestamp**: Format H:MM:SS.mmm (e.g., \"0:03:01.039\", \"2:30:15.789\")\n- **cta_start_timestamp**: Format H:MM:SS.mmm - when Skool CTA STARTS (same for all clips)\n- **cta_end_timestamp**: Format H:MM:SS.mmm - when Skool CTA ENDS (same for all clips)\n- **youtube_title**: Under 100 characters, engaging and clear, benefit-driven\n- **caption**: Write in DIRECT, benefit-driven language that hooks attention immediately. Follow these rules:\n\n**CAPTION WRITING RULES (CRITICAL):**\n\n1. **Start with a HOOK** - First 5-10 words must grab attention\n   - Lead with the RESULT or BENEFIT, not the process\n   - Use specific numbers or outcomes when possible\n   - Make it feel valuable and urgent\n\n2. **Use \"you\" language** - Talk directly to the viewer\n   - NOT: \"Shows how to generate an AI influencer\"\n   - YES: \"Turn a 10-word prompt into a photorealistic AI influencer\"\n\n3. **Lead with WHAT THEY GET, not what you show**\n   - NOT: \"Demonstrates the workflow for product analysis\"\n   - YES: \"Let Perplexity write your entire TikTok script in 30 seconds\"\n\n4. **Be SPECIFIC with numbers and outcomes**\n   - NOT: \"Quick way to create influencers\"\n   - YES: \"One button generates a photorealistic influencer in under 60 seconds\"\n\n5. **NO generic verbs** - Banned words: \"shows\", \"demonstrates\", \"walks through\", \"explains\", \"goes over\"\n   - Use action verbs: \"Turn\", \"Generate\", \"Create\", \"Build\", \"Get\", \"Watch\", \"Let\"\n\n6. **Include the benefit/result IN the caption**\n   - Tell them WHAT they'll achieve, not just what the video covers\n   - \"Learn X\" is weak. \"Get X\" or \"Build X\" is strong.\n\n7. **Natural Skool mention** - Weave it in at the end\n   - \"(grab the template in my Skool)\"\n   - \"(free workflow in my Skool community)\"\n   - \"(copy the setup from my Skool)\"\n\n8. **Keep it under 200 characters** - Punchy, not rambling\n\n9. **Make it feel URGENT and VALUABLE**\n   - This should feel like something they NEED to watch\n   - NOT: \"Helpful tutorial on AI workflows\"\n   - YES: \"Stop wasting hours on UGC - this AI does it in 60 seconds\"\n\n**CAPTION EXAMPLES:**\n\n\u274c BAD: \"Shows how to create an AI influencer character using n8n and Airtable\"\n\u2705 GOOD: \"Turn a 10-word prompt into a photorealistic AI influencer - one button in n8n generates the image, creates a name, and saves everything to Airtable automatically (grab the free template in my Skool).\"\n\n\u274c BAD: \"Demonstrates generating product analysis with Perplexity AI\"\n\u2705 GOOD: \"Let Perplexity write your entire TikTok UGC script - just drop the product name and watch it generate a complete influencer briefing in 30 seconds (template in my Skool).\"\n\n\u274c BAD: \"Walks through the screenshot technique for character consistency\"\n\u2705 GOOD: \"Keep your AI character identical across 10+ video clips - screenshot the last frame, use it as the next starting frame, perfect consistency every time (full workflow in my Skool).\"\n\n\u274c BAD: \"Shows how to combine clips with FFmpeg\"\n\u2705 GOOD: \"Stitch three 8-second AI clips into one TikTok-ready video - FAI + FFmpeg does it in one button click, no editing software needed (grab the JSON template from my Skool).\"\n\nAlways spell \"Skool\" correctly (capital S, two o's). No em dashes (use hyphens instead).\n\n### CRITICAL TIMESTAMP RULES\n\n- **Format:** H:MM:SS.mmm\n- **Under 1 hour:** \"0:MM:SS.mmm\" (e.g., \"0:15:30.500\")\n- **Over 1 hour:** \"H:MM:SS.mmm\" (e.g., \"1:30:45.250\")\n- **Milliseconds:** Always 3 digits (e.g., \".878\" not \".87\")\n- **CTA timestamps:** Same for ALL clips (the one Skool segment in the video)\n\n### CRITICAL FORMATTING RULES\n\n- **NEVER use em dashes** (the long dash character)\n- Use regular hyphens (-) instead\n- Example: \"Step-by-step guide\" NOT \"Step\u2014by\u2014step guide\"\n\n## QUALITY STANDARDS\n\n**ONLY select clips that:**\n- \u2705 Are at least 45 seconds long (30 seconds absolute minimum)\n- \u2705 Start at the beginning of an idea with FULL context (pass the \"cold open\" test)\n- \u2705 End at a natural conclusion with the RESULT shown (pass the \"satisfaction\" test)\n- \u2705 Are self-contained and understandable within 5 seconds\n- \u2705 Deliver complete, valuable content from start to finish\n- \u2705 Would perform well as standalone content on TikTok\n- \u2705 Have captions that HOOK attention and lead with benefits\n\n**REJECT clips that:**\n- \u274c Are under 45 seconds (unless truly exceptional)\n- \u274c Start mid-explanation without context\n- \u274c End abruptly or feel incomplete\n- \u274c End before showing the result/outcome\n- \u274c Require prior knowledge from earlier in video\n- \u274c Are low-value or filler content\n- \u274c Feel like teasers rather than complete content\n- \u274c Have boring, generic captions\n\n## QUANTITY GUIDANCE\n\n- **NO minimum required** - quality over quantity\n- **NO maximum limit** - return all elite clips found\n- **Expected outcomes:**\n  - Tutorial/demo videos: 3-8 elite clips typical\n  - Conversational videos: 1-3 elite clips typical\n  - Technical videos: 2-5 elite clips typical\n- **If NO clips meet criteria:** Return `{\"clips\": []}`\n\n**DO NOT:**\n- Force clips that don't meet criteria\n- Reject good clips just to be selective\n- Create clips under 45 seconds unless exceptional\n- Write boring, generic captions\n\n## VERIFICATION CHECKLIST\n\nBefore finalizing each clip, verify:\n\n**START VERIFICATION:**\n1. Read the EXACT first words spoken\n2. Would a new viewer understand full context within 3 seconds?\n3. Is this truly the beginning of an idea with proper setup?\n4. Are there any pronouns (\"it\", \"this\", \"that\") without clear antecedents?\n5. Did I include enough CONTEXT before the action starts?\n\n**END VERIFICATION:**\n1. Read the EXACT last words spoken\n2. Does the thought feel complete?\n3. Is there a natural conclusion or pause?\n4. Would a viewer feel satisfied?\n5. Did we show the RESULT/OUTCOME, not just explain the process?\n\n**LENGTH VERIFICATION:**\n1. Is the clip at least 45 seconds?\n2. If under 45 seconds, is it truly exceptional?\n3. If under 30 seconds, REJECT it\n4. Could this clip benefit from 10-15 more seconds of context?\n\n**CTA VERIFICATION:**\n1. Did you identify the FULL Skool CTA segment (15-30 seconds)?\n2. Does the CTA end timestamp include all access instructions?\n3. Are the same CTA timestamps used for ALL clips?\n\n**VALUE VERIFICATION:**\n1. Does this clip deliver complete, standalone value?\n2. Would someone scrolling TikTok stop and watch the whole thing?\n3. Is this truly ELITE content worthy of posting?\n\n**CAPTION VERIFICATION:**\n1. Does the caption HOOK attention in the first 5-10 words?\n2. Does it lead with BENEFIT/RESULT, not process?\n3. Is it written in \"you\" language?\n4. Does it avoid generic verbs like \"shows\" and \"demonstrates\"?\n5. Would this caption make someone WANT to watch?\n\n## MINDSET\n\n- **Quality over quantity** - ONLY identify truly excellent clips\n- **Complete value** - Every clip must deliver full value, not teasers\n- **Natural boundaries** - Clips should feel designed to stand alone with full context\n- **Viewer-first** - Would this stop someone mid-scroll?\n- **Elite standard** - Every clip must be posting-worthy\n- **Proper length** - 45+ seconds to deliver real value\n- **Benefit-driven captions** - Hook attention, lead with results, make it feel valuable\n\n---\n\nReturn ONLY the JSON array of identified clips. No preamble, no explanation."
            }
          ]
        },
        "promptType": "define"
      },
      "typeVersion": 1.7
    },
    {
      "id": "9fffb350-1673-4801-95a8-e926cdd6a801",
      "name": "Delete a file1",
      "type": "n8n-nodes-base.googleDrive",
      "position": [
        2880,
        1392
      ],
      "parameters": {
        "fileId": {
          "__rl": true,
          "mode": "url",
          "value": "={{ $('Get a record4').item.json[\"Longform edited video\"] }}"
        },
        "options": {},
        "operation": "deleteFile"
      },
      "credentials": {
        "googleDriveOAuth2Api": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 3
    },
    {
      "id": "70bf5f14-44f8-4e4e-a493-15e54bb98d57",
      "name": "Sticky Note7",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        1056,
        960
      ],
      "parameters": {
        "color": 4,
        "width": 2160,
        "height": 656,
        "content": "## Once you mark the video as \"uploaded to youtube\" by checking the check box in airtable this system is then triggered. This system then gets the video you uploaded with title 1 (thats on private for now) and uses and apify actor to get the transcript of the video. That transcript then gets fed down 2 different paths. 1st path is our clipping path that identifies clips and outputs the timestamps of each clip and the timestamp of the main CTA while also outputting the caption of the video. Path 2 is designed with filling in the description of the video (using the transcript to fill in the timestamp part of the description)"
      },
      "typeVersion": 1
    },
    {
      "id": "0543f560-fe93-4d9b-b158-ed1b7e16514f",
      "name": "Update a video1",
      "type": "n8n-nodes-base.youTube",
      "position": [
        2736,
        1392
      ],
      "parameters": {
        "title": "={{ $('Get a record4').item.json['Title 1'] }}",
        "videoId": "={{ $('Get a video1').item.json.id }}",
        "resource": "video",
        "operation": "update",
        "categoryId": "28",
        "regionCode": "US",
        "updateFields": {
          "description": "={{ $json.output[0].content[0].text }}"
        }
      },
      "credentials": {
        "youTubeOAuth2Api": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 1
    },
    {
      "id": "563ac700-f221-4f24-81c5-a0db623c1e32",
      "name": "Get a video1",
      "type": "n8n-nodes-base.youTube",
      "position": [
        1392,
        1296
      ],
      "parameters": {
        "options": {},
        "videoId": "={{ $json['Video ID '] }}",
        "resource": "video",
        "operation": "get"
      },
      "credentials": {
        "youTubeOAuth2Api": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 1
    },
    {
      "id": "b7e5fdb8-4861-4d21-a78e-50936587c01b",
      "name": "Sticky Note3",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        1520,
        1568
      ],
      "parameters": {
        "width": 608,
        "height": 384,
        "content": "## IMPORTANT READ BELOW"
      },
      "typeVersion": 1
    }
  ],
  "active": false,
  "settings": {
    "executionOrder": "v1"
  },
  "versionId": "0d444b36-02c4-4cf0-8fc2-972bf0c33865",
  "connections": {
    "Wait10": {
      "main": [
        [
          {
            "node": "Get image1",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Switch4": {
      "main": [
        [
          {
            "node": "Download image",
            "type": "main",
            "index": 0
          }
        ],
        [
          {
            "node": "Wait10",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Webhook": {
      "main": [
        [
          {
            "node": "Get a record",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Webhook2": {
      "main": [
        [
          {
            "node": "Get a record2",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Webhook3": {
      "main": [
        [
          {
            "node": "Get a record4",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Get image1": {
      "main": [
        [
          {
            "node": "Switch4",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Wait 2 mins": {
      "main": [
        [
          {
            "node": "Get image1",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Wait 5 mins": {
      "main": [
        [
          {
            "node": "Check to see if transcript is ready",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Get a record": {
      "main": [
        [
          {
            "node": "Generate 3 titles",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Get a video1": {
      "main": [
        [
          {
            "node": "Check to see if transcript is ready",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Get a record2": {
      "main": [
        [
          {
            "node": "Thumbnail prompt optimizer",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Get a record4": {
      "main": [
        [
          {
            "node": "Get a video1",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Download image": {
      "main": [
        [
          {
            "node": "Extract from File5",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Clipping agent1": {
      "main": [
        [
          {
            "node": "Key value pair clips",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Update a video1": {
      "main": [
        [
          {
            "node": "Delete a file1",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "clean up prompt": {
      "main": [
        [
          {
            "node": "Code in JavaScript",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Create thumbnail": {
      "main": [
        [
          {
            "node": "Wait 2 mins",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Generate 3 titles": {
      "main": [
        [
          {
            "node": "Add titles to record",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Code in JavaScript": {
      "main": [
        [
          {
            "node": "Create thumbnail",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Extract from File5": {
      "main": [
        [
          {
            "node": "Add thumbnail to airtable",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    " Description agent1": {
      "main": [
        [
          {
            "node": "Update a video1",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Formatt transcript1": {
      "main": [
        [
          {
            "node": " Description agent1",
            "type": "main",
            "index": 0
          },
          {
            "node": "Clipping agent1",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Is transcript ready?": {
      "main": [
        [
          {
            "node": " Get transcript from video1",
            "type": "main",
            "index": 0
          }
        ],
        [
          {
            "node": "Wait 5 mins",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Key value pair clips": {
      "main": [
        [
          {
            "node": "cleanly formatt clips",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "cleanly formatt clips": {
      "main": [
        [
          {
            "node": "Update record",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "OpenRouter Chat Model1": {
      "ai_languageModel": [
        [
          {
            "node": "Clipping agent1",
            "type": "ai_languageModel",
            "index": 0
          }
        ]
      ]
    },
    "Thumbnail prompt optimizer": {
      "main": [
        [
          {
            "node": "clean up prompt",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    " Get transcript from video1": {
      "main": [
        [
          {
            "node": "Formatt transcript1",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Check to see if transcript is ready": {
      "main": [
        [
          {
            "node": "Is transcript ready?",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "When video is added to drive folder": {
      "main": [
        [
          {
            "node": "Create a record",
            "type": "main",
            "index": 0
          }
        ]
      ]
    }
  }
}