This workflow corresponds to n8n.io template #10664 — we link there as the canonical source.
This workflow follows the Agent → Gmail 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 →
{
"id": "xgrbRGmOiwsrm54g",
"meta": {
"templateCredsSetupCompleted": true
},
"name": "AI Gmail Manager",
"tags": [],
"nodes": [
{
"id": "9f9eac49-b13b-47d2-9801-3c46c11cddc2",
"name": "Gmail Trigger",
"type": "n8n-nodes-base.gmailTrigger",
"position": [
0,
-208
],
"parameters": {
"filters": {},
"pollTimes": {
"item": [
{
"mode": "everyMinute"
}
]
}
},
"credentials": {
"gmailOAuth2": {
"name": "<your credential>"
}
},
"typeVersion": 1.3
},
{
"id": "a66eeb1f-57ee-4b43-9aea-6abeb47c9a1c",
"name": "Structured Output Parser",
"type": "@n8n/n8n-nodes-langchain.outputParserStructured",
"position": [
832,
16
],
"parameters": {
"jsonSchemaExample": "{\n \"label\": \"Label name\",\n \"labelID\": \"Label ID\",\n \"id\": \"Email message ID\",\n \"requiresResponse\": true\n}"
},
"typeVersion": 1.3
},
{
"id": "f3d14e47-7403-481f-a15d-87adf9713bdb",
"name": "RemoveLabel",
"type": "n8n-nodes-base.gmail",
"position": [
224,
-208
],
"parameters": {
"labelIds": [
"YELLOW_STAR",
"INBOX",
"IMPORTANT",
"CATEGORY_UPDATES",
"CATEGORY_SOCIAL",
"CATEGORY_PROMOTIONS",
"CATEGORY_PERSONAL",
"CATEGORY_FORUMS"
],
"messageId": "={{ $json.id }}",
"operation": "removeLabels"
},
"credentials": {
"gmailOAuth2": {
"name": "<your credential>"
}
},
"typeVersion": 2.1
},
{
"id": "1883ad7e-1712-4f95-9164-8b1742d08343",
"name": "AddLabel",
"type": "n8n-nodes-base.gmail",
"position": [
1264,
-112
],
"parameters": {
"labelIds": "={{ $json.output.labelID }}",
"messageId": "={{ $('Gmail Trigger').item.json.id }}",
"operation": "addLabels"
},
"credentials": {
"gmailOAuth2": {
"name": "<your credential>"
}
},
"typeVersion": 2.1
},
{
"id": "a4c1fbf6-4111-4d97-9ea3-8963f48b1648",
"name": "TrashMessage",
"type": "n8n-nodes-base.gmail",
"position": [
1264,
-304
],
"parameters": {
"labelIds": [
"TRASH"
],
"messageId": "={{ $('Gmail Trigger').item.json.id }}",
"operation": "addLabels"
},
"credentials": {
"gmailOAuth2": {
"name": "<your credential>"
}
},
"typeVersion": 2.1
},
{
"id": "94a9bed2-df2c-4e55-87ed-5aa495a9f0ea",
"name": "Sticky Note",
"type": "n8n-nodes-base.stickyNote",
"position": [
464,
-544
],
"parameters": {
"color": 7,
"width": 544,
"height": 720,
"content": "## Classify emails\n\nThis step uses Gemini (or any compatible AI model) to automatically categorize incoming emails.\nThe model follows your predefined Gmail labels to decide where each message belongs.\n\nIt can also check the full conversation history and past replies for extra context:\n\n- GetThread \u2192 Reads the entire email thread\n- CheckSent \u2192 Checks if you\u2019ve replied to this sender before\n\nIt outputs clean, structured JSON with the chosen label and message details."
},
"typeVersion": 1
},
{
"id": "96e9fbad-4274-4649-8f71-1a97bba948df",
"name": "GetThread",
"type": "n8n-nodes-base.gmailTool",
"position": [
576,
16
],
"parameters": {
"filters": {
"q": "=from:{{ $('Gmail Trigger').item.json.From }}"
},
"operation": "getAll",
"returnAll": "={{ /*n8n-auto-generated-fromAI-override*/ $fromAI('Return_All', ``, 'boolean') }}"
},
"credentials": {
"gmailOAuth2": {
"name": "<your credential>"
}
},
"typeVersion": 2.1
},
{
"id": "335c960f-eedc-4d90-9fd6-6e174fdcd0a8",
"name": "CheckSent",
"type": "n8n-nodes-base.gmailTool",
"position": [
704,
16
],
"parameters": {
"filters": {
"q": "=to:{{ $('Gmail Trigger').item.json.From }}"
},
"operation": "getAll",
"returnAll": "={{ /*n8n-auto-generated-fromAI-override*/ $fromAI('Return_All', ``, 'boolean') }}"
},
"credentials": {
"gmailOAuth2": {
"name": "<your credential>"
}
},
"typeVersion": 2.1
},
{
"id": "9db911b8-430c-41a8-8dd2-09f446526358",
"name": "Gemini",
"type": "@n8n/n8n-nodes-langchain.lmChatGoogleGemini",
"position": [
1296,
208
],
"parameters": {
"options": {}
},
"credentials": {
"googlePalmApi": {
"name": "<your credential>"
}
},
"typeVersion": 1
},
{
"id": "390214f0-5930-4655-a2c4-b0a814652388",
"name": "IF Delete",
"type": "n8n-nodes-base.if",
"position": [
1040,
-208
],
"parameters": {
"options": {},
"conditions": {
"options": {
"version": 2,
"leftValue": "",
"caseSensitive": true,
"typeValidation": "strict"
},
"combinator": "and",
"conditions": [
{
"id": "dac0c540-5afe-4df3-b20b-8526effbe68b",
"operator": {
"name": "filter.operator.equals",
"type": "string",
"operation": "equals"
},
"leftValue": "={{ $json.output.label }}",
"rightValue": "DELETE"
}
]
}
},
"typeVersion": 2.2
},
{
"id": "fdf0e08d-5184-4ae4-aa5e-ed8dc1bd1f00",
"name": "IF Response",
"type": "n8n-nodes-base.if",
"position": [
1488,
-112
],
"parameters": {
"options": {},
"conditions": {
"options": {
"version": 2,
"leftValue": "",
"caseSensitive": true,
"typeValidation": "strict"
},
"combinator": "and",
"conditions": [
{
"id": "63984b31-4839-46d1-9c3e-0bf2a966e126",
"operator": {
"type": "boolean",
"operation": "true",
"singleValue": true
},
"leftValue": "={{ $('AI Email Classifier').item.json.output.requiresResponse }}",
"rightValue": "true"
}
]
}
},
"typeVersion": 2.2
},
{
"id": "4ad414d5-1f4d-42e6-9ee4-c6e3f3b348d4",
"name": "Create a draft",
"type": "n8n-nodes-base.gmail",
"position": [
2176,
-112
],
"parameters": {
"message": "={{ $json.output.draft }}",
"options": {
"sendTo": "={{ $('Gmail Trigger').item.json.From }}",
"threadId": "={{ $('Gmail Trigger').item.json.threadId }}"
},
"subject": "=Re: {{ $('Gmail Trigger').item.json.Subject }}",
"resource": "draft"
},
"credentials": {
"gmailOAuth2": {
"name": "<your credential>"
}
},
"typeVersion": 2.1
},
{
"id": "242f05bd-60e6-4e78-87c3-a4c96647ce18",
"name": "GetThread1",
"type": "n8n-nodes-base.gmailTool",
"position": [
1712,
112
],
"parameters": {
"filters": {
"q": "=from:{{ $('Gmail Trigger').item.json.From }}"
},
"operation": "getAll",
"returnAll": "={{ /*n8n-auto-generated-fromAI-override*/ $fromAI('Return_All', ``, 'boolean') }}"
},
"credentials": {
"gmailOAuth2": {
"name": "<your credential>"
}
},
"typeVersion": 2.1
},
{
"id": "8df829c7-fb54-41fd-bd6e-dc3e6f35ddbf",
"name": "CheckCalendar",
"type": "n8n-nodes-base.googleCalendarTool",
"position": [
1840,
112
],
"parameters": {
"options": {
"timezone": {
"__rl": true,
"mode": "list",
"value": "[YOUR OWN TIMEZEONE HERE]",
"cachedResultName": "[YOUR OWN TIMEZONE HERE]"
}
},
"timeMax": "={{ /*n8n-auto-generated-fromAI-override*/ $fromAI('End_Time', ``, 'string') }}",
"timeMin": "={{ /*n8n-auto-generated-fromAI-override*/ $fromAI('Start_Time', ``, 'string') }}",
"calendar": {
"__rl": true,
"mode": "list",
"value": "[YOUR OWN EMAIL HERE]",
"cachedResultName": "Google"
},
"resource": "calendar"
},
"credentials": {
"googleCalendarOAuth2Api": {
"name": "<your credential>"
}
},
"typeVersion": 1.3
},
{
"id": "7d87941c-a1d7-4476-ba1d-ad60a08c08ad",
"name": "Structured Output Parser1",
"type": "@n8n/n8n-nodes-langchain.outputParserStructured",
"position": [
1984,
112
],
"parameters": {
"jsonSchemaExample": "{\n \"draft\": \"string\",\n \"notes\": \"string\"\n}"
},
"typeVersion": 1.3
},
{
"id": "cf93dee2-2c6c-4d01-ab7c-442bd32a1d7b",
"name": "Sticky Note1",
"type": "n8n-nodes-base.stickyNote",
"position": [
1680,
-400
],
"parameters": {
"color": 7,
"width": 608,
"height": 656,
"content": "## Draft response\nWhen an email needs a reply, this step creates a short, friendly draft you can review before sending.\nThe AI reads the full conversation for context and, if scheduling is mentioned, suggests meeting times based on your calendar.\n\nIt outputs:\n\n- draft \u2192 the suggested reply text\n- notes \u2192 optional AI guidance (not included in the message)\n\nThe draft is saved in Gmail \u2014 it\u2019s never sent automatically."
},
"typeVersion": 1
},
{
"id": "e44b892d-b865-4fd2-86f7-6750f621fef4",
"name": "AI Email Classifier",
"type": "@n8n/n8n-nodes-langchain.agent",
"position": [
568,
-208
],
"parameters": {
"text": "=Objective:\nAnalyze the provided email and classify it with the most appropriate label. Respond strictly in JSON (schema: label, labelID, id, requiresResponse).\nOnly output JSON \u2014 no explanations. You have access to Gmail tools to gather context and should use them when necessary.\n\nTool Access:\n- GetThread: use this to fetch all messages in the same Gmail thread using the provided threadId. This lets you review past exchanges for context.\n- CheckSent: use this to check if there are any emails previously sent by me to this sender (helps identify ongoing conversations).\n\n\nYour email (for context): [INPUT YOUR EMAIL HERE]\n\nInput Email Data (from n8n JSON item for the current email):\nSender Email: {{ $('Gmail Trigger').item.json.from }}\nSubject: {{ $('Gmail Trigger').item.json.subject }}\nSnippet: {{ $('Gmail Trigger').item.json.snippet }}\nDate: {{ $('Gmail Trigger').item.json.internalDate }}\nEmail ID: {{ $('Gmail Trigger').item.json.id }}\nThread ID: {{ $('Gmail Trigger').item.json.threadId }}\nExisting Gmail Labels: {{ $json.labelIds.join(', ') }}\n\nLabeling Rules:\n\n[01] [INPUTE LABEL 1] (labelID: [INPUT LABEL 1's ID]) \u2192 [INPUT: Types of emails that should be part of Label 1, e.g. vendor emails for ecommerce business].\n[02] [INPUT LABEL 2] (labelID: [INPUT LABEL 2's ID]) \u2192 [INPUT: Types of emails that should be part of Label 2].\n\nDELETE (does NOT have a LabelID)\u2192 Emails that do not fit any SAVE rules.\n\nBehavior Rules:\n1. Before classifying, use GetThread with the provided threadId to see if this is a reply or part of an existing conversation.\n2. Use CheckSent to confirm whether I\u2019ve interacted with this sender before \u2014 this can help detect ongoing conversations.\n3. If this email requires a reply (scheduling, questions directed to me, next-step confirmations that request action), set requiresResponse to true and do NOT write the draft here \u2014 only set the flag. The actual draft will be created by a separate drafting node.\n4. Else set requiresResponse to false.\n\nOutput Format (strict JSON):\n{\n \"label\": \"Label name\",\n \"labelID\": \"Label ID\",\n \"id\": \"Email message ID\",\n \"requiresResponse\": true or false\n}\n\nAdditional Guidance:\n\n-Only return one label per email.\n-Do not include any text outside of the JSON object.",
"options": {},
"promptType": "define",
"hasOutputParser": true
},
"typeVersion": 3
},
{
"id": "db5ab5f9-320c-4b89-ba46-5ea013109f64",
"name": "AI Draft Maker",
"type": "@n8n/n8n-nodes-langchain.agent",
"position": [
1768,
-112
],
"parameters": {
"text": "=Objective:\nCreate a concise, friendly, and professional reply draft for the provided email thread. Do NOT send the message \u2014 only generate the draft text.\n\nTool Access:\n- GetThread1: use this to fetch the full thread using the threadId below, if more context is needed.\n- CheckCalendar: use this to find available time slots within the next 7 days (local time: [INPUT YOUR LOCAL TZ]) if scheduling is requested.\n\nContext:\n- My email: [INPUT YOUR EMAIL HERE]\n- Recipient (original sender): {{ $('Gmail Trigger').item.json.From }}\n- Original subject: {{ $('Gmail Trigger').item.json.Subject }}\n- Thread ID: {{ $('Gmail Trigger').item.json.threadId }}\n- Snippet: {{ $('Gmail Trigger').item.json.snippet }}\n- Full thread: use GetThread if additional context is required.\n\nDrafting Rules:\n1. Detect the sender\u2019s language. If they wrote in English, reply in English; if Spanish, reply in Spanish; if French, reply in French. If unclear, default to English.\n2. Tone: friendly, professional, natural.\n3. Length: keep it short (3\u20136 sentences).\n4. If scheduling is requested:\n - Use CheckCalendar to propose 2\u20133 available time slots in the next 7 days (local time).\n - Format times like: \u201cTuesday, May 12 at 15:00 CEST\u201d.\n - Make time zone clear ([INPUT YOUR LOCAL TIMEZONE]).\n5. For confirmations/info requests: answer directly and clearly.\n6. For document requests: say you will attach them and include: \u201c[Attach documents]\u201d.\n7. Start with a greeting: \u201cHi [Name],\u201d (adapted to language).\n8. End with: \u201cBest, [INPUT YOUR NAME/YOUR BUSINESS' NAME]\u201d or the equivalent in that language.\n9. Never include internal notes in the email body. Put any short reviewer guidance in `notes`.\n\nOutput Format (JSON):\n{\n \"draft\": \"email body here\",\n \"notes\": \"short reasoning or summary\"\n}\n",
"options": {},
"promptType": "define",
"hasOutputParser": true
},
"typeVersion": 3
},
{
"id": "739c6768-6fa3-45fe-ab51-84b07da6e6a0",
"name": "Sticky Note2",
"type": "n8n-nodes-base.stickyNote",
"position": [
-592,
-448
],
"parameters": {
"width": 544,
"height": 608,
"content": "# AI Gmail Manager\n\nThis workflow automatically classifies incoming Gmail messages and, when needed, creates reply drafts using AI.\nIt\u2019s designed to keep your inbox organized and help you respond faster, without ever sending messages automatically.\n\n## How it works:\n1. Gmail Trigger detects a new email.\n2. Gemini (Classify Emails) analyzes the message, checks your past threads and sent history, and assigns the right label.\n3. If the email requires a response, the workflow moves on to the Draft \n4. Response step, where the AI creates a short, professional reply you can review in Gmail.\n\n## Benefits:\n- Works with your existing Gmail labels\n- Uses AI for smart classification and reply generation\n- Safe: drafts are saved, never sent automatically\n\n## Requirements:\n- Gemini account for LLM\n- Google OAuth2 credentials"
},
"typeVersion": 1
}
],
"active": true,
"settings": {
"callerPolicy": "workflowsFromSameOwner",
"errorWorkflow": "2wvl7ae8yQzVXgvA",
"availableInMCP": false,
"executionOrder": "v1",
"timeSavedPerExecution": 5
},
"versionId": "f8cb4394-0baf-4c9d-95e4-aaec8335e3cd",
"connections": {
"Gemini": {
"ai_languageModel": [
[
{
"node": "AI Email Classifier",
"type": "ai_languageModel",
"index": 0
},
{
"node": "AI Draft Maker",
"type": "ai_languageModel",
"index": 0
}
]
]
},
"AddLabel": {
"main": [
[
{
"node": "IF Response",
"type": "main",
"index": 0
}
]
]
},
"CheckSent": {
"ai_tool": [
[
{
"node": "AI Email Classifier",
"type": "ai_tool",
"index": 0
}
]
]
},
"GetThread": {
"ai_tool": [
[
{
"node": "AI Email Classifier",
"type": "ai_tool",
"index": 0
}
]
]
},
"IF Delete": {
"main": [
[
{
"node": "TrashMessage",
"type": "main",
"index": 0
}
],
[
{
"node": "AddLabel",
"type": "main",
"index": 0
}
]
]
},
"GetThread1": {
"ai_tool": [
[
{
"node": "AI Draft Maker",
"type": "ai_tool",
"index": 0
}
]
]
},
"IF Response": {
"main": [
[
{
"node": "AI Draft Maker",
"type": "main",
"index": 0
}
]
]
},
"RemoveLabel": {
"main": [
[
{
"node": "AI Email Classifier",
"type": "main",
"index": 0
}
]
]
},
"CheckCalendar": {
"ai_tool": [
[
{
"node": "AI Draft Maker",
"type": "ai_tool",
"index": 0
}
]
]
},
"Gmail Trigger": {
"main": [
[
{
"node": "RemoveLabel",
"type": "main",
"index": 0
}
]
]
},
"AI Draft Maker": {
"main": [
[
{
"node": "Create a draft",
"type": "main",
"index": 0
}
]
]
},
"AI Email Classifier": {
"main": [
[
{
"node": "IF Delete",
"type": "main",
"index": 0
}
]
]
},
"Structured Output Parser": {
"ai_outputParser": [
[
{
"node": "AI Email Classifier",
"type": "ai_outputParser",
"index": 0
}
]
]
},
"Structured Output Parser1": {
"ai_outputParser": [
[
{
"node": "AI Draft Maker",
"type": "ai_outputParser",
"index": 0
}
]
]
}
}
}
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.
gmailOAuth2googleCalendarOAuth2ApigooglePalmApi
For the full experience including quality scoring and batch install features for each workflow upgrade to Pro
About this workflow
Keep your Gmail inbox organized and stress-free with this AI-powered workflow. Ideal for freelancers, small business owners, and productivity enthusiasts who receive a high volume of mixed emails. This template automatically sorts messages into predefined labels and drafts a…
Source: https://n8n.io/workflows/10664/ — original creator credit. Request a take-down →
Related workflows
Workflows that share integrations, category, or trigger type with this one. All free to copy and import.
This n8n workflow automates email management by classifying incoming messages, drafting replies, and sending alerts—all powered by AI.
Use cases are many: Manage your Gmail inbox, schedule calendar events, and handle contact details — all from one central AI-powered assistant. Perfect for freelancers managing clients, agency owners w
This workflow automatically transforms your messy inbox into a neatly organized space while ensuring you never miss a critical message. It connects to your Gmail account and triggers for every new ema
N8N-Gmail-Ai-Auto-Labeler. Uses gmailTrigger, lmChatGoogleGemini, gmailTool, agent. Event-driven trigger; 25 nodes.
> An intelligent n8n workflow that automatically classifies and labels Gmail emails using Google Gemini AI, keeping your inbox organized with zero manual effort.