{
  "id": "eZdA1ppXX1RX9AqubV9gu",
  "name": "Create Video with Google Veo3 and Upload to Youtube",
  "tags": [],
  "nodes": [
    {
      "id": "3941733f-a23d-402b-ab3d-32f1f3f0d6a9",
      "name": "When clicking \u2018Test workflow\u2019",
      "type": "n8n-nodes-base.manualTrigger",
      "position": [
        0,
        1312
      ],
      "parameters": {},
      "typeVersion": 1
    },
    {
      "id": "b66a0e84-845a-4739-9ca2-f2dd97b5a8de",
      "name": "Get status",
      "type": "n8n-nodes-base.httpRequest",
      "position": [
        1072,
        1312
      ],
      "parameters": {
        "url": "=https://queue.fal.run/fal-ai/veo3/requests/{{ $('Create Video').item.json.request_id }}/status ",
        "options": {},
        "authentication": "genericCredentialType",
        "genericAuthType": "httpHeaderAuth"
      },
      "typeVersion": 4.2
    },
    {
      "id": "667a3af5-08dc-4b05-a5f9-76d24f0d64cc",
      "name": "Wait 60 sec.",
      "type": "n8n-nodes-base.wait",
      "position": [
        880,
        1312
      ],
      "parameters": {
        "amount": 60
      },
      "typeVersion": 1.1
    },
    {
      "id": "81e4cec5-85a8-476e-9813-70e7cf85129c",
      "name": "Schedule Trigger",
      "type": "n8n-nodes-base.scheduleTrigger",
      "position": [
        0,
        1168
      ],
      "parameters": {
        "rule": {
          "interval": [
            {
              "field": "minutes"
            }
          ]
        }
      },
      "typeVersion": 1.2
    },
    {
      "id": "9f6296c0-f1f5-4984-b94d-cc160ab37cbf",
      "name": "Sticky Note3",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        0,
        0
      ],
      "parameters": {
        "color": 3,
        "width": 740,
        "height": 280,
        "content": "# Generate AI Videos with Google Veo3, Save to Google Drive and Upload to YouTube\n\nThis workflow allows users to **generate AI videos** using **Google Veo3**, save them to **Google Drive**, generate optimized YouTube titles with GPT-4o, and **automatically upload them to YouTube** . The entire process is triggered from a Google Sheet that acts as the central interface for input and output.\n\nIT automates video creation, uploading, and tracking, ensuring seamless integration between Google Sheets, Google Drive, Google Veo3, and YouTube.\n\n\n\n\n"
      },
      "typeVersion": 1
    },
    {
      "id": "9f6fa130-128d-4171-9fc7-78d800008580",
      "name": "Sticky Note4",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        0,
        320
      ],
      "parameters": {
        "width": 740,
        "height": 200,
        "content": "## STEP 1 - GOOGLE SHEET\nCreate a [Google Sheet like this](https://docs.google.com/spreadsheets/d/1pcoY9N_vQp44NtSRR5eskkL5Qd0N0BGq7Jh_4m-7VEQ/edit?usp=sharing).\n\nPlease insert:\n- in the \"PROMPT\" column the accurate description of the video you want to create\n- in the \"DURATION\" column the lenght of the video you want to create\n\nLeave the \"VIDEO\" column unfilled. It will be inserted by the system once the video has been created"
      },
      "typeVersion": 1
    },
    {
      "id": "0e20e92c-55b2-4e44-a519-2ee54b1b8c69",
      "name": "Completed?",
      "type": "n8n-nodes-base.if",
      "position": [
        1248,
        1312
      ],
      "parameters": {
        "options": {},
        "conditions": {
          "options": {
            "version": 2,
            "leftValue": "",
            "caseSensitive": true,
            "typeValidation": "strict"
          },
          "combinator": "and",
          "conditions": [
            {
              "id": "383d112e-2cc6-4dd4-8985-f09ce0bd1781",
              "operator": {
                "name": "filter.operator.equals",
                "type": "string",
                "operation": "equals"
              },
              "leftValue": "={{ $json.status }}",
              "rightValue": "COMPLETED"
            }
          ]
        }
      },
      "typeVersion": 2.2
    },
    {
      "id": "d46e0303-eb0b-4d4f-9bf9-c61e1d577265",
      "name": "Update result",
      "type": "n8n-nodes-base.googleSheets",
      "position": [
        1088,
        1568
      ],
      "parameters": {
        "columns": {
          "value": {
            "VIDEO": "={{ $('Get Url Video').item.json.video.url }}",
            "row_number": "={{ $('Get new video').item.json.row_number }}"
          },
          "schema": [
            {
              "id": "PROMPT",
              "type": "string",
              "display": true,
              "removed": false,
              "required": false,
              "displayName": "PROMPT",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "DURATION",
              "type": "string",
              "display": true,
              "removed": false,
              "required": false,
              "displayName": "DURATION",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "VIDEO",
              "type": "string",
              "display": true,
              "removed": false,
              "required": false,
              "displayName": "VIDEO",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "YOUTUBE_URL",
              "type": "string",
              "display": true,
              "removed": false,
              "required": false,
              "displayName": "YOUTUBE_URL",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "row_number",
              "type": "string",
              "display": true,
              "removed": false,
              "readOnly": true,
              "required": false,
              "displayName": "row_number",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            }
          ],
          "mappingMode": "defineBelow",
          "matchingColumns": [
            "row_number"
          ],
          "attemptToConvertTypes": false,
          "convertFieldsToString": false
        },
        "options": {},
        "operation": "update",
        "sheetName": {
          "__rl": true,
          "mode": "list",
          "value": "gid=0",
          "cachedResultUrl": "https://docs.google.com/spreadsheets/d/11ebWJvwwXHgvQld9kxywKQUvIoBw6xMa0g0BuIqHDxE/edit#gid=0",
          "cachedResultName": "Foglio1"
        },
        "documentId": {
          "__rl": true,
          "mode": "list",
          "value": "1pcoY9N_vQp44NtSRR5eskkL5Qd0N0BGq7Jh_4m-7VEQ",
          "cachedResultUrl": "https://docs.google.com/spreadsheets/d/1pcoY9N_vQp44NtSRR5eskkL5Qd0N0BGq7Jh_4m-7VEQ/edit?usp=drivesdk",
          "cachedResultName": "Video Google Veo3"
        }
      },
      "typeVersion": 4.5
    },
    {
      "id": "4954542f-171a-4eb3-a038-7c941052a770",
      "name": "Set data",
      "type": "n8n-nodes-base.set",
      "position": [
        448,
        1312
      ],
      "parameters": {
        "options": {},
        "assignments": {
          "assignments": [
            {
              "id": "c713d31f-9abd-496a-ac79-e8e2efe60aa0",
              "name": "prompt",
              "type": "string",
              "value": "={{ $json.PROMPT }}\n\nDuration of the video: {{ $json.DURATION }}"
            }
          ]
        }
      },
      "typeVersion": 3.4
    },
    {
      "id": "e8db1b31-21fa-4b1e-9c98-eeb965a82af1",
      "name": "Sticky Note5",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        0,
        992
      ],
      "parameters": {
        "width": 740,
        "height": 100,
        "content": "## STEP 4 - MAIN FLOW\nStart the workflow manually or periodically by hooking the \"Schedule Trigger\" node. It is recommended to set it at 5 minute intervals."
      },
      "typeVersion": 1
    },
    {
      "id": "2d1603f0-8c89-4fe7-b058-7e22c9cf9bfb",
      "name": "Sticky Note6",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        0,
        560
      ],
      "parameters": {
        "width": 740,
        "height": 140,
        "content": "## STEP 2 - GET API KEY (YOURAPIKEY)\nCreate an account [here](https://fal.ai/) and obtain API KEY.\nIn the node \"Create Image\" set \"Header Auth\" and set:\n- Name: \"Authorization\"\n- Value: \"Key YOURAPIKEY\""
      },
      "typeVersion": 1
    },
    {
      "id": "4ec2b087-e0ae-49ab-9ba2-cd7e3d5563ef",
      "name": "Sticky Note7",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        624,
        1248
      ],
      "parameters": {
        "width": 180,
        "height": 200,
        "content": "Set API Key created in Step 2"
      },
      "typeVersion": 1
    },
    {
      "id": "a8314ad2-949f-476d-92e9-9408fcf20463",
      "name": "Get new video",
      "type": "n8n-nodes-base.googleSheets",
      "position": [
        224,
        1312
      ],
      "parameters": {
        "options": {},
        "filtersUI": {
          "values": [
            {
              "lookupColumn": "VIDEO"
            }
          ]
        },
        "sheetName": {
          "__rl": true,
          "mode": "list",
          "value": "gid=0",
          "cachedResultUrl": "https://docs.google.com/spreadsheets/d/1pcoY9N_vQp44NtSRR5eskkL5Qd0N0BGq7Jh_4m-7VEQ/edit#gid=0",
          "cachedResultName": "Foglio1"
        },
        "documentId": {
          "__rl": true,
          "mode": "list",
          "value": "1pcoY9N_vQp44NtSRR5eskkL5Qd0N0BGq7Jh_4m-7VEQ",
          "cachedResultUrl": "https://docs.google.com/spreadsheets/d/1pcoY9N_vQp44NtSRR5eskkL5Qd0N0BGq7Jh_4m-7VEQ/edit?usp=drivesdk",
          "cachedResultName": "Video Google Veo3"
        }
      },
      "typeVersion": 4.5
    },
    {
      "id": "c0aca14a-194e-4cec-aaed-084e78486a36",
      "name": "Create Video",
      "type": "n8n-nodes-base.httpRequest",
      "position": [
        672,
        1312
      ],
      "parameters": {
        "url": "https://queue.fal.run/fal-ai/veo3",
        "method": "POST",
        "options": {},
        "jsonBody": "={\n     \"prompt\": \"{{$json.prompt}}\"\n}",
        "sendBody": true,
        "sendHeaders": true,
        "specifyBody": "json",
        "authentication": "genericCredentialType",
        "genericAuthType": "httpHeaderAuth",
        "headerParameters": {
          "parameters": [
            {
              "name": "Content-Type",
              "value": "application/json"
            }
          ]
        }
      },
      "typeVersion": 4.2
    },
    {
      "id": "64990394-1d99-470a-82db-42174c59ac95",
      "name": "Get Url Video",
      "type": "n8n-nodes-base.httpRequest",
      "position": [
        0,
        1680
      ],
      "parameters": {
        "url": "=https://queue.fal.run/fal-ai/veo3/requests/{{ $json.request_id }}",
        "options": {},
        "authentication": "genericCredentialType",
        "genericAuthType": "httpHeaderAuth"
      },
      "typeVersion": 4.2
    },
    {
      "id": "8fddedcd-1d0b-43c9-8001-1b006ff02451",
      "name": "Get File Video",
      "type": "n8n-nodes-base.httpRequest",
      "position": [
        624,
        1680
      ],
      "parameters": {
        "url": "={{ $('Get Url Video').item.json.video.url }}",
        "options": {}
      },
      "typeVersion": 4.2
    },
    {
      "id": "abc5ec3b-dcf4-486b-9368-17216bfcaae7",
      "name": "Upload Video",
      "type": "n8n-nodes-base.googleDrive",
      "position": [
        912,
        1568
      ],
      "parameters": {
        "name": "={{ $now.format('yyyyLLddHHmmss') }}-{{ $('Get Url Video').item.json.video.file_name }}",
        "driveId": {
          "__rl": true,
          "mode": "list",
          "value": "My Drive"
        },
        "options": {},
        "folderId": {
          "__rl": true,
          "mode": "list",
          "value": "1aHRwLWyrqfzoVC8HoB-YMrBvQ4tLC-NZ",
          "cachedResultUrl": "https://drive.google.com/drive/folders/1aHRwLWyrqfzoVC8HoB-YMrBvQ4tLC-NZ",
          "cachedResultName": "Fal.run"
        }
      },
      "typeVersion": 3
    },
    {
      "id": "afeac8db-be1b-422b-9c2d-de150083de90",
      "name": "HTTP Request",
      "type": "n8n-nodes-base.httpRequest",
      "position": [
        912,
        1792
      ],
      "parameters": {
        "url": "https://api.upload-post.com/api/upload",
        "method": "POST",
        "options": {},
        "sendBody": true,
        "contentType": "multipart-form-data",
        "authentication": "genericCredentialType",
        "bodyParameters": {
          "parameters": [
            {
              "name": "title",
              "value": "={{ $('Generate title').item.json.message.content }}"
            },
            {
              "name": "user",
              "value": "YOUR_USERNAME"
            },
            {
              "name": "platform[]",
              "value": "youtube"
            },
            {
              "name": "video",
              "parameterType": "formBinaryData",
              "inputDataFieldName": "data"
            }
          ]
        },
        "genericAuthType": "httpHeaderAuth"
      },
      "typeVersion": 4.2
    },
    {
      "id": "0328a4d1-198b-4ae0-a27e-5e9a39b6a5c3",
      "name": "Generate title",
      "type": "@n8n/n8n-nodes-langchain.openAi",
      "position": [
        240,
        1680
      ],
      "parameters": {
        "modelId": {
          "__rl": true,
          "mode": "list",
          "value": "gpt-4o-mini",
          "cachedResultName": "GPT-4O-MINI"
        },
        "options": {},
        "messages": {
          "values": [
            {
              "content": "=Input: {{ $('Get new video').item.json.PROMPT }}"
            },
            {
              "role": "system",
              "content": "You are a YouTube SEO expert specialized in creating engaging and optimized titles.\n\nYour task is to generate an effective title for a YouTube video based on the user's video description.\n\nGUIDELINES:\n- Maximum 60 characters to avoid truncation\n- Use relevant keywords for SEO\n- Make the title catchy and clickable\n- Avoid excessive or misleading clickbait\n- Consider the target audience of the content\n- Use numbers, questions, or power words when appropriate\n- IMPORTANT: Generate the title in the same language as the input description\n\nOUTPUT FORMAT:\nProvide only the title, without additional explanations.\n\nEXAMPLE:\nInput: \"Tutorial video on how to cook perfect pasta carbonara\"\nOutput: \"PERFECT Carbonara in 10 Minutes - Chef's Secrets\""
            }
          ]
        }
      },
      "typeVersion": 1.8
    },
    {
      "id": "32ef6c52-e7c8-46bd-94dc-9a68c1b64a9f",
      "name": "Update Youtube URL",
      "type": "n8n-nodes-base.googleSheets",
      "position": [
        1088,
        1792
      ],
      "parameters": {
        "columns": {
          "value": {
            "VIDEO": "=",
            "row_number": "={{ $('Get new video').item.json.row_number }}",
            "YOUTUBE_URL": "https://youtu.be/{{ $json.results.youtube.video_id }}"
          },
          "schema": [
            {
              "id": "PROMPT",
              "type": "string",
              "display": true,
              "removed": false,
              "required": false,
              "displayName": "PROMPT",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "DURATION",
              "type": "string",
              "display": true,
              "removed": false,
              "required": false,
              "displayName": "DURATION",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "VIDEO",
              "type": "string",
              "display": true,
              "removed": false,
              "required": false,
              "displayName": "VIDEO",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "YOUTUBE_URL",
              "type": "string",
              "display": true,
              "removed": false,
              "required": false,
              "displayName": "YOUTUBE_URL",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "row_number",
              "type": "string",
              "display": true,
              "removed": false,
              "readOnly": true,
              "required": false,
              "displayName": "row_number",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            }
          ],
          "mappingMode": "defineBelow",
          "matchingColumns": [
            "row_number"
          ],
          "attemptToConvertTypes": false,
          "convertFieldsToString": false
        },
        "options": {},
        "operation": "update",
        "sheetName": {
          "__rl": true,
          "mode": "list",
          "value": "gid=0",
          "cachedResultUrl": "https://docs.google.com/spreadsheets/d/11ebWJvwwXHgvQld9kxywKQUvIoBw6xMa0g0BuIqHDxE/edit#gid=0",
          "cachedResultName": "Foglio1"
        },
        "documentId": {
          "__rl": true,
          "mode": "list",
          "value": "1pcoY9N_vQp44NtSRR5eskkL5Qd0N0BGq7Jh_4m-7VEQ",
          "cachedResultUrl": "https://docs.google.com/spreadsheets/d/1pcoY9N_vQp44NtSRR5eskkL5Qd0N0BGq7Jh_4m-7VEQ/edit?usp=drivesdk",
          "cachedResultName": "Video Google Veo3"
        }
      },
      "typeVersion": 4.5
    },
    {
      "id": "3c92c864-b015-42c8-92d1-44c6826346db",
      "name": "Sticky Note",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        880,
        1728
      ],
      "parameters": {
        "width": 180,
        "height": 200,
        "content": "Set YOUR_USERNAME in Step 3"
      },
      "typeVersion": 1
    },
    {
      "id": "caa2ae49-c800-4403-9ef0-88403b466d69",
      "name": "Sticky Note8",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        0,
        752
      ],
      "parameters": {
        "width": 740,
        "height": 200,
        "content": "## STEP 3 - Upload video on Youtube\n- Find your API key in your [Upload-Post Manage Api Keys](https://www.upload-post.com/?linkId=lp_144414&sourceId=n3witalia&tenantId=upload-post-app) 10 FREE uploads per month\n- Set the the \"Auth Header\":\n-- Name: Authorization\n-- Value: Apikey YOUR_API_KEY_HERE\n- Create profiles to manage your social media accounts. The \"Profile\" you choose will be used in the field YOUR_USRNAME (eg. test1 or test2).  "
      },
      "typeVersion": 1
    },
    {
      "id": "573eb0dc-69ee-4707-a054-1fe6eaf6449d",
      "name": "Sticky Note9",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        784,
        352
      ],
      "parameters": {
        "color": 7,
        "width": 736,
        "height": 736,
        "content": "## MY NEW YOUTUBE CHANNEL\n\ud83d\udc49 [Subscribe to my new **YouTube channel**](https://youtube.com/@n3witalia). Here I\u2019ll share videos and Shorts with practical tutorials and **FREE templates for n8n**.\n\n[![image](https://n3wstorage.b-cdn.net/n3witalia/youtube-n8n-cover.jpg)](https://youtube.com/@n3witalia)"
      },
      "typeVersion": 1
    }
  ],
  "active": false,
  "settings": {
    "availableInMCP": false,
    "executionOrder": "v1"
  },
  "versionId": "a5d586ec-76e9-4234-b6b2-77df372b3f94",
  "connections": {
    "Set data": {
      "main": [
        [
          {
            "node": "Create Video",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Completed?": {
      "main": [
        [
          {
            "node": "Get Url Video",
            "type": "main",
            "index": 0
          }
        ],
        [
          {
            "node": "Wait 60 sec.",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Get status": {
      "main": [
        [
          {
            "node": "Completed?",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Create Video": {
      "main": [
        [
          {
            "node": "Wait 60 sec.",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "HTTP Request": {
      "main": [
        [
          {
            "node": "Update Youtube URL",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Upload Video": {
      "main": [
        [
          {
            "node": "Update result",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Wait 60 sec.": {
      "main": [
        [
          {
            "node": "Get status",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Get Url Video": {
      "main": [
        [
          {
            "node": "Generate title",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Get new video": {
      "main": [
        [
          {
            "node": "Set data",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Generate title": {
      "main": [
        [
          {
            "node": "Get File Video",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Get File Video": {
      "main": [
        [
          {
            "node": "Upload Video",
            "type": "main",
            "index": 0
          },
          {
            "node": "HTTP Request",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "When clicking \u2018Test workflow\u2019": {
      "main": [
        [
          {
            "node": "Get new video",
            "type": "main",
            "index": 0
          }
        ]
      ]
    }
  }
}