{
  "id": "MRINKwuP8BvQjCU1",
  "meta": {
    "templateCredsSetupCompleted": true
  },
  "name": "Automate Research with Decodo, OpenAI, and Gmail",
  "tags": [],
  "nodes": [
    {
      "id": "0da43c80-0f67-49cc-a23b-b43502b41f83",
      "name": "Main Overview",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        5776,
        -1488
      ],
      "parameters": {
        "width": 386,
        "height": 519,
        "content": "### How it works\nThis workflow automates the collection and analysis of AI/LLM research. It runs on a weekly schedule to:\n1. **Search:** Fetch the latest articles using the Decodo API.\n2. **Scrape:** Extract the full text content from each result, filtering out noise.\n3. **Summarize:** Use an LLM to generate dense, technical summaries of every article.\n4. **Report:** An AI Agent analyzes all summaries to score their relevance and compiles a final intelligence report email.\n\n### Setup steps\n1. **Credentials:** Add your `Decodo` and `OpenAI` API keys in the workflow credentials.\n2. **Schedule:** Adjust the **Weekly Trigger** node to your preferred day and time.\n3. **Search Config:** Update the `search_query` in the **Set Search Config** node if you want to track a different topic.\n4. **Email:** Change the recipient email address in both **Send Email** nodes.\n\n### Customization tips\n- Adjust the \"Relevance Score\" prompt in the **Research Analyst Agent** node to make the filtering stricter or looser."
      },
      "typeVersion": 1
    },
    {
      "id": "62878aa3-dc4d-41d0-bd3b-b05462e19258",
      "name": "Section 1",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        6176,
        -1328
      ],
      "parameters": {
        "color": 4,
        "width": 950,
        "height": 256,
        "content": "## 1. Search & Filter\nConfigure the search parameters, fetch results from Google via Decodo, and filter out non-article URLs (e.g., YouTube)."
      },
      "typeVersion": 1
    },
    {
      "id": "389d463e-6da6-4d78-a402-771f11878e7d",
      "name": "Section 2",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        7200,
        -1312
      ],
      "parameters": {
        "color": 4,
        "width": 900,
        "height": 592,
        "content": "## 2. Scrape & Sanitize\nLoop through each URL, download the raw HTML, and clean it to remove scripts/styles before passing to the LLM."
      },
      "typeVersion": 1
    },
    {
      "id": "9c87b6e3-05d2-486a-8d74-1552ab66269a",
      "name": "Section 3",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        8176,
        -1344
      ],
      "parameters": {
        "color": 4,
        "width": 480,
        "height": 480,
        "content": "## 3. Summarize Content\nGenerate concise, dense summaries for each individual article using an LLM Chain."
      },
      "typeVersion": 1
    },
    {
      "id": "1b10ef37-abe3-4a5a-aa8d-0a4a9f78779d",
      "name": "Section 4",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        8720,
        -1344
      ],
      "parameters": {
        "color": 4,
        "width": 1000,
        "height": 480,
        "content": "## 4. Analyze & Report\nAn AI Agent reviews all summaries, ranks them by relevance, and sends the final email report."
      },
      "typeVersion": 1
    },
    {
      "id": "4a88cfde-00ef-466f-80e3-f244241c838f",
      "name": "Weekly Trigger",
      "type": "n8n-nodes-base.scheduleTrigger",
      "position": [
        6208,
        -1232
      ],
      "parameters": {
        "rule": {
          "interval": [
            {
              "daysInterval": 7,
              "triggerAtHour": 6
            }
          ]
        }
      },
      "typeVersion": 1.2
    },
    {
      "id": "8467ff7c-d60a-46f1-8daa-94d895dcd0f3",
      "name": "Filter & Parse URLs",
      "type": "n8n-nodes-base.code",
      "position": [
        7024,
        -1232
      ],
      "parameters": {
        "jsCode": "// Safely get the organic results array from Decodo Google Search\n\nconst root = $json.results?.[0]?.content?.results;\n\n// Handle different Decodo response shapes\nconst organic = root?.results?.organic || root?.organic || [];\n\nif (!Array.isArray(organic) || organic.length === 0) {\n  return []; // nothing to process\n}\n\n// Filter out YouTube links, then map\nreturn organic\n  .filter(item => {\n    const url = (item.url || \"\").toLowerCase();\n    return !url.includes(\"youtube.com\") && !url.includes(\"youtu.be\");\n  })\n  .map(item => ({\n    json: {\n      url: item.url || \"\",\n      title: item.title || \"\",\n      desc: item.desc || \"\",\n      pos: item.pos || item.pos_overall || null,\n      url_shown: item.url_shown || \"\",\n      favicon_text: item.favicon_text || \"\",\n      region: $json.region || \"\",\n      platform: $json.platform || \"\"\n    }\n  }));\n"
      },
      "typeVersion": 2
    },
    {
      "id": "f0fa2db8-c14c-4e98-925a-324ccb94610b",
      "name": "Batch Loop",
      "type": "n8n-nodes-base.splitInBatches",
      "position": [
        7232,
        -1232
      ],
      "parameters": {
        "options": {}
      },
      "typeVersion": 3
    },
    {
      "id": "a9f2008f-883a-489f-8934-a162c5ff0166",
      "name": "Sanitize HTML",
      "type": "n8n-nodes-base.code",
      "position": [
        7936,
        -1120
      ],
      "parameters": {
        "mode": "runOnceForEachItem",
        "jsCode": "const item = $input.item.json;\n\nlet html = \"\";\n\ntry {\n  html = item.results[0].content || \"\";\n} catch (e) {\n  html = \"\";\n}\n\nlet cleaned = html\n  .replace(/<script[^>]*>[\\s\\S]*?<\\/script>/gi, \"\")\n  .replace(/<style[^>]*>[\\s\\S]*?<\\/style>/gi, \"\")\n  .replace(/<noscript[^>]*>[\\s\\S]*?<\\/noscript>/gi, \"\")\n  .replace(/<\\/?[^>]+>/g, \" \")\n  .replace(/&nbsp;/gi, \" \")\n  .replace(/&amp;/gi, \"&\")\n  .replace(/&quot;/gi, '\"')\n  .replace(/&#39;/gi, \"'\")\n  .replace(/&lt;/gi, \"<\")\n  .replace(/&gt;/gi, \">\")\n  .replace(/\\s+/g, \" \")\n  .trim();\n\nreturn {\n  json: {\n    text_clean: cleaned\n  }\n};\n"
      },
      "typeVersion": 2
    },
    {
      "id": "70fe01b3-73ec-41c5-a8cc-f5f512063e59",
      "name": "Summarize Chain",
      "type": "@n8n/n8n-nodes-langchain.chainSummarization",
      "position": [
        8208,
        -1248
      ],
      "parameters": {
        "options": {
          "summarizationMethodAndPrompts": {
            "values": {
              "prompt": "=You will receive cleaned raw text {{ $json.text_clean }} from an AI / LLM related webpage\n(article, blog post, research announcement, release note, or news page).\n\nYour task is to produce a short, dense summary focused ONLY on useful AI / LLM insights.\n\nDo NOT rewrite the entire page.\nDo NOT include marketing fluff, branding, author bios, disclaimers, navigation text, or repeated sections.\n\nExtract ONLY the following information IF it appears in the text:\n\n- Main topic or announcement\n- Model / tool / company name (if any)\n- Type of update (model release, research paper, feature update, benchmark, policy, funding, etc.)\n- Key points or changes (max 3 short bullets)\n- Why it matters (1 short line, practical impact)\n\nReturn the result as a **short human-readable text summary**, NOT JSON.\n\nStyle example:\n\n\u201cTopic: New LLM Model Release  \nEntity: Company X \u2013 Model Y  \nType: Model release  \nKey points: \u2014 ; \u2014 ; \u2014  \nWhy it matters: Faster inference and lower cost for production use.\u201d\n\nIf a field is missing, skip it silently.\nKeep the entire summary under **6\u20138 lines**.\nAvoid extra explanations or speculation.\n",
              "summarizationMethod": "stuff"
            }
          }
        }
      },
      "typeVersion": 2.1
    },
    {
      "id": "9975d7e1-6e4f-434b-b74b-e26f03320f6f",
      "name": "Aggregate Summaries",
      "type": "n8n-nodes-base.code",
      "position": [
        8544,
        -1248
      ],
      "parameters": {
        "jsCode": "// Collect all items coming from Summarization/Extraction\nconst items = $input.all();\n\n// Extract each summary from each item\nconst summaries = items.map(item => item.json);\n\n// Build a single output item\nreturn [\n  {\n    json: {\n      summaries\n    }\n  }\n];\n"
      },
      "typeVersion": 2
    },
    {
      "id": "033d4d93-d8f3-4eb1-b843-94fc0bf7138e",
      "name": "Research Analyst Agent",
      "type": "@n8n/n8n-nodes-langchain.agent",
      "position": [
        9136,
        -1248
      ],
      "parameters": {
        "text": "=You are an AI research analyst.\n\nINPUT YOU WILL RECEIVE:\n1. A collection of short summaries generated from AI / LLM related webpages.\n2. Each summary represents one article, announcement, blog post, or research update.\n3. All content comes from the same search context and timeframe.\n\n-----------------------------------\nSTEP 1 \u2014 Understand the Research Focus\n-----------------------------------\nAssume the goal is to track meaningful developments in:\n- AI models and LLMs\n- AI tooling and infrastructure\n- Research breakthroughs\n- Practical production or business impact\n\n-----------------------------------\nSTEP 2 \u2014 Evaluate Each Summary\n-----------------------------------\nFor EACH summary:\n\n1. Determine whether it is **meaningful or actionable**.\n2. Assign a **Relevance Score (0\u2013100%)** based on:\n   - Technical significance\n   - Novelty (new model, update, result, or capability)\n   - Practical or industry impact\n3. Exclude summaries with relevance below **50%**.\n4. For each included summary, prepare:\n   - Topic / Title (if clear)\n   - Entity (model, company, or organization)\n   - Relevance Score (percentage)\n   - 1\u20132 short reasons explaining the score\n\n-----------------------------------\nSTEP 3 \u2014 Generate Final Report\n-----------------------------------\nProduce ONE single consolidated report structured as:\n\nA) High-Level Overview  \n   - 2\u20133 sentences summarizing the overall AI/LLM trend observed.\n\nB) Key Relevant Updates  \n   - List items ordered by Relevance Score (highest \u2192 lowest):\n     - Topic / Entity\n       Relevance: XX%\n       Why it matters:\n         \u2022 <reason 1>\n         \u2022 <reason 2>\n\nC) Notable Patterns or Signals  \n   - 3\u20135 short bullets highlighting:\n     \u2022 Repeated themes\n     \u2022 Emerging model types or tools\n     \u2022 Research vs industry balance\n     \u2022 Signals worth monitoring next week\n\n-----------------------------------\nRULES\n-----------------------------------\n- Output must be plain text (no markdown, no JSON).\n- Do NOT invent facts, models, or companies.\n- Do NOT repeat the same insight in different wording.\n- Keep explanations short and concrete.\n- Maintain a neutral, analytical tone.\n",
        "options": {},
        "promptType": "define"
      },
      "typeVersion": 3
    },
    {
      "id": "bf883fd6-ee8c-4bb5-ae8c-747c3bef9545",
      "name": "Send Email (Report)",
      "type": "n8n-nodes-base.gmail",
      "position": [
        9584,
        -1248
      ],
      "parameters": {
        "sendTo": "user@example.com",
        "message": "={{ $json.output }}",
        "options": {
          "appendAttribution": false
        },
        "subject": "=Weekly AI / LLM Intelligence Report \u2013 {{ new Date().toLocaleDateString() }}\n",
        "emailType": "text",
        "authentication": "serviceAccount"
      },
      "typeVersion": 2.1
    },
    {
      "id": "466aa3a8-93ba-480a-abab-a151baecba40",
      "name": "Search API (Decodo)",
      "type": "@decodo/n8n-nodes-decodo.decodo",
      "position": [
        6832,
        -1232
      ],
      "parameters": {
        "query": "={{ $json.search_query }}",
        "operation": "google_search",
        "results_limit": 1
      },
      "typeVersion": 1
    },
    {
      "id": "161455d9-906d-4492-8a64-f9c4e3e7f29b",
      "name": "Scrape Content (Decodo)",
      "type": "@decodo/n8n-nodes-decodo.decodo",
      "position": [
        7376,
        -1120
      ],
      "parameters": {
        "url": "={{$json.url}}"
      },
      "typeVersion": 1
    },
    {
      "id": "9774fd35-6fe5-449e-adfc-c13a49fcbd82",
      "name": "Set Search Config",
      "type": "n8n-nodes-base.set",
      "position": [
        6448,
        -1232
      ],
      "parameters": {
        "mode": "raw",
        "options": {},
        "jsonOutput": "{\n  \"search_query\": \"latest AI LLM news\",\n  \"max_results\": 10,\n  \"min_relevance_score\": 50,\n  \"summary_language\": \"en\",\n  \"delivery_channel\": \"email\",\n  \"debug_mode\": false\n}\n"
      },
      "typeVersion": 3.4
    },
    {
      "id": "b92d812a-ee0a-4e69-98c1-2cdba7cfb437",
      "name": "Check Content Quality",
      "type": "n8n-nodes-base.if",
      "position": [
        7600,
        -1104
      ],
      "parameters": {
        "options": {},
        "conditions": {
          "options": {
            "version": 3,
            "leftValue": "",
            "caseSensitive": true,
            "typeValidation": "strict"
          },
          "combinator": "and",
          "conditions": [
            {
              "id": "606feef1-6b79-4a74-975d-25181e6c2af2",
              "operator": {
                "type": "string",
                "operation": "notEmpty",
                "singleValue": true
              },
              "leftValue": "={{$json.results?.[0]?.content}}",
              "rightValue": ""
            },
            {
              "id": "502031bd-4346-40c0-aee3-aefd744a99f9",
              "operator": {
                "type": "number",
                "operation": "gt"
              },
              "leftValue": "={{$json.results?.[0]?.content.length}}",
              "rightValue": 300
            }
          ]
        }
      },
      "typeVersion": 2.3
    },
    {
      "id": "f267c3b2-6a23-4aed-a97c-bb91b8fdb56a",
      "name": "OpenAI Model (Summary)",
      "type": "@n8n/n8n-nodes-langchain.lmChatOpenAi",
      "position": [
        8208,
        -1040
      ],
      "parameters": {
        "model": {
          "__rl": true,
          "mode": "list",
          "value": "gpt-4.1-mini"
        },
        "options": {},
        "builtInTools": {}
      },
      "typeVersion": 1.3
    },
    {
      "id": "150b5b6b-cfc1-4cc9-8b2f-623f9cd4a81f",
      "name": "Check Results Exist",
      "type": "n8n-nodes-base.if",
      "position": [
        8752,
        -1248
      ],
      "parameters": {
        "options": {},
        "conditions": {
          "options": {
            "version": 3,
            "leftValue": "",
            "caseSensitive": true,
            "typeValidation": "strict"
          },
          "combinator": "and",
          "conditions": [
            {
              "id": "4944b6a5-9ddc-4116-a95c-d418f686546c",
              "operator": {
                "type": "number",
                "operation": "gt"
              },
              "leftValue": "={{ $json.summaries.length }}",
              "rightValue": 0
            }
          ]
        }
      },
      "typeVersion": 2.3
    },
    {
      "id": "a44050d8-28b8-4da0-b907-9631058f8c3d",
      "name": "Send Email (Empty)",
      "type": "n8n-nodes-base.gmail",
      "position": [
        8864,
        -1072
      ],
      "parameters": {
        "sendTo": "user@example.com",
        "message": "=No Updates Found...",
        "options": {
          "appendAttribution": false
        },
        "subject": "=Weekly AI / LLM Intelligence Report \u2013 {{ new Date().toLocaleDateString() }}\n",
        "emailType": "text",
        "authentication": "serviceAccount"
      },
      "typeVersion": 2.1
    },
    {
      "id": "11719afc-dcc6-4435-a212-574152fe9a2b",
      "name": "OpenAI Model (Agent)",
      "type": "@n8n/n8n-nodes-langchain.lmChatOpenAi",
      "position": [
        9136,
        -1024
      ],
      "parameters": {
        "model": {
          "__rl": true,
          "mode": "list",
          "value": "gpt-4.1-mini"
        },
        "options": {},
        "builtInTools": {}
      },
      "typeVersion": 1.3
    },
    {
      "id": "795a8aae-0023-4a07-8d64-4dcdc47cb821",
      "name": "Telegram Error Alert",
      "type": "n8n-nodes-base.telegram",
      "position": [
        7664,
        -864
      ],
      "parameters": {
        "text": "Warning ... Error in scraping ",
        "chatId": "YOUR_CHAT_ID",
        "additionalFields": {}
      },
      "typeVersion": 1.2
    }
  ],
  "active": false,
  "settings": {
    "executionOrder": "v1"
  },
  "versionId": "8b7b7448-16b3-44ed-9a07-3ecd8679ccad",
  "connections": {
    "Batch Loop": {
      "main": [
        [
          {
            "node": "Summarize Chain",
            "type": "main",
            "index": 0
          }
        ],
        [
          {
            "node": "Scrape Content (Decodo)",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Sanitize HTML": {
      "main": [
        [
          {
            "node": "Batch Loop",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Weekly Trigger": {
      "main": [
        [
          {
            "node": "Set Search Config",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Summarize Chain": {
      "main": [
        [
          {
            "node": "Aggregate Summaries",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Set Search Config": {
      "main": [
        [
          {
            "node": "Search API (Decodo)",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Aggregate Summaries": {
      "main": [
        [
          {
            "node": "Check Results Exist",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Check Results Exist": {
      "main": [
        [
          {
            "node": "Research Analyst Agent",
            "type": "main",
            "index": 0
          }
        ],
        [
          {
            "node": "Send Email (Empty)",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Filter & Parse URLs": {
      "main": [
        [
          {
            "node": "Batch Loop",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Search API (Decodo)": {
      "main": [
        [
          {
            "node": "Filter & Parse URLs",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "OpenAI Model (Agent)": {
      "ai_languageModel": [
        [
          {
            "node": "Research Analyst Agent",
            "type": "ai_languageModel",
            "index": 0
          }
        ]
      ]
    },
    "Check Content Quality": {
      "main": [
        [
          {
            "node": "Sanitize HTML",
            "type": "main",
            "index": 0
          }
        ],
        [
          {
            "node": "Telegram Error Alert",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "OpenAI Model (Summary)": {
      "ai_languageModel": [
        [
          {
            "node": "Summarize Chain",
            "type": "ai_languageModel",
            "index": 0
          }
        ]
      ]
    },
    "Research Analyst Agent": {
      "main": [
        [
          {
            "node": "Send Email (Report)",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Scrape Content (Decodo)": {
      "main": [
        [
          {
            "node": "Check Content Quality",
            "type": "main",
            "index": 0
          }
        ]
      ]
    }
  }
}