AutomationFlowsEmail & Gmail › Gmail → Telegram Daily Report (v3 AI Pro)

Gmail → Telegram Daily Report (v3 AI Pro)

Gmail → Telegram Daily Report (V3 AI Pro). Uses gmail, httpRequest, telegram. Scheduled trigger; 15 nodes.

Cron / scheduled trigger★★★★☆ complexity15 nodesGmailHTTP RequestTelegram
Email & Gmail Trigger: Cron / scheduled Nodes: 15 Complexity: ★★★★☆ Added:

This workflow follows the Gmail → HTTP Request recipe pattern — see all workflows that pair these two integrations.

The workflow JSON

Copy or download the full n8n JSON below. Paste it into a new n8n workflow, add your credentials, activate. Full import guide →

Download .json
{
  "name": "Gmail \u2192 Telegram Daily Report (V3 AI Pro)",
  "nodes": [
    {
      "parameters": {
        "rule": {
          "interval": [
            {
              "triggerAtHour": 7,
              "triggerAtMinute": 0
            }
          ]
        }
      },
      "id": "schedule-trigger",
      "name": "\u23f0 Trigger 7h S\u00e1ng",
      "type": "n8n-nodes-base.scheduleTrigger",
      "typeVersion": 1.1,
      "position": [
        240,
        500
      ]
    },
    {
      "parameters": {
        "resource": "message",
        "operation": "getAll",
        "returnAll": false,
        "limit": 100,
        "filters": {
          "q": "is:unread newer_than:1d"
        },
        "options": {}
      },
      "id": "gmail-get",
      "name": "\ud83d\udcec L\u1ea5y Email (100)",
      "type": "n8n-nodes-base.gmail",
      "typeVersion": 2.1,
      "position": [
        480,
        500
      ],
      "credentials": {
        "gmailOAuth2": {
          "name": "<your credential>"
        }
      }
    },
    {
      "parameters": {
        "jsCode": "// Pre-classify before sending to AI (reduces AI token cost)\nconst emails = $input.all();\n\nconst SPAM_PATTERNS = ['shopee', 'lazada', 'tiki', 'grab', 'noreply', 'no-reply', 'donotreply', 'unsubscribe'];\nconst PROMO_KW = ['gi\u1ea3m gi\u00e1', 'flash sale', 'khuy\u1ebfn m\u00e3i', '\u01b0u \u0111\u00e3i', '% off', 'sale', 'voucher', 'coupon'];\n\nconst preClassified = emails.map(item => {\n  const e = item.json;\n  const from = (e.from || '').toLowerCase();\n  const subject = (e.subject || '').toLowerCase();\n  const isObviousSpam = SPAM_PATTERNS.some(p => from.includes(p));\n  const isObviousPromo = PROMO_KW.some(kw => subject.includes(kw));\n\n  return {\n    id: e.id,\n    from: (e.from || '').replace(/<[^>]+>/g, '').trim(),\n    subject: e.subject || '(no subject)',\n    snippet: (e.snippet || e.textPlain || '').substring(0, 200),\n    date: e.date,\n    pre_category: isObviousSpam ? 'spam' : isObviousPromo ? 'promotion' : 'needs_ai_review'\n  };\n});\n\nconst needsReview = preClassified.filter(e => e.pre_category === 'needs_ai_review');\nconst obviousSpam = preClassified.filter(e => e.pre_category === 'spam');\nconst obviousPromo = preClassified.filter(e => e.pre_category === 'promotion');\n\nconsole.log(`Pre-classified: ${obviousSpam.length} spam, ${obviousPromo.length} promo, ${needsReview.length} needs AI`);\n\nreturn [{ json: {\n  all_emails: preClassified,\n  needs_ai_review: needsReview,\n  obvious_spam: obviousSpam,\n  obvious_promo: obviousPromo,\n  total: emails.length\n}}];"
      },
      "id": "pre-classify",
      "name": "\ud83d\udd0d Pre-Classification (Rule-Based)",
      "type": "n8n-nodes-base.code",
      "typeVersion": 2,
      "position": [
        720,
        500
      ],
      "notes": "Ph\u00e2n lo\u1ea1i s\u01a1 b\u1ed9 tr\u01b0\u1edbc khi g\u1ecdi AI. M\u1ee5c \u0111\u00edch: gi\u1ea3m token cost AI, ch\u1ec9 g\u1eedi email c\u1ea7n ph\u00e2n t\u00edch."
    },
    {
      "parameters": {
        "jsCode": "// Prepare AI prompt with only emails needing review\nconst data = $input.first().json;\nconst emailsForAI = data.needs_ai_review;\n\nif (emailsForAI.length === 0) {\n  return [{ json: { skip_ai: true, ...data } }];\n}\n\nconst emailList = emailsForAI.map((e, i) =>\n  `[${i+1}] From: ${e.from}\\nSubject: ${e.subject}\\nSnippet: ${e.snippet}`\n).join('\\n---\\n');\n\nconst prompt = `B\u1ea1n l\u00e0 tr\u1ee3 l\u00fd qu\u1ea3n l\u00fd email. Ph\u00e2n lo\u1ea1i c\u00e1c email sau v\u00e0o m\u1ed9t trong c\u00e1c nh\u00f3m:\n- IMPORTANT: T\u1eeb s\u1ebfp/kh\u00e1ch h\u00e0ng/\u0111\u1ed1i t\u00e1c, c\u00f3 deadline, c\u1ea7n ph\u1ea3n h\u1ed3i\n- WORK: Li\u00ean quan c\u00f4ng vi\u1ec7c nh\u01b0ng kh\u00f4ng urgent\n- PERSONAL: Email c\u00e1 nh\u00e2n/gia \u0111\u00ecnh\n- NEWSLETTER: B\u1ea3n tin th\u00f4ng th\u01b0\u1eddng\n- SPAM: Qu\u1ea3ng c\u00e1o, r\u00e1c\n\nEmail c\u1ea7n ph\u00e2n lo\u1ea1i:\n${emailList}\n\nTr\u1ea3 l\u1eddi d\u1ea1ng JSON array, m\u1ed7i item c\u00f3: index (1-based), category, reason_vi (l\u00fd do b\u1eb1ng ti\u1ebfng Vi\u1ec7t, ng\u1eafn g\u1ecdn), action (\"keep_urgent\"/\"keep\"/\"archive\"/\"trash\"), priority (\"high\"/\"medium\"/\"low\").\n\nCh\u1ec9 tr\u1ea3 JSON, kh\u00f4ng gi\u1ea3i th\u00edch th\u00eam.`;\n\nreturn [{ json: { prompt, emails_for_ai: emailsForAI, pre_data: data } }];"
      },
      "id": "prepare-ai-prompt",
      "name": "\ud83e\udd16 Chu\u1ea9n B\u1ecb AI Prompt",
      "type": "n8n-nodes-base.code",
      "typeVersion": 2,
      "position": [
        960,
        400
      ],
      "notes": "Chu\u1ea9n b\u1ecb prompt t\u1ed1i \u01b0u cho AI. Ch\u1ec9 g\u1eedi email ch\u01b0a r\u00f5 r\u00e0ng, kh\u00f4ng g\u1eedi spam/promo \u0111\u00e3 bi\u1ebft."
    },
    {
      "parameters": {
        "conditions": {
          "options": {
            "caseSensitive": false,
            "leftValue": "",
            "typeValidation": "loose"
          },
          "conditions": [
            {
              "id": "skip-ai-check",
              "leftValue": "={{ $json.skip_ai }}",
              "rightValue": true,
              "operator": {
                "type": "boolean",
                "operation": "equals"
              }
            }
          ],
          "combinator": "and"
        },
        "options": {}
      },
      "id": "if-need-ai",
      "name": "IF: C\u1ea7n G\u1ecdi AI?",
      "type": "n8n-nodes-base.if",
      "typeVersion": 2,
      "position": [
        1200,
        400
      ],
      "notes": "N\u1ebfu t\u1ea5t c\u1ea3 email \u0111\u00e3 \u0111\u01b0\u1ee3c pre-classify \u2192 b\u1ecf qua AI \u0111\u1ec3 ti\u1ebft ki\u1ec7m chi ph\u00ed."
    },
    {
      "parameters": {
        "method": "POST",
        "url": "https://generativelanguage.googleapis.com/v1beta/models/gemini-1.5-flash:generateContent",
        "authentication": "genericCredentialType",
        "genericAuthType": "httpQueryAuth",
        "sendBody": true,
        "specifyBody": "json",
        "jsonBody": "={\n  \"contents\": [{\n    \"parts\": [{\n      \"text\": \"{{ $json.prompt }}\"\n    }]\n  }],\n  \"generationConfig\": {\n    \"temperature\": 0.1,\n    \"maxOutputTokens\": 2048\n  }\n}",
        "options": {}
      },
      "id": "call-gemini",
      "name": "\ud83e\udde0 G\u1ecdi Gemini API",
      "type": "n8n-nodes-base.httpRequest",
      "typeVersion": 4.2,
      "position": [
        1440,
        300
      ],
      "credentials": {
        "httpQueryAuth": {
          "name": "<your credential>"
        }
      },
      "notes": "\u26a0\ufe0f SECURITY NOTE: D\u00f9ng HTTP Query credential v\u1edbi key=YOUR_API_KEY. KH\u00d4NG hardcode API key tr\u1ef1c ti\u1ebfp v\u00e0o URL. Credential \u0111\u01b0\u1ee3c m\u00e3 h\u00f3a trong n8n database. Demo: D\u00f9ng Gemini 1.5 Flash (mi\u1ec5n ph\u00ed tier)."
    },
    {
      "parameters": {
        "jsCode": "// Parse AI response v\u00e0 k\u1ebft h\u1ee3p v\u1edbi pre-classification\nconst aiResponse = $input.first().json;\nconst prevData = $('\ud83e\udd16 Chu\u1ea9n B\u1ecb AI Prompt').first().json;\n\nlet aiResults = [];\ntry {\n  const rawText = aiResponse.candidates?.[0]?.content?.parts?.[0]?.text || '[]';\n  const jsonMatch = rawText.match(/\\[.*\\]/s);\n  if (jsonMatch) {\n    aiResults = JSON.parse(jsonMatch[0]);\n  }\n} catch(e) {\n  console.error('AI parse error:', e.message);\n  // Fallback: treat all AI emails as 'work'\n  aiResults = (prevData.emails_for_ai || []).map((_, i) => ({\n    index: i + 1, category: 'WORK', action: 'keep', priority: 'medium',\n    reason_vi: 'Kh\u00f4ng th\u1ec3 ph\u00e2n t\u00edch'\n  }));\n}\n\n// Combine AI results with email data\nconst emailsForAI = prevData.emails_for_ai || [];\nconst aiClassified = aiResults.map(r => ({\n  ...emailsForAI[r.index - 1],\n  category: r.category,\n  action: r.action,\n  priority: r.priority,\n  reason: r.reason_vi,\n  classified_by: 'ai'\n})).filter(Boolean);\n\n// Merge all classifications\nconst preData = prevData.pre_data;\nconst allEmails = [\n  ...aiClassified,\n  ...(preData.obvious_spam || []).map(e => ({ ...e, category: 'SPAM', action: 'trash', priority: 'low', classified_by: 'rule' })),\n  ...(preData.obvious_promo || []).map(e => ({ ...e, category: 'PROMOTION', action: 'archive', priority: 'low', classified_by: 'rule' }))\n];\n\nconst grouped = {\n  important: allEmails.filter(e => e.category === 'IMPORTANT'),\n  work: allEmails.filter(e => e.category === 'WORK'),\n  personal: allEmails.filter(e => e.category === 'PERSONAL'),\n  newsletter: allEmails.filter(e => e.category === 'NEWSLETTER' || e.pre_category === 'newsletter'),\n  promotion: allEmails.filter(e => e.category === 'PROMOTION' || e.pre_category === 'promotion'),\n  spam: allEmails.filter(e => e.category === 'SPAM' || e.pre_category === 'spam')\n};\n\nreturn [{ json: { grouped, all: allEmails, total: preData.total || allEmails.length } }];"
      },
      "id": "parse-ai-result",
      "name": "\ud83d\udd17 K\u1ebft H\u1ee3p K\u1ebft Qu\u1ea3 AI",
      "type": "n8n-nodes-base.code",
      "typeVersion": 2,
      "position": [
        1680,
        300
      ],
      "notes": "Parse JSON t\u1eeb AI response v\u00e0 k\u1ebft h\u1ee3p v\u1edbi k\u1ebft qu\u1ea3 rule-based. C\u00f3 error handling khi AI tr\u1ea3 v\u1ec1 l\u1ed7i."
    },
    {
      "parameters": {
        "jsCode": "// Generate comprehensive Telegram report\nconst data = $input.first().json;\nconst { grouped, total } = data;\n\nconst dateStr = new Date().toLocaleDateString('vi-VN', {\n  weekday: 'long', year: 'numeric', month: 'long', day: 'numeric',\n  timeZone: 'Asia/Ho_Chi_Minh'\n});\n\nconst fmtSection = (arr, max = 3) => {\n  if (!arr || arr.length === 0) return '_Kh\u00f4ng c\u00f3_';\n  const items = arr.slice(0, max).map((e, i) => {\n    const tag = e.classified_by === 'ai' ? '\ud83e\udd16' : '\u26a1';\n    const reason = e.reason ? ` _(${e.reason})_` : '';\n    return `  ${i+1}. *${(e.subject||'').substring(0, 50)}*${reason}\\n     \ud83d\udce4 ${(e.from||'').substring(0, 38)} ${tag}`;\n  }).join('\\n');\n  const more = arr.length > max ? `\\n  _... v\u00e0 ${arr.length - max} email kh\u00e1c_` : '';\n  return items + more;\n};\n\n// Build priority section\nconst urgentEmails = (grouped.important || []).filter(e => e.priority === 'high');\nconst urgentSection = urgentEmails.length > 0\n  ? `\\n\ud83d\udea8 *C\u1ea6N X\u1eec L\u00dd NGAY:*\\n${fmtSection(urgentEmails)}`\n  : '';\n\nconst cleanupCount = (grouped.spam?.length || 0) + (grouped.promotion?.length || 0);\nconst toTrashIds = (grouped.spam || []).map(e => e.id).filter(Boolean);\nconst toArchiveIds = (grouped.promotion || []).map(e => e.id).filter(Boolean);\n\nconst mainReport = `\ud83e\udd16 *B\u00c1O C\u00c1O EMAIL AI - S\u00c1NG NAY*\n\ud83d\udcc5 ${dateStr}\n\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\n\n\ud83d\udcca *Th\u1ed1ng k\u00ea to\u00e0n b\u1ed9:*\n\u2022 \u2b50 Quan tr\u1ecdng: ${grouped.important?.length || 0} email\n\u2022 \ud83d\udcbc C\u00f4ng vi\u1ec7c: ${grouped.work?.length || 0} email\n\u2022 \ud83d\udc64 C\u00e1 nh\u00e2n: ${grouped.personal?.length || 0} email\n\u2022 \ud83d\udcf0 Newsletter: ${grouped.newsletter?.length || 0} email\n\u2022 \ud83c\udff7\ufe0f Khuy\u1ebfn m\u00e3i: ${grouped.promotion?.length || 0} email\n\u2022 \ud83d\uddd1\ufe0f Spam: ${grouped.spam?.length || 0} email\n\u2022 \ud83d\udce8 *T\u1ed5ng: ${total} email*\n${urgentSection}\n\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\n\n\u2b50 *QUAN TR\u1eccNG:*\n${fmtSection(grouped.important)}\n\n\ud83d\udcbc *C\u00d4NG VI\u1ec6C:*\n${fmtSection(grouped.work)}\n\n\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\u2501\n\ud83e\uddf9 T\u1ef1 \u0111\u1ed9ng d\u1ecdn: *${cleanupCount} email* (spam + promo)\n\ud83e\udd16 Ph\u00e2n t\u00edch b\u1edfi Gemini AI`;\n\nreturn [{ json: { mainReport, toTrashIds, toArchiveIds, grouped, total } }];"
      },
      "id": "format-ai-report",
      "name": "\ud83d\udcca T\u1ea1o B\u00e1o C\u00e1o AI",
      "type": "n8n-nodes-base.code",
      "typeVersion": 2,
      "position": [
        1920,
        300
      ],
      "notes": "Format b\u00e1o c\u00e1o \u0111\u1ea7y \u0111\u1ee7 v\u1edbi k\u1ebft qu\u1ea3 AI ph\u00e2n t\u00edch. Hi\u1ec3n th\u1ecb l\u00fd do ph\u00e2n lo\u1ea1i c\u1ee7a AI."
    },
    {
      "parameters": {
        "chatId": "={{ $vars.TELEGRAM_CHAT_ID }}",
        "text": "={{ $json.mainReport }}",
        "additionalFields": {
          "parse_mode": "Markdown"
        }
      },
      "id": "send-main-report",
      "name": "\ud83d\udcf1 G\u1eedi B\u00e1o C\u00e1o Ch\u00ednh",
      "type": "n8n-nodes-base.telegram",
      "typeVersion": 1.2,
      "position": [
        2160,
        200
      ],
      "credentials": {
        "telegramApi": {
          "name": "<your credential>"
        }
      }
    },
    {
      "parameters": {
        "jsCode": "// Prepare spam IDs for trashing\nconst toTrashIds = $('\ud83d\udcca T\u1ea1o B\u00e1o C\u00e1o AI').first().json.toTrashIds || [];\nconst toArchiveIds = $('\ud83d\udcca T\u1ea1o B\u00e1o C\u00e1o AI').first().json.toArchiveIds || [];\n\nif (toTrashIds.length === 0 && toArchiveIds.length === 0) {\n  return [{ json: { nothing_to_clean: true } }];\n}\n\nconst tasks = [\n  ...toTrashIds.map(id => ({ emailId: id, action: 'trash' })),\n  ...toArchiveIds.map(id => ({ emailId: id, action: 'archive' }))\n];\n\nconsole.log(`Cleanup tasks: ${tasks.length} (${toTrashIds.length} trash, ${toArchiveIds.length} archive)`);\nreturn tasks.map(t => ({ json: t }));"
      },
      "id": "prepare-cleanup",
      "name": "\ud83e\uddf9 Chu\u1ea9n B\u1ecb D\u1ecdn D\u1eb9p",
      "type": "n8n-nodes-base.code",
      "typeVersion": 2,
      "position": [
        2160,
        400
      ]
    },
    {
      "parameters": {
        "conditions": {
          "options": {
            "caseSensitive": false,
            "leftValue": "",
            "typeValidation": "loose"
          },
          "conditions": [
            {
              "id": "is-trash",
              "leftValue": "={{ $json.action }}",
              "rightValue": "trash",
              "operator": {
                "type": "string",
                "operation": "equals"
              }
            }
          ],
          "combinator": "and"
        },
        "options": {}
      },
      "id": "if-trash-or-archive",
      "name": "IF: Trash hay Archive?",
      "type": "n8n-nodes-base.if",
      "typeVersion": 2,
      "position": [
        2400,
        400
      ]
    },
    {
      "parameters": {
        "resource": "message",
        "operation": "trash",
        "messageId": "={{ $json.emailId }}",
        "options": {}
      },
      "id": "trash-email",
      "name": "\ud83d\uddd1\ufe0f X\u00f3a Spam",
      "type": "n8n-nodes-base.gmail",
      "typeVersion": 2.1,
      "position": [
        2640,
        300
      ],
      "credentials": {
        "gmailOAuth2": {
          "name": "<your credential>"
        }
      },
      "notes": "\u26a0\ufe0f TH\u1eacN TR\u1eccNG: X\u00f3a email v\u00e0o Th\u00f9ng r\u00e1c. C\u1ea7n test k\u1ef9 tr\u01b0\u1edbc khi d\u00f9ng production."
    },
    {
      "parameters": {
        "resource": "message",
        "operation": "archive",
        "messageId": "={{ $json.emailId }}",
        "options": {}
      },
      "id": "archive-promo",
      "name": "\ud83d\udcc1 Archive Promo",
      "type": "n8n-nodes-base.gmail",
      "typeVersion": 2.1,
      "position": [
        2640,
        500
      ],
      "credentials": {
        "gmailOAuth2": {
          "name": "<your credential>"
        }
      }
    },
    {
      "parameters": {
        "jsCode": "const results = $input.all();\nconst report = $('\ud83d\udcca T\u1ea1o B\u00e1o C\u00e1o AI').first().json;\n\nconsole.log(`\u2705 V3 AI Pro completed: ${report.total} emails processed`);\nconsole.log(`\ud83d\uddd1\ufe0f Trashed: ${report.toTrashIds?.length || 0}`);\nconsole.log(`\ud83d\udcc1 Archived: ${report.toArchiveIds?.length || 0}`);\n\nreturn [{\n  json: {\n    status: 'completed',\n    workflow_version: 'v3-ai-pro',\n    total_processed: report.total,\n    trashed: report.toTrashIds?.length || 0,\n    archived: report.toArchiveIds?.length || 0,\n    finished_at: new Date().toISOString()\n  }\n}];"
      },
      "id": "final-log",
      "name": "\u2705 Log Ho\u00e0n T\u1ea5t",
      "type": "n8n-nodes-base.code",
      "typeVersion": 2,
      "position": [
        2880,
        400
      ]
    },
    {
      "parameters": {
        "resource": "message",
        "operation": "getAll",
        "returnAll": false,
        "limit": 5,
        "filters": {
          "q": "is:unread newer_than:1d label:IMPORTANT"
        },
        "options": {}
      },
      "id": "gmail-check-important",
      "name": "\u2b50 Check Gmail Important Label",
      "type": "n8n-nodes-base.gmail",
      "typeVersion": 2.1,
      "position": [
        1440,
        700
      ],
      "credentials": {
        "gmailOAuth2": {
          "name": "<your credential>"
        }
      },
      "notes": "Ch\u1ea1y song song: L\u1ea5y email Gmail \u0111\u00e3 \u0111\u00e1nh d\u1ea5u Important \u0111\u1ec3 b\u1ed5 sung v\u00e0o b\u00e1o c\u00e1o."
    }
  ],
  "connections": {
    "\u23f0 Trigger 7h S\u00e1ng": {
      "main": [
        [
          {
            "node": "\ud83d\udcec L\u1ea5y Email (100)",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "\ud83d\udcec L\u1ea5y Email (100)": {
      "main": [
        [
          {
            "node": "\ud83d\udd0d Pre-Classification (Rule-Based)",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "\ud83d\udd0d Pre-Classification (Rule-Based)": {
      "main": [
        [
          {
            "node": "\ud83e\udd16 Chu\u1ea9n B\u1ecb AI Prompt",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "\ud83e\udd16 Chu\u1ea9n B\u1ecb AI Prompt": {
      "main": [
        [
          {
            "node": "IF: C\u1ea7n G\u1ecdi AI?",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "IF: C\u1ea7n G\u1ecdi AI?": {
      "main": [
        [
          {
            "node": "\ud83d\udcca T\u1ea1o B\u00e1o C\u00e1o AI",
            "type": "main",
            "index": 0
          }
        ],
        [
          {
            "node": "\ud83e\udde0 G\u1ecdi Gemini API",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "\ud83e\udde0 G\u1ecdi Gemini API": {
      "main": [
        [
          {
            "node": "\ud83d\udd17 K\u1ebft H\u1ee3p K\u1ebft Qu\u1ea3 AI",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "\ud83d\udd17 K\u1ebft H\u1ee3p K\u1ebft Qu\u1ea3 AI": {
      "main": [
        [
          {
            "node": "\ud83d\udcca T\u1ea1o B\u00e1o C\u00e1o AI",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "\ud83d\udcca T\u1ea1o B\u00e1o C\u00e1o AI": {
      "main": [
        [
          {
            "node": "\ud83d\udcf1 G\u1eedi B\u00e1o C\u00e1o Ch\u00ednh",
            "type": "main",
            "index": 0
          }
        ],
        [
          {
            "node": "\ud83e\uddf9 Chu\u1ea9n B\u1ecb D\u1ecdn D\u1eb9p",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "\ud83e\uddf9 Chu\u1ea9n B\u1ecb D\u1ecdn D\u1eb9p": {
      "main": [
        [
          {
            "node": "IF: Trash hay Archive?",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "IF: Trash hay Archive?": {
      "main": [
        [
          {
            "node": "\ud83d\uddd1\ufe0f X\u00f3a Spam",
            "type": "main",
            "index": 0
          }
        ],
        [
          {
            "node": "\ud83d\udcc1 Archive Promo",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "\ud83d\uddd1\ufe0f X\u00f3a Spam": {
      "main": [
        [
          {
            "node": "\u2705 Log Ho\u00e0n T\u1ea5t",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "\ud83d\udcc1 Archive Promo": {
      "main": [
        [
          {
            "node": "\u2705 Log Ho\u00e0n T\u1ea5t",
            "type": "main",
            "index": 0
          }
        ]
      ]
    }
  },
  "settings": {
    "executionOrder": "v1",
    "saveManualExecutions": true,
    "saveExecutionProgress": true,
    "timezone": "Asia/Ho_Chi_Minh"
  },
  "tags": [
    "personal",
    "gmail",
    "telegram",
    "daily-report",
    "v3-ai-pro",
    "gemini",
    "spam-cleanup"
  ],
  "meta": {
    "usage": "V3 AI PRO: 13 nodes. AI ph\u00e2n t\u00edch + b\u00e1o c\u00e1o th\u00f4ng minh + t\u1ef1 \u0111\u1ed9ng d\u1ecdn d\u1eb9p.",
    "difficulty": "\u2b50\u2b50\u2b50\u2b50 Advanced",
    "nodes_count": 13,
    "setup_time": "60 ph\u00fat",
    "ai_model": "Gemini 1.5 Flash (free tier)",
    "security_notes": "API key d\u00f9ng n8n credential, kh\u00f4ng hardcode. Spam filter c\u1ea9n th\u1eadn \u0111\u1ec3 tr\u00e1nh x\u00f3a nh\u1ea7m."
  }
}

Credentials you'll need

Each integration node will prompt for credentials when you import. We strip credential IDs before publishing — you'll add your own.

Pro

For the full experience including quality scoring and batch install features for each workflow upgrade to Pro

About this workflow

Gmail → Telegram Daily Report (V3 AI Pro). Uses gmail, httpRequest, telegram. Scheduled trigger; 15 nodes.

Source: https://github.com/congdinh2008/n8n-compose/blob/88a5ccac9ba7441519c42e9dd9b9b31e45baf125/workflows/personal/09-gmail-telegram-report/v3-ai-pro/workflow.json — original creator credit. Request a take-down →

More Email & Gmail workflows → · Browse all categories →

Related workflows

Workflows that share integrations, category, or trigger type with this one. All free to copy and import.

Email & Gmail

Template - SSL Expiry Alert System. Uses googleSheets, scheduleTrigger, httpRequest, stickyNote. Scheduled trigger; 21 nodes.

Google Sheets, HTTP Request, Gmail +2
Email & Gmail

[](https://www.youtube.com/watch?v=q4d404G_OxY)

Gmail, HTTP Request, Telegram
Email & Gmail

This workflow is ideal for administrators or IT professionals responsible for monitoring SSL certificates of multiple websites to ensure they do not expire unexpectedly.

Google Sheets, HTTP Request, Gmail +2
Email & Gmail

url-uptime-monitor. Uses scheduleTrigger, splitOut, googleSheets, summarize. Scheduled trigger; 18 nodes.

Google Sheets, Gmail, HTTP Request +1
Email & Gmail

MPE Kleinanzeigen Unified (Reminder + Poster). Uses gmail, httpRequest, telegram, googleSheets. Scheduled trigger; 15 nodes.

Gmail, HTTP Request, Telegram +1