# templates

name: AI-Powered Stock Market Summary Bot
author_name: kenandrewmiranda
author_username: kenandrewmiranda
categories: []
created_at: 2025-06-11T04:29:53.154Z
updated_at: 2025-06-11T04:29:53.154Z
url: https://n8n.io/workflows/4867
scraped_at: 2025-06-19 22:07:56
description:
  An automated n8n workflow that analyzes stocks using RSI and MACD, summarizes insights with OpenAI, and sends a Slack-ready market update every hour.

  This workflow:
  Runs hourly from 6:30 AM to 2:30 PM PT, Mon–Fri
  Checks if the U.S. stock market is open using Alpaca’s /clock API
  Pulls daily stock bars for a list of tickers via Alpaca’s /v2/stocks/bars
  Calculates RSI and MACD using a Python code node
  Categorizes each stock as Buy / Hold / Sell
  Uses OpenAI Assistant to summarize the results in Slack markdown
  Sends the message to a specific Slack user or channel

nodes_used:
  ["n8n-nodes-base.httpRequest","n8n-nodes-base.slack","n8n-nodes-base.code","@n8n/n8n-nodes-langchain.openAi"]

workflow_json:
  {"id":"e5XxiuYXr5atCH64","meta":{"instanceId":"564ad264d05dc77e4e5afc0ced9da90c41c9a77ab9c35729bf6f29309796798d","templateCredsSetupCompleted":true},"name":"Stock Analysis Assistant","tags":[{"id":"TkUb5sI0Ae0hwCo3","name":"Agent","createdAt":"2025-04-07T21:00:21.151Z","updatedAt":"2025-04-07T21:00:21.151Z"},{"id":"xhCApXrnlelxaW2i","name":"Stock","createdAt":"2025-06-09T04:02:42.364Z","updatedAt":"2025-06-09T04:02:42.364Z"},{"id":"eZArPFfgyfBReNUS","name":"AlpacaAPI","createdAt":"2025-06-09T04:02:47.415Z","updatedAt":"2025-06-09T04:02:47.415Z"}],"nodes":[{"id":"f9e2b1a6-4bc4-429c-a516-78fc440cb259","name":"Ticker List","type":"n8n-nodes-base.set","position":[800,0],"parameters":{"mode":"raw","options":{},"jsonOutput":"{\n  \"symbols\": \"AAPL,MSFT,NVDA,TSLA,AMZN,GOOGL,META,JPM,XOM,UNH,GME\"\n}\n"},"typeVersion":3.4},{"id":"46c712d0-8e65-4da0-bdbc-9eadf4213f2f","name":"Fetch Stock Data","type":"n8n-nodes-base.httpRequest","position":[1020,0],"parameters":{"url":"=https://data.alpaca.markets/v2/stocks/bars","options":{},"sendQuery":true,"authentication":"genericCredentialType","genericAuthType":"httpCustomAuth","queryParameters":{"parameters":[{"name":"symbols","value":"={{ $json.symbols }}"},{"name":"timeframe","value":"1Day"},{"name":"limit","value":"1000"},{"name":"feed","value":"iex"},{"name":"=start","value":"={{ new Date(Date.now() - 100 * 24 * 60 * 60 * 1000).toISOString().split('T')[0] }}"},{"name":"end","value":"={{ new Date().toISOString().split('T')[0] }}"}]}},"credentials":{"httpCustomAuth":{"id":"REDACTED_ID","name":"REDACTED_NAME"}},"typeVersion":4.2},{"id":"e8d96c0c-e927-4676-a02f-7729c0126165","name":"Interpret Data","type":"n8n-nodes-base.code","position":[1240,0],"parameters":{"language":"python","pythonCode":"import pandas as pd\nimport numpy as np\nimport json\n\nbars_by_symbol = items[0]['json']['bars']\nstocks = []\n\nfor symbol, bars in bars_by_symbol.items():\n    closes = [bar['c'] for bar in bars if 'c' in bar]\n    if len(closes) < 30:\n        continue\n\n    df = pd.DataFrame({'close': closes})\n\n    # RSI(14)\n    delta = df['close'].diff()\n    gain = delta.clip(lower=0)\n    loss = -delta.clip(upper=0)\n    avg_gain = gain.rolling(14).mean()\n    avg_loss = loss.rolling(14).mean()\n    rs = avg_gain / avg_loss\n    df['rsi'] = 100 - (100 / (1 + rs))\n\n    # MACD (12,26,9)\n    ema12 = df['close'].ewm(span=12, adjust=False).mean()\n    ema26 = df['close'].ewm(span=26, adjust=False).mean()\n    df['macd'] = ema12 - ema26\n    df['signal'] = df['macd'].ewm(span=9, adjust=False).mean()\n\n    latest = df.iloc[-1]\n    rsi = latest['rsi']\n    macd = latest['macd']\n    signal = latest['signal']\n\n    status = \"Hold\"\n    if rsi < 30 and macd > signal:\n        status = \"Buy\"\n    elif rsi > 70 and macd < signal:\n        status = \"Sell\"\n\n    stocks.append({\n        \"ticker\": symbol,\n        \"rsi\": round(float(rsi), 2),\n        \"macd\": round(float(macd), 2),\n        \"signal\": round(float(signal), 2),\n        \"status\": status\n    })\n\nreturn [{\n    \"json\": {\n        \"summary\": json.dumps({\n            \"stocks\": stocks\n        }, separators=(',', ':')),\n      \"stocks\": stocks\n    }\n}]\n"},"typeVersion":2},{"id":"5ace21ee-80b0-4d79-be68-ded17b53b5a2","name":"Stock Analysis Assistant","type":"@n8n/n8n-nodes-langchain.openAi","position":[1440,0],"parameters":{"text":"=Here is the technical indicator data as JSON:\n\n{{ $json.summary }}\n\nPulled as of {{ $now }}","prompt":"define","options":{},"resource":"assistant","assistantId":{"mode":"list","value":"REDACTED_ASSISTANT_ID","cachedResultName":"REDACTED_ASSISTANT"}},"credentials":{"openAiApi":{"id":"REDACTED_ID","name":"REDACTED_NAME"}},"typeVersion":1.8},{"id":"97f8d2af-02a9-4f93-8bf7-ee083b13dccf","name":"Send Summary to User(s)","type":"n8n-nodes-base.slack","position":[1816,0],"webhookId":"57e1eff1-81c1-42f1-b8ee-fb3e40551362","parameters":{"text":"={{ $json.output }}","user":{"mode":"list","value":"REDACTED_USER_ID","cachedResultName":"REDACTED_USER"},"select":"user","otherOptions":{}},"credentials":{"slackApi":{"id":"REDACTED_ID","name":"REDACTED_NAME"}},"typeVersion":2.3},{"id":"21b091f5-ce81-4d98-8978-f7193734a72c","name":"Schedule Trigger","type":"n8n-nodes-base.scheduleTrigger","position":[120,0],"parameters":{"rule":{"interval":[{"field":"cronExpression","expression":"0 30 6-14 * * 1-5"}]}},"typeVersion":1.2},{"id":"94804d45-b868-4501-a53c-0a1063768f14","name":"Check if Market is open","type":"n8n-nodes-base.if","position":[560,0],"parameters":{"options":{},"conditions":{"options":{"version":2,"leftValue":"","caseSensitive":true,"typeValidation":"strict"},"combinator":"and","conditions":[{"id":"acca2d72-d9db-436d-aee8-81a3a359fe85","operator":{"type":"boolean","operation":"true","singleValue":true},"leftValue":"={{ $json.is_open }}","rightValue":""}]}},"typeVersion":2.2},{"id":"8366acca-42ff-4106-8b37-316727ac8963","name":"Market is Closed","type":"n8n-nodes-base.noOp","position":[800,200],"parameters":{},"typeVersion":1},{"id":"ee50cf08-efe2-4886-8527-23c069495afd","name":"Check Market Status","type":"n8n-nodes-base.httpRequest","position":[360,0],"parameters":{"url":"https://paper-api.alpaca.markets/v2/clock","options":{},"authentication":"genericCredentialType","genericAuthType":"httpCustomAuth"},"credentials":{"httpCustomAuth":{"id":"REDACTED_ID","name":"REDACTED_NAME"}},"typeVersion":4.2},{"id":"97de7640-5be5-4821-9cea-a8d481590256","name":"Sticky Note","type":"n8n-nodes-base.stickyNote","position":[-640,-360],"parameters":{"width":660,"content":"# 🧠 Stock Analysis Assistant\n\nThis workflow analyzes selected S&P 500 stocks using RSI and MACD indicators, summarizes the insights into plain English, and posts an update to Slack every hour during U.S. market hours (Mon–Fri)."},"typeVersion":1},{"id":"4c40864c-ad6d-420f-88b8-a497d7c71a5d","name":"Sticky Note1","type":"n8n-nodes-base.stickyNote","position":[40,-360],"parameters":{"color":7,"height":700,"content":"## 📅 Schedule Trigger\n\n**Node:** `Schedule Trigger`  \nRuns every hour between 6:30 AM and 2:30 PM (PST), Monday to Friday.  \n**Cron Expression:** `0 30 6-14 * * 1-5`\n\n⏰ Triggers analysis only during U.S. stock market hours."},"typeVersion":1},{"id":"28ee034a-cb6a-4a54-8ce1-fef5e439e2de","name":"Sticky Note2","type":"n8n-nodes-base.stickyNote","position":[280,-360],"parameters":{"color":7,"width":460,"height":700,"content":"## 🏛️ Market Status Check\n\n**Node:** `Check Market Status`  \nEndpoint: `https://paper-api.alpaca.markets/v2/clock`\n\nChecks if the market is open using Alpaca’s `/clock` endpoint.\n\n**Node:** `Check if Market is open`  \n- ✅ If true → continue  \n- ❌ If false → exit gracefully via the “Market is Closed” NoOp node"},"typeVersion":1},{"id":"ab88e6c4-bafb-47d6-9292-b54850f1d984","name":"Sticky Note3","type":"n8n-nodes-base.stickyNote","position":[740,-360],"parameters":{"color":4,"width":220,"height":540,"content":"## 📈 Ticker Setup\n\n**Node:** `Ticker List`  \nSets the stock symbols to be analyzed.\n\n📌 You can update this list to monitor different stocks."},"typeVersion":1},{"id":"01892c69-4c22-4c78-a1db-1add2d06993c","name":"Sticky Note4","type":"n8n-nodes-base.stickyNote","position":[960,-360],"parameters":{"color":4,"width":220,"height":540,"content":"## 🔗 Fetch Stock Data\n\n**Node:** `Fetch Stock Data`  \nCalls Alpaca’s `/v2/stocks/bars` endpoint with:\n- `symbols`: from `Ticker List`\n- `timeframe`: `1Day`\n- `limit`: `1000`\n- `feed`: `iex` (avoid SIP permission error)\n- `start`: 100 days ago\n- `end`: today"},"typeVersion":1},{"id":"a1b98ff6-b033-4f0c-90c6-b6bf2ea0e461","name":"Sticky Note5","type":"n8n-nodes-base.stickyNote","position":[1180,-360],"parameters":{"color":4,"width":220,"height":540,"content":"## 🧮 Interpret Data\n\n**Node:** `Interpret Data`  \nPython code calculates:\n- RSI(14)\n- MACD(12,26,9)\n- Decision status: `\"Buy\"`, `\"Hold\"`, or `\"Sell\"`\n\nOutputs:\n- `stocks`: a list of indicator values and status\n- `summary`: JSON string version for GPT"},"typeVersion":1},{"id":"0ac7e6ad-405e-46b6-81b9-3367c7793136","name":"Sticky Note6","type":"n8n-nodes-base.stickyNote","position":[1400,-360],"parameters":{"color":4,"width":360,"height":540,"content":"## 🤖 AI Assistant Summary\n\n**Node:** `Stock Analysis Assistant`  \nUses a custom OpenAI assistant to:\n- Group stocks into categories\n- Provide commentary in plain English\n- Teach users simple market behaviors\n\nPrompt includes:\n- Stock JSON (`summary`)\n- Timestamp (`$now`)\n\n📌 Uses Slack-friendly markdown output."},"typeVersion":1},{"id":"10b73555-9619-4327-beac-d36a5a88f844","name":"Sticky Note7","type":"n8n-nodes-base.stickyNote","position":[740,180],"parameters":{"color":3,"width":220,"content":""},"typeVersion":1},{"id":"91c98665-4226-4579-a9df-2dd4ad137638","name":"End of Flow","type":"n8n-nodes-base.noOp","position":[2040,0],"parameters":{},"typeVersion":1},{"id":"f11bdac9-2fbe-4ea5-a470-d89d26aa01ba","name":"Sticky Note8","type":"n8n-nodes-base.stickyNote","position":[1760,-360],"parameters":{"color":4,"width":220,"height":540,"content":"## 💬 Post to Slack\n\n**Node:** `Send Summary to User(s)`  \nSends the GPT-generated summary to Slack using:\n```js\n{{ $json.output }}\n```\n⚙️ Configured with the appropriate Slack user or channel."},"typeVersion":1},{"id":"8221dafd-302c-4bbe-9cea-25bdbe980acb","name":"Sticky Note9","type":"n8n-nodes-base.stickyNote","position":[1980,-360],"parameters":{"color":4,"width":220,"height":540,"content":""},"typeVersion":1},{"id":"d492d1bc-99ba-43da-bf15-1cbe11badb13","name":"Sticky Note10","type":"n8n-nodes-base.stickyNote","position":[-640,-180],"parameters":{"color":5,"width":660,"height":940,"content":"## 🤖 AI Assistant Prompt\n\nYou are a financial assistant writing a quick, readable market update for a general audience. Your job is to help people understand how well-known stocks are behaving — even if they aren’t professional traders.\n\nYou’ll be given:\n\nA list of stocks with technical indicators (e.g., momentum data)\nA timestamp (in RFC 3339 or ISO format) for when the data was pulled.\n📌 Your task:\nGroup the stocks into three categories:\n🟢 Buy Watchlist – Stocks showing signs of recovery or upward momentum\n⚪ Neutral Hold – Stocks with steady or unclear direction\n🔴 Caution / Sell – Stocks that appear overbought or may pull back\nFor each stock:\nWrite a short, plain-language insight about what’s happening\nUse familiar terms like “gaining steam,” “cooling off,” or “showing hesitation”\nAvoid technical jargon like RSI or MACD unless context makes it helpful\nAdd a helpful tip or comment for each stock (e.g.,\n“This pattern often signals hesitation” or\n“This dip might attract bargain hunters”)\nFinish with a summary line using the timestamp like this:\nSummary as of October 2, 2025 – Most stocks were stable with one or two worth watching.\n📦 Respond in Slack Markdown Only:\nExample Format:\n\n*📊 Market Summary (as of October 2, 2025)*\n\n🟢 *Buy Watchlist*  \n• TSLA – Recovering after a dip; gaining steam. This type of rebound often attracts early buyers.\n\n⚪ *Neutral Hold*  \n• AAPL – Holding steady. This often means the market is waiting on new developments.  \n• GOOGL – Moving sideways. A sign of consolidation before potential breakout.  \n• MSFT – Little movement. Could be digesting prior gains.  \n• NVDA – Slight back-and-forth. May indicate indecision in the market.\n\n🔴 *Caution / Sell*  \n• None at this time.\n\n_Summary as of October 2, 2025: Most stocks appear steady. TSLA could be one to watch if momentum holds._\n🚫 Do NOT:\nReturn raw JSON\nUse code blocks unless formatting Slack markdown (no YAML or tags)\nUse technical finance language unless simplified"},"typeVersion":1}],"active":true,"pinData":{},"settings":{"timezone":"America/Los_Angeles","callerPolicy":"workflowsFromSameOwner","executionOrder":"v1"},"versionId":"0523c0a7-8874-4eff-bcd7-cf3d9ab7c362","connections":{"Ticker List":{"main":[[{"node":"Fetch Stock Data","type":"main","index":0}]]},"Interpret Data":{"main":[[{"node":"Stock Analysis Assistant","type":"main","index":0}]]},"Fetch Stock Data":{"main":[[{"node":"Interpret Data","type":"main","index":0}]]},"Schedule Trigger":{"main":[[{"node":"Check Market Status","type":"main","index":0}]]},"Check Market Status":{"main":[[{"node":"Check if Market is open","type":"main","index":0}]]},"Check if Market is open":{"main":[[{"node":"Ticker List","type":"main","index":0}],[{"node":"Market is Closed","type":"main","index":0}]]},"Send Summary to User(s)":{"main":[[{"node":"End of Flow","type":"main","index":0}]]},"Stock Analysis Assistant":{"main":[[{"node":"Send Summary to User(s)","type":"main","index":0}]]}}}


name: Extract Invoice Data from Google Drive to Sheets with Mistral OCR and Gemini
author_name: Ysqander
author_username: ysqander
categories: []
created_at: 2025-06-11T06:15:58.579Z
updated_at: 2025-06-11T06:15:58.579Z
url: https://n8n.io/workflows/4868
scraped_at: 2025-06-19 22:07:56
description:
  Extract data from any PDF or image invoice dropped in Google Drive directly into Google Sheets – powered by AI OCR. Free, fully modifiable n8n workflow. Optional add-ons for pro features.

  🚀 What this template does

  Stop typing invoice data by hand. Drop a PDF or phone-snapshot into your Invoices Inbox folder in Google Drive and this n8n workflow will:





  Auto-OCR the document with the Mistral OCR API



  Match any fields you list in Row 1 of your Google Sheet (totally schema-agnostic)



  Append a clean, structured row – every time

  Works with both PDFs and images, in any language supported by Mistral.

  Template JSON included, ready to import into self-hosted or n8n Cloud

  👀 Who’s this for?





  Freelancers & agencies processing client invoices



  Small finance teams on Google Workspace



  Anyone self-hosting n8n who wants an AI OCR flow without glue-code

  No coding skills required – but flow tweaking is possible for power users.

  🛠 Upcoming PRO Add-Ons
  I am also working on PRO add-ons for this template: 

  Add-On #1 – Error Handling & Alerts (ships Jul 2025)• Flags missing fields, branches to Email/Slack notification; prevents silent failures



  Add-On #2 – Auto-Currency Converter (ships Jul 2025)• Detects invoice currency symbol/code → converts Total into your base currency via a free FX API



  Add-On #3 – VAT / GST Breakdown (ships Jul 2025)• Extracts VAT number, net, tax rate, tax amount, gross – ready for EU/UK/AU filings

  To pre-order these please see: https://ysqander.gumroad.com/l/N8N-AI-Workflow-Invoice-Data-Extraction-LITE

nodes_used:
  ["n8n-nodes-base.googleSheets","n8n-nodes-base.httpRequest","n8n-nodes-base.googleDrive","n8n-nodes-base.code","@n8n/n8n-nodes-langchain.agent","@n8n/n8n-nodes-langchain.lmChatGoogleGemini"]

workflow_json:
  {"id":"x4DcB7sVAeVmIrMD","meta":{"instanceId":"910d3d65eae3484a05204e7f2f6d897587e3de5b30ca7b532a3b4f6f96a2c11c","templateCredsSetupCompleted":true},"name":"Invoice-Parser-Lite","tags":[],"nodes":[{"id":"a8716edb-e05a-43a5-a38f-384fa05e93cf","name":"When clicking ‘Test workflow’","type":"n8n-nodes-base.manualTrigger","position":[320,-80],"parameters":{},"typeVersion":1},{"id":"bce283e2-29fd-47a1-9cfe-c4cf50f4e35d","name":"On new file in Google Drive","type":"n8n-nodes-base.googleDriveTrigger","position":[320,260],"parameters":{"event":"fileCreated","options":{"fileType":"all"},"pollTimes":{"item":[{}]},"triggerOn":"specificFolder","folderToWatch":{"__rl":true,"mode":"list","value":"15Xpvr0Q4cBwYv1e_jNI8JO4LKAQmgYC2","cachedResultUrl":"https://drive.google.com/drive/folders/15Xpvr0Q4cBwYv1e_jNI8JO4LKAQmgYC2","cachedResultName":"Invoices_Inbox"}},"credentials":{"googleDriveOAuth2Api":{"id":"2wyYFvVBTOBlFJRv","name":"Google Drive account"}},"typeVersion":1},{"id":"160e8e02-8f70-4c8f-a3c4-a94cf2325b82","name":"Load files from Google Drive folder","type":"n8n-nodes-base.googleDrive","position":[880,260],"parameters":{"filter":{"folderId":{"__rl":true,"mode":"list","value":"15Xpvr0Q4cBwYv1e_jNI8JO4LKAQmgYC2","cachedResultUrl":"https://drive.google.com/drive/folders/15Xpvr0Q4cBwYv1e_jNI8JO4LKAQmgYC2","cachedResultName":"Invoices_Inbox"}},"options":{},"resource":"fileFolder","returnAll":true},"credentials":{"googleDriveOAuth2Api":{"id":"2wyYFvVBTOBlFJRv","name":"Google Drive account"}},"executeOnce":true,"typeVersion":3},{"id":"ad1c63fb-4aae-48a2-8329-20afd04e069d","name":"Filter processed files","type":"n8n-nodes-base.merge","position":[1360,140],"parameters":{"mode":"combine","options":{},"joinMode":"keepNonMatches","outputDataFrom":"input2","fieldsToMatchString":"id"},"typeVersion":3},{"id":"1e689ab2-32d1-453f-b30b-61eb8ac5e1db","name":"Download file for OCR","type":"n8n-nodes-base.googleDrive","position":[1560,140],"parameters":{"fileId":{"__rl":true,"mode":"id","value":"={{ $json.id }}"},"options":{},"operation":"download"},"credentials":{"googleDriveOAuth2Api":{"id":"2wyYFvVBTOBlFJRv","name":"Google Drive account"}},"typeVersion":3},{"id":"37e21a39-2383-4934-9b41-81b76c484974","name":"Get already processed rows from Sheets","type":"n8n-nodes-base.googleSheets","position":[1160,-80],"parameters":{"options":{},"sheetName":{"__rl":true,"mode":"list","value":"gid=0","cachedResultUrl":"https://docs.google.com/spreadsheets/d/1WNXkB6SpJyGtPVcHmj1oaaDFikyACCuq6RY5rEPH4OQ/edit#gid=0","cachedResultName":"Sheet1"},"documentId":{"__rl":true,"mode":"list","value":"1WNXkB6SpJyGtPVcHmj1oaaDFikyACCuq6RY5rEPH4OQ","cachedResultUrl":"https://docs.google.com/spreadsheets/d/1WNXkB6SpJyGtPVcHmj1oaaDFikyACCuq6RY5rEPH4OQ/edit?usp=drivesdk","cachedResultName":"n8n_ocr_invoices"}},"credentials":{"googleSheetsOAuth2Api":{"id":"OZHtTUbddU4IboX9","name":"Google Sheets account"}},"executeOnce":true,"typeVersion":4.3,"alwaysOutputData":true},{"id":"140113e8-31da-45f2-901a-cb83bd183478","name":"Save data to Google Sheets","type":"n8n-nodes-base.googleSheets","position":[3640,60],"parameters":{"columns":{"value":{},"schema":[{"id":"Id","type":"string","display":true,"required":false,"displayName":"Id","defaultMatch":false,"canBeUsedToMatch":true},{"id":"Invoice No","type":"string","display":true,"required":false,"displayName":"Invoice No","defaultMatch":false,"canBeUsedToMatch":true},{"id":"Invoice date","type":"string","display":true,"required":false,"displayName":"Invoice date","defaultMatch":false,"canBeUsedToMatch":true},{"id":"Invoice Period","type":"string","display":true,"required":false,"displayName":"Invoice Period","defaultMatch":false,"canBeUsedToMatch":true},{"id":"Gross Amount incl. VAT ","type":"string","display":true,"required":false,"displayName":"Gross Amount incl. VAT ","defaultMatch":false,"canBeUsedToMatch":true},{"id":"IBAN","type":"string","display":true,"required":false,"displayName":"IBAN","defaultMatch":false,"canBeUsedToMatch":true}],"mappingMode":"autoMapInputData","matchingColumns":[],"attemptToConvertTypes":false,"convertFieldsToString":false},"options":{},"operation":"append","sheetName":{"__rl":true,"mode":"list","value":"gid=0","cachedResultUrl":"https://docs.google.com/spreadsheets/d/1WNXkB6SpJyGtPVcHmj1oaaDFikyACCuq6RY5rEPH4OQ/edit#gid=0","cachedResultName":"Sheet1"},"documentId":{"__rl":true,"mode":"list","value":"1WNXkB6SpJyGtPVcHmj1oaaDFikyACCuq6RY5rEPH4OQ","cachedResultUrl":"https://docs.google.com/spreadsheets/d/1WNXkB6SpJyGtPVcHmj1oaaDFikyACCuq6RY5rEPH4OQ/edit?usp=drivesdk","cachedResultName":"n8n_ocr_invoices"}},"credentials":{"googleSheetsOAuth2Api":{"id":"OZHtTUbddU4IboX9","name":"Google Sheets account"}},"typeVersion":4.6},{"id":"fa83c3b3-b58d-40c8-b94e-93925347b2de","name":"Mistral Upload","type":"n8n-nodes-base.httpRequest","position":[2060,120],"parameters":{"url":"https://api.mistral.ai/v1/files","method":"POST","options":{},"sendBody":true,"contentType":"multipart-form-data","authentication":"predefinedCredentialType","bodyParameters":{"parameters":[{"name":"purpose","value":"ocr"},{"name":"file","parameterType":"formBinaryData","inputDataFieldName":"data"}]},"nodeCredentialType":"mistralCloudApi"},"credentials":{"mistralCloudApi":{"id":"1SLwPjP2Z9Gh0p3B","name":"Mistral Cloud account"}},"typeVersion":4.2},{"id":"f0aef4a8-ca9a-48a1-b94e-4879adf679c1","name":"Mistral Signed URL","type":"n8n-nodes-base.httpRequest","position":[2260,120],"parameters":{"url":"=https://api.mistral.ai/v1/files/{{ $json.id }}/url","options":{},"sendQuery":true,"sendHeaders":true,"authentication":"predefinedCredentialType","queryParameters":{"parameters":[{"name":"expiry","value":"24"}]},"headerParameters":{"parameters":[{"name":"Accept","value":"application/json"}]},"nodeCredentialType":"mistralCloudApi"},"credentials":{"mistralCloudApi":{"id":"1SLwPjP2Z9Gh0p3B","name":"Mistral Cloud account"}},"typeVersion":4.2},{"id":"165556d9-c325-4eb9-b1b2-4983f3fda5a4","name":"Mistral DOC OCR","type":"n8n-nodes-base.httpRequest","position":[2460,100],"parameters":{"url":"https://api.mistral.ai/v1/ocr","method":"POST","options":{},"jsonBody":"={\n  \"model\": \"mistral-ocr-latest\",\n  \"document\": {\n    \"type\": \"document_url\",\n    \"document_url\": \"{{ $json.url }}\"\n  },\n  \"include_image_base64\": true\n}","sendBody":true,"specifyBody":"json","authentication":"predefinedCredentialType","nodeCredentialType":"mistralCloudApi"},"credentials":{"mistralCloudApi":{"id":"1SLwPjP2Z9Gh0p3B","name":"Mistral Cloud account"}},"typeVersion":4.2},{"id":"849bbcd3-122d-4375-b6ae-920e6c5d2b9e","name":"extract schema","type":"n8n-nodes-base.code","position":[920,-80],"parameters":{"jsCode":"// Grab the keys from the first row\nconst schema = Object.keys($input.all()[0].json);\n\n// Return a single item whose JSON is just that schema array\nreturn [\n  { json: { schema } }\n];"},"typeVersion":2},{"id":"ff80d6f4-6758-482c-b5eb-3fa927525948","name":"Join OCR Pages and remove id field","type":"n8n-nodes-base.code","position":[2840,100],"parameters":{"jsCode":"// Node name: Join Pages\n// 1. Grab all incoming documents\nconst docs = $input.all();\n\n// 2. Pull in your schema once and filter it\nlet schema = $('extract schema').first().json.schema;\nconst toRemove = ['Id', 'row_number'];\nschema = schema.filter(f => !toRemove.includes(f));\n\n// 3. Build one output per document\nconst results = docs.map(doc => {\n  // join only that doc’s pages\n  const fullText = doc.json.pages\n    .map(p => p.markdown)\n    .join('\\n\\n');\n\n  return {\n    json: {\n      ocr_text: fullText,\n      schema,\n    },\n  };\n});\n\nreturn results;"},"typeVersion":2},{"id":"24f5b810-03cc-49d7-bc64-7748f6be9686","name":"Add google drive Id back","type":"n8n-nodes-base.code","position":[3380,60],"parameters":{"jsCode":"// 1. Get the array of processed files (with id & name)\nconst processed = $('Filter processed files').all();\n\n// 2. Take each LLM output in turn, parse it, inject the matching ID, and return\nreturn $input.all().map((item, index) => {\n  // parse the JSON string your chat node returned\n  const data = JSON.parse(item.json.output);\n\n  // look up the corresponding Drive file ID by array index\n  data.Id   = processed[index]?.json.id ?? null;\n\n\n  // emit for your Sheets node\n  return { json: data };\n});"},"typeVersion":2},{"id":"407bd6d8-8b90-47bd-84f8-c15f32ea1cf4","name":"Google Gemini Chat Model","type":"@n8n/n8n-nodes-langchain.lmChatGoogleGemini","position":[3060,280],"parameters":{"options":{},"modelName":"models/gemini-2.5-flash-preview-05-20"},"credentials":{"googlePalmApi":{"id":"F7phLhVf9DkmhJc7","name":"Google Gemini(PaLM) Api account"}},"typeVersion":1},{"id":"c7ceb651-3f48-49f9-a2f8-f933a63311a8","name":"Mistral Upload1","type":"n8n-nodes-base.httpRequest","position":[2080,340],"parameters":{"url":"https://api.mistral.ai/v1/files","method":"POST","options":{},"sendBody":true,"contentType":"multipart-form-data","authentication":"predefinedCredentialType","bodyParameters":{"parameters":[{"name":"purpose","value":"ocr"},{"name":"file","parameterType":"formBinaryData","inputDataFieldName":"data"}]},"nodeCredentialType":"mistralCloudApi"},"credentials":{"mistralCloudApi":{"id":"1SLwPjP2Z9Gh0p3B","name":"Mistral Cloud account"}},"typeVersion":4.2},{"id":"27c0f663-3833-4f67-8f2d-5efcd1a9b8a2","name":"Mistral Signed URL1","type":"n8n-nodes-base.httpRequest","position":[2260,340],"parameters":{"url":"=https://api.mistral.ai/v1/files/{{ $json.id }}/url","options":{},"sendQuery":true,"sendHeaders":true,"authentication":"predefinedCredentialType","queryParameters":{"parameters":[{"name":"expiry","value":"24"}]},"headerParameters":{"parameters":[{"name":"Accept","value":"application/json"}]},"nodeCredentialType":"mistralCloudApi"},"credentials":{"mistralCloudApi":{"id":"1SLwPjP2Z9Gh0p3B","name":"Mistral Cloud account"}},"typeVersion":4.2},{"id":"027a9c9c-4ebd-497a-8e61-a3ee63b99666","name":"Mistral IMAGE OCR","type":"n8n-nodes-base.httpRequest","position":[2460,320],"parameters":{"url":"https://api.mistral.ai/v1/ocr","method":"POST","options":{},"jsonBody":"={\n  \"model\": \"mistral-ocr-latest\",\n  \"document\": {\n    \"type\": \"image_url\",\n    \"image_url\": \"{{ $json.url }}\"\n  }\n}","sendBody":true,"specifyBody":"json","authentication":"predefinedCredentialType","nodeCredentialType":"mistralCloudApi"},"credentials":{"mistralCloudApi":{"id":"1SLwPjP2Z9Gh0p3B","name":"Mistral Cloud account"}},"typeVersion":4.2},{"id":"be5e7900-7ae8-4c56-83d5-d0984767abff","name":"If","type":"n8n-nodes-base.if","position":[1780,140],"parameters":{"options":{},"conditions":{"options":{"version":2,"leftValue":"","caseSensitive":true,"typeValidation":"strict"},"combinator":"and","conditions":[{"id":"54e4c552-cdf0-4707-8723-65bcf41d8a96","operator":{"type":"string","operation":"startsWith"},"leftValue":"={{$binary.data.mimeType}}","rightValue":"image/"}]}},"typeVersion":2.2},{"id":"f33ce8fa-1412-4889-b586-130119d4bc4b","name":"Sticky Note","type":"n8n-nodes-base.stickyNote","position":[820,460],"parameters":{"color":4,"width":220,"height":80,"content":"### Modify Folder source"},"typeVersion":1},{"id":"fdc0a222-8962-4d4a-a50c-abd347794430","name":"Sticky Note1","type":"n8n-nodes-base.stickyNote","position":[3560,260],"parameters":{"width":320,"height":100,"content":"### File Ids\nYou can view the files using Id from the first column. replace the <Id> below\nhttps://drive.google.com/file/d/<Id>/view"},"typeVersion":1},{"id":"f9e36727-f376-4bb3-b32f-bd55eab82e88","name":"Field Extractor","type":"@n8n/n8n-nodes-langchain.agent","position":[3020,60],"parameters":{"text":"=Extract the following fields from the invoice text:\n\n{{ JSON.stringify($json.schema) }}\n\nImportant: Double-check that all line items are extracted without omission.\n\n- You must respond ONLY with valid raw rendered JSON.\n- Do NOT include the word \"json\".\n- Do NOT include the word \"```json\".\n- Do NOT use triple backticks or markdown formatting.\n- Do NOT wrap the response in any key like \"output\".\n- Do NOT write anything starting at output directly start with valid root-level JSON.\n- Only respond with a valid, root-level JSON object.\n\nText to extract data from: {{ $json.ocr_text }}","options":{"systemMessage":"=You are a document parsing assistant designed to extract structured data from invoice PDFs for automated uploading and validation in a financial system."},"promptType":"define"},"typeVersion":1.8},{"id":"73cc08ed-caa1-405b-8b15-11f2a375fcd9","name":"Sticky Note2","type":"n8n-nodes-base.stickyNote","position":[260,480],"parameters":{"color":4,"width":220,"height":80,"content":"### Set interval for checking drive folder and pull new files"},"typeVersion":1},{"id":"d7df816d-3aee-4bd8-9f12-76c23d2108dd","name":"Sticky Note3","type":"n8n-nodes-base.stickyNote","position":[580,-380],"parameters":{"color":4,"width":300,"height":140,"content":"### Select Sheet\n  \nAdd column headers in the sheet to which you save data on row one to specify which fields you are interested in extracting. "},"typeVersion":1},{"id":"29782ff3-dbdf-4132-90d2-36a9fafa5815","name":"Sticky Note4","type":"n8n-nodes-base.stickyNote","position":[1120,-180],"parameters":{"color":4,"width":200,"height":80,"content":"### Select sheet"},"typeVersion":1},{"id":"3d60e92c-2966-4ed3-900a-582cca0f0b8c","name":"Sticky Note5","type":"n8n-nodes-base.stickyNote","position":[3600,-40],"parameters":{"color":4,"width":200,"height":80,"content":"### Select sheet to save data (same as at the start)"},"typeVersion":1},{"id":"3cabcbee-b685-4d9a-9f11-9a3328d70fcd","name":"Get Fields Schema","type":"n8n-nodes-base.googleSheets","position":[680,-80],"parameters":{"options":{"returnFirstMatch":false,"dataLocationOnSheet":{"values":{"firstDataRow":1,"rangeDefinition":"specifyRange"}}},"sheetName":{"__rl":true,"mode":"list","value":"gid=0","cachedResultUrl":"https://docs.google.com/spreadsheets/d/1WNXkB6SpJyGtPVcHmj1oaaDFikyACCuq6RY5rEPH4OQ/edit#gid=0","cachedResultName":"Sheet1"},"documentId":{"__rl":true,"mode":"list","value":"1WNXkB6SpJyGtPVcHmj1oaaDFikyACCuq6RY5rEPH4OQ","cachedResultUrl":"https://docs.google.com/spreadsheets/d/1WNXkB6SpJyGtPVcHmj1oaaDFikyACCuq6RY5rEPH4OQ/edit?usp=drivesdk","cachedResultName":"n8n_ocr_invoices"}},"credentials":{"googleSheetsOAuth2Api":{"id":"OZHtTUbddU4IboX9","name":"Google Sheets account"}},"typeVersion":4.6},{"id":"2beee512-688a-4c4a-a4eb-b4a20956ead2","name":"Sticky Note6","type":"n8n-nodes-base.stickyNote","position":[580,-220],"parameters":{"color":3,"width":300,"height":120,"content":">> ### First column header in cell A1 MUST BE \"Id\". Id tracks the google drive Id and ensures the workflow is not processing previously processed files"},"typeVersion":1},{"id":"314e28c9-07c3-45f5-acb2-c2307d935638","name":"Sticky Note7","type":"n8n-nodes-base.stickyNote","position":[1540,40],"parameters":{"color":2,"width":160,"height":80,"content":"Uses drive ID - no need to modify"},"typeVersion":1},{"id":"a3e0322c-3224-40fe-9e82-28274a69d77c","name":"Sticky Note8","type":"n8n-nodes-base.stickyNote","position":[2040,-20],"parameters":{"color":2,"width":520,"height":80,"content":"Requires Mistral API Key for La Platforme\nhttps://mistral.ai/products/la-plateforme"},"typeVersion":1}],"active":false,"pinData":{},"settings":{"executionOrder":"v1"},"versionId":"b1ae3903-befa-458f-b6db-ba33ce2d9cac","connections":{"If":{"main":[[{"node":"Mistral Upload1","type":"main","index":0}],[{"node":"Mistral Upload","type":"main","index":0}]]},"Mistral Upload":{"main":[[{"node":"Mistral Signed URL","type":"main","index":0}]]},"extract schema":{"main":[[{"node":"Get already processed rows from Sheets","type":"main","index":0}]]},"Field Extractor":{"main":[[{"node":"Add google drive Id back","type":"main","index":0}]]},"Mistral DOC OCR":{"main":[[{"node":"Join OCR Pages and remove id field","type":"main","index":0}]]},"Mistral Upload1":{"main":[[{"node":"Mistral Signed URL1","type":"main","index":0}]]},"Get Fields Schema":{"main":[[{"node":"extract schema","type":"main","index":0}]]},"Mistral IMAGE OCR":{"main":[[{"node":"Join OCR Pages and remove id field","type":"main","index":0}]]},"Mistral Signed URL":{"main":[[{"node":"Mistral DOC OCR","type":"main","index":0}]]},"Mistral Signed URL1":{"main":[[{"node":"Mistral IMAGE OCR","type":"main","index":0}]]},"Download file for OCR":{"main":[[{"node":"If","type":"main","index":0}]]},"Filter processed files":{"main":[[{"node":"Download file for OCR","type":"main","index":0}]]},"Add google drive Id back":{"main":[[{"node":"Save data to Google Sheets","type":"main","index":0}]]},"Google Gemini Chat Model":{"ai_languageModel":[[{"node":"Field Extractor","type":"ai_languageModel","index":0}]]},"On new file in Google Drive":{"main":[[{"node":"Load files from Google Drive folder","type":"main","index":0},{"node":"Get Fields Schema","type":"main","index":0}]]},"When clicking ‘Test workflow’":{"main":[[{"node":"Load files from Google Drive folder","type":"main","index":0},{"node":"Get Fields Schema","type":"main","index":0}]]},"Join OCR Pages and remove id field":{"main":[[{"node":"Field Extractor","type":"main","index":0}]]},"Load files from Google Drive folder":{"main":[[{"node":"Filter processed files","type":"main","index":1}]]},"Get already processed rows from Sheets":{"main":[[{"node":"Filter processed files","type":"main","index":0}]]}}}


name: Automated Multilingual Gmail Draft Reply with OpenAI GPT-4o
author_name: Henry
author_username: henry
categories: []
created_at: 2025-06-11T08:11:17.450Z
updated_at: 2025-06-11T08:11:17.450Z
url: https://n8n.io/workflows/4870
scraped_at: 2025-06-19 22:07:56
description:
  Automated Multilingual Gmail Draft Reply with OpenAI GPT-4o in n8n

  Who is this for?
  This workflow is ideal for anyone who receives a high volume of Gmail inquiries, especially those providing multilingual customer support or handling diverse client 
  communications.

  What problem is this workflow solving? 
  Managing frequent emails in multiple languages can be overwhelming. This workflow reduces manual drafting by automatically generating context-aware replies using OpenAI GPT-4o, letting users focus on personalization and quality assurance.

  What this workflow does
  Monitors your Gmail inbox for new emails with a specific label (e.g., "Inquiry").
  Uses OpenAI GPT-4o for message assessment and language detection.
  Parses information using a JSON parser.
  Generates an AI-powered draft reply in the detected language via OpenAI GPT-4o.
  Converts the reply to HTML and saves it as a draft in the original Gmail thread for your review.

  Setup
  Connect your Gmail account and set up relevant labels in both Gmail and the workflow.
  Integrate your OpenAI credentials in n8n.
  Configure the workflow trigger for your desired labels.

  How to customize this workflow to your needs
  Adjust label names in both Gmail and the workflow for different email categories.
  Define custom starting and ending phrases for draft replies per supported language.
  Expand supported languages or modify AI prompt instructions to suit your brand’s tone.

nodes_used:
  ["n8n-nodes-base.gmail","@n8n/n8n-nodes-langchain.chainLlm","@n8n/n8n-nodes-langchain.lmChatOpenAi","@n8n/n8n-nodes-langchain.outputParserStructured"]

workflow_json:
  {"id":"OskjNtIb2AnxHXP2","meta":{"instanceId":"1af8a0dc0d2f537b7c08209af728c271b5a03806bdf309bedf99d668f2608ee6","templateCredsSetupCompleted":true},"name":"Automated Multilingual Gmail Draft Reply with OpenAI GPT-4o in n8n","tags":[{"id":"UXY9NrpVC8pjYHmK","name":"n8n Template","createdAt":"2025-06-05T07:41:37.020Z","updatedAt":"2025-06-05T07:41:37.020Z"}],"nodes":[{"id":"579d54f2-8c04-4624-890a-c432d96f3911","name":"If Needs Reply","type":"n8n-nodes-base.if","position":[1500,220],"parameters":{"options":{},"conditions":{"options":{"version":1,"leftValue":"","caseSensitive":true,"typeValidation":"strict"},"combinator":"and","conditions":[{"id":"53849246-ad32-4845-9976-9f9688f5a6f2","operator":{"type":"boolean","operation":"true","singleValue":true},"leftValue":"={{ $json.needsReply }}","rightValue":"true"}]}},"typeVersion":2},{"id":"526ab96e-bf2a-44f5-9e1b-3b1a10b5f55b","name":"Sticky Note","type":"n8n-nodes-base.stickyNote","position":[580,0],"parameters":{"width":444,"height":434,"content":"### Gmail Trigger\n\nGet new incoming messages from Gmail with a specific label.\n\nIn this example, the \"Inquiry\" label is used. Feel free to set it up using other Gmail filters.\n\n⚠️ Adjust the time (polling) interval according to your needs.\n"},"typeVersion":1},{"id":"7289a14b-225e-4399-aa6c-cb56158f450d","name":"Sticky Note1","type":"n8n-nodes-base.stickyNote","position":[1100,0],"parameters":{"width":576,"height":577,"content":"### Assess the email contents that need a reply\n\nThis assessment uses OpenAI GPT-4o and a JSON parser to determine whether a response is necessary and to identify the message’s language."},"typeVersion":1},{"id":"d10724dd-406c-4143-9c22-2c3ecd45e6be","name":"Gmail - Create Draft","type":"n8n-nodes-base.gmail","position":[2760,160],"webhookId":"a39b80e1-12c5-4569-aa46-63a2c2bd2d13","parameters":{"message":"={{ $json.text.replace(/\\n/g, \"<br />\\n\") }}","options":{"sendTo":"={{ $('Gmail trigger').item.json.headers.from }}","threadId":"={{ $('Gmail trigger').item.json.threadId }}"},"subject":"=Re: {{ $('Gmail trigger').item.json.headers.subject }}","resource":"draft","emailType":"html"},"credentials":{"gmailOAuth2":{"id":"2pW13S2GyP5GCdoP","name":"Gmail account"}},"typeVersion":2.1},{"id":"b805dfdb-a68e-458f-9af9-8a9e773a951d","name":"Sticky Note4","type":"n8n-nodes-base.stickyNote","position":[2660,0],"parameters":{"width":326,"height":395,"content":"### Create a Draft in the conversation\n\nDraft Integration: after converting the text to html, it places the draft into the Gmail thread as a reply to the first message"},"typeVersion":1},{"id":"cbb5c6a6-a445-474b-890f-54d1a546c28a","name":"Switch based on email language","type":"n8n-nodes-base.switch","position":[1840,200],"parameters":{"rules":{"values":[{"outputKey":"Japanese version","conditions":{"options":{"version":2,"leftValue":"","caseSensitive":true,"typeValidation":"strict"},"combinator":"and","conditions":[{"id":"b9788587-ad2a-4d44-bf01-f31c9412a48d","operator":{"type":"string","operation":"equals"},"leftValue":"={{ $json.message_language }}","rightValue":"Japanese"}]},"renameOutput":true},{"outputKey":"English version","conditions":{"options":{"version":2,"leftValue":"","caseSensitive":true,"typeValidation":"strict"},"combinator":"and","conditions":[{"id":"429c0f4a-b5f8-4730-9609-40fe20acd496","operator":{"name":"filter.operator.equals","type":"string","operation":"equals"},"leftValue":"={{ $json.message_language }}","rightValue":"English"}]},"renameOutput":true}]},"options":{"fallbackOutput":1}},"typeVersion":3.2},{"id":"a720280e-7c5f-4f83-ad2e-b13572cba762","name":"Sticky Note3","type":"n8n-nodes-base.stickyNote","position":[1760,0],"parameters":{"width":813,"height":740,"content":"### Generate a Reply\n\nDefine the output from the Switch node. Then, generate a draft reply using OpenAI GPT-4 Turbo based on the message’s detected language. Establish the rules and conventions for each supported language, including appropriate greetings, closings, tone, and any other cultural considerations."},"typeVersion":1},{"id":"a107790b-f883-469e-8763-61ec92bf1d8e","name":"Generate email for a Japanese client","type":"@n8n/n8n-nodes-langchain.chainLlm","position":[2080,160],"parameters":{"text":"=Subject: {{ $('Gmail trigger').item.json.subject }}\nMessage: {{ $('Gmail trigger').item.json.textAsHtml }}","messages":{"messageValues":[{"message":"You're a helpful personal assistant and your task is to draft replies on my behalf to my incoming emails. Whenever I provide some text from an email, return an appropriate draft reply for it and nothing else.\nEnsure that the reply is suitable for a professional email setting and addresses the topic in a clear, structured, and detailed manner.\nDo not make things up.\n\nDetailed instructions:\n- Be concise and maintain a business tone (desu-masu).\n- Follow the following content \n[INSERT CLIENT NAME] 様\nお世話になっております。\n株式会社 [INSERT YOUR COMPANY NAME] の[INSERT YOUR NAME]です。\n\nBODY (main content)\n\n引き続き、何卒どうぞ宜しくお願いいたします。\n\n- When replying to yes-no questions, draft 2 responses: one affirmative and one negative separated by \" - - - - - - - OR - - - - - - - \"\n- If you don't know an answer, you can leave placeholders like \"[YOUR_ANSWER_HERE]\".\n- Don't use any special formatting, only plain text.\n- Make sure each request is separated with a new line break\n- Reply in the same language as the inbound email."}]},"promptType":"define"},"typeVersion":1.4},{"id":"a548fcdd-1f5e-4a75-b136-07ecf4e96d3d","name":"Generate email reply for an English client","type":"@n8n/n8n-nodes-langchain.chainLlm","position":[2080,440],"parameters":{"text":"=Subject: {{ $('Gmail trigger').item.json.subject }}\nMessage: {{ $('Gmail trigger').item.json.textAsHtml }}","messages":{"messageValues":[{"message":"You're a helpful personal assistant and your task is to draft replies on my behalf to my incoming emails. Whenever I provide some text from an email, return an appropriate draft reply for it and nothing else.\nEnsure that the reply is suitable for a professional email setting and addresses the topic in a clear, structured, and detailed manner.\nDo not make things up.\n\nDetailed instructions:\n- Be concise and maintain a business casual tone.\n- Start with \"Dear,\", and end with \"Best regards,\"\n- When replying to yes-no questions, draft 2 responses: one affirmative and one negative separated by \" - - - - - - - OR - - - - - - - \"\n- If you don't know an answer, you can leave placeholders like \"[YOUR_ANSWER_HERE]\".\n- Don't use any special formatting, only plain text.\n- Reply in the same language as the inbound email."}]},"promptType":"define"},"typeVersion":1.4},{"id":"dcdf44aa-b313-4a22-ae45-0774e5a85add","name":"Sticky Note5","type":"n8n-nodes-base.stickyNote","position":[-40,0],"parameters":{"color":4,"width":560,"height":941,"content":"## Automated Multilingual Gmail Draft Reply with OpenAI GPT-4o in n8n\n\n### Who is this for?\nThis workflow is ideal for anyone who receives a high volume of Gmail inquiries, especially those providing multilingual customer support or handling diverse client \ncommunications.\n\n### What problem is this workflow solving? \nManaging frequent emails in multiple languages can be overwhelming. This workflow reduces manual drafting by automatically generating context-aware replies using OpenAI GPT-4o, letting users focus on personalization and quality assurance.\n\n### What this workflow does\n- Monitors your Gmail inbox for new emails with a specific label (e.g., \"Inquiry\").\n- Uses OpenAI GPT-4o for message assessment and language detection.\n- Parses information using a JSON parser.\n- Generates an AI-powered draft reply in the detected language via OpenAI GPT-4o.\n- Converts the reply to HTML and saves it as a draft in the original Gmail thread for your review.\n\n### Setup\n- Connect your Gmail account and set up relevant labels in both Gmail and the workflow.\n- Integrate your OpenAI credentials in n8n.\n- Configure the workflow trigger for your desired labels.\n\n## How to customize this workflow to your needs\n- Adjust label names in both Gmail and the workflow for different email categories.\n- Define custom starting and ending phrases for draft replies per supported language.\n- Expand supported languages or modify AI prompt instructions to suit your brand’s tone."},"typeVersion":1},{"id":"323eb990-e7c4-4495-811a-a3c5b26c27f0","name":"Gmail trigger","type":"n8n-nodes-base.gmailTrigger","position":[740,220],"parameters":{"simple":false,"filters":{"q":""},"options":{},"pollTimes":{"item":[{"mode":"everyMinute"}]}},"credentials":{"gmailOAuth2":{"id":"2pW13S2GyP5GCdoP","name":"Gmail account"}},"typeVersion":1},{"id":"1659ef58-d317-4260-99a8-f1de50d50839","name":"OpenAI GPT-4o","type":"@n8n/n8n-nodes-langchain.lmChatOpenAi","position":[1140,420],"parameters":{"model":"gpt-4o","options":{"temperature":0,"responseFormat":"json_object"}},"credentials":{"openAiApi":{"id":"8cWUJS0NExv35YHi","name":"OpenAi account"}},"typeVersion":1},{"id":"aeb51aac-0706-4a0e-8a21-cc09147a6e87","name":"Assess if a message needs a reply and identify the language","type":"@n8n/n8n-nodes-langchain.chainLlm","position":[1140,220],"parameters":{"prompt":"=Subject: {{ $json.subject }}\nMessage:\n{{ $json.textAsHtml }} ","messages":{"messageValues":[{"message":"Your task is to :\n- identify the language of the message and set the value to field \"message_language\" : \"English\", \"Japanese\" or \"Other\"\n- assess if the message requires a response and set the value to field \"needsReply\" : true if it does, false otherwise.\nReturn in JSON format.\nMarketing emails don't require a response."}]}},"typeVersion":1.3},{"id":"7e8a17a4-fc57-4f8f-9755-3984547bfcce","name":"Parser Result","type":"@n8n/n8n-nodes-langchain.outputParserStructured","position":[1300,420],"parameters":{"jsonSchema":"={\n  \"type\": \"array\",\n  \"items\": {\n    \"type\": \"object\",\n    \"properties\": {\n      \"needsReply\": {\n        \"type\": \"boolean\"\n      },\n      \"message_language\": {\n        \"type\": \"string\"\n      }\n    },\n    \"required\": [\"needsReply\", \"message_language\"]\n  }\n}"},"typeVersion":1},{"id":"79600a11-8038-48d7-a7a5-5c0ffdb6d412","name":"OpenAI GPT 4o - For English","type":"@n8n/n8n-nodes-langchain.lmChatOpenAi","position":[2100,580],"parameters":{"model":"gpt-4o","options":{}},"credentials":{"openAiApi":{"id":"8cWUJS0NExv35YHi","name":"OpenAi account"}},"typeVersion":1},{"id":"e0e0ef36-5a52-4d77-ba51-270693ce893f","name":"OpenAI GPT-4o - for Japanese","type":"@n8n/n8n-nodes-langchain.lmChatOpenAi","position":[2060,300],"parameters":{"model":"gpt-4o","options":{}},"credentials":{"openAiApi":{"id":"8cWUJS0NExv35YHi","name":"OpenAi account"}},"typeVersion":1}],"active":false,"pinData":{},"settings":{"executionOrder":"v1"},"versionId":"d9b8e365-5baa-47e6-bafb-8b138266a6f7","connections":{"Gmail trigger":{"main":[[{"node":"Assess if a message needs a reply and identify the language","type":"main","index":0}]]},"OpenAI GPT-4o":{"ai_languageModel":[[{"node":"Assess if a message needs a reply and identify the language","type":"ai_languageModel","index":0}]]},"Parser Result":{"ai_outputParser":[[{"node":"Assess if a message needs a reply and identify the language","type":"ai_outputParser","index":0}]]},"If Needs Reply":{"main":[[{"node":"Switch based on email language","type":"main","index":0}]]},"OpenAI GPT 4o - For English":{"ai_languageModel":[[{"node":"Generate email reply for an English client","type":"ai_languageModel","index":0}]]},"OpenAI GPT-4o - for Japanese":{"ai_languageModel":[[{"node":"Generate email for a Japanese client","type":"ai_languageModel","index":0}]]},"Switch based on email language":{"main":[[{"node":"Generate email for a Japanese client","type":"main","index":0}],[{"node":"Generate email reply for an English client","type":"main","index":0}]]},"Generate email for a Japanese client":{"main":[[{"node":"Gmail - Create Draft","type":"main","index":0}]]},"Generate email reply for an English client":{"main":[[{"node":"Gmail - Create Draft","type":"main","index":0}]]},"Assess if a message needs a reply and identify the language":{"main":[[{"node":"If Needs Reply","type":"main","index":0}]]}}}


name: 🏠 Find your Home with Real Estate Agent and Bright Data
author_name: Miquel Colomer
author_username: mcolomer
categories: []
created_at: 2025-06-11T09:15:41.161Z
updated_at: 2025-06-11T09:15:41.161Z
url: https://n8n.io/workflows/4872
scraped_at: 2025-06-19 22:07:56
description:
  📝 Overview
  This workflow transforms n8n into a smart real-estate concierge by combining an AI chat interface with Bright Data’s marketplace datasets. Users interact via chat to specify city, price, bedrooms, and bathrooms—and receive a curated list of three homes for sale, complete with images and briefings.

  🎥 Workflow in Action
  Want to see this workflow in action? Play the video


  🔑 Key Features

  AI-Powered Chat Trigger:** Instantly start conversations using LangChain’s Chat Trigger node.
  Contextual Memory:** Retain up to 30 recent messages for coherent back-and-forth.
  Bright Data Integration:** Dynamically filter “FOR\_SALE” properties by city, price, bedrooms, and bathrooms (limit = 3).
  Automated Snapshot Retrieval:** Poll for dataset readiness and fetch full snapshot content.
  HTML-Formatted Output:** Present results as a ` of ` items, embedding property images.

  🚀 How It Works (Step-by-Step)

  Prerequisites:

     n8n ≥ v1.0
     Community nodes: install n8n-nodes-brightdata (the unverified community node)
     API credentials: OpenAI, Bright Data
     Webhook endpoint to receive chat messages

  Node Configuration:

     Chat Trigger: Listens for incoming chat messages; shows a welcome screen.
     Memory Buffer: Stores the last 30 messages for context.
     OpenAI Chat Model: Uses GPT-4o-mini to interpret user intent.
     Real Estate AI Agent: Orchestrates filtering logic, calls tools, and formats responses.
     Bright Data “Filter Dataset” Tool: Applies user-defined filters plus homeStatus = FOR_SALE.
     Wait & Recover Snapshot: Polls until snapshot is ready, then fetches content.
     Get Snapshot Content: Converts raw JSON into a structured list.

  Workflow Logic:

     User sends search criteria → Agent validates inputs.
     Agent invokes “Filter Dataset” once all filters are present.
     Upon dataset readiness, the snapshot is retrieved and parsed.
     Final output rendered as a bullet list with property images.

  Testing & Optimization:

     Use the built-in Execute Workflow trigger for rapid dry runs.
     Inspect node outputs in n8n’s UI; adjust filter defaults or snapshot limits.
     Tune OpenAI model parameters (e.g., maxIterations) for faster responses.

  Deployment & Monitoring:

     Activate the main workflow and expose its webhook URL.
     Monitor executions in the “Executions” panel; set up alerts for errors.
     Archive or duplicate workflows as needed; update credentials via credential manager.

  ✅ Pre-requisites

  Bright Data Account:** API key for marketplaceDataset.
  OpenAI Account:** Access to GPT-4o-mini model.
  n8n Version:** v1.0 or later with community node support.
  Permissions:** Webhook access, credential vault read/write.

  👤 Who Is This For?

  Real-estate agencies and brokers seeking to automate client queries.
  PropTech startups building conversational search tools.
  Data analysts who want on-demand property snapshots without manual scraping.

  📈 Benefits & Use Cases

  Time Savings:** Replace manual MLS searches with an AI-driven chat.
  Scalability:** Serve multiple clients simultaneously via webchat or embedded widget.
  Consistency:** Always report exactly three properties, ensuring concise results.
  Engagement:** Visual listings with images boost user satisfaction and conversion.


  Workflow created and verified by Miquel Colomer https://www.linkedin.com/in/miquelcolomersalas/ and N8nHackers https://n8nhackers.com

nodes_used:
  ["@n8n/n8n-nodes-langchain.agent","@n8n/n8n-nodes-langchain.lmChatOpenAi","@n8n/n8n-nodes-langchain.memoryBufferWindow","@n8n/n8n-nodes-langchain.toolWorkflow"]

workflow_json:
  {"meta":{"instanceId":"b1f85eae352fde76d801a1a612661df6824cc2e68bfd6741e31305160a737e6e","templateCredsSetupCompleted":true},"nodes":[{"id":"d9e07286-a8be-4c28-8519-acf7cd35ad86","name":"When chat message received","type":"@n8n/n8n-nodes-langchain.chatTrigger","position":[-900,-40],"webhookId":"57251efe-e57c-43e2-ac58-bf27f1ec639d","parameters":{"public":true,"options":{"showWelcomeScreen":true},"initialMessages":"Hi there! 👋\n\nMy name is Miquel and I am your personal Real Estate agent. I help you to find your new home.\n\nWhat are you looking for?"},"typeVersion":1.1},{"id":"7ca48714-3c65-4f32-9491-7b7b621aaa00","name":"Simple Memory1","type":"@n8n/n8n-nodes-langchain.memoryBufferWindow","position":[-420,140],"parameters":{"contextWindowLength":30},"typeVersion":1.3},{"id":"79bea812-5a33-40a1-aa74-fe202d39dded","name":"OpenAI Chat Model","type":"@n8n/n8n-nodes-langchain.lmChatOpenAi","position":[-580,140],"parameters":{"model":{"__rl":true,"mode":"list","value":"gpt-4o-mini"},"options":{}},"credentials":{"openAiApi":{"id":"oKzfvOwieOm4upQ2","name":"OpenAi account"}},"typeVersion":1.2},{"id":"30ef3cfc-56db-4092-af0d-304afdad94f0","name":"Filter Dataset","type":"n8n-nodes-brightdata.brightDataTool","position":[-260,140],"parameters":{"resource":"marketplaceDataset","operation":"filterDataset","dataset_id":{"__rl":true,"mode":"list","value":"={{ /*n8n-auto-generated-fromAI-override*/ $fromAI('Dataset', ``, 'string') }}"},"filter_type":"filters_group","filters_group":"={{ $fromAI('Filters_Group') }}","records_limit":"=3","descriptionType":"manual","toolDescription":"Create a dataset snapshot based on a provided filter in BrightData. use always filter homeStatus = FOR_SALE. We have the next operators: =, >, >=, in, <, <=, not_array_includes, !=, not_in, not_includes\n\nFilter must follow the next format:\n{\n    \"operator\": \"and\",\n    \"filters\": [\n        {\n            \"name\": \"homeStatus\",\n            \"operator\": \"=\",\n            \"value\": \"FOR_SALE\"\n        },\n        {\n            \"name\": \"price\",\n            \"operator\": \"=\",\n            \"value\": 1000000\n        },\n        {\n            \"name\": \"city\",\n            \"operator\": \"=\",\n            \"value\": \"new york\"\n        },\n        {\n            \"name\": \"bathrooms\",\n            \"operator\": \"=\",\n            \"value\": 2\n        },\n        {\n            \"name\": \"bedrooms\",\n            \"operator\": \"=\",\n            \"value\": 4\n        }\n    ]\n}"},"credentials":{"brightdataApi":{"id":"jk945kIuAFAo9bcg","name":"BrightData account"}},"typeVersion":1},{"id":"6c4c4338-e4d2-40ee-89c0-89e1dd1dc330","name":"When Executed by Another Workflow","type":"n8n-nodes-base.executeWorkflowTrigger","position":[-660,-340],"parameters":{"inputSource":"passthrough"},"typeVersion":1.1},{"id":"9db2680e-8bad-4b91-9cd6-8240f53081a0","name":"Snapshot is ready?","type":"n8n-nodes-base.if","position":[-120,-340],"parameters":{"options":{},"conditions":{"options":{"version":2,"leftValue":"","caseSensitive":true,"typeValidation":"strict"},"combinator":"or","conditions":[{"id":"3e99082f-412a-4e33-ab77-c99ddd4d7ff5","operator":{"type":"string","operation":"exists","singleValue":true},"leftValue":"={{ $json.items[0].abbreviatedAddress }}","rightValue":"NodeApiError"}]}},"typeVersion":2.2},{"id":"75f66a3a-7738-4a1c-af8a-29385ad41749","name":"Wait","type":"n8n-nodes-base.wait","position":[100,-260],"webhookId":"7d5607bb-7cbd-439e-a95e-dfe326486b74","parameters":{},"typeVersion":1.1},{"id":"19beba9e-6089-443f-a384-4be3ec821423","name":"Real Estate AI Agent","type":"@n8n/n8n-nodes-langchain.agent","position":[-460,-40],"parameters":{"text":"={{ $json.chatInput }}","options":{"maxIterations":10,"systemMessage":"=You are an expert AI Real Estate Agent.\n\nFollow the next guidelines always:\n\n1) If you have no memory, recover the metadata from the next databases:\n- Zillow properties listing information gd_lfqkr8wm13ixtbd8f5\nWe have the next filters:\n- city: City name where entity is located. Contains valid US city names as text strings.\n- bedrooms: Column stores the number of bedrooms in properties. Values are positive integers ranging from 1 to 7, with most properties having 2-4 bedrooms and no null values.\n- bathrooms: Number of bathrooms in residential properties. Values are positive integers ranging from 1 to 7, with most properties having 2-3 bathrooms and no null values.\n- price: Property price in US dollars. Format sample: 180,000\n\nInform user that only 3 houses will be reported.\nOnly call filterDataset if user completes city, bedrooms, bathrooms and price filters.\n\n2) Use filterDataset to generate a snapshot of the requested houses by mapping filter of the user.\nOnly allow one call to tool \"Filter Dataset\", \n\n3) After calling \"filter Dataset\" tool, use tool \"Get Snapshot Content\". Pass snapshot_id parameter.\n\n4) Use output from tool \"Get Snapshot Content\" to convert json to a list of properties with ul > li\nuse returned images to present home briefing"},"promptType":"define"},"typeVersion":1.9},{"id":"679e5b92-7b52-4230-a395-f3840d167756","name":"Sticky Note1","type":"n8n-nodes-base.stickyNote","position":[-960,-600],"parameters":{"width":1260,"height":880,"content":"# Real Estate AI Agent with Bright Data\n\n## TODO\n- After pasting this workflow, update node \"Get Snapshot Content\" tool and add current Workflow ID (for instance, if your workflow in n8n has the next url https://n8n-ai.cr.vps2.clients.killia.com/workflow/fjEIEQ1L6n2IKqlx your workflow Id is fjEIEQ1L6n2IKqlx).\n- Add your Bright Data api key to \"Filter Dataset\" tool and \"Recover Snapshot Content\" node."},"typeVersion":1},{"id":"118c60c3-3a46-4ca2-be84-997218949bde","name":"Recover Snapshot Content","type":"n8n-nodes-brightdata.brightData","position":[-340,-340],"parameters":{"resource":"marketplaceDataset","operation":"getSnapshotContent","snapshot_id":"={{ $('When Executed by Another Workflow').item.json.query }}"},"credentials":{"brightdataApi":{"id":"jk945kIuAFAo9bcg","name":"BrightData account"}},"typeVersion":1},{"id":"5cc00806-6995-4d82-a832-f3159a66e31a","name":"Get Snapshot Content","type":"@n8n/n8n-nodes-langchain.toolWorkflow","position":[-100,140],"parameters":{"workflowId":{"__rl":true,"mode":"id","value":"Ky9jD15PJgT7PIgP"},"workflowInputs":{"value":{},"schema":[],"mappingMode":"defineBelow","matchingColumns":[],"attemptToConvertTypes":false,"convertFieldsToString":false}},"typeVersion":2.2}],"pinData":{},"connections":{"Wait":{"main":[[{"node":"Recover Snapshot Content","type":"main","index":0}]]},"Filter Dataset":{"ai_tool":[[{"node":"Real Estate AI Agent","type":"ai_tool","index":0}]]},"Simple Memory1":{"ai_memory":[[{"node":"Real Estate AI Agent","type":"ai_memory","index":0}]]},"OpenAI Chat Model":{"ai_languageModel":[[{"node":"Real Estate AI Agent","type":"ai_languageModel","index":0}]]},"Snapshot is ready?":{"main":[[],[{"node":"Wait","type":"main","index":0}]]},"Get Snapshot Content":{"ai_tool":[[{"node":"Real Estate AI Agent","type":"ai_tool","index":0}]]},"Recover Snapshot Content":{"main":[[{"node":"Snapshot is ready?","type":"main","index":0}]]},"When chat message received":{"main":[[{"node":"Real Estate AI Agent","type":"main","index":0}]]},"When Executed by Another Workflow":{"main":[[{"node":"Recover Snapshot Content","type":"main","index":0}]]}}}


name: 🎯 Precision Prospecting: Automate LinkedIn Lead Gen with Bright Data
author_name: Miquel Colomer
author_username: mcolomer
categories: []
created_at: 2025-06-11T09:26:01.909Z
updated_at: 2025-06-11T09:26:01.909Z
url: https://n8n.io/workflows/4873
scraped_at: 2025-06-19 22:07:56
description:
  🎯 Precision Prospecting: Automate LinkedIn Lead Gen with n8n & Bright Data

  📝 Overview
  This workflow turns n8n into an AI-powered prospector, automatically searching Google for LinkedIn profiles, scraping profile data via Bright Data, and summarizing key details. Ideal for sales and recruitment teams seeking targeted lead lists without manual research.

  🎥 Workflow in Action
  Want to see this workflow in action? You have a chat window output below:


  🔑 Key Features

  AI Chat Trigger**: Start prospecting via conversational prompts.
  Contextual Memory**: Retains the last 20 messages for coherent dialogue.
  Automated Google Search**: Generates site-restricted queries and fetches the top result.
  Bright Data Scraping**: Synchronously scrapes LinkedIn profile details by URL.
  Intelligent Filtering**: Extracts only valid LinkedIn profile links.
  Limit Control**: Returns a single, most relevant profile per request.
  LLM Summary**: Uses GPT-4o-mini to interpret and present scraped data.

  🚀 How It Works (Step-by-Step)

  Prerequisites:

     n8n ≥ v1.0 with community nodes: install n8n-nodes-brightdata (not verified community node).
     API credentials: OpenAI, Bright Data (web unlocker zone “web\_unlocker1”).
     Webhook endpoint for chat trigger.

  Node Configuration:

     When chat message received (chatTrigger): Fires on user prompt.
     Simple Memory1 (memoryBufferWindow): Stores the last 20 chat messages.
     AI Prospector Agent (agent): Orchestrates search logic.
     Get 1 Google Result (brightData): Performs a Google search with site:linkedin.com/in.
     Get Links from Body (html): Extracts all `` hrefs from the search result page.
     Extract Links (splitOut): Splits out individual link entries.
     Filter only LinkedIn Profiles (filter): Ensures the URL contains “linkedin.com/” and starts with “https\://”.
     Limit (limit): Restricts output to the first valid profile URL.
     Search LinkedIn URI (toolWorkflow): Passes the URL to a secondary workflow to fetch the first link.
     Get LinkedIn Profile Data (brightDataTool): Scrapes the profile JSON.
     OpenAI Chat Model (lmChatOpenAi): Summarizes and formats the scraped data.

  Workflow Logic:

     User asks for a person by company & name, company & position, or LinkedIn URL.
     Agent builds a Google query (e.g., site:linkedin.com/in bright data cmo) and calls “Get 1 Google Result.”
     Extracted links are filtered and limited to the top valid profile.
     If user provided a direct LinkedIn URL, Agent skips search and scrapes immediately.
     Scraped profile JSON is passed to GPT-4o-mini to generate a concise summary.

  Testing & Optimization:

     Trigger via Execute Workflow for dry runs.
     Inspect intermediate node outputs in n8n’s Execution panel.
     Adjust maxIterations or memory window length for performance.
     Tune Bright Data zone or country settings to optimize scraping speed.

  Deployment & Monitoring:

     Activate the workflow and expose its webhook URL.
     Use n8n’s built-in Alerts or external monitoring (e.g., Slack notifications) on failures.
     Rotate credentials via n8n’s Credential Vault when needed.
     Version-control workflow via duplicates or Git-backed n8n instances.

  ✅ Pre-requisites

  OpenAI Account**: API key for GPT-4o-mini.
  Bright Data Account**: Zone “web\_unlocker1” and dataset gd_l1viktl72bvl7bjuj0.
  n8n Version**: v1.0+ with community nodes installed.
  Permissions**: Webhook access, Credential Vault read/write.

  👤 Who Is This For?

  Sales teams automating outbound LinkedIn prospecting.
  Recruiters sourcing candidates without manual scraping.
  Marketing ops looking to enrich CRM with accurate profile data.

  📈 Benefits & Use Cases

  Efficiency**: Reduces hours of manual search and data entry to seconds.
  Accuracy**: Filters out non-LinkedIn links and ensures high-quality results.
  Scalability**: Handle multiple prospect requests concurrently via chat or API.
  Integration**: Easily hook into CRMs or email sequencers downstream.

  Workflow created and verified by Miquel Colomer https://www.linkedin.com/in/miquelcolomersalas/ and N8nHackers https://n8nhackers.com

nodes_used:
  ["n8n-nodes-base.html","@n8n/n8n-nodes-langchain.agent","@n8n/n8n-nodes-langchain.lmChatOpenAi","@n8n/n8n-nodes-langchain.memoryBufferWindow","@n8n/n8n-nodes-langchain.toolWorkflow"]

workflow_json:
  {"meta":{"instanceId":"b1f85eae352fde76d801a1a612661df6824cc2e68bfd6741e31305160a737e6e","templateCredsSetupCompleted":true},"nodes":[{"id":"0f2da238-9741-4019-a691-ddf17b523ca3","name":"When chat message received","type":"@n8n/n8n-nodes-langchain.chatTrigger","position":[-880,-20],"webhookId":"22c79cd1-0bd1-4bd1-bde0-88e0b3dcf553","parameters":{"options":{}},"typeVersion":1.1},{"id":"a02120f5-aa93-4269-92af-2e7486768736","name":"Simple Memory1","type":"@n8n/n8n-nodes-langchain.memoryBufferWindow","position":[-320,140],"parameters":{"contextWindowLength":20},"typeVersion":1.3},{"id":"ac560c1c-2e1e-4985-a398-6b837b89a7f3","name":"When Executed by Another Workflow","type":"n8n-nodes-base.executeWorkflowTrigger","position":[-880,-240],"parameters":{"inputSource":"passthrough"},"typeVersion":1.1},{"id":"1bd808f6-bba4-43f5-b28c-d2c9a3dd0003","name":"Search LinkedIn URI","type":"@n8n/n8n-nodes-langchain.toolWorkflow","position":[-100,140],"parameters":{"workflowId":{"__rl":true,"mode":"id","value":"fjEIEQ1L6n2IKqlx"},"description":"Pass the google uri to get first linkedin link from Google Search","workflowInputs":{"value":{},"schema":[],"mappingMode":"defineBelow","matchingColumns":[],"attemptToConvertTypes":false,"convertFieldsToString":false}},"typeVersion":2.2},{"id":"a7a7269a-e091-4327-ac67-a6f5f7946b25","name":"Get LinkedIn Profile Data","type":"n8n-nodes-brightdata.brightDataTool","position":[120,140],"parameters":{"urls":"={{ $fromAI('URLs') }}","resource":"webScrapper","dataset_id":{"__rl":true,"mode":"list","value":"=gd_l1viktl72bvl7bjuj0"},"descriptionType":"manual","toolDescription":"Scrape data synchronously by URL in BrightData\nURLs parameter must follow the next format:\n[{\"url\":\"https://www.linkedin.com/in/dvirsharon/\"}]"},"credentials":{"brightdataApi":{"id":"jk945kIuAFAo9bcg","name":"BrightData account"}},"typeVersion":1},{"id":"b84107a5-0a56-4ec9-82c9-3ef674613bb8","name":"OpenAI Chat Model","type":"@n8n/n8n-nodes-langchain.lmChatOpenAi","position":[-500,140],"parameters":{"model":{"__rl":true,"mode":"list","value":"gpt-4o-mini"},"options":{}},"credentials":{"openAiApi":{"id":"oKzfvOwieOm4upQ2","name":"OpenAi account"}},"typeVersion":1.2},{"id":"27165580-6ed9-428e-a7dc-3c119519894c","name":"Extract Links","type":"n8n-nodes-base.splitOut","position":[40,-240],"parameters":{"options":{"destinationFieldName":"url"},"fieldToSplitOut":"link"},"typeVersion":1},{"id":"2d0f43b7-4818-4f4d-aac4-862cd1bb8729","name":"Get Links from Body","type":"n8n-nodes-base.html","position":[-180,-240],"parameters":{"options":{"trimValues":true,"cleanUpText":true},"operation":"extractHtmlContent","dataPropertyName":"body","extractionValues":{"values":[{"key":"link","attribute":"href","cssSelector":"a","returnArray":true,"returnValue":"attribute"}]}},"typeVersion":1.2},{"id":"c61dd9c4-9c64-4bdb-aaf4-0e7dcf6f340f","name":"Filter only LinkedIn Profiles","type":"n8n-nodes-base.filter","position":[260,-240],"parameters":{"options":{},"conditions":{"options":{"version":2,"leftValue":"","caseSensitive":true,"typeValidation":"strict"},"combinator":"and","conditions":[{"id":"7ccbfe62-09f0-44d1-aa72-c65a2d1750b2","operator":{"type":"string","operation":"contains"},"leftValue":"={{ $json.url }}","rightValue":"linkedin.com/"},{"id":"de368fe2-6559-4316-97c5-2c6bb0a72a51","operator":{"type":"string","operation":"startsWith"},"leftValue":"={{ $json.url }}","rightValue":"https://"}]}},"typeVersion":2.2},{"id":"a689a9f6-d7a1-4e4c-8265-7753bbc41bdb","name":"Limit","type":"n8n-nodes-base.limit","position":[480,-240],"parameters":{},"typeVersion":1},{"id":"424f2539-c0ae-4228-ba9c-86ad15e24654","name":"AI Prospector Agent","type":"@n8n/n8n-nodes-langchain.agent","position":[-400,-80],"parameters":{"text":"={{ $json.chatInput }}","options":{"maxIterations":10,"systemMessage":"=You are an expert AI Prospector Agent.\nYou return information about any person using LinkedIn profiles.\n\nFollow the next guidelines always:\n\n1) User can ask your for people in two ways:\n- by company and first name\n- by company and position\n- by linkedin company\n\n2) if user searches by company and first, do a google search and scrape links matching request. Sample url generated for this case:\n- if company = bright data\n- fullname = dvir\nThe url generated is\nhttps://www.google.com/search?q=site%3Alinkedin.com%2Fin+bright%20data+dvir\n\nCall \"Search LinkedIn URI\", pass as query property the generated url, and get first https:// linkedin.com link\n\n3) if user searches by company and position, do a google search and scrape links matching request. Sample url generated for this case:\n- if company = bright data\n- position = cmo\nThe url generated is\nhttps://www.google.com/search?q=site%3Alinkedin.com%2Fin+bright%20data+cmo\n\nCall \"Search LinkedIn URI\", pass as query property the generated url, and get first https:// linkedin.com link\n\n4) if user searches by LinkedIn URI, pass link to tool \"Get LinkedIn Profile Data\".\n\n5) Present a summary for all data returned by \"Get LinkedIn Profile Data\" tool\n"},"promptType":"define"},"typeVersion":1.9},{"id":"3d0ee963-ed48-4bd1-b7d5-ae8009bfb1d7","name":"Sticky Note1","type":"n8n-nodes-base.stickyNote","position":[-1000,-480],"parameters":{"width":1680,"height":760,"content":"# Precision Prospector with Bright Data\n\n## TODO\n- After pasting this workflow, update node \"Search LinkedIn URI\" tool and add current Workflow ID (for instance, if your workflow in n8n has the next url https://n8n-ai.cr.vps2.clients.killia.com/workflow/fjEIEQ1L6n2IKqlx your workflow Id is fjEIEQ1L6n2IKqlx).\n- Add your Bright Data api key to \"Get LinkedIn Profile Data\" tool and \"Get 1 Google Result\" node."},"typeVersion":1},{"id":"df94a25c-a03e-46d9-92c8-5f0f3a5097f7","name":"Get 1 Google Result","type":"n8n-nodes-brightdata.brightData","position":[-480,-240],"parameters":{"url":"={{ $json.query }}&num=1","zone":{"__rl":true,"mode":"list","value":"web_unlocker1"},"format":"json","country":{"__rl":true,"mode":"list","value":"us"}},"credentials":{"brightdataApi":{"id":"jk945kIuAFAo9bcg","name":"BrightData account"}},"typeVersion":1}],"pinData":{},"connections":{"Extract Links":{"main":[[{"node":"Filter only LinkedIn Profiles","type":"main","index":0}]]},"Simple Memory1":{"ai_memory":[[{"node":"AI Prospector Agent","type":"ai_memory","index":0}]]},"OpenAI Chat Model":{"ai_languageModel":[[{"node":"AI Prospector Agent","type":"ai_languageModel","index":0}]]},"Get 1 Google Result":{"main":[[{"node":"Get Links from Body","type":"main","index":0}]]},"Get Links from Body":{"main":[[{"node":"Extract Links","type":"main","index":0}]]},"Search LinkedIn URI":{"ai_tool":[[{"node":"AI Prospector Agent","type":"ai_tool","index":0}]]},"Get LinkedIn Profile Data":{"ai_tool":[[{"node":"AI Prospector Agent","type":"ai_tool","index":0}]]},"When chat message received":{"main":[[{"node":"AI Prospector Agent","type":"main","index":0}]]},"Filter only LinkedIn Profiles":{"main":[[{"node":"Limit","type":"main","index":0}]]},"When Executed by Another Workflow":{"main":[[{"node":"Get 1 Google Result","type":"main","index":0}]]}}}


name: Create a Telegram Customer Support Bot with GPT4-mini and Google Docs Knowledge
author_name: Automate With Marc
author_username: marconi
categories: []
created_at: 2025-06-11T14:02:23.307Z
updated_at: 2025-06-11T14:02:23.307Z
url: https://n8n.io/workflows/4875
scraped_at: 2025-06-19 22:07:56
description:
  🤖 AI Customer Support Agent with Google Docs Knowledge (Telegram + OpenAI)

  This no-code workflow turns your Telegram bot into an intelligent, always-on AI support agent that references your business documentation in Google Docs to respond to customer queries—instantly and accurately.

  Watch full step-by-step video tutorial of the build here:
  https://www.youtube.com/@Automatewithmarc

  🔧 How it works:
  Telegram Trigger – Captures incoming messages from users on your Telegram bot

  Langchain AI Agent (OpenAI GPT) – Interprets the message and uses RAG (retrieval-augmented generation) techniques to craft an answer

  Google Docs Tool – Connects to and retrieves context from your specified Google Doc (e.g. FAQ, SOPs, policies)

  Memory Buffer – Keeps track of recent chat history for more human-like conversations

  Telegram Reply Node – Sends the AI-generated response back to the user

  💡 Use Cases:
  E-commerce customer service

  SaaS product onboarding

  Internal helpdesk bot for teams

  WhatsApp-style support for digital businesses

  🧠 What makes this powerful:
  Supports complex questions by referencing a live Google Doc knowledge base

  Works in plain conversational language (no buttons or forms needed)

  Runs 24/7 with zero code

  Easily extendable to Slack, WhatsApp, or email support

  🛠️ Tools used:
  Telegram Node (trigger + send)

  Langchain Agent with OpenAI GPT

  Google Docs Tool

  Memory Buffer

  Sticky Notes for easy understanding

nodes_used:
  ["n8n-nodes-base.telegram","@n8n/n8n-nodes-langchain.agent","@n8n/n8n-nodes-langchain.lmChatOpenAi","@n8n/n8n-nodes-langchain.memoryBufferWindow"]

workflow_json:
  {"id":"","meta":{},"name":"My workflow","tags":[],"nodes":[{"id":"f611e34d-0de9-42b7-b438-bc522817f9ba","name":"OpenAI Chat Model","type":"@n8n/n8n-nodes-langchain.lmChatOpenAi","position":[180,180],"parameters":{"model":{"__rl":true,"mode":"list","value":"gpt-4o-mini","cachedResultName":"gpt-4o-mini"},"options":{}},"credentials":{},"typeVersion":1.2},{"id":"7c968986-dcc4-4a26-bedf-5a5f9c75d2dc","name":"Simple Memory","type":"@n8n/n8n-nodes-langchain.memoryBufferWindow","position":[340,180],"parameters":{"sessionKey":"={{ $json.message.chat.id }}","sessionIdType":"customKey"},"typeVersion":1.3},{"id":"fd291678-8522-4e00-94bc-7033689f14b3","name":"Google Docs","type":"n8n-nodes-base.googleDocsTool","position":[480,180],"parameters":{"operation":"get","documentURL":"https://docs.google.com/document/d/1os02TMG0h74DYE_mmv5utPr68LtV946otozP1YZTNr0/edit?tab=t.0"},"credentials":{},"typeVersion":2},{"id":"d3e871cb-48b9-4921-8376-359f53e40942","name":"Telegram Trigger","type":"n8n-nodes-base.telegramTrigger","position":[-100,0],"webhookId":"d546870e-898a-4d37-b290-a4b3e3eac311","parameters":{"updates":["message"],"additionalFields":{}},"credentials":{},"typeVersion":1.2},{"id":"8deb9aa3-4b45-4737-a6a5-4311fb460b04","name":"Telegram","type":"n8n-nodes-base.telegram","position":[680,0],"webhookId":"cfeeb7fc-6dad-4482-b8c7-73998bfc613f","parameters":{"text":"={{ $json.output }}","chatId":"={{ $('Telegram Trigger').item.json.message.chat.id }}","additionalFields":{"appendAttribution":false}},"credentials":{},"typeVersion":1.2},{"id":"eac2e88c-0c0f-4451-bbe2-915de6e9ab1a","name":"Sticky Note","type":"n8n-nodes-base.stickyNote","position":[-200,-100],"parameters":{"width":300,"height":500,"content":"Telegram Trigger"},"typeVersion":1},{"id":"c99be9a9-7368-4b22-be65-26108f8dc23a","name":"Sticky Note1","type":"n8n-nodes-base.stickyNote","position":[120,-100],"parameters":{"color":4,"width":500,"height":500,"content":"Telegram Trigger"},"typeVersion":1},{"id":"ba596aa6-e6fb-4df4-9bdb-7b75536cfbf6","name":"Sticky Note2","type":"n8n-nodes-base.stickyNote","position":[640,-100],"parameters":{"color":3,"width":280,"height":500,"content":"Telegram Trigger"},"typeVersion":1},{"id":"ccf10ec2-eae2-47be-9be7-7bf7b3d974cb","name":"Customer Support AI Agent","type":"@n8n/n8n-nodes-langchain.agent","position":[220,0],"parameters":{"text":"={{ $json.message.text }}","options":{"systemMessage":"You are a helpful Customer Support Agent, cross-reference the Google Doc for any customer queries for relevant information. If relevant information is not found, do not make up facts. Plainly let the user know that the information isn't available. \n\n#Tonality\nFriendly, casual and helpful. if user or customer says hi, inform them that you are a Friendly Customer Support Agent"},"promptType":"define"},"typeVersion":2},{"id":"ac9ffbcd-0b7a-421e-92f4-5e367d6ba4c9","name":"Sticky Note6","type":"n8n-nodes-base.stickyNote","position":[-600,-100],"parameters":{"color":5,"width":360,"height":500,"content":"🤖 AI Customer Support Agent with Google Docs Knowledge (Telegram + OpenAI)\n\nThis no-code workflow turns your Telegram bot into an intelligent, always-on AI support agent that references your business documentation in Google Docs to respond to customer queries—instantly and accurately.\n\nWatch full step-by-step video tutorial of the build here:\nhttps://www.youtube.com/@Automatewithmarc\n\n🔧 How it works:\nTelegram Trigger – Captures incoming messages from users on your Telegram bot\n\nLangchain AI Agent (OpenAI GPT) – Interprets the message and uses RAG (retrieval-augmented generation) techniques to craft an answer\n\nGoogle Docs Tool – Connects to and retrieves context from your specified Google Doc (e.g. FAQ, SOPs, policies)\n\nMemory Buffer – Keeps track of recent chat history for more human-like conversations\n\nTelegram Reply Node – Sends the AI-generated response back to the user\n\n💡 Use Cases:\nE-commerce customer service\n\nSaaS product onboarding\n\nInternal helpdesk bot for teams\n\nWhatsApp-style support for digital businesses\n\n🧠 What makes this powerful:\nSupports complex questions by referencing a live Google Doc knowledge base\n\nWorks in plain conversational language (no buttons or forms needed)\n\nRuns 24/7 with zero code\n\nEasily extendable to Slack, WhatsApp, or email support\n\n🛠️ Tools used:\nTelegram Node (trigger + send)\n\nLangchain Agent with OpenAI GPT\n\nGoogle Docs Tool\n\nMemory Buffer\n\nSticky Notes for easy understanding"},"typeVersion":1}],"active":true,"pinData":{},"settings":{"executionOrder":"v1"},"versionId":"","connections":{"Google Docs":{"ai_tool":[[{"node":"Customer Support AI Agent","type":"ai_tool","index":0}]]},"Simple Memory":{"ai_memory":[[{"node":"Customer Support AI Agent","type":"ai_memory","index":0}]]},"Telegram Trigger":{"main":[[{"node":"Customer Support AI Agent","type":"main","index":0}]]},"OpenAI Chat Model":{"ai_languageModel":[[{"node":"Customer Support AI Agent","type":"ai_languageModel","index":0}]]},"Customer Support AI Agent":{"main":[[{"node":"Telegram","type":"main","index":0}]]}}}


name: Auto-classify Gmail emails with AI and apply labels for inbox organization
author_name: Alex Dunlop
author_username: alexdunlop
categories: []
created_at: 2025-06-11T14:08:25.008Z
updated_at: 2025-06-11T14:08:25.008Z
url: https://n8n.io/workflows/4876
scraped_at: 2025-06-19 22:07:56
description:
  Who is this for?
  Professionals and individuals who receive high volumes of emails, those who want to automatically organize their Gmail inbox using AI classification.

  What problem is this workflow solving?

  Manual email sorting is time-consuming and inconsistent. This workflow automatically categorizes incoming emails into 8 predefined labels (To respond, FYI, Comment, Notification, Meeting update, Awaiting reply, Actioned, Marketing) to help maintain inbox zero and prioritize responses.

  What this workflow does

  Monitors Gmail for new incoming emails
  Uses AI to analyze email content and classify into appropriate categories
  Automatically applies the corresponding Gmail label
  Runs on a schedule to process emails consistently

  Setup

  Prerequisites

  n8n instance (cloud or self-hosted)
  Gmail account with API access enabled
  Access to an LLM provider (OpenAI, Anthropic Claude, or similar)

  Step-by-Step

  Configure Gmail Credentials
  Create Gmail Labels
  Configure LLM Chain
  Set Email Polling Schedule
  Test the Workflow

  Create Gmail Labels
  Before running the workflow, create these 8 labels in your Gmail account:

  To respond
  FYI
  Comment
  Notification
  Meeting update
  Awaiting reply
  Actioned
  Marketing

  How to customize this workflow to your needs

  Modify Classification Categories


  To change the email categories, update two places:

  In the AI prompt (Basic LLM Chain node):

  Your new category - Description of what emails fit here
  Another category - Description
  [... continue with your categories]

  In Gmail labels:
  Create corresponding labels in your Gmail account with the exact same names and numbering.

  Adjust Classification Rules

  The AI prompt contains specific rules for each category. To modify:

  Edit the "Key classification rules" section in the LLM prompt
  Add examples of emails that should go into each category
  Specify edge cases and how they should be handled

  Change Email Sources

  Currently monitors all incoming emails. To filter specific emails:

  In the Gmail Trigger node, add filters such as:

  from:specific-sender@domain.com
  subject:contains-keyword
  -label:already-processed

  You can also change this use Outlook

  Modify Polling Frequency

  More frequent**: Add multiple poll times (e.g., 9 AM, 12 PM, 6 PM)
  Less frequent**: Change to once daily or weekly
  Real-time**: Switch to webhook-based triggering (requires Gmail API setup)

  I choose daily for cost.

nodes_used:
  ["n8n-nodes-base.gmail","n8n-nodes-base.code","@n8n/n8n-nodes-langchain.chainLlm","@n8n/n8n-nodes-langchain.lmChatOpenRouter"]

workflow_json:
  {"meta":{"instanceId":"5a90cf25b26f3375705646dd979ac7968c2f7780e9cb14036112ef363426c72c","templateCredsSetupCompleted":true},"nodes":[{"id":"37166e51-ffb6-43fe-8bd5-fe5eb1249366","name":"OpenRouter Chat Model","type":"@n8n/n8n-nodes-langchain.lmChatOpenRouter","position":[540,540],"parameters":{"model":"google/gemini-2.5-flash-preview-05-20","options":{}},"credentials":{"openRouterApi":{"id":"ogejgDjpnXZzGonu","name":"OpenRouter account"}},"typeVersion":1},{"id":"067f6b55-dc4c-4757-b19e-2d539b8b2526","name":"Aggregate Gmail Messages","type":"n8n-nodes-base.aggregate","position":[-360,220],"parameters":{"options":{},"aggregate":"aggregateAllItemData"},"typeVersion":1},{"id":"7807ff72-49f7-4a7b-9d75-24746d0dfdb7","name":"Merge Labels & Messages","type":"n8n-nodes-base.merge","position":[240,320],"parameters":{"mode":"combine","options":{},"combineBy":"combineAll"},"typeVersion":3.1},{"id":"8c51f04b-3415-4d53-8624-ce8d484145b9","name":"Classify Email with AI","type":"@n8n/n8n-nodes-langchain.chainLlm","position":[520,320],"parameters":{"text":"=You are an email classification assistant. Your task is to analyze Gmail email snippets and categorize them into one of the following labels:\n\n1. To respond - Emails requiring a direct personal response from you (questions from individuals, personal conversations, NOT automated feedback requests)\n2. FYI - Emails requesting you to take action, reminders, or alerts about issues (add money requests, payment failures, action needed)\n3. Comment - Emails specifically asking for your feedback, review, or opinion in a professional/collaborative context\n4. Notification - Automated updates about completed or ongoing events (successful payments, transfers sent, deployments, shipments, security alerts)\n5. Meeting update - Calendar invites, meeting changes, or meeting-related communications\n6. Awaiting reply - Follow-up emails or reminders about your pending responses\n7. Actioned - Confirmations of actions YOU specifically took (not automated system actions)\n8. Marketing - Promotional content, sales emails, feature announcements, newsletters, or automated customer feedback surveys\n\nKey classification rules:\n- Automated status updates (deployments, transfers, payments processed) → Notification\n- Requests to add money or take action → FYI\n- Payment failure alerts → FYI\n- Security alert digests → Notification\n- Shipment updates → Notification\n- Direct Debit payment confirmations → Notification\n- Balance update confirmations → Notification\n- Customer satisfaction surveys or feedback requests → Marketing\n- Automated \"how was your experience\" emails → Marketing\n- Only use \"Actioned\" for confirmations of YOUR manual actions\n- Only use \"Marketing\" for promotional content, including feedback surveys\n\nInstructions:\n1. Read the email snippet carefully\n2. Note the sender (if provided) for context\n3. Choose the single most appropriate label based on the rules above\n4. IMPORTANT: Respond ONLY with the number and label (e.g., \"2. FYI\")\n5. Do not include any other text, explanation, or repeat the email content\n\nEmail From:\n{{ $json.From }}\nEmail To:\n{{ $json.To }}\nEmail subject:\n{{ $json.Subject }}\nEmail snippet:\n{{ $json.snippet }}\n\nYour response must be exactly one of these 8 options:\n1. To respond\n2. FYI\n3. Comment\n4. Notification\n5. Meeting update\n6. Awaiting reply\n7. Actioned\n8. Marketing","batching":{},"promptType":"define"},"typeVersion":1.7},{"id":"ddbdc31a-ea27-415e-b9e2-954959cfcb7a","name":"New Gmail Email Received","type":"n8n-nodes-base.gmailTrigger","position":[-560,340],"parameters":{"filters":{},"pollTimes":{"item":[{"hour":12}]}},"credentials":{"gmailOAuth2":{"id":"V5NiRamelad0WTXx","name":"Gmail account"}},"typeVersion":1.2},{"id":"52b3a1d8-3be8-4f57-8759-7ae9abcdb5cb","name":"Fetch Available Gmail Labels","type":"n8n-nodes-base.gmail","position":[-140,220],"webhookId":"8574ca24-b439-4bc3-aa28-ae2b539a8d8e","parameters":{"resource":"label","returnAll":true},"credentials":{"gmailOAuth2":{"id":"V5NiRamelad0WTXx","name":"Gmail account"}},"typeVersion":2.1},{"id":"2d15670f-5735-4110-a1eb-d5b6b8abef89","name":"Map Label Names to IDs","type":"n8n-nodes-base.code","position":[60,220],"parameters":{"jsCode":"const items = $input.all();\nconst combinedObject = items.reduce((acc, item) => {\n  return { ...acc, [item.json.name]: item.json.id };\n}, {});\n\nreturn { combinedObject };\n"},"typeVersion":2},{"id":"4c5d1e4a-93ce-4f78-b0ce-8b94aff99498","name":"Apply Classification Label","type":"n8n-nodes-base.gmail","position":[960,320],"webhookId":"2ffe45e7-a0e3-4304-a6bf-e217c15ea6cc","parameters":{"labelIds":"={{ $('Map Label Names to IDs').item.json.combinedObject[$json.text] }}","messageId":"={{ $('Merge Labels & Messages').item.json.id }}","operation":"addLabels"},"credentials":{"gmailOAuth2":{"id":"V5NiRamelad0WTXx","name":"Gmail account"}},"typeVersion":2.1}],"pinData":{},"connections":{"OpenRouter Chat Model":{"ai_languageModel":[[{"node":"Classify Email with AI","type":"ai_languageModel","index":0}]]},"Classify Email with AI":{"main":[[{"node":"Apply Classification Label","type":"main","index":0}]]},"Map Label Names to IDs":{"main":[[{"node":"Merge Labels & Messages","type":"main","index":0}]]},"Merge Labels & Messages":{"main":[[{"node":"Classify Email with AI","type":"main","index":0}]]},"Aggregate Gmail Messages":{"main":[[{"node":"Fetch Available Gmail Labels","type":"main","index":0}]]},"New Gmail Email Received":{"main":[[{"node":"Aggregate Gmail Messages","type":"main","index":0},{"node":"Merge Labels & Messages","type":"main","index":1}]]},"Fetch Available Gmail Labels":{"main":[[{"node":"Map Label Names to IDs","type":"main","index":0}]]}}}


name: Automated video creation using Google V3 and n8n workflow
author_name: Lakshit Ukani
author_username: lakshit1996
categories: []
created_at: 2025-06-11T14:24:53.629Z
updated_at: 2025-06-11T14:24:53.629Z
url: https://n8n.io/workflows/4877
scraped_at: 2025-06-19 22:07:56
description:
  Who is this for?
  Content creators, social media managers, digital marketers, and businesses looking to automate video production without expensive equipment or technical expertise.

  What problem is this workflow solving?
  Traditional video creation requires cameras, editing software, voice recording equipment, and hours of post-production work. This workflow eliminates all these barriers by automatically generating professional videos with audio using just text prompts.

  What this workflow does
  This automated workflow takes video ideas from Google Sheets, generates optimized prompts using AI, creates videos through Google's V3 model via Fal AI, monitors the generation progress, and saves the final video URLs back to your spreadsheet for easy access and management.

  Setup
  Sign up for Fal AI account and obtain API key
  Create Google Sheet with video ideas and status columns
  Configure n8n with required credentials (Google Sheets, Fal AI API)
  Import the workflow template
  Set up authentication for all connected services
  Test with sample video idea

  How to customize this workflow to your needs
  Modify the AI prompts to match your brand voice, adjust video styles and camera movements, change polling intervals for video generation status, customize Google Sheet column mappings, and add additional processing steps like thumbnail generation or social media posting.

nodes_used:
  ["n8n-nodes-base.googleSheets","n8n-nodes-base.httpRequest","@n8n/n8n-nodes-langchain.agent","@n8n/n8n-nodes-langchain.lmChatOpenAi","@n8n/n8n-nodes-langchain.outputParserStructured"]

workflow_json:
  {"meta":{"instanceId":"353ac65d120d2007b8a1503e85a96651a9b2cbb94b0334693ebac2129fa6a7ee","templateCredsSetupCompleted":true},"nodes":[{"id":"d790575f-b251-4431-b993-b5b23ac98ed8","name":"When clicking ‘Execute workflow’","type":"n8n-nodes-base.manualTrigger","position":[-500,140],"parameters":{},"typeVersion":1},{"id":"ebd26e9d-956e-49d5-9819-f560c443163f","name":"📊 Fetch Ready Ideas from Sheet","type":"n8n-nodes-base.googleSheets","position":[-280,140],"parameters":{"options":{"returnFirstMatch":true},"filtersUI":{"values":[{"lookupValue":"ready","lookupColumn":"Status"}]},"sheetName":{"__rl":true,"mode":"list","value":"gid=0","cachedResultUrl":"https://docs.google.com/spreadsheets/d/1VHJFdJjqKWT973NK4TVTdzodAiHM4Zzb4tIkK-kqqGc/edit#gid=0","cachedResultName":"Sheet1"},"documentId":{"__rl":true,"mode":"list","value":"1VHJFdJjqKWT973NK4TVTdzodAiHM4Zzb4tIkK-kqqGc","cachedResultUrl":"https://docs.google.com/spreadsheets/d/1VHJFdJjqKWT973NK4TVTdzodAiHM4Zzb4tIkK-kqqGc/edit?usp=drivesdk","cachedResultName":"VEO3 Video Generation"}},"credentials":{"googleSheetsOAuth2Api":{"id":"uvQG3YEEXtu5NVSj","name":"Freelance Account"}},"typeVersion":4.6},{"id":"d47052aa-2bd9-4273-99f0-2d3b8cb593f9","name":"🤖 VEO3 Prompt Generator (GPT-4.1)","type":"@n8n/n8n-nodes-langchain.agent","position":[100,120],"parameters":{"text":"=User Idea: {{ $json.Idea }}","options":{"systemMessage":"=SYSTEM PROMPT TO GENERATE PROMPT FOR VEO3\n\nThe key to crafting a strong prompt in Veo 3 is understanding what truly matters in a video. To ensure you include all the essential details, we recommend starting by breaking your prompt down into clear categories:\n\nScene description: Overall description of the scene you want to create — what’s happening, who’s involved, and the general atmosphere.\nVisual style: Defines the overall look and feel of the video — for example, cinematic, realistic, animated, stylized, or surreal.\nCamera movement: Describes how the camera should move during the scene — for instance, slow pan, static shot, tracking shot, or aerial zoom. Avoid using slang terms (eg ‘robo-arm’ or ‘lens crack’). Be clear and descriptive.\nMain subject: The primary person, character, or object that should be the focus of the video. Clearly describe who is doing what in the scene.\nBackground setting: The specific location or environment where the scene takes place — such as a city street at night, a forest during sunrise, or a futuristic lab., traditional village, etc.\nLighting/mood: Describes the type of lighting and the emotional tone you want — for example, soft natural light with a warm tone, or harsh lighting for a dramatic or tense mood.\nAudio cue (optional): Any specific sound or music that should be heard during the scene — such as a song starting when the character dances, or ambient sounds like rain, footsteps, or birdsong.\nColor palette: The dominant colors or tones used in the video — such as bold and bright, pastel, muted earth tones, or monochrome. This influences the emotional and visual impact.\nDialog / Background Noise (optional): If characters are speaking, specify exactly what they should say and when. You can also include environmental sounds like crowds, wind, or traffic.\nSubtitles and Language : Clearly state whether you want subtitles included or not (e.g., “Do not include subtitles” or “Include subtitles in English”). Note that mentioning a language can influence cultural context (clothing, signs, architecture) even if no spoken language is rendered. To imply language or culture, you can write things like: dialogue in Spanish, with English subtitles, on-screen text in Japanese, Arabic calligraphy visible on walls, Korean street signs in the background, etc.\nAdditional Planning Notes\nUsing ” or ” or ( ) or [ ] for the dialogue may generate subtitles – avoid these if you don’t want them.\nUse natural language\nUse long prompts. The more information and direction you can give, the better your output.\nUse a solid prompting structure, like the one outlined above.\nWriting Your Prompt\nOnce you’ve outlined the key information you want to include using the above structure (or something similar), you need to write your prompt. You can write this prompt yourself, or use a tool like Chat GPT to transform your dot point plan into a fully fledged prompt.\n\nCheck out the examples below to see how your prompt should look before hitting ‘Generate’!\n\nExample\nPrompt Plan:\n\nScene description: A glamorous woman with an afro hairstyle and gold jewellery shares a pool at night with a calm alligator, surrounded by dimly lit classical decor and blue ceramic vases.\nVisual style: Cinematic\nCamera movement: Slow zoom-in on the woman’s face from water level\nMain subject: Elegant woman in the pool next to an alligator, making intense eye contact with the camera\nBackground setting: Luxurious outdoor pool area with classical statues and large ceramic vases\nLighting/mood: Moody and soft, with candlelight reflections and subtle fill light on the face\nAudio cue: Slow ambient electronic music with occasional water ripple sounds\nColor palette: Deep slate gray, ocean blue, and warm gold tones\nDialog: “I’m not afraid of anything… except Sundays without drama.\nSubtitles: Off\nComplete Prompt:\n\nA cinematic scene set at night: a glamorous woman with an afro hairstyle and gold jewellery shares a luxurious outdoor pool with a calm alligator. The pool area is surrounded by classical statues and large blue ceramic vases, all dimly lit. The camera starts at water level and slowly zooms in on the woman’s face as she makes intense eye contact with the camera. The lighting is moody and soft, with candlelight reflections on the water and a subtle fill light on her face. The audio features slow ambient electronic music, with occasional water ripple sounds. The color palette includes deep slate gray, ocean blue, and warm gold tones. The woman says, “I’m not afraid of anything… except Sundays without drama.” No subtitles.\n\n\nNote:\n- At the end just provide me single prompt which contain every details just like \"Complete Prompt above\"\n- Make sure no double qoute is there in the response"},"promptType":"define","hasOutputParser":true},"typeVersion":2},{"id":"45c5196e-37ad-4db2-aa2f-50b79d7d4db2","name":"🧠 OpenAI Chat Model","type":"@n8n/n8n-nodes-langchain.lmChatOpenAi","position":[80,320],"parameters":{"model":{"__rl":true,"mode":"list","value":"gpt-4.1-mini","cachedResultName":"gpt-4.1-mini"},"options":{}},"credentials":{"openAiApi":{"id":"69W0MY1rH5ycGoOb","name":"OpenAi account 2"}},"typeVersion":1.2},{"id":"fb2f6780-f6b4-43fb-93f3-199c33bbdc92","name":"📝 Structured Output Parser","type":"@n8n/n8n-nodes-langchain.outputParserStructured","position":[320,280],"parameters":{"schemaType":"manual","inputSchema":"{\n\t\"type\": \"object\",\n\t\"properties\": {\n\t\t\"prompt\": {\n\t\t\t\"type\": \"string\"\n\t\t}\n\t}\n}"},"typeVersion":1.2},{"id":"bbc4704f-5f9d-4c05-a5b2-1da96c5dd8e7","name":"🎬 Create Video with VEO3 (Fal AI)","type":"n8n-nodes-base.httpRequest","position":[740,120],"parameters":{"url":"https://queue.fal.run/fal-ai/veo3","body":"={\n\"prompt\": \"{{ $json.output.prompt }}\"\n}","method":"POST","options":{"batching":{"batch":{"batchSize":1,"batchInterval":2000}}},"sendBody":true,"contentType":"raw","authentication":"genericCredentialType","rawContentType":"application/json","genericAuthType":"httpHeaderAuth"},"credentials":{"httpHeaderAuth":{"id":"YC8HR4kSfpRBSFrp","name":"Fal AI Accounts"}},"typeVersion":4.2},{"id":"afa88152-0a60-4fb7-b765-7f737df81636","name":"🔍 Check Video Generation Status","type":"n8n-nodes-base.httpRequest","position":[960,120],"parameters":{"url":"=https://queue.fal.run/fal-ai/veo3/requests/{{ $json.request_id }}/status","options":{},"authentication":"genericCredentialType","genericAuthType":"httpHeaderAuth"},"credentials":{"httpHeaderAuth":{"id":"YC8HR4kSfpRBSFrp","name":"Fal AI Accounts"}},"typeVersion":4.2},{"id":"93fda276-8061-4a20-a302-0aecc929a2ec","name":"✅ Is Video Generation Complete?","type":"n8n-nodes-base.if","position":[1180,60],"parameters":{"options":{},"conditions":{"options":{"version":2,"leftValue":"","caseSensitive":true,"typeValidation":"strict"},"combinator":"and","conditions":[{"id":"571d2dfe-8a0c-416a-8780-3f47b17286b3","operator":{"name":"filter.operator.equals","type":"string","operation":"equals"},"leftValue":"={{ $json.status }}","rightValue":"COMPLETED"}]}},"typeVersion":2.2},{"id":"c5803650-1462-41e2-bbf2-2b9f1a26bf98","name":"⏰ Wait Before Retry","type":"n8n-nodes-base.wait","position":[1400,220],"webhookId":"0f17aa86-f5f6-424c-b302-91bc70001367","parameters":{"amount":30},"typeVersion":1.1},{"id":"2ebccd28-fba3-4bb0-9e1a-386e4b71fd05","name":"📥 Download Generated Video","type":"n8n-nodes-base.httpRequest","position":[1400,0],"parameters":{"url":"=https://queue.fal.run/fal-ai/veo3/requests/{{ $json.request_id }}","options":{},"authentication":"genericCredentialType","genericAuthType":"httpHeaderAuth"},"credentials":{"httpHeaderAuth":{"id":"YC8HR4kSfpRBSFrp","name":"Fal AI Accounts"}},"typeVersion":4.2},{"id":"3ab5da68-d834-41f9-aef3-9de8fa81b0b9","name":"📊 Update Sheet with Video URL","type":"n8n-nodes-base.googleSheets","position":[1860,140],"parameters":{"columns":{"value":{"Status":"completed","Video URL":"={{ $json.video.url }}","row_number":"={{ $('📊 Fetch Ready Ideas from Sheet').item.json.row_number }}"},"schema":[{"id":"Idea","type":"string","display":true,"removed":true,"required":false,"displayName":"Idea","defaultMatch":false,"canBeUsedToMatch":true},{"id":"Status","type":"string","display":true,"required":false,"displayName":"Status","defaultMatch":false,"canBeUsedToMatch":true},{"id":"Video URL","type":"string","display":true,"required":false,"displayName":"Video 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/1VHJFdJjqKWT973NK4TVTdzodAiHM4Zzb4tIkK-kqqGc/edit#gid=0","cachedResultName":"Sheet1"},"documentId":{"__rl":true,"mode":"list","value":"1VHJFdJjqKWT973NK4TVTdzodAiHM4Zzb4tIkK-kqqGc","cachedResultUrl":"https://docs.google.com/spreadsheets/d/1VHJFdJjqKWT973NK4TVTdzodAiHM4Zzb4tIkK-kqqGc/edit?usp=drivesdk","cachedResultName":"VEO3 Video Generation"}},"credentials":{"googleSheetsOAuth2Api":{"id":"uvQG3YEEXtu5NVSj","name":"Freelance Account"}},"typeVersion":4.6},{"id":"b5bc4902-7953-4f5e-8ad1-65218fe5bb45","name":"Sticky Note","type":"n8n-nodes-base.stickyNote","position":[420,-660],"parameters":{"color":6,"width":500,"height":320,"content":"## 🎬 VEO3 AI Video Generation Pipeline\n**Automated video creation from ideas to final output**\n\n### 🔄 Workflow Steps:\n1. **Data Input** → Fetch video ideas from Google Sheets\n2. **Prompt Engineering** → AI generates optimized VEO3 prompts  \n3. **Video Creation** → Submit to VEO3 via Fal AI platform\n4. **Status Monitoring** → Poll until video generation completes\n5. **Result Storage** → Save video URL back to Google Sheets\n\n### 📝 Useful Docs\nVeo 3 Model Link - [Fal.ai](https://fal.ai/models/fal-ai/veo3)\n\n⚡ **Auto-retry system included for reliable video generation**"},"typeVersion":1},{"id":"e47be290-c70d-4972-8286-67267eca3302","name":"Sticky Note1","type":"n8n-nodes-base.stickyNote","position":[-640,-100],"parameters":{"width":520,"height":480,"content":"## 📊 Data Input & Trigger System\n**Fetches ready video ideas from Google Sheets**\n\n### 🔧 Configuration Required:\n- Set correct Google Sheets document ID\n- Filter for \"Status = ready\" rows\n- Ensure \"Idea\" column contains video concepts"},"typeVersion":1},{"id":"ece8e050-bc22-4d6c-ac88-178b60f68fe6","name":"Sticky Note2","type":"n8n-nodes-base.stickyNote","position":[-80,-240],"parameters":{"color":2,"width":700,"height":740,"content":"## 🤖 AI-Powered Prompt Engineering\n**Transforms simple ideas into detailed VEO3 prompts**\n\n### 🎯 Process:\n1. **Input:** Basic video idea from sheet\n2. **AI Analysis:** GPT-4 enhances with VEO3 best practices\n3. **Output:** Structured prompt with all required elements\n\n### 📝 Prompt Elements Generated:\n- Scene description & visual style\n- Camera movements & lighting\n- Main subjects & background settings\n- Color palette & audio cues\n- Subtitle preferences"},"typeVersion":1},{"id":"13f89c59-6c96-4d3f-a83a-55901ecbca1a","name":"Sticky Note3","type":"n8n-nodes-base.stickyNote","position":[680,-240],"parameters":{"color":3,"width":980,"height":740,"content":"## 🎬 VEO3 Video Generation & Monitoring\n**Handles video creation with smart retry system**\n\n### ⚙️ Generation Settings:\n- **Aspect Ratio:** 9:16 (Mobile optimized)\n- **Duration:** 5 seconds\n- **Audio:** Generated automatically\n- **Prompt Enhancement:** Enabled\n\n### 🔄 Smart Monitoring:\n- Checks status every 30 seconds\n- Auto-retries until \"COMPLETED\"\n- Downloads final video when ready"},"typeVersion":1},{"id":"9c9e1dc4-afc5-4b90-8a22-acd2b68e86f8","name":"Sticky Note4","type":"n8n-nodes-base.stickyNote","position":[1720,-240],"parameters":{"color":4,"width":400,"height":740,"content":"## 📥 Results Processing & Storage\n**Saves generated video URLs back to Google Sheets**\n\n### 💾 What Gets Saved:\n- Final video download URL\n- Updates same row where idea was fetched\n- Status automatically changes to \"completed\"\n\n### ✅ Success Indicators:\n- Video URL populated in sheet\n- File accessible via direct link\n- Ready for download/sharing"},"typeVersion":1},{"id":"360fb8b0-7a99-4bb3-8b0e-44c58fd15790","name":"Sticky Note5","type":"n8n-nodes-base.stickyNote","position":[-780,-900],"parameters":{"color":6,"width":520,"height":680,"content":"## 👨‍💻 Creator Information\n\n**Created by:** Lakshit Ukani  \n🔗 **LinkedIn:** [Connect with me](https://www.linkedin.com/in/lakshit-ukani/)\n🔗 **Youtube:** [Subscribe to my Channel](https://www.youtube.com/@lakshit-ukani?sub_confirmation=1)\n\n### Youtube Tutorial\n[![Thumbnail](https://i.ytimg.com/vi/kMRTaVRPwTw/hqdefault.jpg?s…BACGAY4AUAB&rs=AOn4CLCW0jAAbexQ34U3892BoCxYgrpDTw)](https://www.youtube.com/watch?v=kMRTaVRPwTw)\n\n### 🤝 Community & Support\n💬 **Join Community:** [Skool Community Link](https://www.skool.com/ai-automation-club-7843)   \n📚 **Documentation:** [VEO3 API Guide](https://docs.fal.ai/models/kling-video)  \n\n### 📞 Need Help?\n- **Quick Questions:** Comment on the YouTube video\n- **Workflow Issues:** Post in our community  \n- **Business Inquiries:** Connect via LinkedIn"},"typeVersion":1}],"pinData":{"📥 Download Generated Video":[{"video":{"url":"https://v3.fal.media/files/elephant/iFIb2SSbBVpakelQJR8NF_output.mp4","file_name":"output.mp4","file_size":7960317,"content_type":"video/mp4"}}],"🔍 Check Video Generation Status":[{"logs":null,"status":"COMPLETED","metrics":{"inference_time":146.31277418136597},"cancel_url":"https://queue.fal.run/fal-ai/veo3/requests/00900707-dbe9-4fa9-ad55-3297bfc4362b/cancel","request_id":"00900707-dbe9-4fa9-ad55-3297bfc4362b","status_url":"https://queue.fal.run/fal-ai/veo3/requests/00900707-dbe9-4fa9-ad55-3297bfc4362b/status","response_url":"https://queue.fal.run/fal-ai/veo3/requests/00900707-dbe9-4fa9-ad55-3297bfc4362b"}],"🎬 Create Video with VEO3 (Fal AI)":[{"logs":null,"status":"IN_QUEUE","metrics":{},"cancel_url":"https://queue.fal.run/fal-ai/veo3/requests/00900707-dbe9-4fa9-ad55-3297bfc4362b/cancel","request_id":"00900707-dbe9-4fa9-ad55-3297bfc4362b","status_url":"https://queue.fal.run/fal-ai/veo3/requests/00900707-dbe9-4fa9-ad55-3297bfc4362b/status","response_url":"https://queue.fal.run/fal-ai/veo3/requests/00900707-dbe9-4fa9-ad55-3297bfc4362b","queue_position":0}],"🤖 VEO3 Prompt Generator (GPT-4.1)":[{"output":{"prompt":"A cozy and enchanting scene of a friendly yeti giving a house tour inside his winter cabin. The visual style is whimsical and slightly animated with soft textures to evoke warmth and charm. The camera operates with gentle tracking shots as it follows the yeti moving through different rooms, highlighting the various quirky and snowy decor. The main subject is the yeti, a large, fluffy white creature with expressive eyes and a warm smile, gesturing enthusiastically as he shows his house. The background setting is a rustic, snow-covered wooden cabin filled with winter-themed decorations, plush furniture, and icicle-shaped lights. The lighting is soft and warm with a golden hue, creating a welcoming and cheerful atmosphere. Ambient sounds include crackling of a fireplace, soft wind blowing outside, and light, playful background music to enhance the friendly mood. The color palette features cool whites and blues mixed with warm wooden browns and soft yellows. The yeti occasionally speaks in a gentle, friendly tone, saying things like I hope you like it here and This is my favorite room to relax. Subtitles are not included."}}]},"connections":{"⏰ Wait Before Retry":{"main":[[{"node":"🔍 Check Video Generation Status","type":"main","index":0}]]},"🧠 OpenAI Chat Model":{"ai_languageModel":[[{"node":"🤖 VEO3 Prompt Generator (GPT-4.1)","type":"ai_languageModel","index":0}]]},"📝 Structured Output Parser":{"ai_outputParser":[[{"node":"🤖 VEO3 Prompt Generator (GPT-4.1)","type":"ai_outputParser","index":0}]]},"📥 Download Generated Video":{"main":[[{"node":"📊 Update Sheet with Video URL","type":"main","index":0}]]},"✅ Is Video Generation Complete?":{"main":[[{"node":"📥 Download Generated Video","type":"main","index":0}],[{"node":"⏰ Wait Before Retry","type":"main","index":0}]]},"📊 Fetch Ready Ideas from Sheet":{"main":[[{"node":"🤖 VEO3 Prompt Generator (GPT-4.1)","type":"main","index":0}]]},"🔍 Check Video Generation Status":{"main":[[{"node":"✅ Is Video Generation Complete?","type":"main","index":0}]]},"When clicking ‘Execute workflow’":{"main":[[{"node":"📊 Fetch Ready Ideas from Sheet","type":"main","index":0}]]},"🎬 Create Video with VEO3 (Fal AI)":{"main":[[{"node":"🔍 Check Video Generation Status","type":"main","index":0}]]},"🤖 VEO3 Prompt Generator (GPT-4.1)":{"main":[[{"node":"🎬 Create Video with VEO3 (Fal AI)","type":"main","index":0}]]}}}


name: Turn Google Sheets Ideas into AI Videos with GPT-4o and Fal.AI Veo 3
author_name: Maximiliano Rojas-Delgado
author_username: maxr
nodes_used: ["n8n-nodes-base.googleSheets","n8n-nodes-base.httpRequest","@n8n/n8n-nodes-langchain.openAi"]
categories: []
created_at: 2025-06-11T19:54:02.502Z
updated_at: 2025-06-11T19:54:02.502Z
url: https://n8n.io/workflows/4881
scraped_at: 2025-06-19 22:07:56
description:
  Turn Your Ideas into Videos—Right from Google Sheets!

  This workflow helps you make cool 8-second videos using Fal.AI and Veo 3, just by typing your idea into a Google Sheet. You can even choose if you want your video to have sound or not. It’s super easy—no tech skills needed!

  Why use this?

  Just type your idea in a sheet—no fancy tools or uploads.

  Get a video link back in the same sheet.

  Works with or without sound—your choice!

  How does it work?

  You write your idea, pick the video shape, and say if you want sound (true or false) in the Google Sheet.

  n8n reads your idea and asks Fal.AI to make your video.

  When your video is ready, the link shows up in your sheet.

  What do you need?

  A Google account and Google Sheets connected with service account (check this link for reference)
  A copy of the following Google Spreadsheet:
  Spreadsheet to copy

  An OpenAI API key

  A Fal.AI account with some money in it

  That’s it! Just add your ideas and let the workflow make the videos for you. Have fun creating!

  if you have any questions, just contact me at max@nervoai.com

workflow_json:
  {"id":"wGQOrU5qak5K99FT","meta":{"instanceId":"d59922ccaab8f9a216dbe3eacc226c7a17998a61f6c4177822cd8e33edb224d7"},"name":"Google Sheets to Veo 3: Instantly Create Videos with n8n & Fal.AI","tags":[{"id":"fElGhCk9TINqseuM","name":"templates","createdAt":"2025-06-11T19:44:28.283Z","updatedAt":"2025-06-11T19:44:28.283Z"},{"id":"I8yfdg9mSqeqo4nX","name":"creator","createdAt":"2025-06-11T19:44:30.157Z","updatedAt":"2025-06-11T19:44:30.157Z"}],"nodes":[{"id":"7beb408f-128b-4e4c-8d03-e5625fbcb2eb","name":"Wait 5s","type":"n8n-nodes-base.wait","position":[340,620],"webhookId":"150069ed-885b-497f-a32a-09e7088136e6","parameters":{},"typeVersion":1.1},{"id":"77d6a74f-b704-40f2-b054-fbf91c93726a","name":"Check if video is ready","type":"n8n-nodes-base.if","position":[160,620],"parameters":{"options":{},"conditions":{"options":{"version":2,"leftValue":"","caseSensitive":true,"typeValidation":"strict"},"combinator":"and","conditions":[{"id":"ac50759b-e2f3-4efd-a2af-f28b7d209b45","operator":{"name":"filter.operator.equals","type":"string","operation":"equals"},"leftValue":"={{ $json.status }}","rightValue":"COMPLETED"}]}},"typeVersion":2.2},{"id":"cd94d480-3562-4ce3-aff0-9caf5dee9f72","name":"Get video url","type":"n8n-nodes-base.httpRequest","position":[0,940],"parameters":{"url":"={{ $json.response_url }}","options":{},"sendHeaders":true,"headerParameters":{"parameters":[{"name":"Authorization","value":"Key <YOUR_API_KEY>"}]}},"typeVersion":4.2},{"id":"5267ac1d-36ad-449a-9f5f-cae01a090b33","name":"Generate prompt for Veo 3 model","type":"@n8n/n8n-nodes-langchain.openAi","position":[180,-20],"parameters":{"modelId":{"__rl":true,"mode":"list","value":"chatgpt-4o-latest","cachedResultName":"CHATGPT-4O-LATEST"},"options":{},"messages":{"values":[{"role":"assistant","content":"=You are a creative prompt engineer for Google's Veo 3 video generation model. For any concept provided, craft a detailed, visually immersive prompt that specifies the subject, setting, lighting, mood, era or style, object details, composition, and background elements. Use evocative, sensory-rich language and guide the model to produce authentic, high-quality images. Match the style and depth of the following example:\n\nA casual street interview on a busy New York City sidewalk in the afternoon. The interviewer holds a plain, unbranded microphone and asks: Have you seen Google's new Veo3 model It is a super good model. Person replies: Yeah I saw it, it's already available on fal. It's crazy good.\n\nRespond only with the crafted prompt."},{"content":"=the input is: {{ $json.Idea }}"}]}},"credentials":{"openAiApi":{"id":"6iZ86Vz38pnHnAuF","name":"OpenAi account"}},"typeVersion":1.8},{"id":"a5864945-030e-4d80-83cb-2f558399d8bf","name":"Submit Request to generate video","type":"n8n-nodes-base.httpRequest","position":[340,300],"parameters":{"url":"https://queue.fal.run/fal-ai/veo3","method":"POST","options":{},"jsonBody":"={\n  \"prompt\": \"{{ $json.prompt }}\",\n  \"aspect_ratio\": \"{{ $json.ratio }}\",\n  \"enhance_prompt\": true,\n  \"generate_audio\": {{ $json.audio }}\n}","sendBody":true,"sendHeaders":true,"specifyBody":"json","headerParameters":{"parameters":[{"name":"Content-Type","value":"application/json"},{"name":"authorization","value":"Key <YOUR_API_KEY>"}]}},"typeVersion":4.2},{"id":"00f339c8-f6e3-42b3-aa56-abe34268c68a","name":"Set variables for Video generation","type":"n8n-nodes-base.set","position":[0,300],"parameters":{"options":{},"assignments":{"assignments":[{"id":"4807c116-ed98-4a0e-8dba-aab1dd2ee971","name":"prompt","type":"string","value":"={{ $json.message.content }}"},{"id":"32437b05-fa7a-4f3b-bad0-fc7201cc7371","name":"ratio","type":"string","value":"={{ $('Google Sheets Trigger').item.json.Ratio }}"},{"id":"4cf00dd2-9057-4868-93ac-7f9725750d77","name":"audio","type":"string","value":"={{ $('Google Sheets Trigger').item.json.Audio }}"}]}},"typeVersion":3.4},{"id":"88429b78-fe9f-42ca-81e1-0b364703ab2a","name":"Check video status","type":"n8n-nodes-base.httpRequest","position":[0,620],"parameters":{"url":"=https://queue.fal.run/fal-ai/veo3/requests/{{ $json.request_id }}/status","options":{},"sendHeaders":true,"headerParameters":{"parameters":[{"name":"Authorization","value":"Key <YOUR_API_KEY>"}]}},"typeVersion":4.2},{"id":"26e74f30-575f-407a-99ee-f75daad9a2e4","name":"Google Sheets Trigger","type":"n8n-nodes-base.googleSheetsTrigger","position":[0,-20],"parameters":{"event":"rowAdded","options":{},"pollTimes":{"item":[{"mode":"everyMinute"}]},"sheetName":{"__rl":true,"mode":"list","value":"gid=0","cachedResultUrl":"https://docs.google.com/spreadsheets/d/100ur8DnU_q2YIAx15ccMfEWC43Di_G7hj19csjxg73A/edit#gid=0","cachedResultName":"Results"},"documentId":{"__rl":true,"mode":"list","value":"100ur8DnU_q2YIAx15ccMfEWC43Di_G7hj19csjxg73A","cachedResultUrl":"https://docs.google.com/spreadsheets/d/100ur8DnU_q2YIAx15ccMfEWC43Di_G7hj19csjxg73A/edit?usp=drivesdk","cachedResultName":"Veo 3 template"}},"credentials":{"googleSheetsTriggerOAuth2Api":{"id":"CUMqe7iFy7F1KIF9","name":"Google Sheets account NervoAI"}},"typeVersion":1},{"id":"57f0306d-3b12-4717-afc6-c548863c2f7f","name":"Sticky Note","type":"n8n-nodes-base.stickyNote","position":[-780,-80],"parameters":{"color":5,"width":700,"height":1140,"content":"## Google Sheets to Veo 3: Instantly Create Videos with n8n & Fal.AI\n\nEasily generate 8-second videos using Fal.AI’s Veo 3 model—just add a row to your Google Sheet with your idea, the video ratio, and whether you want audio (true/false).\n\nHere’s what Fal.AI charges:\n\n1s video: $0.50\n\n1s video with audio: $0.75\n\n8s video (default): $4.00\n\n8s video with audio: $6.00\n\nHere are the execution times:\n\n8s video (default): 3 minutes\n\n8s video with audio: 15 minutes\n\n**Step 1: Connect Google Sheets**\n\nAdd your Google service account credentials and make sure Google Sheets API is enabled in your Google Cloud project.\n\nCopy the shared template sheet in the description.\n\nDouble-check that your n8n Google Sheets nodes are linked to the correct spreadsheet.\n\n**Step 2: Connect OpenAI**\n\nGet your OpenAI API key.\n\nAdd your OpenAI credentials in n8n.\n\n**Step 3: Set Up Fal.ai**\n\nSign up at fal.ai and top up your account.\n\nGrab your API key from the Fal.ai dashboard.\n\nIn n8n, update the \"Submit Request to generate video,\" \"Check video status,\" and \"Get video url\" nodes. Replace the authorization header with your API key: 'Key <YOUR_API_KEY>'\n\n**Step 4: View Results in the Sheet**\n\nOnce your sheet updates, you’ll see the prompt used and the video URL.\n\n** Troubleshoot**\nIf the “Audio” column shows as a boolean instead of text and gives error generating the video, enter it as '=\"true\"' or '=\"false\"' in the spreadsheet.\n\nif any other issue, please contact me at max@nervoai.com\n\n\nThat’s it! You’re ready to create Veo 3 videos straight from Google Sheets.\n"},"typeVersion":1},{"id":"9dc75bc3-25a7-4c3c-bb65-8372acb2703b","name":"Update sheet with video url and prompt used in Veo3","type":"n8n-nodes-base.googleSheets","position":[340,940],"parameters":{"columns":{"value":{"Idea":"={{ $('Google Sheets Trigger').item.json.Idea }}","Video Generated":"={{ $json.video.url }}","Prompt Generated":"={{ $('Generate prompt for Veo 3 model').item.json.message.content }}"},"schema":[{"id":"Idea","type":"string","display":true,"removed":false,"required":false,"displayName":"Idea","defaultMatch":false,"canBeUsedToMatch":true},{"id":"Ratio","type":"string","display":true,"required":false,"displayName":"Ratio","defaultMatch":false,"canBeUsedToMatch":true},{"id":"Audio","type":"string","display":true,"required":false,"displayName":"Audio","defaultMatch":false,"canBeUsedToMatch":true},{"id":"Prompt Generated","type":"string","display":true,"required":false,"displayName":"Prompt Generated","defaultMatch":false,"canBeUsedToMatch":true},{"id":"Video Generated","type":"string","display":true,"required":false,"displayName":"Video Generated","defaultMatch":false,"canBeUsedToMatch":true},{"id":"row_number","type":"string","display":true,"removed":true,"readOnly":true,"required":false,"displayName":"row_number","defaultMatch":false,"canBeUsedToMatch":true}],"mappingMode":"defineBelow","matchingColumns":["Idea"],"attemptToConvertTypes":false,"convertFieldsToString":false},"options":{},"operation":"update","sheetName":{"__rl":true,"mode":"list","value":"gid=0","cachedResultUrl":"https://docs.google.com/spreadsheets/d/100ur8DnU_q2YIAx15ccMfEWC43Di_G7hj19csjxg73A/edit#gid=0","cachedResultName":"Results"},"documentId":{"__rl":true,"mode":"list","value":"100ur8DnU_q2YIAx15ccMfEWC43Di_G7hj19csjxg73A","cachedResultUrl":"https://docs.google.com/spreadsheets/d/100ur8DnU_q2YIAx15ccMfEWC43Di_G7hj19csjxg73A/edit?usp=drivesdk","cachedResultName":"Veo 3 template"}},"credentials":{"googleSheetsOAuth2Api":{"id":"f8o05SKiFZmuFhu9","name":"Google Sheets account nervoAI"}},"typeVersion":4.6},{"id":"774b9b76-4cd8-4d5a-8b8b-587ee1cae464","name":"Sticky Note1","type":"n8n-nodes-base.stickyNote","position":[-40,-140],"parameters":{"color":3,"width":540,"height":300,"content":"## Stage 1: Trigger & Prompt Generation\nStarts the workflow when a new row is added in Google Sheets, then when the workflow is actioned, it generates a prompt for the Veo 3 video model based on the sheet data."},"typeVersion":1},{"id":"169699a3-6208-4586-8c3c-a3df7f3cdaf2","name":"Sticky Note2","type":"n8n-nodes-base.stickyNote","position":[-40,180],"parameters":{"color":6,"width":540,"height":300,"content":"## Stage 2: Prepare & Submit Video Request\nSets up all necessary variables for video creation and sends a request to Fal.AI to generate the video."},"typeVersion":1},{"id":"739cdf63-5e11-4364-b4f8-3b65e962ce3e","name":"Sticky Note3","type":"n8n-nodes-base.stickyNote","position":[-40,500],"parameters":{"width":540,"height":300,"content":"## Stage 3: Monitor Video Status\nChecks the status of the video generation. Waits and repeatedly checks every 5 seconds until the video is ready."},"typeVersion":1},{"id":"49c27097-de0e-4516-8ee0-8936507d7455","name":"Sticky Note4","type":"n8n-nodes-base.stickyNote","position":[-40,820],"parameters":{"color":4,"width":540,"height":300,"content":"## Stage 4: Retrieve & Update Results\nGets the final video URL and updates the Google Sheet with the video link and the prompt used."},"typeVersion":1}],"active":false,"pinData":{},"settings":{"executionOrder":"v1"},"versionId":"9f0cad2c-2edc-4ab2-9a10-0ae019069b35","connections":{"Wait 5s":{"main":[[{"node":"Check video status","type":"main","index":0}]]},"Get video url":{"main":[[{"node":"Update sheet with video url and prompt used in Veo3","type":"main","index":0}]]},"Check video status":{"main":[[{"node":"Check if video is ready","type":"main","index":0}]]},"Google Sheets Trigger":{"main":[[{"node":"Generate prompt for Veo 3 model","type":"main","index":0}]]},"Check if video is ready":{"main":[[{"node":"Get video url","type":"main","index":0}],[{"node":"Wait 5s","type":"main","index":0}]]},"Generate prompt for Veo 3 model":{"main":[[{"node":"Set variables for Video generation","type":"main","index":0}]]},"Submit Request to generate video":{"main":[[{"node":"Check video status","type":"main","index":0}]]},"Set variables for Video generation":{"main":[[{"node":"Submit Request to generate video","type":"main","index":0}]]}}}


name: Convert PDF Documents to AI Podcasts with Google Gemini and Text-to-Speech
author_name: Mathis
author_username: iamthis
categories: []
created_at: 2025-06-11T20:48:43.573Z
updated_at: 2025-06-11T20:48:43.573Z
url: https://n8n.io/workflows/4883
scraped_at: 2025-06-19 22:07:56
description:
  Convert PDF documents to AI-generated podcasts with Google Gemini and Text-to-Speech

  Transform any PDF document into an engaging, natural-sounding podcast using Google's Gemini AI and advanced Text-to-Speech technology. This automated workflow extracts text content, generates conversational scripts, and produces high-quality audio files.

  Who is this for?

  This workflow template is perfect for content creators, educators, researchers, and marketing professionals who want to repurpose written content into audio format. Ideal for creating podcast episodes, educational content, or making documents more accessible.

  What problem does this solve?

  Converting written documents to engaging audio content manually is time-consuming and requires scriptwriting skills. This workflow automates the entire process, turning static PDFs into dynamic, conversational podcasts that sound natural and engaging.

  What this workflow does

  Extracts text from uploaded PDF documents
  Generates podcast script using Google Gemini AI with conversational tone
  Converts script to speech using Google's advanced TTS with customizable voices
  Processes audio into properly formatted WAV files
  Saves final podcast ready for distribution

  Setup

  Obtain API credentials:
     Get Google Gemini API key from AI Studio
     Configure credentials in n8n as "Google Gemini(PaLM) Api account"

  Configure voice settings:
     Choose from available voices: Kore (professional), Aoede (conversational), Laomedeia (energetic)
     Customize script generation prompts if needed

  Test the workflow:
     Upload a sample PDF file
     Verify audio output quality
     Adjust voice settings as preferred

  How to customize this workflow

  Modify script style:** Edit the prompt in the "Generate Podcast Script" node to change tone, length, or format
  Change voice:** Update the voice name in "Prepare TTS Request" node
  Add preprocessing:** Insert text cleaning nodes before script generation
  Integrate with storage:** Connect to Google Drive, Dropbox, or other storage services
  Add notifications:** Include Slack or email notifications when podcasts are ready

  Note: This template requires Google Gemini API access and works best with text-based PDF files under 10MB.

nodes_used:
  ["n8n-nodes-base.httpRequest","n8n-nodes-base.code","@n8n/n8n-nodes-langchain.chainLlm","@n8n/n8n-nodes-langchain.lmChatGoogleGemini"]

workflow_json:
  {"meta":{"instanceId":"3b439b2efefd3a3727fcde770e801989ddd80f304fce43a46dd089f21c19f2fb","templateCredsSetupCompleted":true},"nodes":[{"id":"37a9addb-a90e-4491-8b7a-a42fad57329a","name":"🎬 Start: Upload PDF File","type":"n8n-nodes-base.manualTrigger","position":[-340,-60],"parameters":{},"typeVersion":1},{"id":"dd475138-a5fa-4818-aeaa-27e8e0969367","name":"📄 Extract Text from PDF","type":"n8n-nodes-base.extractFromFile","position":[-120,-60],"parameters":{"options":{},"operation":"pdf","binaryPropertyName":"data0"},"typeVersion":1},{"id":"9a24fae8-ac8c-48a0-a985-69e0b4a3e0b8","name":"🤖 Generate Podcast Script","type":"@n8n/n8n-nodes-langchain.chainLlm","position":[100,-160],"parameters":{"text":"={{ $json.text }}","batching":{},"messages":{"messageValues":[{"message":"=Create an engaging podcast script based on the following content. The script should be exactly 5-7 minutes when read aloud (approximately 750-1000 words).  CONTENT TO DISCUSS: {content}  STYLE: {style}  PODCAST SCRIPT REQUIREMENTS: 1. Start with: \"Welcome to our AI-generated podcast. Today we're diving into...\" 2. Structure: Introduction, 2-3 main discussion points, conclusion 3. Use natural conversational language 4. Include smooth transitions between topics 5. Add brief pauses with periods and commas for natural speech 6. Avoid complex punctuation that might confuse TTS 7. End with: \"Thanks for listening! This has been your AI podcast.\" 8. Write ONLY the spoken content (no stage directions) 9. Keep sentences moderate length for clear speech 10. Use engaging storytelling techniques"}]},"promptType":"define"},"typeVersion":1.7},{"id":"87891658-777b-47bf-9a86-9c23076a7477","name":"Google Gemini Flash 2.0","type":"@n8n/n8n-nodes-langchain.lmChatGoogleGemini","position":[188,60],"parameters":{"options":{},"modelName":"models/gemini-2.0-flash-001"},"credentials":{"googlePalmApi":{"id":"ssUBiwRgjxx0Dj8n","name":"Google Gemini(PaLM) Api account"}},"typeVersion":1},{"id":"8ebba81a-a42e-48cf-aeaa-1263fe59ed90","name":"⚙️ Prepare TTS Request","type":"n8n-nodes-base.code","position":[480,-60],"parameters":{"jsCode":"const script = $input.first().json.text;\nconst voiceName = $input.first().json.voiceName || \"Kore\";\n\nreturn {\n  json: {\n    requestBody: {\n      contents: [{\n        parts: [{\n          text: script\n        }]\n      }],\n      generationConfig: {\n        responseModalities: [\"AUDIO\"],\n        speechConfig: {\n          voiceConfig: {\n            prebuiltVoiceConfig: {\n              voiceName: voiceName\n            }\n          }\n        }\n      }\n    }\n  }\n};"},"typeVersion":2},{"id":"78e3f968-ec21-4d85-a802-688f1d33b48c","name":"🎙️ Convert Text to Speech With Gemini","type":"n8n-nodes-base.httpRequest","position":[696,-60],"parameters":{"url":"https://generativelanguage.googleapis.com/v1beta/models/gemini-2.5-flash-preview-tts:generateContent","method":"POST","options":{},"jsonBody":"={{ $json.requestBody }}","sendBody":true,"sendHeaders":true,"specifyBody":"json","authentication":"predefinedCredentialType","headerParameters":{"parameters":[{"name":"Content-Type","value":"application/json"}]},"nodeCredentialType":"googlePalmApi"},"credentials":{"googlePalmApi":{"id":"ssUBiwRgjxx0Dj8n","name":"Google Gemini(PaLM) Api account"},"httpCustomAuth":{"id":"wGstDoq0x8ov0ube","name":"Tavily Custom Auth account"}},"typeVersion":4.2},{"id":"1baddfca-84c4-4ffd-beb8-5acb919112fe","name":"🔧 Process Audio Response","type":"n8n-nodes-base.code","position":[916,-60],"parameters":{"jsCode":"const response = $input.all()[0].json;\n\nconsole.log('=== GEMINI TTS DEBUG ===');\nconsole.log('Response status:', response.candidates?.[0]?.finishReason);\n\nif (response.candidates?.[0]?.finishReason === 'STOP') {\n  try {\n    // Get the base64 audio data\n    const base64AudioData = response.candidates[0].content.parts[0].inlineData.data;\n    const mimeType = response.candidates[0].content.parts[0].inlineData.mimeType;\n    \n    console.log('Audio data length:', base64AudioData.length);\n    console.log('Mime type:', mimeType);\n    \n    // CRITICAL FIX: Properly decode base64 to actual audio bytes\n    const actualAudioBytes = Buffer.from(base64AudioData, 'base64');\n    \n    console.log('Decoded audio size:', actualAudioBytes.length);\n    \n    // Create WAV file with proper PCM16 format\n    const sampleRate = 24000;\n    const channels = 1;\n    const bitsPerSample = 16;\n    \n    // Create WAV header\n    const wavHeader = createWavHeader(actualAudioBytes.length, sampleRate, channels, bitsPerSample);\n    const wavFile = Buffer.concat([wavHeader, actualAudioBytes]);\n    \n    const filename = `tts_fixed_${Date.now()}.wav`;\n    \n    return {\n      json: {\n        success: true,\n        filename: filename,\n        audioSize: wavFile.length,\n        audioSizeMB: (wavFile.length / 1024 / 1024).toFixed(2),\n        originalBase64Length: base64AudioData.length,\n        decodedAudioLength: actualAudioBytes.length\n      },\n      binary: {\n        audio: {\n          data: wavFile,\n          mimeType: 'audio/wav',\n          fileName: filename\n        }\n      }\n    };\n    \n  } catch (error) {\n    return {\n      json: {\n        success: false,\n        error: error.message,\n        step: 'audio_processing'\n      }\n    };\n  }\n} else {\n  return {\n    json: {\n      success: false,\n      error: 'TTS generation failed',\n      finishReason: response.candidates?.[0]?.finishReason || 'unknown',\n      response: response\n    }\n  };\n}\n\n// Helper function to create WAV header\nfunction createWavHeader(dataLength, sampleRate, channels, bitsPerSample) {\n  const byteRate = sampleRate * channels * bitsPerSample / 8;\n  const blockAlign = channels * bitsPerSample / 8;\n  const header = Buffer.alloc(44);\n  \n  // \"RIFF\" chunk descriptor\n  header.write('RIFF', 0);\n  header.writeUInt32LE(36 + dataLength, 4);\n  header.write('WAVE', 8);\n  \n  // \"fmt \" sub-chunk\n  header.write('fmt ', 12);\n  header.writeUInt32LE(16, 16); // Sub-chunk size\n  header.writeUInt16LE(1, 20);  // Audio format (PCM)\n  header.writeUInt16LE(channels, 22);\n  header.writeUInt32LE(sampleRate, 24);\n  header.writeUInt32LE(byteRate, 28);\n  header.writeUInt16LE(blockAlign, 32);\n  header.writeUInt16LE(bitsPerSample, 34);\n  \n  // \"data\" sub-chunk\n  header.write('data', 36);\n  header.writeUInt32LE(dataLength, 40);\n  \n  return header;\n}"},"typeVersion":2},{"id":"36978e98-5d80-4859-868f-5f8e6ddcb569","name":"💾 Save Podcast Audio","type":"n8n-nodes-base.writeBinaryFile","position":[1136,-60],"parameters":{"options":{},"fileName":"={{ $json.filename }}","dataPropertyName":"audio"},"typeVersion":1},{"id":"0deff03c-60f7-4fd0-84e2-96527caba405","name":"Sticky Note","type":"n8n-nodes-base.stickyNote","position":[-360,-680],"parameters":{"width":320,"height":400,"content":"## 🎯 Main Template Overview\nWhat this workflow does:\n- Extracts text from uploaded PDF files\n- Generates conversational podcast script using AI\n- Converts script to natural-sounding audio\n- Saves final podcast as WAV file\n\nSetup required:\n- Google Gemini API key (for AI script generation)\n- Google PaLM API credentials (for TTS)\n- File upload capability"},"typeVersion":1},{"id":"b867911c-8add-450c-89d8-906cace883ad","name":"Sticky Note1","type":"n8n-nodes-base.stickyNote","position":[-20,-680],"parameters":{"color":5,"width":300,"height":400,"content":"## 🔧 Setup Instructions\nBefore You Start:\n\nGet API Keys:\n- Gemini API: https://aistudio.google.com/\n- Add to n8n credentials as \"Google Gemini(PaLM) Api account\"\n\n\nTest the workflow:\n- Use the manual trigger\n- Upload a PDF file\n- Check that audio file is generated"},"typeVersion":1}],"pinData":{},"connections":{"Google Gemini Flash 2.0":{"ai_languageModel":[[{"node":"🤖 Generate Podcast Script","type":"ai_languageModel","index":0}]]},"⚙️ Prepare TTS Request":{"main":[[{"node":"🎙️ Convert Text to Speech With Gemini","type":"main","index":0}]]},"📄 Extract Text from PDF":{"main":[[{"node":"🤖 Generate Podcast Script","type":"main","index":0}]]},"🎬 Start: Upload PDF File":{"main":[[{"node":"📄 Extract Text from PDF","type":"main","index":0}]]},"🔧 Process Audio Response":{"main":[[{"node":"💾 Save Podcast Audio","type":"main","index":0}]]},"🤖 Generate Podcast Script":{"main":[[{"node":"⚙️ Prepare TTS Request","type":"main","index":0}]]},"🎙️ Convert Text to Speech With Gemini":{"main":[[{"node":"🔧 Process Audio Response","type":"main","index":0}]]}}}


name: Auto-Generate AI News Commentary with Dumpling AI and GPT-4o
author_name: Yang
author_username: yang
categories: []
created_at: 2025-06-11T21:42:44.885Z
updated_at: 2025-06-11T21:42:44.885Z
url: https://n8n.io/workflows/4884
scraped_at: 2025-06-19 22:07:56
description:
  This workflow turns trending news into thoughtful first-person commentary for platforms like LinkedIn. It uses Dumpling AI’s News Search and Scraping APIs to find and extract article content, then feeds the cleaned text to GPT-4o to write personalized insights. The final output is saved back to Google Sheets as a draft for easy review or posting.

  ✅ What this workflow does

  Triggers daily using a Schedule node.
  Fetches a list of content topics from a Google Sheet.
  Uses Dumpling AI to search for relevant news articles based on each topic.
  Scrapes the article content with Dumpling AI’s /scrape endpoint.
  Cleans and aggregates the article content using a Code node.
  Generates first-person commentary with GPT-4o tailored for LinkedIn.
  Appends the generated post back to the Google Sheet next to its topic.

  🧩 Nodes in this workflow

  Schedule Trigger**: Starts the workflow daily.
  Google Sheets (Read Topics)**: Pulls topic rows that don’t have a generated commentary yet.
  Split In Batches**: Processes each topic one at a time.
  Wait**: Adds a delay to manage API limits.
  HTTP Request (Search News)**: Uses Dumpling AI's /search-news to find relevant articles for the topic.
  Split Out**: Iterates over the list of article results.
  HTTP Request (Scrape Article)**: Extracts the full article text using Dumpling AI’s /scrape.
  Aggregate**: Collects and merges article content fields.
  Code (Clean Article)**: Strips links, formatting, and irrelevant text.
  OpenAI (GPT-4o)**: Generates a short, first-person LinkedIn post-style commentary using a custom prompt.
  Google Sheets (Write Back)**: Appends the final output next to the original topic in the sheet.

  🧑‍💼 Who is this for?

  Founders, content creators, marketers, or **agency teams looking to maintain an active presence on LinkedIn or newsletters by sharing smart takes on industry trends.

  💡 What problem does this solve?

  Most people want to comment on current events but don't have the time to summarize articles or write well-structured posts. This automation saves hours of manual work by:
  Finding the right article.
  Extracting and cleaning the content.
  Writing it in a natural, first-person voice using AI.

  ⚙️ What you need to use this:

  A Google Sheet with at least two columns: topic and generated commentary.
  A Dumpling AI API Key with access to the /search-news and /scrape endpoints.
  An OpenAI GPT-4o connection.

nodes_used:
  ["n8n-nodes-base.googleSheets","n8n-nodes-base.httpRequest","n8n-nodes-base.code","@n8n/n8n-nodes-langchain.openAi"]

workflow_json:
  {"id":"M8PPLx0heLyG4kmQ","meta":{"instanceId":"a1ae5c8dc6c65e674f9c3947d083abcc749ef2546dff9f4ff01de4d6a36ebfe6","templateCredsSetupCompleted":true},"name":"Auto-Generate AI News Commentary with Dumpling AI and GPT-4o","tags":[],"nodes":[{"id":"35ce9dd5-cc21-4cf9-a7ac-6cc9718fa86a","name":"No Operation, do nothing","type":"n8n-nodes-base.noOp","position":[-420,-160],"parameters":{},"typeVersion":1},{"id":"c572b2c3-9e72-4d7d-89f9-364aa5c00f79","name":"Run on Schedule (Daily)","type":"n8n-nodes-base.scheduleTrigger","position":[-1080,-60],"parameters":{"rule":{"interval":[{}]}},"typeVersion":1.2},{"id":"412b5965-1278-4748-8d77-4c85d9eb9cff","name":"Fetch Topics with Empty Commentary","type":"n8n-nodes-base.googleSheets","position":[-860,-60],"parameters":{"options":{"returnFirstMatch":true},"filtersUI":{"values":[{"lookupColumn":"generated commentary"}]},"sheetName":{"__rl":true,"mode":"list","value":"","cachedResultUrl":"https://docs.google.com/spreadsheets/d/1rCXEWnIZd6cKIqsVRRynHEygQTztJM76rm4HM8Xlqbw/edit#gid=0","cachedResultName":"Sheet1"},"documentId":{"__rl":true,"mode":"list","value":"","cachedResultUrl":"https://docs.google.com/spreadsheets/d/1rCXEWnIZd6cKIqsVRRynHEygQTztJM76rm4HM8Xlqbw/edit?usp=drivesdk","cachedResultName":"News articles"}},"credentials":{"googleSheetsOAuth2Api":{"id":"GaJqJHuS5mQxap7q","name":"Google Sheets account"}},"typeVersion":4.6},{"id":"c04e7811-4e30-4e68-8342-55d79669072e","name":"Loop Through Each Topic","type":"n8n-nodes-base.splitInBatches","position":[-640,-60],"parameters":{"options":{}},"typeVersion":3},{"id":"435798d5-59b3-4379-831a-9b8801a99f38","name":"Wait Before News Search","type":"n8n-nodes-base.wait","position":[-420,40],"webhookId":"2f67769b-0637-4b7e-9324-f8ba9520969c","parameters":{},"typeVersion":1.1},{"id":"f0098d01-fa3b-40e8-aeeb-e9dd31606ddb","name":"Search News with Dumpling AI","type":"n8n-nodes-base.httpRequest","position":[-200,40],"parameters":{"url":"https://app.dumplingai.com/api/v1/search-news","method":"POST","options":{},"jsonBody":"={\n  \"query\": \"{{ $json.Topic }}\",\n  \"country\": \"US\",\n  \"page\": 3,\n  \"language\": \"en\"\n}\n","sendBody":true,"specifyBody":"json","authentication":"genericCredentialType","genericAuthType":"httpHeaderAuth"},"credentials":{"httpHeaderAuth":{"id":"RLFzAcGRepr5eXZB","name":"Dumpling AI-n8n"}},"typeVersion":4.2},{"id":"43862942-4e19-4856-a3b0-2546d8a7a462","name":"Split Returned News Articles","type":"n8n-nodes-base.splitOut","position":[20,40],"parameters":{"options":{},"fieldToSplitOut":"news"},"typeVersion":1},{"id":"9b45eb16-66b1-45bc-b4a3-5ad46696b295","name":"Scrape Article Content with Dumpling AI","type":"n8n-nodes-base.httpRequest","position":[240,40],"parameters":{"url":"https://app.dumplingai.com/api/v1/scrape","method":"POST","options":{},"jsonBody":"={\n  \"url\": \"{{ $json.link}}\"\n}\n","sendBody":true,"specifyBody":"json","authentication":"genericCredentialType","genericAuthType":"httpHeaderAuth"},"credentials":{"httpHeaderAuth":{"id":"RLFzAcGRepr5eXZB","name":"Dumpling AI-n8n"}},"typeVersion":4.2},{"id":"ffa392af-04d1-4c6a-a05e-f63f765d7eca","name":"Aggregate Scraped Article Content","type":"n8n-nodes-base.aggregate","position":[460,40],"parameters":{"options":{},"fieldsToAggregate":{"fieldToAggregate":[{"fieldToAggregate":"content"}]}},"typeVersion":1},{"id":"5204f7c9-e5f8-4594-9428-4b46e92ba81d","name":"Clean Article Content","type":"n8n-nodes-base.code","position":[680,40],"parameters":{"jsCode":"let rawContent = $input.first().json.content;\n\n// If content is not a string, try to stringify it\nif (typeof rawContent !== 'string') {\n  rawContent = JSON.stringify(rawContent);\n}\n\nconst cleaned = rawContent\n  .replace(/https?:\\/\\/[^\\s]+/g, '')           // Remove full URLs\n  .replace(/www\\.[^\\s]+/g, '')                  // Remove www links\n  .replace(/\\[([^\\]]+)\\]\\(([^)]+)\\)/g, '$1')    // Remove markdown links\n  .replace(/<a[^>]*>(.*?)<\\/a>/gi, '$1')        // Remove HTML anchor tags\n  .replace(/\\s{2,}/g, ' ')                      // Remove extra spaces\n  .trim();\n\nreturn [{\n  json: {\n    cleaned_content: cleaned\n  }\n}];\n"},"typeVersion":2},{"id":"04fe4476-023b-49a5-8e72-0d251d78ae1a","name":"Generate LinkedIn Commentary (GPT-4o)","type":"@n8n/n8n-nodes-langchain.openAi","position":[900,40],"parameters":{"modelId":{"__rl":true,"mode":"list","value":"chatgpt-4o-latest","cachedResultName":"CHATGPT-4O-LATEST"},"options":{},"messages":{"values":[{"content":"=You are a thought leader on LinkedIn. I will provide you with a news articles related to {{ $('Fetch Topics with Empty Commentary').item.json.Topic }}, and you will write a personal commentary in a confident, insightful, first-person voice.\n\nYour response should:\n- Start with a strong personal opinion or observation\n- Briefly connect the news to real-world trends or implications\n- Mention how this relates to your work, experience, or thinking\n- Use a human tone, no robotic phrasing or generic statements\n- End with a question or call to action to invite engagement\n\nKeep it under 600 characters. Avoid buzzwords or fluff. Be authentic.\n\nHere are the news articles:{{ $json.cleaned_content }}\n"}]}},"credentials":{"openAiApi":{"id":"dd8NvMC6rvx8RITo","name":"OpenAi account 2"}},"typeVersion":1.8},{"id":"ecc25fb7-52c0-4b89-94eb-06088b92e095","name":"Append Commentary Back to Sheet","type":"n8n-nodes-base.googleSheets","position":[1260,40],"parameters":{"columns":{"value":{"Topic":"={{ $('Fetch Topics with Empty Commentary').item.json.Topic }}","generated commentary":"={{ $json.message.content }}"},"schema":[{"id":"Topic","type":"string","display":true,"removed":false,"required":false,"displayName":"Topic","defaultMatch":false,"canBeUsedToMatch":true},{"id":"generated commentary","type":"string","display":true,"required":false,"displayName":"generated commentary","defaultMatch":false,"canBeUsedToMatch":true},{"id":"Image","type":"string","display":true,"removed":true,"required":false,"displayName":"Image","defaultMatch":false,"canBeUsedToMatch":true}],"mappingMode":"defineBelow","matchingColumns":["Topic"],"attemptToConvertTypes":false,"convertFieldsToString":false},"options":{},"operation":"appendOrUpdate","sheetName":{"__rl":true,"mode":"list","value":"","cachedResultUrl":"https://docs.google.com/spreadsheets/d/1rCXEWnIZd6cKIqsVRRynHEygQTztJM76rm4HM8Xlqbw/edit#gid=0","cachedResultName":"Sheet1"},"documentId":{"__rl":true,"mode":"list","value":"","cachedResultUrl":"https://docs.google.com/spreadsheets/d/1rCXEWnIZd6cKIqsVRRynHEygQTztJM76rm4HM8Xlqbw/edit?usp=drivesdk","cachedResultName":"News articles"}},"credentials":{"googleSheetsOAuth2Api":{"id":"GaJqJHuS5mQxap7q","name":"Google Sheets account"}},"typeVersion":4.6},{"id":"62e5001b-0aa9-40eb-bf65-6ca6ff1e3b32","name":"Sticky Note","type":"n8n-nodes-base.stickyNote","position":[-1100,-260],"parameters":{"width":1100,"height":340,"content":"### 📥 Fetch Topics and Search News via Dumpling AI\n\nThis section starts with a scheduled trigger. It pulls entries from a Google Sheet where the “generated commentary” is empty, meaning the topic hasn’t been processed. Each topic is looped individually. A short wait is applied to manage rate limits. Dumpling AI’s `/search-news` endpoint is then triggered to retrieve relevant articles based on the topic keyword.\n"},"typeVersion":1},{"id":"3c3904a5-90d3-486a-8f69-bb6b33b5d234","name":"Sticky Note1","type":"n8n-nodes-base.stickyNote","position":[240,-280],"parameters":{"width":1120,"height":360,"content":"### ✍️ Scrape Articles, Clean Text, Generate Commentary, and Append\n\nEach article is split out and scraped using Dumpling AI’s `/scrape` endpoint to get full content. The aggregated content is cleaned via a Code node, removing links and excess formatting. GPT-4o generates a LinkedIn-style first-person commentary using this cleaned content. The final output is saved back to the Google Sheet under the “generated commentary” field.\n"},"typeVersion":1}],"active":false,"pinData":{},"settings":{"executionOrder":"v1"},"versionId":"2f3ec71f-7ba1-46bf-bbd3-633a9e526a47","connections":{"Clean Article Content":{"main":[[{"node":"Generate LinkedIn Commentary (GPT-4o)","type":"main","index":0}]]},"Loop Through Each Topic":{"main":[[{"node":"No Operation, do nothing","type":"main","index":0}],[{"node":"Wait Before News Search","type":"main","index":0}]]},"Run on Schedule (Daily)":{"main":[[{"node":"Fetch Topics with Empty Commentary","type":"main","index":0}]]},"Wait Before News Search":{"main":[[{"node":"Search News with Dumpling AI","type":"main","index":0}]]},"Search News with Dumpling AI":{"main":[[{"node":"Split Returned News Articles","type":"main","index":0}]]},"Split Returned News Articles":{"main":[[{"node":"Scrape Article Content with Dumpling AI","type":"main","index":0}]]},"Append Commentary Back to Sheet":{"main":[[{"node":"Loop Through Each Topic","type":"main","index":0}]]},"Aggregate Scraped Article Content":{"main":[[{"node":"Clean Article Content","type":"main","index":0}]]},"Fetch Topics with Empty Commentary":{"main":[[{"node":"Loop Through Each Topic","type":"main","index":0}]]},"Generate LinkedIn Commentary (GPT-4o)":{"main":[[{"node":"Append Commentary Back to Sheet","type":"main","index":0}]]},"Scrape Article Content with Dumpling AI":{"main":[[{"node":"Aggregate Scraped Article Content","type":"main","index":0}]]}}}


name: AI Icebreaker Builder: Scrape Sites with Dumpling AI and Save to Airtable
author_name: Yang
author_username: yang
nodes_used: ["n8n-nodes-base.airtable","n8n-nodes-base.httpRequest","@n8n/n8n-nodes-langchain.openAi"]
categories: []
created_at: 2025-06-11T21:52:55.601Z
updated_at: 2025-06-11T21:52:55.601Z
url: https://n8n.io/workflows/4885
scraped_at: 2025-06-19 22:07:56
description:
  Who is this for?

  This workflow is ideal for sales teams, marketers, and virtual assistants who manage outbound campaigns and want to improve their cold outreach personalization. It helps automate the research and writing process for each lead, saving time while improving quality.

  What problem is this workflow solving?

  Cold outreach often lacks personalization because manually reviewing each lead's website takes time. This workflow eliminates that bottleneck by using AI to auto-generate personalized icebreakers, summaries, and outreach emails based on a lead’s website—without human research.

  What this workflow does

  This n8n workflow runs on a schedule and pulls leads from Airtable who don't yet have an "Ice breaker" field filled out. For each lead, it does the following:

  Trigger: Scheduled daily via the Run Daily to Process New Leads node.
  Search Airtable: Finds leads in Airtable where the Ice breaker field is empty using the Search Cold Leads Without Icebreaker node.
  Split in Batches: Iterates through each lead one by one using Loop Through Each Lead.
  Rate Limiting: Waits briefly before each request using Wait Before Making Request to avoid rate limits.
  Scrape Website: Sends each lead’s website to Dumpling AI's /scrape endpoint via the Scrape Lead Website with Dumpling AI HTTP request.
  Generate AI Copy: Sends the scraped content to GPT-4o using the Generate Icebreaker, Summary & Email (GPT-4o) node. It asks the LLM to create:
     A short personalized icebreaker
     A 2–3 line website summary
     A short email body for cold outreach
  Save Results: Updates the original Airtable record with the generated content using the Save AI Output Back to Airtable node.
  Sticky Note: Provides an overview of the workflow and usage instructions for future editors or collaborators.

  This loop continues for all leads found, updating Airtable with fresh AI-generated outreach content.

  Integration Requirements

  Airtable (Personal Access Token)
  Dumpling AI API Key (Header Auth)
  OpenAI (GPT-4o)

workflow_json:
  {"id":"FQ3d3ucbw3NXgnUo","meta":{"instanceId":"a1ae5c8dc6c65e674f9c3947d083abcc749ef2546dff9f4ff01de4d6a36ebfe6","templateCredsSetupCompleted":true},"name":"AI Icebreaker Builder: Scrape Sites with Dumpling AI and Save to Airtable","tags":[],"nodes":[{"id":"40c158ab-6e9c-4296-873c-c879714b65a6","name":"No Operation, do nothing","type":"n8n-nodes-base.noOp","position":[100,-140],"parameters":{},"typeVersion":1},{"id":"d63720a5-9785-45d1-a8ba-a9c961031095","name":"Run Daily to Process New Leads","type":"n8n-nodes-base.scheduleTrigger","position":[-560,60],"parameters":{"rule":{"interval":[{}]}},"typeVersion":1.2},{"id":"e5804c37-2a8d-4574-852a-f885c6941e31","name":"Search Cold Leads Without Icebreaker","type":"n8n-nodes-base.airtable","position":[-340,60],"parameters":{"base":{"__rl":true,"mode":"list","value":"","cachedResultUrl":"https://airtable.com/appPSvSKdA6075xJC","cachedResultName":"Testing n8n"},"table":{"__rl":true,"mode":"list","value":"","cachedResultUrl":"https://airtable.com/appPSvSKdA6075xJC/tbl1KgkRF2EEMc2Fq","cachedResultName":"cold leads"},"options":{},"operation":"search","filterByFormula":"{Ice breaker} = ''"},"credentials":{"airtableTokenApi":{"id":"H8PVkBgUPCcUhhRC","name":"Airtable Personal Access Token account"}},"typeVersion":2.1},{"id":"839fd20b-5a5d-4419-85b0-9b82223c8b95","name":"Loop Through Each Lead","type":"n8n-nodes-base.splitInBatches","position":[-120,60],"parameters":{"options":{}},"typeVersion":3},{"id":"78b197e2-6028-49a0-9100-5cc44838a9cd","name":"Wait Before Making Request","type":"n8n-nodes-base.wait","position":[100,60],"webhookId":"d6b29fad-724c-49ad-93ed-6ebfe17d3a4c","parameters":{},"typeVersion":1.1},{"id":"de96d330-006b-4410-8b75-83c3b9658045","name":"Scrape Lead Website with Dumpling AI","type":"n8n-nodes-base.httpRequest","position":[320,60],"parameters":{"url":"https://app.dumplingai.com/api/v1/scrape","method":"POST","options":{},"jsonBody":"={\n  \"url\": \"{{ $json.Website }}\"\n}\n","sendBody":true,"specifyBody":"json","authentication":"genericCredentialType","genericAuthType":"httpHeaderAuth"},"credentials":{"httpHeaderAuth":{"id":"RLFzAcGRepr5eXZB","name":"Dumpling AI-n8n"}},"typeVersion":4.2},{"id":"5d5675b6-4245-4562-a9d2-7cf54fe20b75","name":"Generate Icebreaker, Summary & Email (GPT-4o)","type":"@n8n/n8n-nodes-langchain.openAi","position":[540,60],"parameters":{"modelId":{"__rl":true,"mode":"list","value":"chatgpt-4o-latest","cachedResultName":"CHATGPT-4O-LATEST"},"options":{},"messages":{"values":[{"role":"system","content":"=You are a smart assistant helping write personalized outreach. Below is content scraped from a lead’s website, along with the lead’s name.\n\nUsing this, please generate the following:\n\nIcebreaker: A short, friendly opening line that shows we took time to look at their business.\n\nEmail Body: A short cold outreach email that introduces what we do and how we can help, referencing their business or needs where relevant.\n\nWebsite Summary: A short summary (2 or 3 lines) of what their website is about, written in plain English.\n\nPlease return your response in this JSON format:\n\n{\n  \"icebreaker\": \"string\",\n  \"email_body\": \"string\",\n  \"website_summary\": \"string\"\n}"},{"content":"=Lead Name: {{ $('Search Cold Leads Without Icebreaker').item.json.Name }}\nScraped Website Content:{{ $json.content }}"}]},"jsonOutput":true},"credentials":{"openAiApi":{"id":"dd8NvMC6rvx8RITo","name":"OpenAi account 2"}},"typeVersion":1.8},{"id":"05a2b673-8e2a-41cf-9a01-eb19b2e584ea","name":"Save AI Output Back to Airtable","type":"n8n-nodes-base.airtable","position":[960,60],"parameters":{"base":{"__rl":true,"mode":"list","value":"","cachedResultUrl":"https://airtable.com/appPSvSKdA6075xJC","cachedResultName":"Testing n8n"},"table":{"__rl":true,"mode":"list","value":"","cachedResultUrl":"https://airtable.com/appPSvSKdA6075xJC/tbl1KgkRF2EEMc2Fq","cachedResultName":"cold leads"},"columns":{"value":{"id":"={{ $('Search Cold Leads Without Icebreaker').item.json.id }}","Name":"={{ $('Search Cold Leads Without Icebreaker').item.json.Name }}","Phone":"={{ $('Search Cold Leads Without Icebreaker').item.json.Phone }}","Website":"={{ $('Search Cold Leads Without Icebreaker').item.json.Website }}","Email body":"={{ $json.message.content.email_body }}","Ice breaker":"={{ $json.message.content.icebreaker }}","website summary":"={{ $json.message.content.website_summary }}"},"schema":[{"id":"id","type":"string","display":true,"removed":false,"readOnly":true,"required":false,"displayName":"id","defaultMatch":true},{"id":"Name","type":"string","display":true,"removed":false,"readOnly":false,"required":false,"displayName":"Name","defaultMatch":false,"canBeUsedToMatch":true},{"id":"Website","type":"string","display":true,"removed":false,"readOnly":false,"required":false,"displayName":"Website","defaultMatch":false,"canBeUsedToMatch":true},{"id":"Phone","type":"string","display":true,"removed":false,"readOnly":false,"required":false,"displayName":"Phone","defaultMatch":false,"canBeUsedToMatch":true},{"id":"Ice breaker","type":"string","display":true,"removed":false,"readOnly":false,"required":false,"displayName":"Ice breaker","defaultMatch":false,"canBeUsedToMatch":true},{"id":"website summary","type":"string","display":true,"removed":false,"readOnly":false,"required":false,"displayName":"website summary","defaultMatch":false,"canBeUsedToMatch":true},{"id":"Email body","type":"string","display":true,"removed":false,"readOnly":false,"required":false,"displayName":"Email body","defaultMatch":false,"canBeUsedToMatch":true}],"mappingMode":"defineBelow","matchingColumns":["id"],"attemptToConvertTypes":false,"convertFieldsToString":false},"options":{},"operation":"update"},"credentials":{"airtableTokenApi":{"id":"H8PVkBgUPCcUhhRC","name":"Airtable Personal Access Token account"}},"typeVersion":2.1},{"id":"cd8dac4b-6575-45fc-95fd-3052b244b0a2","name":"Sticky Note","type":"n8n-nodes-base.stickyNote","position":[-640,-260],"parameters":{"width":810,"height":480,"content":"### 🔄 Automated Cold Email Writing from Lead Websites\n\nThis workflow runs on a schedule and pulls new cold leads from Airtable that have no \"Ice breaker\" yet. For each lead, it waits briefly to prevent API overuse, then sends the lead’s website URL to Dumpling AI's scraping endpoint.\n\nThe scraped content is passed to GPT-4o to generate:\n- A personalized icebreaker\n- A website summary\n- A tailored cold email body\n\nFinally, all generated results are saved back into Airtable for each lead record.\n"},"typeVersion":1}],"active":false,"pinData":{},"settings":{"executionOrder":"v1"},"versionId":"710a2065-24ec-4681-aaa4-43028ec8acee","connections":{"Loop Through Each Lead":{"main":[[{"node":"No Operation, do nothing","type":"main","index":0}],[{"node":"Wait Before Making Request","type":"main","index":0}]]},"Wait Before Making Request":{"main":[[{"node":"Scrape Lead Website with Dumpling AI","type":"main","index":0}]]},"Run Daily to Process New Leads":{"main":[[{"node":"Search Cold Leads Without Icebreaker","type":"main","index":0}]]},"Save AI Output Back to Airtable":{"main":[[{"node":"Loop Through Each Lead","type":"main","index":0}]]},"Scrape Lead Website with Dumpling AI":{"main":[[{"node":"Generate Icebreaker, Summary & Email (GPT-4o)","type":"main","index":0}]]},"Search Cold Leads Without Icebreaker":{"main":[[{"node":"Loop Through Each Lead","type":"main","index":0}]]},"Generate Icebreaker, Summary & Email (GPT-4o)":{"main":[[{"node":"Save AI Output Back to Airtable","type":"main","index":0}]]}}}


name: Auto-Create Podcast from YouTube Transcript using Dumpling AI and GPT-4o
author_name: Yang
author_username: yang
nodes_used: ["n8n-nodes-base.airtable","n8n-nodes-base.httpRequest","@n8n/n8n-nodes-langchain.openAi"]
categories: []
created_at: 2025-06-11T22:06:28.989Z
updated_at: 2025-06-11T22:06:28.989Z
url: https://n8n.io/workflows/4887
scraped_at: 2025-06-19 22:07:56
description:
  🔎 Who is this for?
  This workflow is designed for podcast creators, content marketers, and video producers who want to convert YouTube videos into podcast-ready scripts. It's perfect for anyone repurposing long-form content to reach audio-first audiences without manual effort.

  🧠 What problem is this workflow solving?
  Creating podcast scripts from YouTube videos manually is time-consuming. This workflow automates the process by pulling transcripts, cleaning the text, organizing the dialogue, summarizing the key points, and saving everything in one place. It removes the need for manual transcription, formatting, and structuring.

  ⚙️ What this workflow does

  This workflow uses Dumpling AI and GPT-4o to automate the transformation of YouTube video transcripts into polished podcast scripts. Here's how it works:

  RSS Feed Trigger
     Monitors a YouTube RSS feed for new video uploads. When a new video is detected, the workflow begins automatically.

  Get YouTube Transcript (Dumpling AI)
     Uses Dumpling AI's get-youtube-transcript endpoint to extract the full transcript from the video URL.

  Generate Podcast Script with GPT-4o
     GPT-4o receives the transcript and generates a structured JSON output including:
       Cleaned transcript with filler words removed
       Speaker labels for clarity
       A short, engaging podcast title
       A concise summary of the episode

  Save to Airtable
     The structured data (title, summary, cleaned transcript) is saved to Airtable for easy review, editing, or publishing.

  This automation is an ideal workflow for repurposing video content into audio-friendly formats, cutting down production time while increasing content output across platforms.

workflow_json:
  {"id":"I4j3HnFGPa5UWkIO","meta":{"instanceId":"a1ae5c8dc6c65e674f9c3947d083abcc749ef2546dff9f4ff01de4d6a36ebfe6","templateCredsSetupCompleted":true},"name":"Auto-Create Podcast from YouTube Video Transcript using Dumpling AI and GPT-4o","tags":[],"nodes":[{"id":"d95bcf10-2bb4-4bfd-a8ad-4128a792deb8","name":" Watch for New YouTube Video via RSS","type":"n8n-nodes-base.rssFeedReadTrigger","position":[-500,-20],"parameters":{"feedUrl":"https://rss.app/feeds/Vw076Uzh7bIinpci.xml","pollTimes":{"item":[{"mode":"everyMinute"}]}},"typeVersion":1},{"id":"a5492dab-f400-48d9-abd7-6c832d9d6816","name":"Get Transcript from YouTube Video using Dumpling AI","type":"n8n-nodes-base.httpRequest","position":[-280,-20],"parameters":{"url":"https://app.dumplingai.com/api/v1/get-youtube-transcript","method":"POST","options":{},"jsonBody":"={\n  \"videoUrl\": \"{{ $json.link }}\",\n  \"preferredLanguage\": \"en\"\n}\n","sendBody":true,"specifyBody":"json","authentication":"genericCredentialType","genericAuthType":"httpHeaderAuth"},"credentials":{"httpHeaderAuth":{"id":"RLFzAcGRepr5eXZB","name":"Dumpling AI-n8n"}},"typeVersion":4.2},{"id":"bce2bb18-c9ee-4165-ac27-5d300e354c7e","name":"Transform Transcript into Podcast Script using GPT-4o","type":"@n8n/n8n-nodes-langchain.openAi","position":[-60,-20],"parameters":{"modelId":{"__rl":true,"mode":"list","value":"chatgpt-4o-latest","cachedResultName":"CHATGPT-4O-LATEST"},"options":{},"messages":{"values":[{"role":"system","content":"=Instructions:\nYou are a professional transcript editor and podcast summarizer. For the transcript below, complete these tasks:\n\nLabel each speaker (e.g., Speaker 1:) and remove all filler words such as \"um,\" \"uh,\" \"you know,\" \"like,\" \"basically,\" \"actually,\" \"so.\"\n\nCombine the cleaned speaker labels and their text into one single string, clearly formatted.\n\nSummarize the key points of the conversation in 2–4 concise sentences.\n\nExtract or infer a short, relevant title based on the content.\n\nReturn your response strictly in the following JSON format:\n{\n  \"title\": \"Relevant podcast title here\",\n  \"cleaned_transcript\": \"Speaker 1: Cleaned text. Speaker 2: Cleaned text. (Continue in this format.)\",\n  \"summary\": \"Concise summary of the key points here.\"\n}"},{"content":"=\nHere’s the transcript:{{ $json.transcript }}"}]},"jsonOutput":true},"credentials":{"openAiApi":{"id":"dd8NvMC6rvx8RITo","name":"OpenAi account 2"}},"typeVersion":1.8},{"id":"7782b5a6-c842-41be-a5c5-9eaa28a0abd0","name":"Save Podcast Script and Metadata to Airtable","type":"n8n-nodes-base.airtable","position":[300,-20],"parameters":{"base":{"__rl":true,"mode":"list","value":"","cachedResultUrl":"https://airtable.com/appPSvSKdA6075xJC","cachedResultName":"Testing n8n"},"table":{"__rl":true,"mode":"list","value":"","cachedResultUrl":"https://airtable.com/appPSvSKdA6075xJC/tbl4MDOqdNZweqXU9","cachedResultName":"podcast"},"columns":{"value":{"Title":"={{ $json.message.content.title }}","summary":"={{ $json.message.content.summary }}","podcast transcript":"={{ $json.message.content.cleaned_transcript }}"},"schema":[{"id":"Title","type":"string","display":true,"removed":false,"readOnly":false,"required":false,"displayName":"Title","defaultMatch":false,"canBeUsedToMatch":true},{"id":"podcast transcript","type":"string","display":true,"removed":false,"readOnly":false,"required":false,"displayName":"podcast transcript","defaultMatch":false,"canBeUsedToMatch":true},{"id":"summary","type":"string","display":true,"removed":false,"readOnly":false,"required":false,"displayName":"summary","defaultMatch":false,"canBeUsedToMatch":true}],"mappingMode":"defineBelow","matchingColumns":[],"attemptToConvertTypes":false,"convertFieldsToString":false},"options":{},"operation":"create"},"credentials":{"airtableTokenApi":{"id":"H8PVkBgUPCcUhhRC","name":"Airtable Personal Access Token account"}},"typeVersion":2.1},{"id":"af143efd-be64-48fc-a405-173575289ed3","name":"Sticky Note","type":"n8n-nodes-base.stickyNote","position":[-500,-220],"parameters":{"width":640,"height":280,"content":"### 🎙️ Auto-Create Podcast Script from YouTube Videos\n\nThis workflow starts by monitoring a YouTube RSS feed for new uploads. Once a new video is detected, Dumpling AI extracts the full transcript. GPT-4o then converts that transcript into a well-formatted podcast script, ensuring it’s clean, structured, and engaging. The final script along with the video title and summary is saved into Airtable, where it can be reviewed, edited, or used to produce an actual podcast episode.\n\nIdeal for creators repurposing video content into audio format.\n"},"typeVersion":1}],"active":false,"pinData":{},"settings":{"executionOrder":"v1"},"versionId":"0c39768f-93c9-42d7-8b9f-ca4e0ede2312","connections":{" Watch for New YouTube Video via RSS":{"main":[[{"node":"Get Transcript from YouTube Video using Dumpling AI","type":"main","index":0}]]},"Get Transcript from YouTube Video using Dumpling AI":{"main":[[{"node":"Transform Transcript into Podcast Script using GPT-4o","type":"main","index":0}]]},"Transform Transcript into Podcast Script using GPT-4o":{"main":[[{"node":"Save Podcast Script and Metadata to Airtable","type":"main","index":0}]]}}}


name: Voice-Powered Marketing Assistant with ElevenLabs, OpenAI & Content Generation
author_name: David Olusola
author_username: dae221
categories: []
created_at: 2025-06-12T00:20:50.025Z
updated_at: 2025-06-12T00:20:50.025Z
url: https://n8n.io/workflows/4888
scraped_at: 2025-06-19 22:07:56
description:
  🧠 Gwen – The AI Voice Marketing Agent
  Gwen is your intelligent voice-powered marketing assistant built in n8n. She combines the power of OpenAI, ElevenLabs, and automation workflows to handle content creation, image generation, and voice delivery — all from a single agent interface.

  This template shows a graphical illustration of how Gwen will work with subworkflows. These subworkflows are modular placeholders and need to be linked into Gwen for full deployment.

  ✨ What Gwen Can Do
  📝 Generate Voice-Optimized Blog Posts
  Tailored for your target audience with engaging intros, real-time research, and polished structure.
  🖼️ Create AI-Generated Visuals
  From simple concepts to detailed image prompts and Google Drive uploads.
  🧑‍🎨 Edit Images On Demand
  Modify past images with a few words — powered by OpenAI's image editing API.
  🔍 Search Image Database
  Quickly find past content using title or intent.
  🧠 Think Tool
  Gwen uses this to clarify uncertain tasks or analyze complex requests.
  🔊 Deliver Results in Natural Voice
  With ElevenLabs, Gwen transforms all responses into human-like audio, perfect for marketing, social content, or voice interfaces.
  🛠️ Setup Instructions
  Estimated Time: 15–30 mins

  ✅ Step 1: Subworkflows

  Import These Workflows
  Blog Post, Create Image, Edit Image, Search Images
  Connect Them to Gwen
  Assign as tools inside the Gwen agent node (Langchain AI Agent in n8n).
  🎙️ Step 2: Enable ElevenLabs Voice Agent

  Sign up or log in: https://try.elevenlabs.io
  Copy your API key
  In the ElevenLabs interface, create a new tool:
  Method: POST
  URL: https://your-n8n-domain/webhook/042cc868-28b7-42a2-ab65-bc2944fc5a54
  Under Body Parameters, add:
  prompt → value type: LLM Prompt
  sessionId → value type: Dynamic variable, name: system__conversation_id
  Save and connect this tool to your ElevenLabs agent
  Run a test and check n8n execution logs to confirm Gwen’s voice integration is active
  🔐 Step 3: Credentials to Set

  OpenAI – For text and image generation
  ElevenLabs – For voice output
  Tavily – For real-time research in blog generation
  Telegram – For sending content to users
  Google Sheets – To log all outputs like blogs and images

nodes_used:
  ["n8n-nodes-base.googleSheets","n8n-nodes-base.httpRequest","n8n-nodes-base.telegram","n8n-nodes-base.googleDrive","@n8n/n8n-nodes-langchain.agent","@n8n/n8n-nodes-langchain.lmChatOpenAi","@n8n/n8n-nodes-langchain.memoryBufferWindow","@n8n/n8n-nodes-langchain.outputParserStructured","@n8n/n8n-nodes-langchain.toolWorkflow","@n8n/n8n-nodes-langchain.toolHttpRequest","@n8n/n8n-nodes-langchain.toolThink"]

workflow_json:
  {"id":"YEuoA3Cq84m057vt","meta":{"instanceId":"2000c64071c20843606b95c63795bb0797c41036047055a6586498e855b96efc"},"name":"ELEVEN LABS WITH MULTI AGENTS","tags":[],"nodes":[{"id":"130f11d3-e09a-4913-84e4-eaa0dd2964f0","name":"Webhook","type":"n8n-nodes-base.webhook","position":[-1820,440],"webhookId":"042cc868-28b7-42a2-ab65-bc2944fc5a54","parameters":{},"typeVersion":2},{"id":"7d672479-775a-4322-ac6d-dd19002a7fab","name":"Sticky Note8","type":"n8n-nodes-base.stickyNote","position":[-3020,-520],"parameters":{"content":""},"typeVersion":1},{"id":"d21ab3c4-cdbe-4622-910e-0b12d1409485","name":"ElevenLabs Setup","type":"n8n-nodes-base.stickyNote","position":[-3020,1040],"parameters":{"content":""},"typeVersion":1},{"id":"25af0cf7-9623-4d8c-82ff-d319728b4a40","name":"Create Image","type":"@n8n/n8n-nodes-langchain.toolWorkflow","position":[-1180,740],"parameters":{},"typeVersion":2.1},{"id":"062fcb06-a6d4-46ca-b5a3-03f9f4cac6c3","name":"Simple Memory","type":"@n8n/n8n-nodes-langchain.memoryBufferWindow","position":[-1460,760],"parameters":{},"typeVersion":1.3},{"id":"1bed5d7a-f88b-445d-af03-9197f3c1007a","name":"Edit Image","type":"@n8n/n8n-nodes-langchain.toolWorkflow","position":[-920,760],"parameters":{},"typeVersion":2.1},{"id":"08bdced3-7113-433b-8996-a8f3b0830792","name":"Search Images","type":"@n8n/n8n-nodes-langchain.toolWorkflow","position":[-1320,760],"parameters":{},"typeVersion":2.1},{"id":"5e385186-d38d-41c4-8178-aded256ec2e9","name":"Blog Post","type":"@n8n/n8n-nodes-langchain.toolWorkflow","position":[-1620,760],"parameters":{},"typeVersion":2.1},{"id":"9f0dcfb9-523c-4fce-b0a9-2177e8ad305d","name":"Marketing Team Agent","type":"@n8n/n8n-nodes-langchain.agent","position":[-1560,440],"parameters":{},"typeVersion":1.9},{"id":"762f673c-54aa-41e9-9414-e8331cb139c8","name":"Think","type":"@n8n/n8n-nodes-langchain.toolThink","position":[-1080,740],"parameters":{},"typeVersion":1},{"id":"b643093a-cbcf-4ebd-b628-08421735c70f","name":"OpenAI Chat Model","type":"@n8n/n8n-nodes-langchain.lmChatOpenAi","position":[-1760,740],"parameters":{},"typeVersion":1.2},{"id":"6d5de957-96ee-48de-8bd2-25e27ef6d0ed","name":"Respond to Webhook","type":"n8n-nodes-base.respondToWebhook","position":[-1120,440],"parameters":{},"typeVersion":1.4},{"id":"16c4ef2c-a1aa-40cd-aa66-482e9495a097","name":"Convert to File","type":"n8n-nodes-base.convertToFile","position":[1356,960],"parameters":{},"typeVersion":1.1},{"id":"37fc4987-50d4-4b61-a6ef-0388ea35692f","name":"Generate Image","type":"n8n-nodes-base.httpRequest","position":[1136,960],"parameters":{},"typeVersion":4.2},{"id":"3a5b7abd-a55e-428c-b86c-5e13a7d5071c","name":"Image Prompt","type":"@n8n/n8n-nodes-langchain.agent","position":[760,960],"parameters":{},"typeVersion":1.9},{"id":"a35b782f-9cea-4a22-ad54-73b61941fe4e","name":"Google Drive","type":"n8n-nodes-base.googleDrive","position":[1576,1060],"parameters":{},"typeVersion":3},{"id":"0c4d9982-0962-49a6-b493-c3599d45cf37","name":"Image Log","type":"n8n-nodes-base.googleSheets","position":[1796,1060],"parameters":{},"typeVersion":4.5},{"id":"2b8359bf-6efd-4e03-a4b7-03b0ad372dbe","name":"Sticky Note4","type":"n8n-nodes-base.stickyNote","position":[698,680],"parameters":{"content":""},"typeVersion":1},{"id":"8dd7a0fe-03f8-452c-af92-7fb9510ac0ea","name":"Send Photo","type":"n8n-nodes-base.telegram","position":[1576,860],"webhookId":"8fcbda9c-8396-41f7-8f2d-39e4ae4337c7","parameters":{},"typeVersion":1.2},{"id":"cb36b8dc-8bd7-4e82-959b-4d6909b59ae6","name":"OpenAI Chat Model1","type":"@n8n/n8n-nodes-langchain.lmChatOpenAi","position":[848,1180],"parameters":{},"typeVersion":1.2},{"id":"cb748f5e-ae93-458d-8c10-a7a4037fc56f","name":"When Executed by Another Workflow","type":"n8n-nodes-base.executeWorkflowTrigger","position":[80,1820],"parameters":{},"typeVersion":1.1},{"id":"d1ba7187-e428-4c32-9041-0ef1e3d213d3","name":"Upload Image","type":"n8n-nodes-base.googleDrive","position":[1420,1520],"parameters":{},"typeVersion":3},{"id":"83cdd5e7-3d8d-4b64-8b98-e009e12325a9","name":"Sticky Note1","type":"n8n-nodes-base.stickyNote","position":[428,1060],"parameters":{"content":""},"typeVersion":1},{"id":"1dac3089-7593-4ae8-9ac8-d3b24f50b24d","name":"Download","type":"n8n-nodes-base.googleDrive","position":[760,1420],"parameters":{},"typeVersion":3},{"id":"9e6ed86b-956d-4465-acd2-800b663ca868","name":"Edit Image1","type":"n8n-nodes-base.httpRequest","position":[980,1420],"parameters":{},"typeVersion":4.2},{"id":"c49919d7-9548-4ef6-8697-180dc5471788","name":"Convert to File1","type":"n8n-nodes-base.convertToFile","position":[1200,1420],"parameters":{},"typeVersion":1.1},{"id":"abbc8451-6365-4d6f-8801-e511f3cf4d1c","name":"Image Log1","type":"n8n-nodes-base.googleSheets","position":[1640,1520],"parameters":{},"typeVersion":4.5},{"id":"79324f1a-272d-4de4-b415-1fdadcf5f8aa","name":"Send Photo1","type":"n8n-nodes-base.telegram","position":[1420,1320],"webhookId":"85dc0064-e5c5-45a9-91a5-60e5b2bc4f1e","parameters":{},"typeVersion":1.2},{"id":"2ef66da8-4df4-4d98-ae00-9e9d78c69940","name":"Tavily","type":"@n8n/n8n-nodes-langchain.toolHttpRequest","position":[908,2000],"parameters":{},"typeVersion":1.1},{"id":"7c192389-5203-49c8-821d-d6b2ea18f610","name":"Image Prompt Agent","type":"@n8n/n8n-nodes-langchain.agent","position":[1136,1780],"parameters":{},"typeVersion":1.9},{"id":"8d1612d2-6216-4cd7-9b05-e1e31c72dc09","name":"Convert to Binary","type":"n8n-nodes-base.convertToFile","position":[1732,1880],"parameters":{},"typeVersion":1.1},{"id":"98fa6795-d31a-49e2-9440-64dc415c7ba3","name":"Sticky Note","type":"n8n-nodes-base.stickyNote","position":[200,1460],"parameters":{"content":""},"typeVersion":1},{"id":"0a61fdec-b42d-4e14-98a4-6a679773d45e","name":"Sticky Note2","type":"n8n-nodes-base.stickyNote","position":[698,1900],"parameters":{"content":""},"typeVersion":1},{"id":"070ebd2b-08ea-4020-b321-3a7d2892e7cc","name":"Blog Post Agent","type":"@n8n/n8n-nodes-langchain.agent","position":[760,1780],"parameters":{},"typeVersion":1.9},{"id":"3cf78814-14ba-477d-96f9-ff2e84198778","name":"Image & Title","type":"@n8n/n8n-nodes-langchain.outputParserStructured","position":[1224,2000],"parameters":{},"typeVersion":1.2},{"id":"b7790843-68e1-4e77-a537-be9cba0c8c97","name":"Sticky Note3","type":"n8n-nodes-base.stickyNote","position":[1104,1900],"parameters":{"content":""},"typeVersion":1},{"id":"7b853910-8415-4d14-8075-ad2d336f9ec8","name":"Send Blog","type":"n8n-nodes-base.telegram","position":[2172,1780],"webhookId":"94fa70af-f2fc-4c05-8fa1-d9f55637485f","parameters":{},"typeVersion":1.2},{"id":"0992b8b3-d481-407d-8979-e1a8719c254c","name":"Upload","type":"n8n-nodes-base.googleDrive","position":[1952,1980],"parameters":{},"typeVersion":3},{"id":"97d5c498-24a3-447a-83c9-8683c1f1903a","name":"Generate Image1","type":"n8n-nodes-base.httpRequest","position":[1512,1880],"parameters":{},"typeVersion":4.2},{"id":"ebe5b6c3-bfbe-4c0b-aa4b-52e6d520937d","name":"Image Log2","type":"n8n-nodes-base.googleSheets","position":[2172,1980],"parameters":{},"typeVersion":4.5},{"id":"d9da5605-28b9-4b0f-b74a-65cfebdb0d17","name":"Send Photo2","type":"n8n-nodes-base.telegram","position":[1952,1780],"webhookId":"8fcbda9c-8396-41f7-8f2d-39e4ae4337c7","parameters":{},"typeVersion":1.2},{"id":"ba985b89-8be6-4e79-b56d-0f5688fdb9a2","name":"OpenAI Chat Model2","type":"@n8n/n8n-nodes-langchain.lmChatOpenAi","position":[788,2000],"parameters":{},"typeVersion":1.2},{"id":"e17ef6b0-1151-4035-b157-c282d84bcc8e","name":"Image Database","type":"n8n-nodes-base.googleSheetsTool","position":[880,2560],"parameters":{},"typeVersion":4.5},{"id":"5c383fa5-3cdf-4f83-91e4-49772496daa0","name":"Image Search Agent","type":"@n8n/n8n-nodes-langchain.agent","position":[792,2340],"parameters":{},"typeVersion":1.9},{"id":"a6614f96-f944-4e19-95c7-4b31fdafcdca","name":"Not Found","type":"n8n-nodes-base.set","position":[1420,2240],"parameters":{},"typeVersion":3.4},{"id":"810cfba2-c96a-4d16-8b78-847715e67b57","name":"Get?","type":"n8n-nodes-base.if","position":[1420,2440],"parameters":{},"typeVersion":2.2},{"id":"3acb5f29-87e6-48b3-a30f-8d29eb161230","name":"Not Found?","type":"n8n-nodes-base.if","position":[1200,2340],"parameters":{},"typeVersion":2.2},{"id":"4b351945-b69f-4631-bec7-9a4abf3b0185","name":"Download File","type":"n8n-nodes-base.googleDrive","position":[1640,2340],"parameters":{},"typeVersion":3},{"id":"2c380825-054c-4a83-a298-7bca3048aaa9","name":"Name, ID, & Link","type":"@n8n/n8n-nodes-langchain.outputParserStructured","position":[1000,2560],"parameters":{},"typeVersion":1.2},{"id":"3b04334b-6e5b-47c2-9aae-08a481e98188","name":"Edit","type":"n8n-nodes-base.set","position":[1640,2540],"parameters":{},"typeVersion":3.4},{"id":"c85da303-2572-4c66-88f2-5393d5fa8398","name":"Sticky Note7","type":"n8n-nodes-base.stickyNote","position":[1600,2500],"parameters":{"content":""},"typeVersion":1},{"id":"1822eab5-a432-476a-b0c1-516112ab05d5","name":"Sticky Note11","type":"n8n-nodes-base.stickyNote","position":[420,2240],"parameters":{"content":""},"typeVersion":1},{"id":"f7a2595e-254b-4bc7-b3df-bf7233af4a06","name":"Sticky Note14","type":"n8n-nodes-base.stickyNote","position":[1380,2200],"parameters":{"content":""},"typeVersion":1},{"id":"e80112f7-0e8a-4003-9bbd-01aff4277fd5","name":"Send Photo3","type":"n8n-nodes-base.telegram","position":[1860,2340],"webhookId":"85dc0064-e5c5-45a9-91a5-60e5b2bc4f1e","parameters":{},"typeVersion":1.2},{"id":"1b1bf2ad-fc9f-4d0d-84ab-4cc8cd98c2b5","name":"OpenAI Chat Model3","type":"@n8n/n8n-nodes-langchain.lmChatOpenAi","position":[760,2560],"parameters":{},"typeVersion":1.2},{"id":"2aab7466-16e3-4164-8282-e13b97554950","name":"Sticky Note5","type":"n8n-nodes-base.stickyNote","position":[-2000,200],"parameters":{"content":""},"typeVersion":1}],"active":false,"pinData":{},"settings":{"executionOrder":"v1"},"versionId":"7c64f75e-3f59-4abf-a9d6-58526fd9f71d","connections":{"Get?":{"main":[[{"node":"Download File","type":"main","index":0}],[{"node":"Edit","type":"main","index":0}]]},"Think":{"ai_tool":[[{"node":"Marketing Team Agent","type":"ai_tool","index":0}]]},"Tavily":{"ai_tool":[[{"node":"Blog Post Agent","type":"ai_tool","index":0}]]},"Upload":{"main":[[{"node":"Image Log2","type":"main","index":0}]]},"Webhook":{"main":[[{"node":"Marketing Team Agent","type":"main","index":0}]]},"Download":{"main":[[{"node":"Edit Image1","type":"main","index":0}]]},"Blog Post":{"ai_tool":[[{"node":"Marketing Team Agent","type":"ai_tool","index":0}]]},"Edit Image":{"ai_tool":[[{"node":"Marketing Team Agent","type":"ai_tool","index":0}]]},"Not Found?":{"main":[[{"node":"Not Found","type":"main","index":0}],[{"node":"Get?","type":"main","index":0}]]},"Edit Image1":{"main":[[{"node":"Convert to File1","type":"main","index":0}]]},"Send Photo2":{"main":[[{"node":"Send Blog","type":"main","index":0}]]},"Create Image":{"ai_tool":[[{"node":"Marketing Team Agent","type":"ai_tool","index":0}]]},"Google Drive":{"main":[[{"node":"Image Log","type":"main","index":0}]]},"Image Prompt":{"main":[[{"node":"Generate Image","type":"main","index":0}]]},"Upload Image":{"main":[[{"node":"Image Log1","type":"main","index":0}]]},"Download File":{"main":[[{"node":"Send Photo3","type":"main","index":0}]]},"Image & Title":{"ai_outputParser":[[{"node":"Image Prompt Agent","type":"ai_outputParser","index":0}]]},"Search Images":{"ai_tool":[[{"node":"Marketing Team Agent","type":"ai_tool","index":0}]]},"Simple Memory":{"ai_memory":[[{"node":"Marketing Team Agent","type":"ai_memory","index":0}]]},"Generate Image":{"main":[[{"node":"Convert to File","type":"main","index":0}]]},"Image Database":{"ai_tool":[[{"node":"Image Search Agent","type":"ai_tool","index":0}]]},"Blog Post Agent":{"main":[[{"node":"Image Prompt Agent","type":"main","index":0}]]},"Convert to File":{"main":[[{"node":"Google Drive","type":"main","index":0},{"node":"Send Photo","type":"main","index":0}]]},"Generate Image1":{"main":[[{"node":"Convert to Binary","type":"main","index":0}]]},"Convert to File1":{"main":[[{"node":"Send Photo1","type":"main","index":0},{"node":"Upload Image","type":"main","index":0}]]},"Name, ID, & Link":{"ai_outputParser":[[{"node":"Image Search Agent","type":"ai_outputParser","index":0}]]},"Convert to Binary":{"main":[[{"node":"Send Photo2","type":"main","index":0},{"node":"Upload","type":"main","index":0}]]},"OpenAI Chat Model":{"ai_languageModel":[[{"node":"Marketing Team Agent","type":"ai_languageModel","index":0}]]},"Image Prompt Agent":{"main":[[{"node":"Generate Image1","type":"main","index":0}]]},"Image Search Agent":{"main":[[{"node":"Not Found?","type":"main","index":0}]]},"OpenAI Chat Model1":{"ai_languageModel":[[{"node":"Image Prompt","type":"ai_languageModel","index":0}]]},"OpenAI Chat Model2":{"ai_languageModel":[[{"node":"Image Prompt Agent","type":"ai_languageModel","index":0},{"node":"Blog Post Agent","type":"ai_languageModel","index":0}]]},"OpenAI Chat Model3":{"ai_languageModel":[[{"node":"Image Search Agent","type":"ai_languageModel","index":0}]]},"Marketing Team Agent":{"main":[[{"node":"Respond to Webhook","type":"main","index":0}]]},"When Executed by Another Workflow":{"main":[[{"node":"Image Prompt","type":"main","index":0},{"node":"Image Search Agent","type":"main","index":0},{"node":"Blog Post Agent","type":"main","index":0},{"node":"Download","type":"main","index":0}]]}}}


name: LinkedIn Auto Message Router and Responder with Request Detection
author_name: Angel Menendez
author_username: djangelic
categories: []
created_at: 2025-06-12T00:34:35.995Z
updated_at: 2025-06-12T00:34:35.995Z
url: https://n8n.io/workflows/4889
scraped_at: 2025-06-19 22:07:56
description:
  Who is this for?

  Public-facing professionals (developer advocates, founders, marketers, content creators) who get bombarded with LinkedIn messages that aren't actually for them - support requests when you're in marketing, sales inquiries when you're a devrel, partnership pitches when you handle content, etc.

  What problem is this workflow solving?

  When you're visible online, people assume you handle everything at your company. You end up spending hours daily playing human router, forwarding messages like "How do I reset my password?" or "What's your enterprise pricing?" to the right teams. This LinkedIn automation workflow stops you from being your company's unofficial customer service representative.

  What this workflow does

  This AI-powered LinkedIn DM management workflow automatically assesses incoming LinkedIn messages and routes them intelligently:

  Automated Message Assessment: Receives inbound LinkedIn messages via UniPile and looks up sender details from both personal and company LinkedIn profiles.

  Smart Route Matching: Compares the message content against your message routing workflow table in Notion, which contains:
    Question: "How can I become an n8n ambassador?"
    Description: "Route here when a user is requesting to become an n8n ambassador. Also when they're asking how they could do more to evangelize n8n in their city, or to start organizing n8n meetups and events in their city."
    Action: "Tell the user to open the following notion page which has details on ambassador program including how to apply, as well as perks of the program: https://www.notion.so/n8n-Ambassador-Program-d883b2a130e5448faedbebe5139187ea?pvs=21"

  AI Response Generation: When a message matches an existing route, this AI assistant generates a personalized response draft based on the "Action" instructions from your routing table.

  Human-in-the-Loop Approval: Sends the draft response to Slack with approve/reject buttons, so you maintain control while saving time. Draft can be edited from within Slack on desktop and mobile.

  Automated LinkedIn Responses: Once approved, sends the reply back via LinkedIn and marks the original message as handled.

  The result: You stop being a human switchboard and can focus on your actual job while people still get helpful, timely responses through automated customer service. You can also add routes for things you do handle but get asked about daily (like 'How do I join your beta?' or 'What's your content strategy?') to standardize your responses.

  Setup

  Sign up for a UniPile account and create a webhook under the Messaging section
  Set the callback URL to this workflow's production URL
  Generate a UniPile API key with all required scopes and store it in your n8n credentials
  Create a Slack app and enable interactive message buttons and webhooks

  Here is a slack App manifest template for easy deployment in slack:

  {
      "display_information": {
          "name": "Request Router",
          "description": "A bot that alerts when a new linkedin question comes in.",
          "background_color": "#12575e"
      },
      "features": {
          "bot_user": {
              "display_name": "Request Router",
              "always_online": false
          }
      },
      "oauth_config": {
          "scopes": {
              "bot": [
                  "chat:write",
                  "chat:write.customize",
                  "chat:write.public",
                  "links:write",
                  "im:history",
                  "im:read",
                  "im:write"
              ]
          }
      },
      "settings": {
          "interactivity": {
              "is_enabled": true,
              "request_url": "Your webhook url here"
          },
          "org_deploy_enabled": false,
          "socket_mode_enabled": false,
          "token_rotation_enabled": false
      }
  }


  Set up your Notion database with the three-column structure (Question, Description, Action)
  Configure the AI node with your preferred provider (OpenAI, Gemini, Ollama etc)
  Replace placeholder LinkedIn user and organization IDs with your own

  How to customize this workflow to your needs

  Database Options**: Swap Notion with Google Sheets, Airtable, or another database
  Filtering Logic**: Add custom filters based on keywords, message length, follower count, or business logic
  AI Customization**: Adjust the system prompt to match your brand tone and response goals
  Approval Platform**: Replace Slack with email, Discord, or another review platform
  Team Routing**: Use Slack metadata to route approvals to specific team members based on message category
  Enrichment**: Add secondary data enrichment using tools like Clearbit or FullContact
  Response Rules**: Create conditional logic for different response types based on sender profile or message content

  Perfect for anyone who's tired of being their company's accidental customer service department while trying to do their real job.

  This LinkedIn automation template was inspired by a live build done by Max Tkacz and Angel Menendez for The Studio.

nodes_used:
  ["n8n-nodes-base.httpRequest","n8n-nodes-base.slack","n8n-nodes-base.notion","@n8n/n8n-nodes-langchain.agent","@n8n/n8n-nodes-langchain.lmChatOpenAi","@n8n/n8n-nodes-langchain.memoryBufferWindow","@n8n/n8n-nodes-langchain.outputParserStructured"]

workflow_json:
  {"meta":{"instanceId":"cb484ba7b742928a2048bf8829668bed5b5ad9787579adea888f05980292a4a7","templateCredsSetupCompleted":true},"nodes":[{"id":"5f71a0e6-d5ec-4712-9feb-2b10a1b0a3ea","name":"Webhook","type":"n8n-nodes-base.webhook","position":[0,0],"webhookId":"12a0b328-1d39-44b4-b29d-9ac465cf134b","parameters":{"path":"12a0b328-1d39-44b4-b29d-9ac465cf134b","options":{},"httpMethod":"POST"},"typeVersion":2},{"id":"bd66537c-6fe5-4877-9127-3b78af08c499","name":"Check if from me","type":"n8n-nodes-base.if","position":[440,0],"parameters":{"options":{},"conditions":{"options":{"version":2,"leftValue":"","caseSensitive":true,"typeValidation":"strict"},"combinator":"or","conditions":[{"id":"711303bb-aef2-4cff-b4c7-c2a898e454ac","operator":{"type":"string","operation":"notEquals"},"leftValue":"={{ $json.sender_id }}","rightValue":"OzJlgZHDXWi0PmxVdqnPOQ"},{"id":"d115500d-8e14-4b8e-b0ed-4e26a895bb37","operator":{"name":"filter.operator.equals","type":"string","operation":"equals"},"leftValue":"={{ $json.sender_id }}","rightValue":"9va5ul-NUYejvzb7ADJzuw"}]}},"typeVersion":2.2},{"id":"e14aedab-47e9-4811-b991-ee0d00290c39","name":"Response, No action","type":"n8n-nodes-base.noOp","position":[700,120],"parameters":{},"typeVersion":1},{"id":"8adbb07e-4897-4421-b581-c963b754aa2b","name":"New Message","type":"n8n-nodes-base.noOp","position":[680,-140],"parameters":{},"typeVersion":1},{"id":"39865ae2-a266-47ba-a6fd-c9b1f5d5a931","name":"Global Variables","type":"n8n-nodes-base.set","position":[220,0],"parameters":{"options":{},"assignments":{"assignments":[{"id":"5483f235-49d0-404d-82dd-fd5688671044","name":"type","type":"string","value":"={{ $json.body.account_info.type }}"},{"id":"d737da4a-cc6f-4dc5-a8b7-0fd60f6a45b5","name":"message","type":"string","value":"={{ $json.body.message }}"},{"id":"924bd124-4ef1-4f41-8a3d-819d97f053e2","name":"message_id","type":"string","value":"={{ $json.body.message_id }}"},{"id":"c05786b0-b2af-4d87-a111-aae969ce50e9","name":"chat_id","type":"string","value":"={{ $json.body.chat_id }}"},{"id":"342fd20c-81be-42c7-aa85-a525fa9760fb","name":"sender","type":"string","value":"={{ $json.body.sender.attendee_name }}"},{"id":"b40f55d7-928e-436f-90b7-b4048cd80423","name":"sender_profile","type":"string","value":"={{ $json.body.sender.attendee_profile_url }}"},{"id":"efb12c87-42f5-4087-82b8-8dbda5aaf465","name":"sender_id","type":"string","value":"={{ $json.body.sender.attendee_id }}"}]}},"typeVersion":3.4},{"id":"3c58401c-cb83-4d71-9469-7563d6ce9c16","name":"Slack Button Press","type":"n8n-nodes-base.webhook","position":[0,800],"webhookId":"e3182811-630a-4959-b91c-71d8c8093e1c","parameters":{"path":"e3182811-630a-4959-b91c-71d8c8093e1c","options":{},"httpMethod":"POST","responseMode":"responseNode"},"typeVersion":2},{"id":"b87d4806-423b-4656-bbd6-9d0808242cc4","name":"Parse Webhook","type":"n8n-nodes-base.set","position":[480,800],"parameters":{"options":{},"assignments":{"assignments":[{"id":"94e30709-cf7a-4131-bc89-dbe56f8f3b16","name":"body.payload","type":"object","value":"={{ $json.body.payload }}"}]}},"typeVersion":3.4},{"id":"ee147347-1a88-4e96-9580-d08285e901c0","name":"Verify Webhook","type":"n8n-nodes-base.respondToWebhook","position":[240,800],"parameters":{"options":{"responseCode":200,"responseHeaders":{"entries":[{"name":"Content-type","value":"application/json"}]}},"respondWith":"json","responseBody":"={\"challenge\":\"{{ $json.body.challenge }}\"}"},"typeVersion":1},{"id":"ac2cb5e1-394a-4a5c-a999-a56d315bc3ff","name":"Check if approved","type":"n8n-nodes-base.if","position":[1140,580],"parameters":{"options":{},"conditions":{"options":{"version":2,"leftValue":"","caseSensitive":true,"typeValidation":"strict"},"combinator":"and","conditions":[{"id":"cf275c3e-347d-4028-8209-682f52d540e3","operator":{"name":"filter.operator.equals","type":"string","operation":"equals"},"leftValue":"={{ $json.body.payload.actions[0].value.action }}","rightValue":"approve"}]}},"typeVersion":2.2},{"id":"3812b521-2e15-4c24-9883-79ef04fc6cb3","name":"Send User Message","type":"n8n-nodes-base.slack","position":[4080,-100],"webhookId":"e3624af3-3604-4d6a-b776-e3860b51b24e","parameters":{"text":"=New LinkedIn Message from {{ $('Webhook').item.json.body.sender.attendee_name }}","user":{"__rl":true,"mode":"id","value":"U07G1JBR76W"},"select":"user","blocksUi":"={\n  \"blocks\": [\n    {\n      \"type\": \"section\",\n      \"block_id\": \"profile_card\",\n      \"text\": {\n        \"type\": \"mrkdwn\",\n        \"text\": \"👤*<{{ $('Webhook').item.json.body.sender.attendee_profile_url }}|{{ $('Webhook').item.json.body.sender.attendee_name }}>*\\n\\n💼 {{ $('Set all potential Inputs').item.json.linkedinprofile[0].headline }}\\n\\n📍 {{ $('Set all potential Inputs').item.json.linkedinprofile[0].location }}\\n👥 {{ $('Set all potential Inputs').item.json.linkedinprofile[0].follower_count }} followers | 🔗 {{ $('Set all potential Inputs').item.json.linkedinprofile[0].connections_count }} connections\"\n      },\n      \"accessory\": {\n        \"type\": \"image\",\n        \"image_url\": \"{{ $('Set all potential Inputs').item.json.linkedinprofile[0].profile_picture_url }}\",\n        \"alt_text\": \"LinkedIn Profile Picture\"\n      }\n    },\n    {\n      \"type\": \"section\",\n      \"block_id\": \"incoming_message\",\n      \"text\": {\n        \"type\": \"mrkdwn\",\n        \"text\": \"*📩 <https://www.linkedin.com/messaging/thread/{{ $('Webhook').item.json.body.provider_chat_id }}/|New LinkedIn Message>:*\\n> {{ $('Global Variables').item.json.message.replace(/\\n/g, '\\\\n').replace(/\\\"/g, '\\\\\"') }}\"\n      }\n    },\n    {\n      \"type\": \"input\",\n      \"block_id\": \"ai_response\",\n      \"element\": {\n        \"type\": \"plain_text_input\",\n        \"action_id\": \"response_input\",\n        \"multiline\": true,\n        \"initial_value\": \"{{ $('AI Agent').item.json.output.output.replace(/\\n/g, '\\\\n').replace(/\\\"/g, '\\\\\"') }}\",\n        \"placeholder\": {\n          \"type\": \"plain_text\",\n          \"text\": \"Edit the AI-generated response before approving...\"\n        }\n      },\n      \"label\": {\n        \"type\": \"plain_text\",\n        \"text\": \"🤖 Suggested Reply\"\n      }\n    },\n    {\n      \"type\": \"actions\",\n      \"block_id\": \"actions_block\",\n      \"elements\": [\n        {\n          \"type\": \"button\",\n          \"action_id\": \"approve_response\",\n          \"text\": {\n            \"type\": \"plain_text\",\n            \"text\": \"✅ Approve\"\n          },\n          \"style\": \"primary\",\n          \"value\": \"{\\\"action\\\":\\\"approve\\\",\\\"message_id\\\":\\\"{{ $('Global Variables').item.json.message_id }}\\\",\\\"channel_id\\\":\\\"{{ $('Global Variables').item.json.chat_id }}\\\"}\"\n        },\n        {\n          \"type\": \"button\",\n          \"action_id\": \"archive_message\",\n          \"text\": {\n            \"type\": \"plain_text\",\n            \"text\": \"🗃️ Archive\"\n          },\n          \"style\": \"danger\",\n          \"value\": \"{\\\"action\\\":\\\"archive\\\",\\\"message_id\\\":\\\"{{ $('Global Variables').item.json.message_id }}\\\",\\\"channel_id\\\":\\\"{{ $('Global Variables').item.json.chat_id }}\\\"}\"\n        }\n      ]\n    }\n  ]\n}\n","messageType":"block","otherOptions":{}},"credentials":{"slackApi":{"id":"6xKmxBfKWNPnre2E","name":"Request Router"}},"typeVersion":2.3},{"id":"7470b927-8a4d-4421-b6d3-cc55623d77dd","name":"Send Org Message","type":"n8n-nodes-base.slack","position":[4080,60],"webhookId":"9a621f5a-854e-4725-81c4-3ce075d87d96","parameters":{"text":"=New LinkedIn Message from {{ $('Webhook').item.json.body.sender.attendee_name }}","user":{"__rl":true,"mode":"id","value":"U07G1JBR76W"},"select":"user","blocksUi":"={\n  \"blocks\": [\n    {\n      \"type\": \"section\",\n      \"block_id\": \"profile_card_org\",\n      \"text\": {\n        \"type\": \"mrkdwn\",\n        \"text\": \"🏢*<{{ $('Webhook').item.json.body.sender.attendee_profile_url }}|{{ $('Webhook').item.json.body.sender.attendee_name }}>*\\n\\n💼 {{ $('Set all potential Inputs').item.json.linkedinprofile[0].headline }}\\n\\n📍 {{ $('Set all potential Inputs').item.json.linkedinprofile[0].location }}\\n👥 {{ $('Set all potential Inputs').item.json.linkedinprofile[0].follower_count }} followers | 🧑‍💼 {{ $('Set all potential Inputs').item.json.linkedinprofile[0].employee_count }} employees\"\n      },\n      \"accessory\": {\n        \"type\": \"image\",\n        \"image_url\": \"{{ $('Set all potential Inputs').item.json.linkedinprofile[0].profile_picture_url }}\",\n        \"alt_text\": \"Organization Profile Picture\"\n      }\n    },\n    {\n      \"type\": \"section\",\n      \"block_id\": \"incoming_message\",\n      \"text\": {\n        \"type\": \"mrkdwn\",\n        \"text\": \"*📩 New LinkedIn Message:*\\n> {{ $('Global Variables').item.json.message.replace(/\\n/g, '\\\\n').replace(/\\\"/g, '\\\\\"') }}\"\n      }\n    },\n    {\n      \"type\": \"input\",\n      \"block_id\": \"ai_response\",\n      \"element\": {\n        \"type\": \"plain_text_input\",\n        \"action_id\": \"response_input\",\n        \"multiline\": true,\n        \"initial_value\": \"{{ $('AI Agent').item.json.output.output.replace(/\\n/g, '\\\\n').replace(/\\\"/g, '\\\\\"') }}\",\n        \"placeholder\": {\n          \"type\": \"plain_text\",\n          \"text\": \"Edit the AI-generated response before approving...\"\n        }\n      },\n      \"label\": {\n        \"type\": \"plain_text\",\n        \"text\": \"🤖 Suggested Reply\"\n      }\n    },\n    {\n      \"type\": \"actions\",\n      \"block_id\": \"actions_block\",\n      \"elements\": [\n        {\n          \"type\": \"button\",\n          \"action_id\": \"approve_response\",\n          \"text\": {\n            \"type\": \"plain_text\",\n            \"text\": \"✅ Approve\"\n          },\n          \"style\": \"primary\",\n          \"value\": \"{\\\"action\\\":\\\"approve\\\",\\\"message_id\\\":\\\"{{ $('Global Variables').item.json.message_id }}\\\",\\\"channel_id\\\":\\\"{{ $('Global Variables').item.json.chat_id }}\\\"}\"\n        },\n        {\n          \"type\": \"button\",\n          \"action_id\": \"archive_message\",\n          \"text\": {\n            \"type\": \"plain_text\",\n            \"text\": \"🗃️ Archive\"\n          },\n          \"style\": \"danger\",\n          \"value\": \"{\\\"action\\\":\\\"archive\\\",\\\"message_id\\\":\\\"{{ $('Global Variables').item.json.message_id }}\\\",\\\"channel_id\\\":\\\"{{ $('Global Variables').item.json.chat_id }}\\\"}\"\n        }\n      ]\n    }\n  ]\n}\n","messageType":"block","otherOptions":{}},"credentials":{"slackApi":{"id":"6xKmxBfKWNPnre2E","name":"Request Router"}},"typeVersion":2.3},{"id":"0c63c0e7-752d-4bd7-ab78-23a1ff4d70ae","name":"Send Nothing Found Message","type":"n8n-nodes-base.slack","position":[4080,220],"webhookId":"64dddbb2-1bf6-4a5a-884b-057b82596ef1","parameters":{"user":{"__rl":true,"mode":"id","value":"U07G1JBR76W"},"select":"user","blocksUi":"={\n  \"blocks\": [\n    {\n      \"type\": \"section\",\n      \"block_id\": \"incoming_message\",\n      \"text\": {\n        \"type\": \"mrkdwn\",\n        \"text\": \"*New LinkedIn Message:*\\n> {{ $('Global Variables').item.json.message.replace(/\\n/g, '\\\\n').replace(/\"/g, '\\\\\"') }}\"\n      }\n    },\n    {\n      \"type\": \"input\",\n      \"block_id\": \"ai_response\",\n      \"element\": {\n        \"type\": \"plain_text_input\",\n        \"action_id\": \"response_input\",\n        \"multiline\": true,\n        \"initial_value\": \"{{ $json.output.output.replace(/\\n/g, '\\\\n').replace(/\"/g, '\\\\\"') }}\",\n        \"placeholder\": {\n          \"type\": \"plain_text\",\n          \"text\": \"Edit the AI-generated response before approving...\"\n        }\n      },\n      \"label\": {\n        \"type\": \"plain_text\",\n        \"text\": \"Suggested Reply\"\n      }\n    },\n    {\n      \"type\": \"actions\",\n      \"block_id\": \"actions_block\",\n      \"elements\": [\n        {\n          \"type\": \"button\",\n          \"action_id\": \"approve_response\",\n          \"text\": {\n            \"type\": \"plain_text\",\n            \"text\": \"✅ Approve\"\n          },\n          \"style\": \"primary\",\n          \"value\": \"{\\\"action\\\":\\\"approve\\\",\\\"message_id\\\":\\\"{{ $('Global Variables').item.json.message_id }}\\\",\\\"channel_id\\\":\\\"{{ $('Global Variables').item.json.chat_id }}\\\"}\"\n        },\n        {\n          \"type\": \"button\",\n          \"action_id\": \"archive_message\",\n          \"text\": {\n            \"type\": \"plain_text\",\n            \"text\": \"🗃️ Archive\"\n          },\n          \"style\": \"danger\",\n          \"value\": \"{\\\"action\\\":\\\"archive\\\",\\\"message_id\\\":\\\"{{ $('Global Variables').item.json.message_id }}\\\",\\\"channel_id\\\":\\\"{{ $('Global Variables').item.json.chat_id }}\\\"}\"\n        }\n      ]\n    }\n  ]\n}\n","messageType":"block","otherOptions":{}},"credentials":{"slackApi":{"id":"6xKmxBfKWNPnre2E","name":"Request Router"}},"typeVersion":2.3},{"id":"fb29432d-7603-4b42-902f-7784459dd40d","name":"Sticky Note","type":"n8n-nodes-base.stickyNote","position":[-80,-420],"parameters":{"color":7,"width":980,"height":720,"content":"![unipile](https://uploads.n8n.io/templates/unipile.png)\n## LinkedIn Message Processing\nReceives the LinkedIn message via Unipile api webhook."},"typeVersion":1},{"id":"388d621c-7339-4d74-a2c4-4da9c41a441f","name":"Sticky Note11","type":"n8n-nodes-base.stickyNote","position":[-80,320],"parameters":{"color":7,"width":2097,"height":693,"content":"![Slack](https://uploads.n8n.io/templates/slack.png)\n## Slack Bot Button Press\nThis workflow gets the button presses from the Slack interface and passes it along to Unipile for processing."},"typeVersion":1},{"id":"13ed0034-df98-46a8-931c-4e87667e624c","name":"Decide on Message Type","type":"n8n-nodes-base.switch","position":[3760,-80],"parameters":{"rules":{"values":[{"outputKey":"User","conditions":{"options":{"version":2,"leftValue":"","caseSensitive":true,"typeValidation":"strict"},"combinator":"and","conditions":[{"id":"4670af46-5774-4fec-8b12-a608aefa3d89","operator":{"type":"string","operation":"equals"},"leftValue":"={{ $('Set all potential Inputs').item.json.linkedinprofile[0].type }}","rightValue":"user"}]},"renameOutput":true},{"outputKey":"Organization","conditions":{"options":{"version":2,"leftValue":"","caseSensitive":true,"typeValidation":"strict"},"combinator":"and","conditions":[{"id":"0a484630-343d-4b9a-9bf0-6ef5bd9b1b4b","operator":{"name":"filter.operator.equals","type":"string","operation":"equals"},"leftValue":"={{ $('Set all potential Inputs').item.json.linkedinprofile[0].type }}","rightValue":"organization"}]},"renameOutput":true}]},"options":{"fallbackOutput":"extra"}},"typeVersion":3.2},{"id":"e4c36cc2-9ad1-4ceb-8698-05079c9c6509","name":"User Switcher","type":"n8n-nodes-base.switch","position":[680,800],"parameters":{"rules":{"values":[{"outputKey":"angel","conditions":{"options":{"version":2,"leftValue":"","caseSensitive":true,"typeValidation":"strict"},"combinator":"and","conditions":[{"id":"27c0a3cc-b768-4aba-bab0-19971fb2d38d","operator":{"type":"string","operation":"equals"},"leftValue":"={{ $json.body.payload.user.id }}","rightValue":"U07G1JBR76W"}]},"renameOutput":true},{"outputKey":"max","conditions":{"options":{"version":2,"leftValue":"","caseSensitive":true,"typeValidation":"strict"},"combinator":"and","conditions":[{"id":"b16b07b2-c77b-439f-9acb-e7799dceaa6b","operator":{"name":"filter.operator.equals","type":"string","operation":"equals"},"leftValue":"={{ $json.body.payload.user.id }}","rightValue":"U035CE97JGM"}]},"renameOutput":true}]},"options":{}},"typeVersion":3.2},{"id":"f84186be-8ded-47c5-8bdb-9366c8be59fa","name":"Isolate Message and Payload","type":"n8n-nodes-base.set","position":[920,580],"parameters":{"options":{},"assignments":{"assignments":[{"id":"2a9278cb-3f2a-4f90-852a-3ca16b404c58","name":"message","type":"string","value":"={{ $json.body.payload.state.values.ai_response.response_input.value }}"},{"id":"3c16c98d-a7db-42e9-aacd-9ede379b1f49","name":"body.payload.actions[0].value","type":"object","value":"={{ $json.body.payload.actions[0].value }}"}]}},"typeVersion":3.4},{"id":"7dc03482-8c14-4494-a475-3f958a1fd445","name":"Isolate Payload","type":"n8n-nodes-base.set","position":[920,820],"parameters":{"options":{},"assignments":{"assignments":[{"id":"f334a7f4-4c85-466c-8278-3da5dd5a2486","name":"body","type":"object","value":"={{ $('Slack Button Press').item.json.body.payload }}"}]}},"typeVersion":3.4},{"id":"425b2b79-447d-4736-9edf-0033969d64b4","name":"Send webhook to Coworker Workflow","type":"n8n-nodes-base.httpRequest","position":[1140,820],"parameters":{"url":"https://n8n.cloud/webhook/89659f10-574e-s42c-530d-e7dd9158d177","method":"POST","options":{}},"typeVersion":4.2},{"id":"4c36fc5c-75a5-4279-9555-13fdfa033510","name":"Send Message to LinkedIn via Unipile","type":"n8n-nodes-base.httpRequest","position":[1380,520],"parameters":{"url":"=https://api9.unipile.com:13976/api/v1/chats/{{ $json.body.payload.actions[0].value.channel_id }}/messages","method":"POST","options":{},"sendBody":true,"contentType":"form-urlencoded","sendHeaders":true,"authentication":"genericCredentialType","bodyParameters":{"parameters":[{"name":"text","value":"={{ $('Isolate Message and Payload').item.json.message }}"}]},"genericAuthType":"httpHeaderAuth","headerParameters":{"parameters":[{"name":"accept","value":"application/json"}]}},"credentials":{"httpHeaderAuth":{"id":"VfYHlcsosNuUS2YD","name":"unipile angel"}},"typeVersion":4.2},{"id":"bed8608b-b474-4472-87ad-1e3454799a81","name":"Delete Approved Message from Slack","type":"n8n-nodes-base.slack","position":[1680,520],"webhookId":"08e7c073-569a-4400-aa60-80c7cddf8b03","parameters":{"select":"channel","channelId":{"__rl":true,"mode":"id","value":"={{ $('User Switcher').item.json.body.payload.channel.id }}"},"operation":"delete","timestamp":"={{ $('User Switcher').item.json.body.payload.container.message_ts }}"},"credentials":{"slackApi":{"id":"6xKmxBfKWNPnre2E","name":"Request Router"}},"typeVersion":2.3},{"id":"b79429a6-3b46-4898-a933-3b6ec77a1f97","name":"Delete Denied Message from Slack","type":"n8n-nodes-base.slack","position":[1680,720],"webhookId":"70630dad-c2a5-4c40-aef3-070994ce4b83","parameters":{"select":"channel","channelId":{"__rl":true,"mode":"id","value":"={{ $('User Switcher').item.json.body.payload.channel.id }}"},"operation":"delete","timestamp":"={{ $('User Switcher').item.json.body.payload.container.message_ts }}"},"credentials":{"slackApi":{"id":"6xKmxBfKWNPnre2E","name":"Request Router"}},"typeVersion":2.3},{"id":"9a475e01-a250-44f2-8cc6-4ef60aedaa36","name":"AI Agent","type":"@n8n/n8n-nodes-langchain.agent","position":[3220,-80],"parameters":{"text":"=Sender Name: {{ $('Isolate parent workflow data for AI').item.json.sender }}\nSender Message: {{ $('Isolate parent workflow data for AI').item.json.message }}\nMy Name: Your Name\n\nIf found, the linkedin profile will be below, pay close attention to the number of followers and connections: \n{{ $('Set all potential Inputs').item.json.linkedinprofile.toJsonString() }}","options":{"systemMessage":"=You are an expert professional assistant designed to help generate smart, personalized responses to LinkedIn messages.\n\nYou will be provided with:\n1. The **incoming message** and name from a LinkedIn user.\n2. A **database of past requests and responses**. These are known message types and the preferred replies.\n3. Context about the assistant's voice and tone.\n\n### Your Objective:\n- First, scan the database for any message that closely matches the incoming LinkedIn message. If a match is found, use the **corresponding response** as a base — you may slightly tailor it if needed (e.g., change names or dates).\n- If no close match is found, generate a **new, thoughtful reply** based on the message content, tone guidelines, and best practices in business networking. If you do not have a direct link or URL to provide from the Request Database, do not reference a website or URL. Instead say a variation of let me get back to you on that and see what I can find. \n\n### Tone Guidelines:\n- Friendly, confident, and professional — but never robotic.\n- Lightly personalized. Use the sender’s name if available.\n- Avoid sounding like a sales pitch.\n- Keep replies concise and natural, like something you'd actually send on LinkedIn.\n\n### When generating a new message:\n- Acknowledge the sender’s message.\n- Add a relevant, helpful comment or question to continue the conversation.\n- Keep the tone warm and open-ended.\n\n### Output format:\nOnly output the message text that should be sent to the user. Do not explain your reasoning. If you do not have a direct link to provide, do not reference a website or URL. Instead say let me get back to you on that and see what I can find. \n\nLet’s begin.\nRequest Database:\n\n{{ $json.dbObject.join('\\n\\n----\\n\\n') }}\n\nWhen responding, use the following format:\n{\n\t\"output\": \"message response\",\n\t\"found\": true\n}\nFor output output the message response, for found output a boolean, true if an example is found in the Request Database, false if a response is not found. The output is going to slack so ensure you escape your outputs like new lines. "},"promptType":"define","hasOutputParser":true},"typeVersion":1.9},{"id":"53011c4c-b9aa-4b47-84c8-060e4b7a2db9","name":"Simple Memory","type":"@n8n/n8n-nodes-langchain.memoryBufferWindow","position":[3340,160],"parameters":{"sessionKey":"={{ $('Isolate parent workflow data for AI').item.json.chatid }}","sessionIdType":"customKey"},"typeVersion":1.3},{"id":"b5eb7520-c887-4a72-89d0-d616c24fdfca","name":"OpenAI Chat Model","type":"@n8n/n8n-nodes-langchain.lmChatOpenAi","position":[3120,180],"parameters":{"model":{"__rl":true,"mode":"list","value":"gpt-4o","cachedResultName":"gpt-4o"},"options":{}},"credentials":{"openAiApi":{"id":"QpFZ2EiM3WGl6Zr3","name":"Marketing OpenAI"}},"typeVersion":1.2},{"id":"b405f410-4d76-43f9-b21c-b6cb363daa43","name":"Structured Output Parser","type":"@n8n/n8n-nodes-langchain.outputParserStructured","position":[3500,160],"parameters":{"jsonSchemaExample":"{\n\t\"output\": \"message response\",\n\t\"found\": true\n}"},"typeVersion":1.2},{"id":"8ad9d20b-07a4-46f2-9dbb-5d3d8d502641","name":"Sticky Note3","type":"n8n-nodes-base.stickyNote","position":[3020,-400],"parameters":{"color":7,"width":668,"height":718,"content":"![hctiapi](https://uploads.n8n.io/templates/openai.png)\n## Generate Automated response\nThe AI bot receives not only the message from LinkedIn, but also LinkedIn user context, such as the number of followers and connections, allowing for tailored responses. For example if a user asks to meet, but they don't meet a certain number of followers threshold, they are politely declined. However if an influencer reaches out, they are automatically given a booking link to ensure that high priority requests are immediately followed up on. "},"typeVersion":1},{"id":"8d593035-111a-45dc-93ea-950aad7b0ebb","name":"Isolate parent workflow data for AI","type":"n8n-nodes-base.set","position":[2260,20],"parameters":{"options":{},"assignments":{"assignments":[{"id":"91a1191e-bac0-4b8b-b263-a03c63435470","name":"sender","type":"string","value":"={{ $('Global Variables').item.json.sender }}"},{"id":"0f8c17c8-d598-4840-8b89-8dbdcd529231","name":"message","type":"string","value":"={{ $('Global Variables').item.json.message }}"},{"id":"c9132b69-5e0e-4ccf-86bb-0e4cfa734860","name":"chatid","type":"string","value":"={{ $('Global Variables').item.json.chat_id }}"}]}},"typeVersion":3.4},{"id":"d267a541-a739-49b8-a2f6-b8afbb6cc837","name":"Get Request Router Directory Database","type":"n8n-nodes-base.notion","position":[2460,20],"parameters":{"options":{},"resource":"databasePage","operation":"getAll","databaseId":{"__rl":true,"mode":"list","value":"1da5b6e0-c94f-8086-80b6-eab8e340d60e","cachedResultUrl":"https://www.notion.so/1da5b6e0c94f808680b6eab8e340d60e","cachedResultName":"RequestRouterDB"}},"credentials":{"notionApi":{"id":"2B3YIiD4FMsF9Rjn","name":"Angelbot Notion"}},"typeVersion":2.2},{"id":"af762a13-5774-4608-a221-7860dce3f27c","name":"Format DB data for AI Context","type":"n8n-nodes-base.set","position":[2660,20],"parameters":{"options":{},"assignments":{"assignments":[{"id":"c4ac8c33-a220-4c07-bc0d-dc7ba7cc068e","name":"dbObject","type":"string","value":"=Request Example: {{ $json.name }}\n--\nRequest Description: {{ $json.property_request_description }}\n--\nRequest Action: {{ $json.property_request_action }}"}]}},"typeVersion":3.4},{"id":"88da9528-2a4c-426a-bd27-8caa47bed3f5","name":"Aggregate DB objects into one item","type":"n8n-nodes-base.aggregate","position":[2860,20],"parameters":{"options":{},"fieldsToAggregate":{"fieldToAggregate":[{"fieldToAggregate":"dbObject"}]}},"typeVersion":1},{"id":"204ce89b-9443-4ece-8385-cb3b59bd5a0b","name":"Sticky Note9","type":"n8n-nodes-base.stickyNote","position":[2180,-400],"parameters":{"color":7,"width":826,"height":700,"content":"![notion](https://uploads.n8n.io/templates/notionlogo.png)\n## Get routing Database data\nAn AI bot that does not get smarter over time is not a useful bot. That is why this bot references a shared internal database where requests routing can be updated without having to touch the n8n workflows. When a request comes in that does not have a standardized process, the AI will generate a response based on its model training. You can use this as a starting point, but when this becomes a pattern, simply updating the notion database instantly upgrades the AI bot. Not only that, but others can update the database, not only giving the AI context, but also creating a centralized location for standardized processes for handling different request types. This can be adapted for any platform, not just linkedIn, such as shared email inboxes, shared social media pages, and even for support requests. "},"typeVersion":1},{"id":"d4a894d6-334b-4abe-9d1a-0e449da46b6f","name":"Sticky Note8","type":"n8n-nodes-base.stickyNote","position":[920,-540],"parameters":{"color":7,"width":1246,"height":840,"content":"![Linkedin](https://uploads.n8n.io/templates/linkedinlogo.png))\n## Enrich LinkedIn Data with User or Org Data from Unipile\nLinkedIn messages arrive from one of two object types, users or organizations. This workflow extracts the user data and passes it along. If the user is not found, then the Organization endpoint is searched instead. If it's found, it send that, otherwise it sends a not found object. "},"typeVersion":1},{"id":"ec186db1-e7e8-480e-a94a-d4c1de5ee420","name":"Get Linkedin User Data from Unipile","type":"n8n-nodes-base.httpRequest","onError":"continueErrorOutput","position":[980,-140],"parameters":{"url":"=https://api9.unipile.com:13976/api/v1/users/{{ $('Webhook').item.json.body.sender.attendee_provider_id }}","options":{},"sendQuery":true,"sendHeaders":true,"authentication":"genericCredentialType","genericAuthType":"httpHeaderAuth","queryParameters":{"parameters":[{"name":"account_id","value":"-oWmWRkASjKGUZadYcjcyg"}]},"headerParameters":{"parameters":[{"name":"accept","value":"application/json"}]}},"credentials":{"httpHeaderAuth":{"id":"VfYHlcsosNuUS2YD","name":"unipile angel"}},"typeVersion":4.2},{"id":"d3fb953a-f3cf-4005-934c-b091bb784d84","name":"Set User Data from Unipile","type":"n8n-nodes-base.set","position":[1240,-280],"parameters":{"options":{},"assignments":{"assignments":[{"id":"aee91408-b68d-472e-8c3e-89260dd38c1c","name":"first_name","type":"string","value":"={{ $json.first_name }}"},{"id":"57b3be6f-ba76-48c3-8f2e-1d9bb03d0dd5","name":"last_name","type":"string","value":"={{ $json.last_name }}"},{"id":"75167f30-96d6-4442-9542-9d1b8e17fcb6","name":"headline","type":"string","value":"={{ $json.headline }}"},{"id":"3e8bccc1-04a9-49f6-8053-eba22fe8d2f4","name":"websites","type":"array","value":"={{ $json.websites }}"},{"id":"2e3dd2fe-5f71-4d19-bee8-085dd9bfc18c","name":"follower_count","type":"number","value":"={{ $json.follower_count }}"},{"id":"ac5cc567-3c4f-481c-b229-9dc1e48d39fb","name":"connections_count","type":"number","value":"={{ $json.connections_count }}"},{"id":"6bad07a6-4641-48cb-b436-fb735319865f","name":"location","type":"string","value":"={{ $json.location }}"},{"id":"029fa351-f49f-4388-a59e-5719fcf8a506","name":"profile_picture_url","type":"string","value":"={{ $json.profile_picture_url }}"},{"id":"2f96dca6-acee-41c0-83b5-00cd406d3301","name":"is_influencer","type":"boolean","value":"={{ $json.is_influencer }}"},{"id":"4278e070-ce56-4993-b637-57ac60e83a49","name":"is_premium","type":"boolean","value":"={{ $json.is_premium }}"},{"id":"b92c38f1-1423-4b7e-a807-320d13e0a944","name":"shared_connections_count","type":"number","value":"={{ $json.shared_connections_count }}"},{"id":"96b24500-e6a4-444a-806c-0b61a1f00407","name":"type","type":"string","value":"user"}]}},"typeVersion":3.4},{"id":"c6077ddb-362d-45f4-a497-2529348148ab","name":"Group in one object - User","type":"n8n-nodes-base.aggregate","position":[1420,-280],"parameters":{"options":{},"aggregate":"aggregateAllItemData","destinationFieldName":"linkedinprofile"},"typeVersion":1},{"id":"1eb09bf7-fb93-4c19-bc41-86330c7b33e6","name":"Get Linkedin Org Data from Unipile","type":"n8n-nodes-base.httpRequest","onError":"continueErrorOutput","position":[1240,80],"parameters":{"url":"=https://api9.unipile.com:13976/api/v1/linkedin/company/{{ $('Webhook').item.json.body.sender.attendee_provider_id }}","options":{},"sendQuery":true,"sendHeaders":true,"authentication":"genericCredentialType","genericAuthType":"httpHeaderAuth","queryParameters":{"parameters":[{"name":"account_id","value":"-oWmWRkASjKGUZadYcjcyg"}]},"headerParameters":{"parameters":[{"name":"accept","value":"application/json"}]}},"credentials":{"httpHeaderAuth":{"id":"VfYHlcsosNuUS2YD","name":"unipile angel"}},"typeVersion":4.2},{"id":"38f5ed6f-9302-4979-b964-c1d231a344b6","name":"Set Linkedin Org Data from Unipile","type":"n8n-nodes-base.set","position":[1520,-80],"parameters":{"options":{},"assignments":{"assignments":[{"id":"aee91408-b68d-472e-8c3e-89260dd38c1c","name":"first_name","type":"string","value":"={{ $json.name }}"},{"id":"57b3be6f-ba76-48c3-8f2e-1d9bb03d0dd5","name":"last_name","type":"string","value":"="},{"id":"75167f30-96d6-4442-9542-9d1b8e17fcb6","name":"headline","type":"string","value":"={{ $json.description }}"},{"id":"3e8bccc1-04a9-49f6-8053-eba22fe8d2f4","name":"websites","type":"string","value":"={{ $json.website }}"},{"id":"2e3dd2fe-5f71-4d19-bee8-085dd9bfc18c","name":"follower_count","type":"number","value":"={{ $json.followers_count }}"},{"id":"ac5cc567-3c4f-481c-b229-9dc1e48d39fb","name":"employee_count","type":"number","value":"={{ $json.employee_count_range.from }}"},{"id":"6bad07a6-4641-48cb-b436-fb735319865f","name":"location","type":"string","value":"={{ $json.locations[0].street.join(' ') }}, {{ $json.locations[0].city }} {{ $json.locations[0].area }}, {{ $json.locations[0].postalCode }} {{ $json.locations[0].country }}."},{"id":"89035aa7-e7bb-46eb-9f4b-633e2c17478a","name":"hashtags","type":"array","value":"={{ $json.hashtags }}"},{"id":"25b0abe6-aef7-4d6f-88ea-5fcbd3472089","name":"profile_picture_url","type":"string","value":"={{ $json.logo }}"},{"id":"decf44b7-520e-4977-9df5-276c5117d8e4","name":"type","type":"string","value":"organization"}]}},"typeVersion":3.4},{"id":"45bd4b50-01e6-468b-815a-58073c137693","name":"Group in one object - Org","type":"n8n-nodes-base.aggregate","position":[1720,-80],"parameters":{"options":{},"aggregate":"aggregateAllItemData","destinationFieldName":"linkedinprofile"},"typeVersion":1},{"id":"c97c50b6-b491-43cd-8eb6-e48b368c862e","name":"Set unable to find data object","type":"n8n-nodes-base.set","position":[1640,120],"parameters":{"options":{},"assignments":{"assignments":[{"id":"438518ca-d55a-45d5-9210-0c53de7ae108","name":"linkedinprofile","type":"string","value":"Unable to find LinkedIn Data"},{"id":"2d0595aa-bdd4-46e3-9f4d-e13e69c5a7a9","name":"type","type":"string","value":"none"}]}},"typeVersion":3.4},{"id":"b42b967a-b127-458c-94b6-7a81052e6ba1","name":"Sticky Note12","type":"n8n-nodes-base.stickyNote","position":[3700,-400],"parameters":{"color":7,"width":857,"height":813,"content":"![Slack](https://uploads.n8n.io/templates/slack.png)\n## Slack Bot Button Press\nThis workflow gets the button presses from the Slack interface and passes it along to Unipile for processing."},"typeVersion":1},{"id":"48da88b3-beac-4c52-bf0c-460bc4d525fb","name":"Set all potential Inputs","type":"n8n-nodes-base.set","position":[2020,-80],"parameters":{"options":{},"includeOtherFields":true},"typeVersion":3.4},{"id":"7e091689-7905-4101-8dc9-0609b4f80233","name":"Sticky Note1","type":"n8n-nodes-base.stickyNote","position":[-60,-180],"parameters":{"color":3,"height":360,"content":"#### Add me to Unipile Webhook Dashboard\nEnsure that you have created a webhook in the Unipile dashboard that links to this node. [Link to Webhook Dashboard](https://dashboard.unipile.com/webhooks)"},"typeVersion":1},{"id":"97da9488-0e37-42c0-8dbf-912731fc5091","name":"Sticky Note2","type":"n8n-nodes-base.stickyNote","position":[-60,540],"parameters":{"color":3,"height":420,"content":"#### Add me to your Slack App Interactivity and Shortcuts\nTo receive button presses in this webhook, ensure that you've created a slack app and then set the webhook URL in the Interactivity & Shortcuts tab to this production URL. Use our App Manifest template to quickly deploy the app with the correct scopes. [Link to template with App Manifest](https://dashboard.unipile.com/webhooks)"},"typeVersion":1},{"id":"c9be1dca-da24-4f18-b2a4-36f89b7520a1","name":"Sticky Note4","type":"n8n-nodes-base.stickyNote","position":[940,-300],"parameters":{"width":180,"height":320,"content":"#### Update Credentials\nEnsure to use generic header auth. The name for the header is X-API-KEY. [Link to access token page on Unipile Site](https://dashboard.unipile.com/access-tokens)"},"typeVersion":1},{"id":"6e81a9bf-1c50-4366-9bae-be6241fc7875","name":"Sticky Note5","type":"n8n-nodes-base.stickyNote","position":[1200,-80],"parameters":{"width":180,"height":320,"content":"#### Update Credentials\nEnsure to use generic header auth. The name for the header is X-API-KEY. [Link to access token page on Unipile Site](https://dashboard.unipile.com/access-tokens)"},"typeVersion":1},{"id":"d8d5d5d1-6fe4-4f03-95cb-4d3cb6182f59","name":"Sticky Note6","type":"n8n-nodes-base.stickyNote","position":[2400,-80],"parameters":{"width":220,"height":280,"content":"#### Update Credentials\nDoes not have to be notion, can be any database type node like Google sheets. "},"typeVersion":1},{"id":"6a8202e9-e3c0-48db-b894-a009d801bddd","name":"Sticky Note7","type":"n8n-nodes-base.stickyNote","position":[380,-180],"parameters":{"width":220,"height":340,"content":"#### Update with your Unipile UserID\nEasiest way to do this is to send a message to someone so it triggers this workflow and then copy the senderID that shows in this node"},"typeVersion":1},{"id":"36b271d3-53f6-4548-bf3f-8dea39e05b05","name":"Sticky Note10","type":"n8n-nodes-base.stickyNote","position":[3060,60],"parameters":{"width":220,"height":240,"content":"#### Update Credentials"},"typeVersion":1},{"id":"2391f630-e071-4720-81c8-7937452e0523","name":"Sticky Note13","type":"n8n-nodes-base.stickyNote","position":[4020,-160],"parameters":{"width":220,"height":560,"content":"#### Update Credentials"},"typeVersion":1},{"id":"c533f8ea-1391-4b2f-81ba-2caa8a919e3b","name":"Sticky Note14","type":"n8n-nodes-base.stickyNote","position":[1320,360],"parameters":{"width":220,"height":340,"content":"#### Update Credentials\nEnsure to use generic header auth. The name for the header is X-API-KEY. [Link to access token page on Unipile Site](https://dashboard.unipile.com/access-tokens)"},"typeVersion":1},{"id":"6f0ef5cc-ef53-4a02-bdd9-5931c9ba8a0e","name":"Sticky Note15","type":"n8n-nodes-base.stickyNote","position":[1620,460],"parameters":{"width":220,"height":460,"content":"#### Update Credentials"},"typeVersion":1}],"pinData":{},"connections":{"Webhook":{"main":[[{"node":"Global Variables","type":"main","index":0}]]},"AI Agent":{"main":[[{"node":"Decide on Message Type","type":"main","index":0}]]},"New Message":{"main":[[{"node":"Get Linkedin User Data from Unipile","type":"main","index":0}]]},"Parse Webhook":{"main":[[{"node":"User Switcher","type":"main","index":0}]]},"Simple Memory":{"ai_memory":[[{"node":"AI Agent","type":"ai_memory","index":0}]]},"User Switcher":{"main":[[{"node":"Isolate Message and Payload","type":"main","index":0}],[{"node":"Isolate Payload","type":"main","index":0}]]},"Verify Webhook":{"main":[[{"node":"Parse Webhook","type":"main","index":0}]]},"Isolate Payload":{"main":[[{"node":"Send webhook to Coworker Workflow","type":"main","index":0}]]},"Check if from me":{"main":[[{"node":"New Message","type":"main","index":0}],[{"node":"Response, No action","type":"main","index":0}]]},"Global Variables":{"main":[[{"node":"Check if from me","type":"main","index":0}]]},"Check if approved":{"main":[[{"node":"Send Message to LinkedIn via Unipile","type":"main","index":0}],[{"node":"Delete Denied Message from Slack","type":"main","index":0}]]},"OpenAI Chat Model":{"ai_languageModel":[[{"node":"AI Agent","type":"ai_languageModel","index":0}]]},"Slack Button Press":{"main":[[{"node":"Verify Webhook","type":"main","index":0}]]},"Decide on Message Type":{"main":[[{"node":"Send User Message","type":"main","index":0}],[{"node":"Send Org Message","type":"main","index":0}],[{"node":"Send Nothing Found Message","type":"main","index":0}]]},"Set all potential Inputs":{"main":[[{"node":"Isolate parent workflow data for AI","type":"main","index":0}]]},"Structured Output Parser":{"ai_outputParser":[[{"node":"AI Agent","type":"ai_outputParser","index":0}]]},"Group in one object - Org":{"main":[[{"node":"Set all potential Inputs","type":"main","index":0}]]},"Group in one object - User":{"main":[[{"node":"Set all potential Inputs","type":"main","index":0}]]},"Set User Data from Unipile":{"main":[[{"node":"Group in one object - User","type":"main","index":0}]]},"Isolate Message and Payload":{"main":[[{"node":"Check if approved","type":"main","index":0}]]},"Format DB data for AI Context":{"main":[[{"node":"Aggregate DB objects into one item","type":"main","index":0}]]},"Set unable to find data object":{"main":[[{"node":"Set all potential Inputs","type":"main","index":0}]]},"Aggregate DB objects into one item":{"main":[[{"node":"AI Agent","type":"main","index":0}]]},"Get Linkedin Org Data from Unipile":{"main":[[{"node":"Set Linkedin Org Data from Unipile","type":"main","index":0}],[{"node":"Set unable to find data object","type":"main","index":0}]]},"Set Linkedin Org Data from Unipile":{"main":[[{"node":"Group in one object - Org","type":"main","index":0}]]},"Get Linkedin User Data from Unipile":{"main":[[{"node":"Set User Data from Unipile","type":"main","index":0}],[{"node":"Get Linkedin Org Data from Unipile","type":"main","index":0}]]},"Isolate parent workflow data for AI":{"main":[[{"node":"Get Request Router Directory Database","type":"main","index":0}]]},"Send Message to LinkedIn via Unipile":{"main":[[{"node":"Delete Approved Message from Slack","type":"main","index":0}]]},"Get Request Router Directory Database":{"main":[[{"node":"Format DB data for AI Context","type":"main","index":0}]]}}}


name: UniPile LinkedIn Profile Lookup Subworkflow
author_name: Angel Menendez
author_username: djangelic
nodes_used: ["n8n-nodes-base.httpRequest"]
categories: []
created_at: 2025-06-12T00:39:27.995Z
updated_at: 2025-06-12T00:39:27.995Z
url: https://n8n.io/workflows/4890
scraped_at: 2025-06-19 22:07:56
description:
  Who is this for?

  This subworkflow is ideal for developers and automation builders working with UniPile and n8n to automate message enrichment and LinkedIn lead routing.

  What problem is this workflow solving?

  UniPile separates personal and organization accounts into two different API endpoints. This flow handles both intelligently so you're not missing sender context due to API quirks or bad assumptions.

  What this workflow does

  This subworkflow is used by:

  LinkedIn Auto Message Router with Request Detection**  
  LinkedIn AI Response Generator with Slack Approval**

  It receives a message sender ID and tries to enrich it using UniPile's /people and /organizations endpoints. It returns a clean, consistent profile object regardless of which source was used.

  Setup

  Generate a UniPile API token and save it in your n8n credentials
  Make sure this subworkflow is triggered correctly by your parent flows
  Test both people and organization lookups to verify responses are normalized

  How to customize this workflow to your needs

  Add a secondary enrichment layer using tools like Clearbit or FullContact
  Customize the fallback logic or error handling
  Expand the returned data for more AI context or user routing (e.g., job title, region)

workflow_json:
  {"meta":{"instanceId":"cb484ba7b742928a2048bf8829668bed5b5ad9787579adea888f05980292a4a7"},"nodes":[{"id":"f87a2a83-11c2-40f6-9b80-c1c13cb1d71f","name":"When Executed by Another Workflow","type":"n8n-nodes-base.executeWorkflowTrigger","position":[-560,-100],"parameters":{"workflowInputs":{"values":[{"name":"sender"}]}},"typeVersion":1.1},{"id":"43349b3c-cdc8-445b-8f03-6e42d19ccce9","name":"Sticky Note8","type":"n8n-nodes-base.stickyNote","position":[-840,-500],"parameters":{"color":7,"width":1386,"height":840,"content":"![unipile](https://uploads.n8n.io/templates/unipile.png)\n## Enrich LinkedIn Data with User or Org Data\nLinkedIn messages arrive from one of two object types, users or organizations. This workflow extracts the user data and passes it along. If the user is not found, then the Organization endpoint is searched instead. If it's found, it send that, otherwise it sends a not found object. "},"typeVersion":1},{"id":"880c3f22-bb81-4311-bcf2-6943dd7a0988","name":"Get Linkedin User Data from Unipile","type":"n8n-nodes-base.httpRequest","onError":"continueErrorOutput","position":[-360,-100],"parameters":{"url":"=https://api9.unipile.com:13976/api/v1/users/{{ $json.sender }}","options":{},"sendQuery":true,"sendHeaders":true,"authentication":"genericCredentialType","genericAuthType":"httpHeaderAuth","queryParameters":{"parameters":[{"name":"account_id","value":"-oWmWRkASjKGUZadYcjcyg"}]},"headerParameters":{"parameters":[{"name":"accept","value":"application/json"}]}},"credentials":{"httpHeaderAuth":{"id":"VfYHlcsosNuUS2YD","name":"unipile angel"}},"typeVersion":4.2},{"id":"0e15d998-a820-48d6-80fe-56331df2998d","name":"Set User Data from Unipile","type":"n8n-nodes-base.set","position":[-100,-240],"parameters":{"options":{},"assignments":{"assignments":[{"id":"aee91408-b68d-472e-8c3e-89260dd38c1c","name":"first_name","type":"string","value":"={{ $json.first_name }}"},{"id":"57b3be6f-ba76-48c3-8f2e-1d9bb03d0dd5","name":"last_name","type":"string","value":"={{ $json.last_name }}"},{"id":"75167f30-96d6-4442-9542-9d1b8e17fcb6","name":"headline","type":"string","value":"={{ $json.headline }}"},{"id":"3e8bccc1-04a9-49f6-8053-eba22fe8d2f4","name":"websites","type":"array","value":"={{ $json.websites }}"},{"id":"2e3dd2fe-5f71-4d19-bee8-085dd9bfc18c","name":"follower_count","type":"number","value":"={{ $json.follower_count }}"},{"id":"ac5cc567-3c4f-481c-b229-9dc1e48d39fb","name":"connections_count","type":"number","value":"={{ $json.connections_count }}"},{"id":"6bad07a6-4641-48cb-b436-fb735319865f","name":"location","type":"string","value":"={{ $json.location }}"},{"id":"029fa351-f49f-4388-a59e-5719fcf8a506","name":"profile_picture_url","type":"string","value":"={{ $json.profile_picture_url }}"},{"id":"2f96dca6-acee-41c0-83b5-00cd406d3301","name":"is_influencer","type":"boolean","value":"={{ $json.is_influencer }}"},{"id":"4278e070-ce56-4993-b637-57ac60e83a49","name":"is_premium","type":"boolean","value":"={{ $json.is_premium }}"},{"id":"b92c38f1-1423-4b7e-a807-320d13e0a944","name":"shared_connections_count","type":"number","value":"={{ $json.shared_connections_count }}"},{"id":"96b24500-e6a4-444a-806c-0b61a1f00407","name":"type","type":"string","value":"user"}]}},"typeVersion":3.4},{"id":"5eca56b3-e771-40c7-8415-2b9553a281ec","name":"Group in one object - User","type":"n8n-nodes-base.aggregate","position":[80,-240],"parameters":{"options":{},"aggregate":"aggregateAllItemData","destinationFieldName":"linkedinprofile"},"typeVersion":1},{"id":"778e02d4-a6ab-4eaf-98e1-840cc09aa773","name":"Get Linkedin Org Data from Unipile","type":"n8n-nodes-base.httpRequest","onError":"continueErrorOutput","position":[-100,-20],"parameters":{"url":"=https://api9.unipile.com:13976/api/v1/linkedin/company/{{ $json.sender }}","options":{},"sendQuery":true,"sendHeaders":true,"authentication":"genericCredentialType","genericAuthType":"httpHeaderAuth","queryParameters":{"parameters":[{"name":"account_id","value":"-oWmWRkASjKGUZadYcjcyg"}]},"headerParameters":{"parameters":[{"name":"accept","value":"application/json"}]}},"credentials":{"httpHeaderAuth":{"id":"VfYHlcsosNuUS2YD","name":"unipile angel"}},"typeVersion":4.2},{"id":"acd3ec80-4e8e-4539-bc06-b21e1aa63774","name":"Set Linkedin Org Data from Unipile","type":"n8n-nodes-base.set","position":[180,-40],"parameters":{"options":{},"assignments":{"assignments":[{"id":"aee91408-b68d-472e-8c3e-89260dd38c1c","name":"first_name","type":"string","value":"={{ $json.name }}"},{"id":"57b3be6f-ba76-48c3-8f2e-1d9bb03d0dd5","name":"last_name","type":"string","value":"="},{"id":"75167f30-96d6-4442-9542-9d1b8e17fcb6","name":"headline","type":"string","value":"={{ $json.description }}"},{"id":"3e8bccc1-04a9-49f6-8053-eba22fe8d2f4","name":"websites","type":"string","value":"={{ $json.website }}"},{"id":"2e3dd2fe-5f71-4d19-bee8-085dd9bfc18c","name":"follower_count","type":"number","value":"={{ $json.followers_count }}"},{"id":"ac5cc567-3c4f-481c-b229-9dc1e48d39fb","name":"employee_count","type":"number","value":"={{ $json.employee_count_range.from }}"},{"id":"6bad07a6-4641-48cb-b436-fb735319865f","name":"location","type":"string","value":"={{ $json.locations[0].street.join(' ') }}, {{ $json.locations[0].city }} {{ $json.locations[0].area }}, {{ $json.locations[0].postalCode }} {{ $json.locations[0].country }}."},{"id":"89035aa7-e7bb-46eb-9f4b-633e2c17478a","name":"hashtags","type":"array","value":"={{ $json.hashtags }}"},{"id":"25b0abe6-aef7-4d6f-88ea-5fcbd3472089","name":"profile_picture_url","type":"string","value":"={{ $json.logo }}"},{"id":"decf44b7-520e-4977-9df5-276c5117d8e4","name":"type","type":"string","value":"organization"}]}},"typeVersion":3.4},{"id":"ad3d70cf-adec-47d0-a0d2-48ddaf4d11fb","name":"Group in one object - Org","type":"n8n-nodes-base.aggregate","position":[380,-40],"parameters":{"options":{},"aggregate":"aggregateAllItemData","destinationFieldName":"linkedinprofile"},"typeVersion":1},{"id":"45516b60-4465-4140-adbc-df9bf66b22ef","name":"Set unable to find data object","type":"n8n-nodes-base.set","position":[180,160],"parameters":{"options":{},"assignments":{"assignments":[{"id":"438518ca-d55a-45d5-9210-0c53de7ae108","name":"linkedinprofile","type":"string","value":"Unable to find LinkedIn Data"}]}},"typeVersion":3.4}],"pinData":{},"connections":{"Group in one object - Org":{"main":[[]]},"Group in one object - User":{"main":[[]]},"Set User Data from Unipile":{"main":[[{"node":"Group in one object - User","type":"main","index":0}]]},"When Executed by Another Workflow":{"main":[[{"node":"Get Linkedin User Data from Unipile","type":"main","index":0}]]},"Get Linkedin Org Data from Unipile":{"main":[[{"node":"Set Linkedin Org Data from Unipile","type":"main","index":0}],[{"node":"Set unable to find data object","type":"main","index":0}]]},"Set Linkedin Org Data from Unipile":{"main":[[{"node":"Group in one object - Org","type":"main","index":0}]]},"Get Linkedin User Data from Unipile":{"main":[[{"node":"Set User Data from Unipile","type":"main","index":0}],[{"node":"Get Linkedin Org Data from Unipile","type":"main","index":0}]]}}}


name: Personalized LinkedIn Responses with OpenAI GPT & Notion-based Routing
author_name: Angel Menendez
author_username: djangelic
categories: []
created_at: 2025-06-12T00:44:08.589Z
updated_at: 2025-06-12T00:44:08.589Z
url: https://n8n.io/workflows/4891
scraped_at: 2025-06-19 22:07:56
description:
  Who is this for?

  This workflow is for professionals and teams who want to automate LinkedIn message replies with intelligent, human-like responses — without losing control over tone or accuracy. Ideal for founders, sales teams, DevRel, or community managers handling high-volume inbound messages.

  What problem is this workflow solving?

  Responding to every LinkedIn message manually is slow and inconsistent. Basic AI bots generate replies without context or nuance. This subworkflow solves both problems by using structured message routing from Notion and profile insights from UniPile to craft smart, context-aware responses.

  What this workflow does

  This workflow takes the sender’s message and profile (from LinkedIn Auto Message Router with Request Detection) and references your centralized Notion database of message types. It uses that to either match the message to a known response or generate a new one using OpenAI's GPT model — all while following professional tone guidelines.

  This is the third workflow in a 3-part automation system:

  Receives data from LinkedIn Auto Message Router with Request Detection
  Uses UniPile LinkedIn Profile Lookup Subworkflow to enrich responses based on follower count or org data

  Example Use Case

  If a message comes from someone with low reach (e.g., under 1,000 followers), the AI politely deflects a meeting request. If an influencer reaches out, the AI immediately offers a booking link. Your team controls this logic by updating the Notion database — no edits to the workflow required.

  Setup

  Connect this workflow as a subworkflow in your router or Slack approval flow
  Store your Notion API key and database ID in n8n
  Provide the following parent inputs:
     message – The LinkedIn message text
     sender – Name of the sender
     chatid – Session ID (optional for memory)
     linkedinprofile – Enriched array with LinkedIn context (follower count, connection info, etc.)

  Add your preferred AI model credentials (supports OpenAI, Gemini, or Ollama)
  Optional: Customize system prompt to better match your brand voice

  How to customize this workflow to your needs

  Update the Notion schema to include industry-specific categories or actions
  Change the AI tone (e.g., humorous, more corporate, etc.)
  Add conditional logic for auto-sending messages without Slack approval
  Extend to support multiple platforms (e.g., email, X/Twitter, Instagram DMs)

nodes_used:
  ["n8n-nodes-base.notion","@n8n/n8n-nodes-langchain.agent","@n8n/n8n-nodes-langchain.lmChatOpenAi","@n8n/n8n-nodes-langchain.memoryBufferWindow","@n8n/n8n-nodes-langchain.outputParserStructured"]

workflow_json:
  {"meta":{"instanceId":"cb484ba7b742928a2048bf8829668bed5b5ad9787579adea888f05980292a4a7"},"nodes":[{"id":"ae3cbbb0-1987-4457-b91f-d1a766e09fb7","name":"When Executed by Another Workflow","type":"n8n-nodes-base.executeWorkflowTrigger","position":[-180,-60],"parameters":{"workflowInputs":{"values":[{"name":"message"},{"name":"sender"},{"name":"chatid"},{"name":"linkedinprofile","type":"array"}]}},"typeVersion":1.1},{"id":"0c10e97f-1de0-493e-9eda-a36507f40429","name":"AI Agent","type":"@n8n/n8n-nodes-langchain.agent","position":[980,-60],"parameters":{"text":"=Sender Name: {{ $('Isolate parent workflow data for AI').item.json.sender }}\nSender Message: {{ $('Isolate parent workflow data for AI').item.json.message }}\nMy Name: Your Name\n\nIf found, the linkedin profile will be below, pay close attention to the number of followers and connections: \n{{ $('When Executed by Another Workflow').item.json.linkedinprofile.toJsonString() }}","options":{"systemMessage":"=You are an expert professional assistant designed to help generate smart, personalized responses to LinkedIn messages.\n\nYou will be provided with:\n1. The **incoming message** and name from a LinkedIn user.\n2. A **database of past requests and responses**. These are known message types and the preferred replies.\n3. Context about the assistant's voice and tone.\n\n### Your Objective:\n- First, scan the database for any message that closely matches the incoming LinkedIn message. If a match is found, use the **corresponding response** as a base — you may slightly tailor it if needed (e.g., change names or dates).\n- If no close match is found, generate a **new, thoughtful reply** based on the message content, tone guidelines, and best practices in business networking. If you do not have a direct link or URL to provide from the Request Database, do not reference a website or URL. Instead say a variation of let me get back to you on that and see what I can find. \n\n### Tone Guidelines:\n- Friendly, confident, and professional — but never robotic.\n- Lightly personalized. Use the sender’s name if available.\n- Avoid sounding like a sales pitch.\n- Keep replies concise and natural, like something you'd actually send on LinkedIn.\n\n### When generating a new message:\n- Acknowledge the sender’s message.\n- Add a relevant, helpful comment or question to continue the conversation.\n- Keep the tone warm and open-ended.\n\n### Output format:\nOnly output the message text that should be sent to the user. Do not explain your reasoning. If you do not have a direct link to provide, do not reference a website or URL. Instead say let me get back to you on that and see what I can find. \n\nLet’s begin.\nRequest Database:\n\n{{ $json.dbObject.join('\\n\\n----\\n\\n') }}\n\nWhen responding, use the following format:\n{\n\t\"output\": \"message response\",\n\t\"found\": true\n}\nFor output output the message response, for found output a boolean, true if an example is found in the Request Database, false if a response is not found. The output is going to slack so ensure you escape your outputs like new lines. "},"promptType":"define","hasOutputParser":true},"typeVersion":1.9},{"id":"46cefba2-2107-4d41-b270-8442d2aae09b","name":"Simple Memory","type":"@n8n/n8n-nodes-langchain.memoryBufferWindow","position":[1100,180],"parameters":{"sessionKey":"={{ $('Isolate parent workflow data for AI').item.json.chatid }}","sessionIdType":"customKey"},"typeVersion":1.3},{"id":"3a1e8f2d-5ea9-4f31-b489-93fca3c8442e","name":"OpenAI Chat Model","type":"@n8n/n8n-nodes-langchain.lmChatOpenAi","position":[920,180],"parameters":{"model":{"__rl":true,"mode":"list","value":"gpt-4o","cachedResultName":"gpt-4o"},"options":{}},"credentials":{"openAiApi":{"id":"QpFZ2EiM3WGl6Zr3","name":"Marketing OpenAI"}},"typeVersion":1.2},{"id":"2a69d1d4-5c30-4cc1-930b-7b72cd1c0ed1","name":"Structured Output Parser","type":"@n8n/n8n-nodes-langchain.outputParserStructured","position":[1260,180],"parameters":{"jsonSchemaExample":"{\n\t\"output\": \"message response\",\n\t\"found\": true\n}"},"typeVersion":1.2},{"id":"bb9a7e05-d641-4caa-9fcc-7b1d39dd62d7","name":"Sticky Note3","type":"n8n-nodes-base.stickyNote","position":[780,-380],"parameters":{"color":7,"width":668,"height":718,"content":"![hctiapi](https://uploads.n8n.io/templates/openai.png)\n## Generate Automated response\nThe AI bot receives not only the message from LinkedIn, but also LinkedIn user context, such as the number of followers and connections, allowing for tailored responses. For example if a user asks to meet, but they don't meet a certain number of followers threshold, they are politely declined. However if an influencer reaches out, they are automatically given a booking link to ensure that high priority requests are immediately followed up on. "},"typeVersion":1},{"id":"a7f5f2b3-bc0c-450e-bbd8-60a01dc4b202","name":"Isolate parent workflow data for AI","type":"n8n-nodes-base.set","position":[20,-60],"parameters":{"options":{},"assignments":{"assignments":[{"id":"91a1191e-bac0-4b8b-b263-a03c63435470","name":"sender","type":"string","value":"={{ $json.sender }}"},{"id":"0f8c17c8-d598-4840-8b89-8dbdcd529231","name":"message","type":"string","value":"={{ $json.message }}"},{"id":"c9132b69-5e0e-4ccf-86bb-0e4cfa734860","name":"chatid","type":"string","value":"={{ $json.chatid }}"}]}},"typeVersion":3.4},{"id":"ca7625b3-2c2a-48c5-82b5-61a00ac95c81","name":"Get Request Router Directory Database","type":"n8n-nodes-base.notion","position":[220,-60],"parameters":{"options":{},"resource":"databasePage","operation":"getAll","databaseId":{"__rl":true,"mode":"list","value":"1da5b6e0-c94f-8086-80b6-eab8e340d60e","cachedResultUrl":"https://www.notion.so/1da5b6e0c94f808680b6eab8e340d60e","cachedResultName":"RequestRouterDB"}},"credentials":{"notionApi":{"id":"2B3YIiD4FMsF9Rjn","name":"Angelbot Notion"}},"typeVersion":2.2},{"id":"ffa17cbf-a9ae-4427-8aa4-a07ab97bf60b","name":"Format DB data for AI Context","type":"n8n-nodes-base.set","position":[420,-60],"parameters":{"options":{},"assignments":{"assignments":[{"id":"c4ac8c33-a220-4c07-bc0d-dc7ba7cc068e","name":"dbObject","type":"string","value":"=Request Example: {{ $json.name }}\n--\nRequest Description: {{ $json.property_request_description }}\n--\nRequest Action: {{ $json.property_request_action }}"}]}},"typeVersion":3.4},{"id":"96980e0e-632a-49dc-9cbb-a487d117e2af","name":"Aggregate DB objects into one item","type":"n8n-nodes-base.aggregate","position":[620,-60],"parameters":{"options":{},"fieldsToAggregate":{"fieldToAggregate":[{"fieldToAggregate":"dbObject"}]}},"typeVersion":1},{"id":"d66e6cc9-2955-4d45-a65b-ffc734f9a4cf","name":"Sticky Note9","type":"n8n-nodes-base.stickyNote","position":[-240,-380],"parameters":{"color":7,"width":1006,"height":640,"content":"![notion](https://uploads.n8n.io/templates/notionlogo.png)\n## Get routing Database data\nAn AI bot that does not get smarter over time is not a useful bot. That is why this bot references a shared internal database where requests routing can be updated without having to touch the n8n workflows. When a request comes in that does not have a standardized process, the AI will generate a response based on its model training. You can use this as a starting point, but when this becomes a pattern, simply updating the notion database instantly upgrades the AI bot. Not only that, but others can update the database, not only giving the AI context, but also creating a centralized location for standardized processes for handling different request types. This can be adapted for any platform, not just linkedIn, such as shared email inboxes, shared social media pages, and even for support requests. "},"typeVersion":1}],"pinData":{},"connections":{"Simple Memory":{"ai_memory":[[{"node":"AI Agent","type":"ai_memory","index":0}]]},"OpenAI Chat Model":{"ai_languageModel":[[{"node":"AI Agent","type":"ai_languageModel","index":0}]]},"Structured Output Parser":{"ai_outputParser":[[{"node":"AI Agent","type":"ai_outputParser","index":0}]]},"Format DB data for AI Context":{"main":[[{"node":"Aggregate DB objects into one item","type":"main","index":0}]]},"When Executed by Another Workflow":{"main":[[{"node":"Isolate parent workflow data for AI","type":"main","index":0}]]},"Aggregate DB objects into one item":{"main":[[{"node":"AI Agent","type":"main","index":0}]]},"Isolate parent workflow data for AI":{"main":[[{"node":"Get Request Router Directory Database","type":"main","index":0}]]},"Get Request Router Directory Database":{"main":[[{"node":"Format DB data for AI Context","type":"main","index":0}]]}}}


name: 3D Product Video Generator from 2D Image for E-Commerce Stores
author_name: InfyOm Technologies
author_username: infyom
categories: []
created_at: 2025-06-17T07:39:15.730Z
updated_at: 2025-06-17T07:39:15.730Z
url: https://n8n.io/workflows/4987
scraped_at: 2025-06-19 22:07:56
description:
  ✅ What problem does this workflow solve?

  Shopify and E-Commerce store owners often struggle to create engaging 3D videos from static product images. This workflow automates that entire process—from image upload to video delivery—so store owners can get professional-looking 3D videos without any manual editing or follow-up.

  ⚙️ What does this workflow do?

  Accepts a 2D product image and name via a public n8n form.
  Generates a unique slug and folder in Google Drive for the product.
  Uploads the original image to Google Drive and logs data in a spreadsheet.
  Removes the background from the image using remove.bg API.
  Uploads the cleaned image to Google Drive and updates the spreadsheet.
  Creates a 3D product video using the cleaned image via the Fal.ai API.
  Periodically checks the video creation status.
  Once completed, download the video, upload it to Google Drive, and log the link.
  Notifies the store owner via email with the video download link.

  🔧 Setup

  🟢 Google Services
  Google Drive**: Create and connect a folder where all product assets will be stored.
  Google Spreadsheet**: A spreadsheet to log the product name, original image link, cleaned image link, and final video URL.
  Gmail**: Connect Gmail to send the final notification email to the store owner.

  🔑 API Keys Required
  Remove.bg**: Get an API key from remove.bg.
  Fal.ai**: Sign up at fal.ai and obtain your API key to use the image-to-video generation service.

  🧠 How it Works

  📝 1. Product Form Submission
  A store owner submits the product name and 2D image via a public n8n form.

  🗂 2. Organize in Google Drive
  A unique slug is generated for the product.
  A new folder is created inside Google Drive using that slug.
  The original image is uploaded into the folder.

  📊 3. Record in a Spreadsheet
  The product name and original image URL are stored in a Google Sheet.

  🧹 4. Background Removal
  The uploaded image is processed through remove.bg API to eliminate noisy or cluttered backgrounds.
  The cleaned image is uploaded back into the product’s Drive folder.
  The cleaned image link is updated in the spreadsheet.

  🎥 5. Create 3D Video (via Fal.ai)
  The cleaned image is passed to the Fal.ai video generation API.
  The workflow periodically checks the status until the video is ready.

  ☁️ 6. Store Final Video
  Once the video is ready, the file is downloaded.
  The final video is uploaded into the same Google Drive folder.
  Its link is saved in the spreadsheet next to the respective product entry.

  📧 7. Notify the Store Owner
  An automated email is sent to the store owner with the video link, letting them know it's ready for use—no waiting, no manual follow-up needed.

  👤 Who can use it?

  This workflow is ideal for:
  🛍 Shopify Sellers
  🧺 E-commerce Store Owners
  📸 Product Photographers
  🎬 Marketing Teams
  🤖 Automation Enthusiasts

  If you want to automate 3D product video creation using AI—this is the no-code workflow you’ve been waiting for!

nodes_used:
  ["n8n-nodes-base.googleSheets","n8n-nodes-base.httpRequest","n8n-nodes-base.googleDrive","n8n-nodes-base.gmail","n8n-nodes-base.code"]

workflow_json:
  {"id":"Njfc4Qsoi6p35Bfj","meta":{"instanceId":"fcb622cbd5234c565b9b78babeaf0ea2455df9d2aad0d1adff7c1ef99583e685","templateCredsSetupCompleted":true},"name":"3D Product Video","tags":[],"nodes":[{"id":"a27f6012-7a92-436d-8c28-fa0ffca700f6","name":"Wait","type":"n8n-nodes-base.wait","position":[1120,180],"webhookId":"4d338cdb-1534-43be-97dc-070299cd6278","parameters":{"amount":40},"typeVersion":1.1},{"id":"78761c5e-dfe1-4aab-bd0f-f2812d6c0b4e","name":"On Form Submission","type":"n8n-nodes-base.formTrigger","position":[-1080,80],"webhookId":"7980414e-c599-45fe-98a7-4fd1d121154a","parameters":{"options":{},"formTitle":"Shopify 3D Product Video","formFields":{"values":[{"fieldType":"file","fieldLabel":"Product Photo","multipleFiles":false,"requiredField":true},{"fieldLabel":"Product Title","placeholder":"Product Title","requiredField":true}]},"formDescription":"Give us a product photo, title and we'll get back to you with professional marketing 3D video. "},"typeVersion":2.2},{"id":"1506bc41-d914-4031-bb47-7822c33bddcb","name":"Sticky Note","type":"n8n-nodes-base.stickyNote","position":[-1080,-160],"parameters":{"width":880,"height":140,"content":"## 3D Product Video\n\nSample Google Sheet\n- https://docs.google.com/spreadsheets/d/18k1Gq2X2J3_cbwJ9XyJoysVuhIpWhgc1cmlTKBnB3Yw/edit?gid=0#gid=0"},"typeVersion":1},{"id":"d615090d-236d-444a-add9-f9a429019088","name":"Give Access to folder","type":"n8n-nodes-base.googleDrive","position":[-420,80],"parameters":{"fileId":{"__rl":true,"mode":"id","value":"={{ $('Create Folder').item.json.id }}"},"options":{},"operation":"share","permissionsUi":{"permissionsValues":{"role":"reader","type":"anyone"}}},"credentials":{"googleDriveOAuth2Api":{"id":"aqCousOTolMFE3cy","name":"Google Drive account"}},"typeVersion":3},{"id":"29230056-71c0-4900-9d00-d017213fe856","name":"Get Image File","type":"n8n-nodes-base.code","position":[-200,80],"parameters":{"jsCode":"let results = [];\nconst items = $(\"On Form Submission\").all()\n\nfor (item of items) {\n    for (key of Object.keys(item.binary)) {\n        results.push({\n            json: {\n                fileName: item.binary[key].fileName\n            },\n            binary: {\n                data: item.binary[key],\n            }\n        });\n    }\n}\n\nreturn results;"},"executeOnce":true,"retryOnFail":true,"typeVersion":2,"alwaysOutputData":true},{"id":"ee55f4d4-475f-4220-843a-4ad8b16bbad8","name":"Upload Remove BG image","type":"n8n-nodes-base.googleDrive","position":[240,180],"parameters":{"name":"=(no-bg){{ $('Create Folder').item.json.name }}","driveId":{"__rl":true,"mode":"list","value":"My Drive"},"options":{},"folderId":{"__rl":true,"mode":"id","value":"={{ $('Create Folder').item.json.id }}"},"inputDataFieldName":"=no-bg.png"},"credentials":{"googleDriveOAuth2Api":{"id":"aqCousOTolMFE3cy","name":"Google Drive account"}},"typeVersion":3},{"id":"33180073-9abe-4a92-9f82-2486a8b58eab","name":"Extract Image ID from URL","type":"n8n-nodes-base.code","position":[680,180],"parameters":{"jsCode":"const url = $input.first().json['BG Remove Image']\n\n// Extract the ID using a regular expression\nconst match = url.match(/\\/d\\/([^/]+)/);\n\nreturn {\n  json: {\n    fileId: match ? match[1] : null,\n  },\n};"},"typeVersion":2},{"id":"88d1f349-959a-498f-8f2f-ab45d3d9b25f","name":"Upload Video","type":"n8n-nodes-base.googleDrive","position":[2220,180],"parameters":{"name":"=Video-file","driveId":{"__rl":true,"mode":"list","value":"My Drive"},"options":{},"folderId":{"__rl":true,"mode":"id","value":"={{ $('Create Folder').item.json.id }}"},"inputDataFieldName":"Video-file"},"credentials":{"googleDriveOAuth2Api":{"id":"aqCousOTolMFE3cy","name":"Google Drive account"}},"typeVersion":3},{"id":"bf26fc49-f91c-40f1-83d3-d2330f242f56","name":"Create Folder","type":"n8n-nodes-base.googleDrive","position":[-640,80],"parameters":{"name":"={{ $json.slug }}","driveId":{"__rl":true,"mode":"list","value":"My Drive"},"options":{},"folderId":{"__rl":true,"mode":"list","value":"root","cachedResultUrl":"https://drive.google.com/drive","cachedResultName":"/ (Root folder)"},"resource":"folder"},"credentials":{"googleDriveOAuth2Api":{"id":"aqCousOTolMFE3cy","name":"Google Drive account"}},"typeVersion":3},{"id":"4eadd7af-a13d-40a8-b886-71c798acc547","name":"Create Slug","type":"n8n-nodes-base.code","position":[-860,80],"parameters":{"jsCode":"const title = $json[\"Product Title\"] || \"default\";\nconst slug = title.toLowerCase().replace(/\\s+/g, '-') + '-' + Math.random().toString(36).substring(2, 8);\nreturn { slug };\n"},"typeVersion":2},{"id":"e53cab81-e81c-412a-a8c1-bf889e6ee063","name":"Create Video","type":"n8n-nodes-base.httpRequest","position":[900,180],"parameters":{"url":"https://queue.fal.run/fal-ai/kling-video/v1/standard/image-to-video","method":"POST","options":{},"sendBody":true,"sendHeaders":true,"bodyParameters":{"parameters":[{"name":"prompt","value":"A product placed on a reflective surface slowly rotates 360 degrees with dramatic studio lighting, soft shadows, and a smooth camera pan. The background is clean, minimal, and cinematic, highlighting the product’s details and elegance"},{"name":"image_url","value":"=https://drive.usercontent.google.com/download?id={{ $json.fileId }}&export=view&authuser=0"}]},"headerParameters":{"parameters":[{"name":"Authorization","value":"Key api_key"}]}},"typeVersion":4.2},{"id":"037d6b30-34fe-4fd7-918a-c7d3025b5bfe","name":"Check Video Status","type":"n8n-nodes-base.httpRequest","position":[1340,105],"parameters":{"url":"={{ $json.status_url }}","options":{},"sendHeaders":true,"headerParameters":{"parameters":[{"name":"Authorization","value":"Key api_key"}]}},"typeVersion":4.2},{"id":"2a74bdb2-efcb-4ede-ba3d-e0716a719c96","name":"Get Video Link","type":"n8n-nodes-base.httpRequest","position":[1780,180],"parameters":{"url":"={{ $json.response_url }}","options":{},"sendHeaders":true,"headerParameters":{"parameters":[{"name":"Authorization","value":"Key api_key"}]}},"typeVersion":4.2},{"id":"fbf59ebf-991e-4b77-8987-77716c06af0f","name":"Remove Image Background","type":"n8n-nodes-base.httpRequest","position":[20,180],"parameters":{"url":"https://api.remove.bg/v1.0/removebg","method":"POST","options":{"response":{"response":{"responseFormat":"file","outputPropertyName":"no-bg.png"}}},"sendBody":true,"contentType":"multipart-form-data","sendHeaders":true,"bodyParameters":{"parameters":[{"name":"size","value":"auto"},{"name":"image_file","parameterType":"formBinaryData","inputDataFieldName":"=data"}]},"headerParameters":{"parameters":[{"name":"X-API-Key","value":"api_key"}]}},"executeOnce":false,"typeVersion":4.2},{"id":"4c10c26e-3caa-45f0-bf12-9779cd82d87c","name":"Upload Original Image","type":"n8n-nodes-base.googleDrive","position":[20,-20],"parameters":{"name":"={{ $('Create Folder').item.json.name }}","driveId":{"__rl":true,"mode":"list","value":"My Drive"},"options":{},"folderId":{"__rl":true,"mode":"id","value":"={{ $('Create Folder').item.json.id }}"}},"credentials":{"googleDriveOAuth2Api":{"id":"aqCousOTolMFE3cy","name":"Google Drive account"}},"typeVersion":3},{"id":"1b9c83e7-5d77-4477-9518-d72a6c2f624a","name":"Insert New Product","type":"n8n-nodes-base.googleSheets","position":[240,-20],"parameters":{"columns":{"value":{"Slug":"={{ $('Create Slug').item.json.slug }}","Product Title":"={{ $('On Form Submission').item.json['Product Title'] }}","Original Image":"={{ $json.webViewLink }}"},"schema":[{"id":"Original Image","type":"string","display":true,"removed":false,"required":false,"displayName":"Original Image","defaultMatch":false,"canBeUsedToMatch":true},{"id":"BG Remove Image","type":"string","display":true,"removed":true,"required":false,"displayName":"BG Remove Image","defaultMatch":false,"canBeUsedToMatch":true},{"id":"Product Title","type":"string","display":true,"removed":false,"required":false,"displayName":"Product Title","defaultMatch":false,"canBeUsedToMatch":true},{"id":"Video Link","type":"string","display":true,"removed":true,"required":false,"displayName":"Video Link","defaultMatch":false,"canBeUsedToMatch":true},{"id":"Slug","type":"string","display":true,"removed":false,"required":false,"displayName":"Slug","defaultMatch":false,"canBeUsedToMatch":true}],"mappingMode":"defineBelow","matchingColumns":[],"attemptToConvertTypes":false,"convertFieldsToString":false},"options":{},"operation":"append","sheetName":{"__rl":true,"mode":"list","value":"gid=0","cachedResultUrl":"https://docs.google.com/spreadsheets/d/18k1Gq2X2J3_cbwJ9XyJoysVuhIpWhgc1cmlTKBnB3Yw/edit#gid=0","cachedResultName":"Sheet1"},"documentId":{"__rl":true,"mode":"list","value":"18k1Gq2X2J3_cbwJ9XyJoysVuhIpWhgc1cmlTKBnB3Yw","cachedResultUrl":"https://docs.google.com/spreadsheets/d/18k1Gq2X2J3_cbwJ9XyJoysVuhIpWhgc1cmlTKBnB3Yw/edit?usp=drivesdk","cachedResultName":"3D Product Video"}},"credentials":{"googleSheetsOAuth2Api":{"id":"9JjVrrcwf7D4bsa6","name":"Google Credentials"}},"typeVersion":4.5},{"id":"b3492513-e591-4106-a806-9fb1c43f513b","name":"Update Remove BG URL","type":"n8n-nodes-base.googleSheets","position":[460,180],"parameters":{"columns":{"value":{"Slug":"={{ $('Create Folder').item.json.name }}","BG Remove Image":"={{ $json.webViewLink }}"},"schema":[{"id":"Original Image","type":"string","display":true,"removed":true,"required":false,"displayName":"Original Image","defaultMatch":false,"canBeUsedToMatch":true},{"id":"BG Remove Image","type":"string","display":true,"removed":false,"required":false,"displayName":"BG Remove Image","defaultMatch":false,"canBeUsedToMatch":true},{"id":"Product Title","type":"string","display":true,"removed":true,"required":false,"displayName":"Product Title","defaultMatch":false,"canBeUsedToMatch":true},{"id":"Video Link","type":"string","display":true,"removed":true,"required":false,"displayName":"Video Link","defaultMatch":false,"canBeUsedToMatch":true},{"id":"Slug","type":"string","display":true,"removed":false,"required":false,"displayName":"Slug","defaultMatch":false,"canBeUsedToMatch":true}],"mappingMode":"defineBelow","matchingColumns":["Slug"],"attemptToConvertTypes":false,"convertFieldsToString":false},"options":{},"operation":"appendOrUpdate","sheetName":{"__rl":true,"mode":"list","value":"gid=0","cachedResultUrl":"https://docs.google.com/spreadsheets/d/18k1Gq2X2J3_cbwJ9XyJoysVuhIpWhgc1cmlTKBnB3Yw/edit#gid=0","cachedResultName":"Sheet1"},"documentId":{"__rl":true,"mode":"list","value":"18k1Gq2X2J3_cbwJ9XyJoysVuhIpWhgc1cmlTKBnB3Yw","cachedResultUrl":"https://docs.google.com/spreadsheets/d/18k1Gq2X2J3_cbwJ9XyJoysVuhIpWhgc1cmlTKBnB3Yw/edit?usp=drivesdk","cachedResultName":"3D Product Video"}},"credentials":{"googleSheetsOAuth2Api":{"id":"9JjVrrcwf7D4bsa6","name":"Google Credentials"}},"typeVersion":4.5},{"id":"cbc141e9-7cf5-4c57-a4b1-d719182cb997","name":"Is In Progress","type":"n8n-nodes-base.if","position":[1560,180],"parameters":{"options":{},"conditions":{"options":{"version":2,"leftValue":"","caseSensitive":true,"typeValidation":"strict"},"combinator":"and","conditions":[{"id":"8ada0859-b74f-4d48-ae95-30c34340e39f","operator":{"type":"string","operation":"equals"},"leftValue":"={{ $json.status }}","rightValue":"IN_PROGRESS"}]}},"typeVersion":2.2},{"id":"eb09040d-f4d9-419e-be9c-361a2ef65531","name":"Convert to Binary File","type":"n8n-nodes-base.httpRequest","position":[2000,180],"parameters":{"url":"={{ $json.video.url }}","options":{"response":{"response":{"responseFormat":"file","outputPropertyName":"Video-file"}}}},"typeVersion":4.2},{"id":"b2c905dc-2743-4b5d-b850-facecd489166","name":"Update Video Link","type":"n8n-nodes-base.googleSheets","position":[2440,180],"parameters":{"columns":{"value":{"Slug":"={{ $('Create Folder').item.json.name }}","Video Link":"={{ $('Get Video Link').item.json.video.url }}"},"schema":[{"id":"Original Image","type":"string","display":true,"removed":true,"required":false,"displayName":"Original Image","defaultMatch":false,"canBeUsedToMatch":true},{"id":"BG Remove Image","type":"string","display":true,"removed":true,"required":false,"displayName":"BG Remove Image","defaultMatch":false,"canBeUsedToMatch":true},{"id":"Product Title","type":"string","display":true,"removed":true,"required":false,"displayName":"Product Title","defaultMatch":false,"canBeUsedToMatch":true},{"id":"Video Link","type":"string","display":true,"removed":false,"required":false,"displayName":"Video Link","defaultMatch":false,"canBeUsedToMatch":true},{"id":"Slug","type":"string","display":true,"removed":false,"required":false,"displayName":"Slug","defaultMatch":false,"canBeUsedToMatch":true}],"mappingMode":"defineBelow","matchingColumns":["Slug"],"attemptToConvertTypes":false,"convertFieldsToString":false},"options":{},"operation":"appendOrUpdate","sheetName":{"__rl":true,"mode":"list","value":"gid=0","cachedResultUrl":"https://docs.google.com/spreadsheets/d/18k1Gq2X2J3_cbwJ9XyJoysVuhIpWhgc1cmlTKBnB3Yw/edit#gid=0","cachedResultName":"Sheet1"},"documentId":{"__rl":true,"mode":"list","value":"18k1Gq2X2J3_cbwJ9XyJoysVuhIpWhgc1cmlTKBnB3Yw","cachedResultUrl":"https://docs.google.com/spreadsheets/d/18k1Gq2X2J3_cbwJ9XyJoysVuhIpWhgc1cmlTKBnB3Yw/edit?usp=drivesdk","cachedResultName":"3D Product Video"}},"credentials":{"googleSheetsOAuth2Api":{"id":"9JjVrrcwf7D4bsa6","name":"Google Credentials"}},"typeVersion":4.5},{"id":"7adb552d-939f-42d1-b425-45b88d52aa71","name":"Send E-Mail Notification","type":"n8n-nodes-base.gmail","position":[2660,180],"webhookId":"346e7266-8fb6-4b86-9b32-2ca6c1258566","parameters":{"sendTo":"example@gmail.com","message":"=<p>Hi there! 👋</p>\n\n<p><b>We’re excited to share our latest product video with you! 🎉<b></p>\n\n<p>Watch it here to see the product video you’ll love:<br>\n<a href=\"{{ $('Get Video Link').item.json.video.url }}\">{{ $('Get Video Link').item.json.video.url }}</a></p>\n\n<p>Don’t miss out—this could be just what you’ve been looking for! ✨</p>\n\n<p><b>Thanks for being part of our community! 🙌<b></p>\n","options":{"appendAttribution":false},"subject":"Product Video"},"credentials":{"gmailOAuth2":{"id":"hLh5uexmYpuaLRC3","name":"Gmail account 2"}},"typeVersion":2.1}],"active":false,"pinData":{},"settings":{"executionOrder":"v1"},"versionId":"51abcabc-2833-4f0d-a153-404df659bfb6","connections":{"Wait":{"main":[[{"node":"Check Video Status","type":"main","index":0}]]},"Create Slug":{"main":[[{"node":"Create Folder","type":"main","index":0}]]},"Create Video":{"main":[[{"node":"Wait","type":"main","index":0}]]},"Upload Video":{"main":[[{"node":"Update Video Link","type":"main","index":0}]]},"Create Folder":{"main":[[{"node":"Give Access to folder","type":"main","index":0}]]},"Get Image File":{"main":[[{"node":"Upload Original Image","type":"main","index":0},{"node":"Remove Image Background","type":"main","index":0}]]},"Get Video Link":{"main":[[{"node":"Convert to Binary File","type":"main","index":0}]]},"Is In Progress":{"main":[[{"node":"Wait","type":"main","index":0}],[{"node":"Get Video Link","type":"main","index":0}]]},"Update Video Link":{"main":[[{"node":"Send E-Mail Notification","type":"main","index":0}]]},"Check Video Status":{"main":[[{"node":"Is In Progress","type":"main","index":0}]]},"Insert New Product":{"main":[[]]},"On Form Submission":{"main":[[{"node":"Create Slug","type":"main","index":0}]]},"Update Remove BG URL":{"main":[[{"node":"Extract Image ID from URL","type":"main","index":0}]]},"Give Access to folder":{"main":[[{"node":"Get Image File","type":"main","index":0}]]},"Upload Original Image":{"main":[[{"node":"Insert New Product","type":"main","index":0}]]},"Convert to Binary File":{"main":[[{"node":"Upload Video","type":"main","index":0}]]},"Upload Remove BG image":{"main":[[{"node":"Update Remove BG URL","type":"main","index":0}]]},"Remove Image Background":{"main":[[{"node":"Upload Remove BG image","type":"main","index":0}]]},"Extract Image ID from URL":{"main":[[{"node":"Create Video","type":"main","index":0}]]}}}


name: RAG Starter Template using Simple Vector Stores, Form trigger and OpenAI
author_name: n8n Team
author_username: n8n-team
categories: []
created_at: 2025-06-17T19:16:08.694Z
updated_at: 2025-06-17T19:16:08.694Z
url: https://n8n.io/workflows/5010
scraped_at: 2025-06-19 22:07:56
description:
  This template quickly shows how to use RAG in n8n.

  Who is this for?
  This template is for everyone who wants to start giving knowledge to their Agents through RAG.

  Requirements
  Have a PDF with custom knowledge that you want to provide to your agent.

  Setup
  No setup required. Just hit Execute Workflow, upload your knowledge document and then start chatting.

  How to customize this to your needs
  Add custom instructions to your Agent by changing the prompts in it.
  Add a different way to load in knowledge to your vector store, e.g. by looking at some Google Drive files or loading knowledge from a table.
  Exchange the Simple Vector Store nodes with your own vector store tools ready for production.
  Add a more sophisticated way to rank files found in the vector store.

  For more information read our docs on RAG in n8n.

nodes_used:
  ["@n8n/n8n-nodes-langchain.agent","@n8n/n8n-nodes-langchain.embeddingsOpenAi","@n8n/n8n-nodes-langchain.lmChatOpenAi","@n8n/n8n-nodes-langchain.vectorStoreInMemory","@n8n/n8n-nodes-langchain.documentDefaultDataLoader"]

workflow_json:
  {"meta":{"instanceId":"257476b1ef58bf3cb6a46e65fac7ee34a53a5e1a8492d5c6e4da5f87c9b82833"},"nodes":[{"id":"83ed351e-90e8-458f-a01b-73001ef1800f","name":"Upload your file here","type":"n8n-nodes-base.formTrigger","position":[220,-120],"webhookId":"82848bc4-5ea2-4e5a-8bb6-3c09b94a8c5d","parameters":{"options":{},"formTitle":"Upload your data to test RAG","formFields":{"values":[{"fieldType":"file","fieldLabel":"Upload your file(s)","requiredField":true,"acceptFileTypes":".pdf, .csv"}]}},"typeVersion":2.2},{"id":"26d63e24-2592-41f9-9b4b-edab81e99f21","name":"Embeddings OpenAI","type":"@n8n/n8n-nodes-langchain.embeddingsOpenAi","position":[860,360],"parameters":{"options":{}},"credentials":{"openAiApi":{"id":"14","name":"OpenAi account"}},"typeVersion":1.2},{"id":"3a69c8a7-bf95-4de2-84b0-ae2cc3d2e4e7","name":"Default Data Loader","type":"@n8n/n8n-nodes-langchain.documentDefaultDataLoader","position":[660,40],"parameters":{"options":{},"dataType":"binary"},"typeVersion":1.1},{"id":"0b42832b-c9e8-4627-b36c-94fc5e242b33","name":"Sticky Note","type":"n8n-nodes-base.stickyNote","position":[-320,-180],"parameters":{"color":4,"width":440,"height":300,"content":"### Readme\nLoad your data into a vector database with the 📚 **Load Data** flow, and then use your data as chat context with the 🐕 **Retriever** flow.\n\n**Quick start**\n1. Click on the `Execute Workflow` button to run the 📚 **Load Data** flow.\n2. Click on `Open Chat` button to run the 🐕 **Retriever** flow. Then ask a question about content from your document(s)\n\n\nFor more info, check our [docs on RAG in n8n](https://docs.n8n.io/advanced-ai/rag-in-n8n/)"},"typeVersion":1},{"id":"f902ab8f-4620-4a95-86f7-c5857c4d6c4f","name":"Sticky Note1","type":"n8n-nodes-base.stickyNote","position":[160,-180],"parameters":{"color":7,"width":700,"height":460,"content":"### 📚 Load Data Flow"},"typeVersion":1},{"id":"0f4185ea-d7a9-44a9-a824-98f9dc2c2a5d","name":"Insert Data to Store","type":"@n8n/n8n-nodes-langchain.vectorStoreInMemory","position":[400,-120],"parameters":{"mode":"insert","memoryKey":{"__rl":true,"mode":"list","value":"vector_store_key","cachedResultName":"vector_store_key"}},"typeVersion":1.2},{"id":"ce86b41b-7e1b-458f-ab13-d6b187854ae8","name":"Query Data Tool","type":"@n8n/n8n-nodes-langchain.vectorStoreInMemory","position":[1280,80],"parameters":{"mode":"retrieve-as-tool","toolName":"knowledge_base","memoryKey":{"__rl":true,"mode":"list","value":"vector_store_key"},"toolDescription":"Use this knowledge base to answer questions from the user"},"typeVersion":1.2},{"id":"0039537b-558c-4fe8-9716-f8aa13676f4a","name":"AI Agent","type":"@n8n/n8n-nodes-langchain.agent","position":[1280,-140],"parameters":{"options":{}},"typeVersion":2},{"id":"2669a65e-f0f3-45aa-95c0-621b15a4fc67","name":"When chat message received","type":"@n8n/n8n-nodes-langchain.chatTrigger","position":[1060,-140],"webhookId":"4091fa09-fb9a-4039-9411-7104d213f601","parameters":{"options":{}},"typeVersion":1.1},{"id":"d43cf585-4192-4f53-9532-4677923289ba","name":"OpenAI Chat Model","type":"@n8n/n8n-nodes-langchain.lmChatOpenAi","position":[1060,80],"parameters":{"model":{"__rl":true,"mode":"list","value":"gpt-4o-mini"},"options":{}},"typeVersion":1.2},{"id":"3d1b3f5a-bc35-4739-a618-9c85820d39a0","name":"Sticky Note2","type":"n8n-nodes-base.stickyNote","position":[940,-180],"parameters":{"color":7,"width":680,"height":460,"content":"### 🐕 2. Retriever Flow"},"typeVersion":1},{"id":"8d4c68cf-64d1-4b3a-bb19-2f003303c1df","name":"Sticky Note3","type":"n8n-nodes-base.stickyNote","position":[1000,320],"parameters":{"color":4,"width":320,"height":240,"content":"### Embeddings\n\nThe Insert and Retrieve operation use the same embedding node.\n\nThis is to ensure that they are using the **exact same embeddings and settings**.\n\nDifferent embeddings might not work at all, or have unintended consequences.\n"},"typeVersion":1}],"pinData":{},"connections":{"Query Data Tool":{"ai_tool":[[{"node":"AI Agent","type":"ai_tool","index":0}]]},"Embeddings OpenAI":{"ai_embedding":[[{"node":"Insert Data to Store","type":"ai_embedding","index":0},{"node":"Query Data Tool","type":"ai_embedding","index":0}]]},"OpenAI Chat Model":{"ai_languageModel":[[{"node":"AI Agent","type":"ai_languageModel","index":0}]]},"Default Data Loader":{"ai_document":[[{"node":"Insert Data to Store","type":"ai_document","index":0}]]},"Upload your file here":{"main":[[{"node":"Insert Data to Store","type":"main","index":0}]]},"When chat message received":{"main":[[{"node":"AI Agent","type":"main","index":0}]]}}}


name: Save Costs In RAG Workflows using the Q&A Tool With Multiple Models
author_name: Niklas Hatje
author_username: nik8n
categories: []
created_at: 2025-06-17T19:30:43.009Z
updated_at: 2025-06-17T19:30:43.009Z
url: https://n8n.io/workflows/5011
scraped_at: 2025-06-19 22:07:56
description:
  This template shows how to use the Question and Answer tool to save costs in RAG use cases.

  Who is this for?
  This template is for everyone who wants to start giving knowledge to their Agents through RAG.

  Requirements
  Have a PDF with custom knowledge that you want to provide to your agent.

  Setup
  No setup required. Just hit Execute Workflow, upload your knowledge document and then start chatting.

  How to customize this to your needs
  Add custom instructions to your Agent by changing the prompts in it.
  Add a different way to load in knowledge to your vector store, e.g. by looking at some Google Drive files or loading knowledge from a table.
  Describe your data properly in the Q&A tool
  Exchange the Simple Vector Store nodes with your own vector store tools ready for production.
  Add a more sophisticated way to rank files found in the vector store.

  For more information read our docs on RAG in n8n.

nodes_used:
  ["@n8n/n8n-nodes-langchain.agent","@n8n/n8n-nodes-langchain.embeddingsOpenAi","@n8n/n8n-nodes-langchain.lmChatOpenAi","@n8n/n8n-nodes-langchain.vectorStoreInMemory","@n8n/n8n-nodes-langchain.documentDefaultDataLoader","@n8n/n8n-nodes-langchain.toolVectorStore"]

workflow_json:
  {"meta":{"instanceId":"257476b1ef58bf3cb6a46e65fac7ee34a53a5e1a8492d5c6e4da5f87c9b82833","templateCredsSetupCompleted":true},"nodes":[{"id":"83ed351e-90e8-458f-a01b-73001ef1800f","name":"Upload your file here","type":"n8n-nodes-base.formTrigger","position":[220,-120],"webhookId":"82848bc4-5ea2-4e5a-8bb6-3c09b94a8c5d","parameters":{"options":{},"formTitle":"Upload your data to test RAG","formFields":{"values":[{"fieldType":"file","fieldLabel":"Upload your file(s)","requiredField":true,"acceptFileTypes":".pdf, .csv"}]}},"typeVersion":2.2},{"id":"26d63e24-2592-41f9-9b4b-edab81e99f21","name":"Embeddings OpenAI","type":"@n8n/n8n-nodes-langchain.embeddingsOpenAi","position":[860,460],"parameters":{"options":{}},"credentials":{"openAiApi":{"id":"14","name":"OpenAi account"}},"typeVersion":1.2},{"id":"3a69c8a7-bf95-4de2-84b0-ae2cc3d2e4e7","name":"Default Data Loader","type":"@n8n/n8n-nodes-langchain.documentDefaultDataLoader","position":[660,40],"parameters":{"options":{},"dataType":"binary"},"typeVersion":1.1},{"id":"0b42832b-c9e8-4627-b36c-94fc5e242b33","name":"Sticky Note","type":"n8n-nodes-base.stickyNote","position":[-320,-180],"parameters":{"color":4,"width":440,"height":300,"content":"### Readme\nLoad your data into a vector database with the 📚 **Load Data** flow, and then use your data as chat context with the 🐕 **Retriever** flow.\n\n**Quick start**\n1. Click on the `Execute Workflow` button to run the 📚 **Load Data** flow.\n2. Click on `Open Chat` button to run the 🐕 **Retriever** flow. Then ask a question about content from your document(s)\n\n\nFor more info, check our [docs on RAG in n8n](https://docs.n8n.io/advanced-ai/rag-in-n8n/)"},"typeVersion":1},{"id":"f902ab8f-4620-4a95-86f7-c5857c4d6c4f","name":"Sticky Note1","type":"n8n-nodes-base.stickyNote","position":[160,-180],"parameters":{"color":7,"width":700,"height":460,"content":"### 📚 Load Data Flow"},"typeVersion":1},{"id":"0f4185ea-d7a9-44a9-a824-98f9dc2c2a5d","name":"Insert Data to Store","type":"@n8n/n8n-nodes-langchain.vectorStoreInMemory","position":[400,-120],"parameters":{"mode":"insert","memoryKey":{"__rl":true,"mode":"list","value":"vector_store_key","cachedResultName":"vector_store_key"}},"typeVersion":1.2},{"id":"ce86b41b-7e1b-458f-ab13-d6b187854ae8","name":"Query Data Tool","type":"@n8n/n8n-nodes-langchain.vectorStoreInMemory","position":[1300,200],"parameters":{"memoryKey":{"__rl":true,"mode":"list","value":"vector_store_key"}},"typeVersion":1.2},{"id":"0039537b-558c-4fe8-9716-f8aa13676f4a","name":"AI Agent","type":"@n8n/n8n-nodes-langchain.agent","position":[1280,-140],"parameters":{"options":{}},"typeVersion":2},{"id":"2669a65e-f0f3-45aa-95c0-621b15a4fc67","name":"When chat message received","type":"@n8n/n8n-nodes-langchain.chatTrigger","position":[1060,-140],"webhookId":"4091fa09-fb9a-4039-9411-7104d213f601","parameters":{"options":{}},"typeVersion":1.1},{"id":"3d1b3f5a-bc35-4739-a618-9c85820d39a0","name":"Sticky Note2","type":"n8n-nodes-base.stickyNote","position":[940,-180],"parameters":{"color":7,"width":820,"height":520,"content":"### 🐕 2. Retriever Flow"},"typeVersion":1},{"id":"6553a758-c655-4196-88be-9d93187f9c7b","name":"Answer questions with a vector store","type":"@n8n/n8n-nodes-langchain.toolVectorStore","position":[1440,60],"parameters":{"description":"The data contains custom knowledge"},"typeVersion":1.1},{"id":"d43cf585-4192-4f53-9532-4677923289ba","name":"Expensive model","type":"@n8n/n8n-nodes-langchain.lmChatOpenAi","position":[1060,80],"parameters":{"model":{"__rl":true,"mode":"list","value":"gpt-4.1","cachedResultName":"gpt-4.1"},"options":{}},"credentials":{"openAiApi":{"id":"14","name":"OpenAi account"}},"typeVersion":1.2},{"id":"18dcc49d-9ce0-4746-8135-7e4c77cfa501","name":"Cheap Model","type":"@n8n/n8n-nodes-langchain.lmChatOpenAi","position":[1600,200],"parameters":{"model":{"__rl":true,"mode":"list","value":"gpt-4.1-mini"},"options":{}},"credentials":{"openAiApi":{"id":"14","name":"OpenAi account"}},"typeVersion":1.2}],"pinData":{},"connections":{"Cheap Model":{"ai_languageModel":[[{"node":"Answer questions with a vector store","type":"ai_languageModel","index":0}]]},"Expensive model":{"ai_languageModel":[[{"node":"AI Agent","type":"ai_languageModel","index":0}]]},"Query Data Tool":{"ai_tool":[[]],"ai_vectorStore":[[{"node":"Answer questions with a vector store","type":"ai_vectorStore","index":0}]]},"Embeddings OpenAI":{"ai_embedding":[[{"node":"Insert Data to Store","type":"ai_embedding","index":0},{"node":"Query Data Tool","type":"ai_embedding","index":0}]]},"Default Data Loader":{"ai_document":[[{"node":"Insert Data to Store","type":"ai_document","index":0}]]},"Upload your file here":{"main":[[{"node":"Insert Data to Store","type":"main","index":0}]]},"When chat message received":{"main":[[{"node":"AI Agent","type":"main","index":0}]]},"Answer questions with a vector store":{"ai_tool":[[{"node":"AI Agent","type":"ai_tool","index":0}]]}}}


