AutomationFlowsAI & RAG › Automate Pet Grooming Posts & Bookings with Ai, Facebook & Telegram Bot

Automate Pet Grooming Posts & Bookings with Ai, Facebook & Telegram Bot

ByChristian Moises @hyxcreation on n8n.io

This workflow automates Facebook posting and appointment booking directly from a Telegram bot, making it especially useful for pet grooming businesses that want to keep their social media active while also confirming new bookings in real time.

Event trigger★★★★★ complexityAI-powered36 nodesGoogle SheetsOpenAI ChatOutput Parser StructuredGoogle Gemini ChatTelegram TriggerAgentTelegramGoogle Calendar
AI & RAG Trigger: Event Nodes: 36 Complexity: ★★★★★ AI nodes: yes Added:

This workflow corresponds to n8n.io template #7554 — we link there as the canonical source.

This workflow follows the Agent → Facebookgraphapi 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
{
  "meta": {
    "templateCredsSetupCompleted": true
  },
  "nodes": [
    {
      "id": "a9bf4049-419f-4fc2-8f35-0222d0e441dd",
      "name": "Get row(s) in sheet",
      "type": "n8n-nodes-base.googleSheets",
      "position": [
        -528,
        -400
      ],
      "parameters": {
        "options": {
          "returnFirstMatch": true
        },
        "filtersUI": {
          "values": [
            {
              "lookupValue": "False",
              "lookupColumn": "Uploaded"
            }
          ]
        },
        "sheetName": {
          "__rl": true,
          "mode": "list",
          "value": "gid=0",
          "cachedResultUrl": "https://docs.google.com/spreadsheets/d/1LPX3j53agLsFtpuyQ_tgJ1xY1STPJMnjHux560beu3c/edit#gid=0",
          "cachedResultName": "Sheet1"
        },
        "documentId": {
          "__rl": true,
          "mode": "list",
          "value": "1LPX3j53agLsFtpuyQ_tgJ1xY1STPJMnjHux560beu3c",
          "cachedResultUrl": "https://docs.google.com/spreadsheets/d/1LPX3j53agLsFtpuyQ_tgJ1xY1STPJMnjHux560beu3c/edit?usp=drivesdk",
          "cachedResultName": "Posting Details"
        }
      },
      "credentials": {
        "googleSheetsOAuth2Api": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 4.6,
      "alwaysOutputData": true
    },
    {
      "id": "9fccccc7-ca1e-477d-b0ae-551f26a9e6fd",
      "name": "OpenAI Chat Model",
      "type": "@n8n/n8n-nodes-langchain.lmChatOpenAi",
      "position": [
        576,
        -272
      ],
      "parameters": {
        "model": {
          "__rl": true,
          "mode": "list",
          "value": "gpt-4o-mini",
          "cachedResultName": "gpt-4o-mini"
        },
        "options": {}
      },
      "typeVersion": 1.2
    },
    {
      "id": "85dbf0aa-c85f-48ab-ae5f-734f2c1ce873",
      "name": "Structured Output Parser",
      "type": "@n8n/n8n-nodes-langchain.outputParserStructured",
      "position": [
        928,
        -288
      ],
      "parameters": {
        "autoFix": true,
        "jsonSchemaExample": "{\n  \"caption\": \"Astig ng glow si Maki ngayong July 29, 2025, fresh cut na sobrang kintab! \u2728\ud83d\udc3e\\nGrabe siya, ang bait niya habang pinapamper namin kaya talagang pet glow up siya! \ud83d\ude0d\\nMagpa\u2011appointment ka na para ma\u2011experience ng furbaby mo ang glow magic! \ud83d\udc96\ud83d\udcc5\\n---\\nFind us on #GoogleMaps:\\n\ud83d\udccc Floodway Pethouse\\nSamagta St Floodway, Taytay, 1920 Rizal\\n.\\n\ud83d\udcccGOOGLE MAPS LINK:\\nhttps://maps.app.goo.gl/XJwJLR3bB1YugpmE6\",\n  \"image_url\": \"https://api.telegram.org/file/bot8283668440:AAG6wg_YOUR_AWS_SECRET_KEY_HERE_18.jpg\"\n}\n"
      },
      "typeVersion": 1.3
    },
    {
      "id": "33ac6849-1ec5-4303-a79e-60c68084d35c",
      "name": "Google Gemini Chat Model1",
      "type": "@n8n/n8n-nodes-langchain.lmChatGoogleGemini",
      "position": [
        928,
        -128
      ],
      "parameters": {
        "options": {}
      },
      "typeVersion": 1
    },
    {
      "id": "75098650-571a-4ec3-b7f7-4f2a54534f8c",
      "name": "On Message Receive",
      "type": "n8n-nodes-base.telegramTrigger",
      "position": [
        -1600,
        -544
      ],
      "parameters": {
        "updates": [
          "message"
        ],
        "additionalFields": {
          "chatIds": ""
        }
      },
      "credentials": {
        "telegramApi": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 1.2
    },
    {
      "id": "073baf82-c455-40db-bfe0-6ccf362e804d",
      "name": "Check Message",
      "type": "n8n-nodes-base.switch",
      "position": [
        -1376,
        -560
      ],
      "parameters": {
        "rules": {
          "values": [
            {
              "outputKey": "Booking",
              "conditions": {
                "options": {
                  "version": 2,
                  "leftValue": "",
                  "caseSensitive": true,
                  "typeValidation": "strict"
                },
                "combinator": "and",
                "conditions": [
                  {
                    "id": "8ed0f5e6-4919-46f2-8062-81e577a1405e",
                    "operator": {
                      "type": "string",
                      "operation": "startsWith"
                    },
                    "leftValue": "={{ $json.message.text }}",
                    "rightValue": "/book"
                  }
                ]
              },
              "renameOutput": true
            },
            {
              "outputKey": "Post Command",
              "conditions": {
                "options": {
                  "version": 2,
                  "leftValue": "",
                  "caseSensitive": true,
                  "typeValidation": "strict"
                },
                "combinator": "and",
                "conditions": [
                  {
                    "id": "98fa8fd5-2a32-4bd7-80c1-afa4b64b8746",
                    "operator": {
                      "name": "filter.operator.equals",
                      "type": "string",
                      "operation": "equals"
                    },
                    "leftValue": "={{ $json.message.text }}",
                    "rightValue": "/post"
                  }
                ]
              },
              "renameOutput": true
            },
            {
              "outputKey": "Queue",
              "conditions": {
                "options": {
                  "version": 2,
                  "leftValue": "",
                  "caseSensitive": true,
                  "typeValidation": "strict"
                },
                "combinator": "and",
                "conditions": [
                  {
                    "id": "2da51619-9670-42b7-b91c-bb39c5aaa337",
                    "operator": {
                      "type": "array",
                      "operation": "lengthGt",
                      "rightType": "number"
                    },
                    "leftValue": "={{ $json.message.photo }}",
                    "rightValue": 0
                  }
                ]
              },
              "renameOutput": true
            }
          ]
        },
        "options": {
          "ignoreCase": false,
          "allMatchingOutputs": false
        }
      },
      "typeVersion": 3.2,
      "alwaysOutputData": false
    },
    {
      "id": "9554b807-009f-4bbf-bb11-848fe98d1fdf",
      "name": "If",
      "type": "n8n-nodes-base.if",
      "position": [
        -320,
        -400
      ],
      "parameters": {
        "options": {},
        "conditions": {
          "options": {
            "version": 2,
            "leftValue": "",
            "caseSensitive": true,
            "typeValidation": "loose"
          },
          "combinator": "or",
          "conditions": [
            {
              "id": "b603a886-6d5d-4b84-bdf0-d05d8d58d5da",
              "operator": {
                "type": "number",
                "operation": "exists",
                "singleValue": true
              },
              "leftValue": "={{ $json.row_number }}",
              "rightValue": ""
            }
          ]
        },
        "looseTypeValidation": true
      },
      "typeVersion": 2.2
    },
    {
      "id": "fc356777-d2fb-46ee-8014-c8018fe1bd6f",
      "name": "Set Upload to True",
      "type": "n8n-nodes-base.googleSheets",
      "position": [
        800,
        -688
      ],
      "parameters": {
        "columns": {
          "value": {
            "Uploaded": "True",
            "row_number": "={{ $json.row_number }}"
          },
          "schema": [
            {
              "id": "Pet_Name",
              "type": "string",
              "display": true,
              "removed": true,
              "required": false,
              "displayName": "Pet_Name",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Owners_Name",
              "type": "string",
              "display": true,
              "removed": true,
              "required": false,
              "displayName": "Owners_Name",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Image_Url",
              "type": "string",
              "display": true,
              "removed": true,
              "required": false,
              "displayName": "Image_Url",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Uploaded",
              "type": "string",
              "display": true,
              "removed": false,
              "required": false,
              "displayName": "Uploaded",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "row_number",
              "type": "number",
              "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": {
          "cellFormat": "RAW"
        },
        "operation": "update",
        "sheetName": {
          "__rl": true,
          "mode": "list",
          "value": "gid=0",
          "cachedResultUrl": "https://docs.google.com/spreadsheets/d/1LPX3j53agLsFtpuyQ_tgJ1xY1STPJMnjHux560beu3c/edit#gid=0",
          "cachedResultName": "Sheet1"
        },
        "documentId": {
          "__rl": true,
          "mode": "list",
          "value": "1LPX3j53agLsFtpuyQ_tgJ1xY1STPJMnjHux560beu3c",
          "cachedResultUrl": "https://docs.google.com/spreadsheets/d/1LPX3j53agLsFtpuyQ_tgJ1xY1STPJMnjHux560beu3c/edit?usp=drivesdk",
          "cachedResultName": "Posting Details"
        }
      },
      "credentials": {
        "googleSheetsOAuth2Api": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 4.6
    },
    {
      "id": "78ca79da-ec49-4b5c-a953-ee8211c509dd",
      "name": "Caption Generation",
      "type": "@n8n/n8n-nodes-langchain.agent",
      "position": [
        608,
        -496
      ],
      "parameters": {
        "text": "=We are a Grooming Business Called Floodway Pethouse,\nPet's Name:  {{ $json.Pet_Name }}\nOwner's Name: {{ $json.Owners_Name }}\nCurrent Date: {{ $now.format('DDD') }}\nImage_URL: {{ $json.Image_Url }}\n\nImage Content:{{ $json.content }}",
        "options": {
          "systemMessage": "{\n  \"caption\": \"Ang cute mo naman Goldie, nakakagigil ka \ud83d\ude0d\ud83d\ude0d\\n\ud83d\udd34 Visit us today! \u2728\\n.\\nBusiness hours:\\n\u2714\ufe0f PET SHOP:\\n\ud83d\udcc5 Wednesday\u2013Monday\\n\u23f0 9:00\u202fAM to 6:00\u202fPM\\n\u274c GROOMING:\\n\ud83d\udcc5 CLOSED every Tuesday\",\n  \"image_url\": \"https://api.telegram.org/file/bot8283668440:AAG6wg_YOUR_AWS_SECRET_KEY_HERE_18.jpg\"\n}\n"
        },
        "promptType": "define",
        "hasOutputParser": true
      },
      "typeVersion": 2.1
    },
    {
      "id": "bfc57be1-d132-4a9e-b720-a816a6c57428",
      "name": "Typing Effect",
      "type": "n8n-nodes-base.telegram",
      "position": [
        -1104,
        -976
      ],
      "parameters": {
        "chatId": "{Your Chat ID here}",
        "operation": "sendChatAction"
      },
      "credentials": {
        "telegramApi": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 1.2
    },
    {
      "id": "caa41d53-63db-4ec3-b7cb-2690e2ea8ac5",
      "name": "AI Agent1",
      "type": "@n8n/n8n-nodes-langchain.agent",
      "maxTries": 2,
      "position": [
        -192,
        -1200
      ],
      "parameters": {
        "text": "=The date today is: {{ $now }}/\nJSON Input:\n{{ $json.content.parts[0].text }}\n",
        "options": {
          "systemMessage": "\n### \ud83e\udd16 **n8n AI AGENT ROLE: Appointment Availability Checker**\n\nYou are an automated agent in an n8n workflow. Your task is to validate grooming appointment availability using the **Google Calendar API**, applying strict logic and format compliance.\n\n---\n\n### \ud83d\udd52 **TIME & FORMAT RULES**\n\n* All datetime values **must use RFC3339 format**\n  \u2192 Example: `2025-07-30T09:00:00+08:00`\n* Always apply the **+08:00 timezone offset** (PST / UTC+08:00)\n* When generating **error messages**, use **12-hour time format** for readability\n\n---\n\n### \ud83d\uddd3 **OPERATING HOURS**\n\n* **Open Days**: Monday, Wednesday\u2013Sunday\n* **Closed**: Tuesday\n* **Business Hours**: 9:00 AM \u2192 6:00 AM next day (21-hour operating window)\n\n---\n\n### \ud83d\udccb **BOOKING VALIDATION RULES**\n\n* **2 hours per pet** \u2192 total time = pets \u00d7 2 hours\n* Reject if:\n\n  * Falls on **Tuesday**\n  * Start or end time is **outside the 21-hour window**\n  * **Overlaps** with existing confirmed events on Google Calendar\n  * Uses **wrong format** or **missing timezone offset**\n\n---\n\n### \u2705 **CONFIRM AVAILABILITY ONLY IF:**\n\n* Time block is fully within allowed hours\n* No conflict exists in Google Calendar\n* Input datetime uses **valid RFC3339 format** with `+08:00` offset\n\n---\n\n### \ud83d\udd0d **CALENDAR API LOGIC (FOR n8n HTTP NODE):**\n\n* Use the following window to check availability:\n\n  * `timeMin` = Appointment start\n  * `timeMax` = Appointment end\n* Example:\n\n  ```\n  timeMin: 2025-07-30T00:00:00+08:00  \n  timeMax: 2025-07-31T00:00:00+08:00\n  ```\n* Convert Google Calendar API response from `America/New_York` to **Asia/Manila** (`+08:00`) before comparison\n\n---\n\n### \u26a0\ufe0f **AGENT RULES IN n8n:**\n\n* Output only: `available: true` or `available: false`\n* If `false`, provide clear reason (e.g., `\"Overlaps with existing booking\"`, `\"Outside business hours\"`)\n\n---\n"
        },
        "promptType": "define",
        "needsFallback": true,
        "hasOutputParser": true
      },
      "retryOnFail": true,
      "typeVersion": 2.1
    },
    {
      "id": "8affd593-b996-4c2e-99cd-1a7315d8a33a",
      "name": "If1",
      "type": "n8n-nodes-base.if",
      "position": [
        624,
        -1200
      ],
      "parameters": {
        "options": {},
        "conditions": {
          "options": {
            "version": 2,
            "leftValue": "",
            "caseSensitive": true,
            "typeValidation": "strict"
          },
          "combinator": "or",
          "conditions": [
            {
              "id": "aeea5ca0-a4d3-4597-990a-cabf04db26ce",
              "operator": {
                "type": "string",
                "operation": "equals"
              },
              "leftValue": "={{ $json.output.available }}",
              "rightValue": "true"
            }
          ]
        }
      },
      "typeVersion": 2.2
    },
    {
      "id": "09c0528e-8ad9-4a2e-8d70-3f5b9ab6edcd",
      "name": "Create an event",
      "type": "n8n-nodes-base.googleCalendar",
      "position": [
        1056,
        -1296
      ],
      "parameters": {
        "end": "={{ $json.output.end }}",
        "start": "={{ $json.output.start }}",
        "calendar": {
          "__rl": true,
          "mode": "list",
          "value": "user@example.com",
          "cachedResultName": "Grooming Schedule"
        },
        "additionalFields": {
          "summary": "={{ $json.output['Appointment Name'] }}"
        }
      },
      "typeVersion": 1.3
    },
    {
      "id": "6e5130cd-97a3-498e-86ee-2783143fb1c3",
      "name": "Format Fixing",
      "type": "@n8n/n8n-nodes-langchain.googleGemini",
      "position": [
        -672,
        -1168
      ],
      "parameters": {
        "modelId": {
          "__rl": true,
          "mode": "list",
          "value": "models/gemini-2.0-flash-lite",
          "cachedResultName": "models/gemini-2.0-flash-lite"
        },
        "options": {
          "systemMessage": " ---  ### \ud83e\udde0 SYSTEM ROLE: Smart Format Fixer  You process grooming appointment requests using the format:  ``` /book <number_of_pets>, <preferred_datetime>, <optional_details> ```  ---  ### \ud83d\udccc FORMAT RULES:  * `<number_of_pets>`: Positive integer * `<preferred_datetime>`: Must follow **RFC3339** format with `+08:00` offset   \u2192 Example: `2025-07-30T14:00:00+08:00` * `<optional_details>`: Optional notes (e.g., breed, requests).   \u2192 Must not break comma structure  ---  ### \ud83e\udd16 BEHAVIOR:  * If format is **missing elements** or is **ambiguous**, try to **infer** missing parts using:    * Current **date** if no date is mentioned   * Nearest **valid time** if input is vague (e.g., `2pm`) * If input **can be fixed**, return only the corrected format:    ```   /book 1, 2025-07-30T14:00:00+08:00, later jorblok   ``` * If it **cannot** be reliably fixed, respond with:    ```   ERROR: Invalid format. Use /book <number_of_pets>, <preferred_datetime>, <optional_details>   ```  ---  ### \u274c DO NOT:  * Include explanations, markdown, breakdowns, or analysis * Output anything other than:    * The **fixed** `/book` command   * Or the single-line **ERROR message**  ---"
        },
        "messages": {
          "values": [
            {
              "content": "=Current Time:{{ $now.setZone('Asia/Manila')}}\n\ninput: {{ $json.message.text }}\n"
            }
          ]
        }
      },
      "typeVersion": 1
    },
    {
      "id": "8e13ea40-006c-4960-bb75-18bfb3720a48",
      "name": "Structured Output Parser1",
      "type": "@n8n/n8n-nodes-langchain.outputParserStructured",
      "position": [
        192,
        -976
      ],
      "parameters": {
        "jsonSchemaExample": "{\n  \"available\": \"True\",\n  \"Appointment Name\": \"Goldie's Appointment\",\n  \"start\": \"2025-07-30T09:00:00+08:00\",\n  \"end\": \"2025-07-30T13:00:00+08:00\",\n  \"error\":\"There is an overlap\"\n}"
      },
      "typeVersion": 1.3
    },
    {
      "id": "86ba4ff0-ff3d-437c-9683-acce38a98df5",
      "name": "Get availability in a calendar in Google Calendar",
      "type": "n8n-nodes-base.googleCalendarTool",
      "position": [
        -64,
        -976
      ],
      "parameters": {
        "options": {},
        "timeMax": "={{ /*n8n-auto-generated-fromAI-override*/ $fromAI('Before', ``, 'string') }}",
        "timeMin": "={{ /*n8n-auto-generated-fromAI-override*/ $fromAI('Start_Time', ``, 'string') }}",
        "calendar": {
          "__rl": true,
          "mode": "list",
          "value": "user@example.com",
          "cachedResultName": "Grooming Schedule"
        },
        "resource": "calendar"
      },
      "retryOnFail": false,
      "typeVersion": 1.3
    },
    {
      "id": "d340e325-6934-4513-9c00-3efc1bca4444",
      "name": "Think",
      "type": "@n8n/n8n-nodes-langchain.toolThink",
      "position": [
        64,
        -976
      ],
      "parameters": {},
      "typeVersion": 1
    },
    {
      "id": "425c11f5-9cdc-4f92-8538-31849a13d6ec",
      "name": "OpenAI Chat Model2",
      "type": "@n8n/n8n-nodes-langchain.lmChatOpenAi",
      "position": [
        -320,
        -976
      ],
      "parameters": {
        "model": {
          "__rl": true,
          "mode": "list",
          "value": "gpt-4o-mini",
          "cachedResultName": "gpt-4o-mini"
        },
        "options": {}
      },
      "typeVersion": 1.2
    },
    {
      "id": "71b1f09d-9503-4a93-ae84-bcb98565cde6",
      "name": "Google Gemini Chat Model2",
      "type": "@n8n/n8n-nodes-langchain.lmChatGoogleGemini",
      "position": [
        -192,
        -976
      ],
      "parameters": {
        "options": {}
      },
      "typeVersion": 1
    },
    {
      "id": "b956d981-6b57-4f88-a168-8f2f35ef3232",
      "name": "Add Row1",
      "type": "n8n-nodes-base.googleSheetsTool",
      "position": [
        -112,
        448
      ],
      "parameters": {
        "columns": {
          "value": {
            "Pet_Name": "={{ /*n8n-auto-generated-fromAI-override*/ $fromAI('Pet_Name', ``, 'string') }}",
            "Uploaded": "False",
            "Image_Url": "={{ $json.image_url }}",
            "Owners_Name": "={{ /*n8n-auto-generated-fromAI-override*/ $fromAI('Owners_Name', ``, 'string') }}"
          },
          "schema": [
            {
              "id": "Pet_Name",
              "type": "string",
              "display": true,
              "removed": false,
              "required": false,
              "displayName": "Pet_Name",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Owners_Name",
              "type": "string",
              "display": true,
              "removed": false,
              "required": false,
              "displayName": "Owners_Name",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Image_Url",
              "type": "string",
              "display": true,
              "removed": false,
              "required": false,
              "displayName": "Image_Url",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "Uploaded",
              "type": "string",
              "display": true,
              "removed": false,
              "required": false,
              "displayName": "Uploaded",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            }
          ],
          "mappingMode": "defineBelow",
          "matchingColumns": [
            "Pet_Name"
          ],
          "attemptToConvertTypes": false,
          "convertFieldsToString": false
        },
        "options": {
          "cellFormat": "RAW"
        },
        "operation": "appendOrUpdate",
        "sheetName": {
          "__rl": true,
          "mode": "list",
          "value": "gid=0",
          "cachedResultUrl": "https://docs.google.com/spreadsheets/d/1LPX3j53agLsFtpuyQ_tgJ1xY1STPJMnjHux560beu3c/edit#gid=0",
          "cachedResultName": "Sheet1"
        },
        "documentId": {
          "__rl": true,
          "mode": "list",
          "value": "1LPX3j53agLsFtpuyQ_tgJ1xY1STPJMnjHux560beu3c",
          "cachedResultUrl": "https://docs.google.com/spreadsheets/d/1LPX3j53agLsFtpuyQ_tgJ1xY1STPJMnjHux560beu3c/edit?usp=drivesdk",
          "cachedResultName": "Posting Details"
        }
      },
      "credentials": {
        "googleSheetsOAuth2Api": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 4.6
    },
    {
      "id": "5715f9ce-c0a4-4e35-9c7a-331ee981fdfa",
      "name": "AI Post Scheduler1",
      "type": "@n8n/n8n-nodes-langchain.agent",
      "position": [
        -176,
        256
      ],
      "parameters": {
        "text": "=User Input:\n{{ $json.caption }}\n{{ $json.image_url || \"\" }}\n\nIf the attachment does not contain Pet_name and Owners_Name update the previous Row, with the Previous URL + \",\" + Current URL\ncurrent time:\n{{ $now}}",
        "options": {
          "systemMessage": "You are a data automation agent.\nYour task is to process image album messages received from Telegram and manage their metadata.\nFollow these steps precisely:\n\n\ud83d\udce5 1. Gather Inputs:\nExtract all image file URLs from an incoming Telegram message (Note: albums send multiple messages).\n\nOnly the first image may contain a caption with details.\n\nUse this caption to extract:\nPet_Name\nOwners_Name\n\n\ud83d\udcc2 2. Track and Group Album Images:\nIf image doesn't have Pet name or Owners Name, Set Cell name to Unavailable\n\n\ud83d\udcca 3. Store in Google Sheets:\nAppend each image and metadata as a new row in the Google Sheet.\n\n\ud83d\udcac 5. Telegram Feedback via sendMessage:\nAfter each upload (or failed upload), send a Telegram status update using the sendMessage node.\n\nSuccess Message:\n\u2705 Successfully added facebook post for queuing.\n\n\ud83e\udde0 Tools You Can Use:\nTelegram Node for input\n\nGoogle Sheets Node for append/update/GET ROW\n"
        },
        "promptType": "define"
      },
      "typeVersion": 2.1
    },
    {
      "id": "657c4501-a982-43b3-9f9d-87ce2050966a",
      "name": "Format Response1",
      "type": "n8n-nodes-base.set",
      "position": [
        -480,
        336
      ],
      "parameters": {
        "options": {},
        "assignments": {
          "assignments": [
            {
              "id": "0b94ad06-0461-48e6-9075-8bb66787b623",
              "name": "image_url",
              "type": "string",
              "value": "=https://api.telegram.org/file/bot<YOUR_BOT_TOKEN>/{{ $json.result.file_path }}\n"
            },
            {
              "id": "2f2ce553-82cf-408a-b9be-3fb09f06deff",
              "name": "caption",
              "type": "string",
              "value": "={{ $('On Message Receive').item.json.message.caption }}"
            }
          ]
        }
      },
      "typeVersion": 3.4
    },
    {
      "id": "e479fdd7-e918-486b-9317-b9f1911d0489",
      "name": "Get FileID1",
      "type": "n8n-nodes-base.telegram",
      "position": [
        -704,
        336
      ],
      "parameters": {
        "fileId": "={{ $json.message.photo[$json.message.photo.length - 1].file_id }}",
        "download": false,
        "resource": "file"
      },
      "credentials": {
        "telegramApi": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 1.2
    },
    {
      "id": "86485653-9095-4f66-af9a-a07f231333d4",
      "name": "OpenAI Chat Model1",
      "type": "@n8n/n8n-nodes-langchain.lmChatOpenAi",
      "position": [
        -272,
        464
      ],
      "parameters": {
        "model": {
          "__rl": true,
          "mode": "list",
          "value": "gpt-4o-mini",
          "cachedResultName": "gpt-4o-mini"
        },
        "options": {}
      },
      "typeVersion": 1.2
    },
    {
      "id": "73429452-3aca-4b10-8e6f-271be6810edc",
      "name": "Send a text message in Telegram1",
      "type": "n8n-nodes-base.telegramTool",
      "position": [
        64,
        448
      ],
      "parameters": {
        "text": "={{ /*n8n-auto-generated-fromAI-override*/ $fromAI('Text', ``, 'string') }}",
        "chatId": "{Your Chat ID}",
        "additionalFields": {
          "appendAttribution": false
        }
      },
      "credentials": {
        "telegramApi": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 1.2
    },
    {
      "id": "a7cb00f3-54f0-465f-8f78-73785eb74900",
      "name": "Sticky Note1",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        -752,
        -736
      ],
      "parameters": {
        "color": 4,
        "width": 2336,
        "height": 800,
        "content": "# Social Media Manager Agent (/post) \n\n- ### Triggered on Command call & Scheduled Trigger(Optional)\n## Flow\n1. Access the google sheet and check for all rows with Uploaded=False (means it hasn't been uploaded yet)\n2. Proceeds with the Row that hasn't been posted yet and returns Image URL, Pet and Owner's name.\n3. Send the Image URL to an Image Analyzer model, to explain what the image is\n4. Auto Generate Caption with based on the Image URL, Pet and Owner's name.\n5. Access Google sheet and set the row to True since it has been processed and uploaded.\n6. Send a status update on telegram."
      },
      "typeVersion": 1
    },
    {
      "id": "8d117704-38b6-40d5-952c-1a69ef7860ea",
      "name": "Sticky Note2",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        -752,
        64
      ],
      "parameters": {
        "color": 6,
        "width": 1216,
        "height": 528,
        "content": "# Facebook Post Scheduler\n-All messages sent on the bot with an image and a caption are all passed here.\n## Flow\n1. Get file ID of the image (File ID is needed to get the Image URL)\n2. Format Response (Add your bot_token in the Format_response node) \n3. Use an AI Agent with Access to Telegram Node to send a message and Google sheets, to push your image and details to the queue."
      },
      "typeVersion": 1
    },
    {
      "id": "b7de59e5-d97e-41da-a1a4-2b9ec9402def",
      "name": "Analyze image",
      "type": "@n8n/n8n-nodes-langchain.openAi",
      "position": [
        352,
        -496
      ],
      "parameters": {
        "modelId": {
          "__rl": true,
          "mode": "list",
          "value": "gpt-4o-mini",
          "cachedResultName": "GPT-4O-MINI"
        },
        "options": {},
        "resource": "image",
        "imageUrls": "={{ $json.Image_Url }}",
        "operation": "analyze"
      },
      "typeVersion": 1.8
    },
    {
      "id": "b4ae0d96-edd3-433d-9982-1426cd449e86",
      "name": "Schedule Trigger",
      "type": "n8n-nodes-base.scheduleTrigger",
      "position": [
        -704,
        -400
      ],
      "parameters": {
        "rule": {
          "interval": [
            {
              "triggerAtHour": 1
            }
          ]
        }
      },
      "typeVersion": 1.2
    },
    {
      "id": "82e5882e-013a-4b06-b680-c0472084ec79",
      "name": "Post  on Facebook",
      "type": "n8n-nodes-base.facebookGraphApi",
      "position": [
        1056,
        -496
      ],
      "parameters": {
        "edge": "photos",
        "node": "me",
        "options": {
          "queryParameters": {
            "parameter": [
              {
                "name": "caption",
                "value": "={{ $json.output.caption }}"
              },
              {
                "name": "=url",
                "value": "={{ $('Get row(s) in sheet').item.json.Image_Url }}"
              }
            ]
          }
        },
        "graphApiVersion": "v22.0",
        "httpRequestMethod": "POST"
      },
      "typeVersion": 1
    },
    {
      "id": "fbed1f4f-84de-49a0-9878-66d577c989e7",
      "name": "Sticky Note",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        -752,
        -1536
      ],
      "parameters": {
        "color": 6,
        "width": 2336,
        "height": 800,
        "content": "# Booking Agent (Queue)\nFlow:\n-Format the message to proper Format accordingly\n-Send to Agent with access to Google Calendar\n-Agent Checks if the specified timeslot is empty\n-Condition: If  timeslot available, Proceed and create a calendar event then send a message. , Else, Just send a telegram message about the status\n\n"
      },
      "typeVersion": 1
    },
    {
      "id": "5a1f077f-f7c5-4669-9f64-57a66acb97e7",
      "name": "No post on queue",
      "type": "n8n-nodes-base.telegram",
      "position": [
        240,
        -304
      ],
      "parameters": {
        "text": "Sorry. There's no Post on queue.",
        "chatId": "123456789",
        "forceReply": {},
        "replyMarkup": "forceReply",
        "additionalFields": {
          "appendAttribution": false,
          "reply_to_message_id": "={{ $json.message.message_id }}"
        }
      },
      "credentials": {
        "telegramApi": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 1.2
    },
    {
      "id": "4cb65717-2f65-490a-b057-1dfec0321245",
      "name": "Success Message",
      "type": "n8n-nodes-base.telegram",
      "position": [
        1056,
        -688
      ],
      "parameters": {
        "text": "Will Start Posting now.",
        "chatId": "{Your chat id here}",
        "forceReply": {},
        "replyMarkup": "forceReply",
        "additionalFields": {
          "appendAttribution": false,
          "reply_to_message_id": "={{ $json.message.message_id }}"
        }
      },
      "credentials": {
        "telegramApi": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 1.2
    },
    {
      "id": "956bb4a5-95b2-4f76-915f-4037cd51e22f",
      "name": "Error Message",
      "type": "n8n-nodes-base.telegram",
      "position": [
        1056,
        -1104
      ],
      "parameters": {
        "text": "={{ $json.output.error }}",
        "chatId": "123456789",
        "forceReply": {},
        "replyMarkup": "forceReply",
        "additionalFields": {
          "appendAttribution": false
        }
      },
      "credentials": {
        "telegramApi": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 1.2
    },
    {
      "id": "a33750df-00aa-49fb-9422-11fd23ddecfa",
      "name": "Success Message1",
      "type": "n8n-nodes-base.telegram",
      "position": [
        1280,
        -1296
      ],
      "parameters": {
        "text": "Appointment Added!",
        "chatId": "123456789",
        "forceReply": {},
        "replyMarkup": "forceReply",
        "additionalFields": {
          "appendAttribution": false
        }
      },
      "credentials": {
        "telegramApi": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 1.2
    },
    {
      "id": "8f6b6427-40e5-4891-b33e-4e0fb28fde11",
      "name": "Sticky Note3",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        -1232,
        -1120
      ],
      "parameters": {
        "width": 352,
        "height": 320,
        "content": "## Typing effect \nThe purpose of this node is to add an indicator that the workflow is working by adding a typing effect from the bot once a message is received."
      },
      "typeVersion": 1
    }
  ],
  "connections": {
    "If": {
      "main": [
        [
          {
            "node": "Set Upload to True",
            "type": "main",
            "index": 0
          },
          {
            "node": "Analyze image",
            "type": "main",
            "index": 0
          }
        ],
        [
          {
            "node": "No post on queue",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "If1": {
      "main": [
        [
          {
            "node": "Create an event",
            "type": "main",
            "index": 0
          }
        ],
        [
          {
            "node": "Error Message",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Think": {
      "ai_tool": [
        [
          {
            "node": "AI Agent1",
            "type": "ai_tool",
            "index": 0
          }
        ]
      ]
    },
    "Add Row1": {
      "ai_tool": [
        [
          {
            "node": "AI Post Scheduler1",
            "type": "ai_tool",
            "index": 0
          }
        ]
      ]
    },
    "AI Agent1": {
      "main": [
        [
          {
            "node": "If1",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Get FileID1": {
      "main": [
        [
          {
            "node": "Format Response1",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Analyze image": {
      "main": [
        [
          {
            "node": "Caption Generation",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Check Message": {
      "main": [
        [
          {
            "node": "Typing Effect",
            "type": "main",
            "index": 0
          },
          {
            "node": "Format Fixing",
            "type": "main",
            "index": 0
          }
        ],
        [
          {
            "node": "Get row(s) in sheet",
            "type": "main",
            "index": 0
          },
          {
            "node": "Typing Effect",
            "type": "main",
            "index": 0
          }
        ],
        [
          {
            "node": "Get FileID1",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Format Fixing": {
      "main": [
        [
          {
            "node": "AI Agent1",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Create an event": {
      "main": [
        [
          {
            "node": "Success Message1",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Format Response1": {
      "main": [
        [
          {
            "node": "AI Post Scheduler1",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Schedule Trigger": {
      "main": [
        [
          {
            "node": "Get row(s) in sheet",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "OpenAI Chat Model": {
      "ai_languageModel": [
        [
          {
            "node": "Caption Generation",
            "type": "ai_languageModel",
            "index": 0
          }
        ]
      ]
    },
    "Caption Generation": {
      "main": [
        [
          {
            "node": "Post  on Facebook",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "On Message Receive": {
      "main": [
        [
          {
            "node": "Check Message",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "OpenAI Chat Model1": {
      "ai_languageModel": [
        [
          {
            "node": "AI Post Scheduler1",
            "type": "ai_languageModel",
            "index": 0
          }
        ]
      ]
    },
    "OpenAI Chat Model2": {
      "ai_languageModel": [
        [
          {
            "node": "AI Agent1",
            "type": "ai_languageModel",
            "index": 0
          }
        ]
      ]
    },
    "Set Upload to True": {
      "main": [
        [
          {
            "node": "Success Message",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Get row(s) in sheet": {
      "main": [
        [
          {
            "node": "If",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Structured Output Parser": {
      "ai_outputParser": [
        [
          {
            "node": "Caption Generation",
            "type": "ai_outputParser",
            "index": 0
          }
        ]
      ]
    },
    "Google Gemini Chat Model1": {
      "ai_languageModel": [
        [
          {
            "node": "Structured Output Parser",
            "type": "ai_languageModel",
            "index": 0
          }
        ]
      ]
    },
    "Google Gemini Chat Model2": {
      "ai_languageModel": [
        [
          {
            "node": "AI Agent1",
            "type": "ai_languageModel",
            "index": 1
          }
        ]
      ]
    },
    "Structured Output Parser1": {
      "ai_outputParser": [
        [
          {
            "node": "AI Agent1",
            "type": "ai_outputParser",
            "index": 0
          }
        ]
      ]
    },
    "Send a text message in Telegram1": {
      "ai_tool": [
        [
          {
            "node": "AI Post Scheduler1",
            "type": "ai_tool",
            "index": 0
          }
        ]
      ]
    },
    "Get availability in a calendar in Google Calendar": {
      "ai_tool": [
        [
          {
            "node": "AI Agent1",
            "type": "ai_tool",
            "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.

Pro

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

About this workflow

This workflow automates Facebook posting and appointment booking directly from a Telegram bot, making it especially useful for pet grooming businesses that want to keep their social media active while also confirming new bookings in real time.

Source: https://n8n.io/workflows/7554/ — original creator credit. Request a take-down →

More AI & RAG workflows → · Browse all categories →

Related workflows

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

AI & RAG

🎯 Create viral TikToks, Shorts, Reels, podcasts, and ASMR videos in minutes — all on autopilot.

OpenAI, HTTP Request, Form Trigger +7
AI & RAG

This workflow creates a multi-talented AI assistant named Simran that interacts with users via Telegram. It can handle text and voice messages, understand the user's intent, and perform various tasks.

MongoDB, Chain Llm, Google Gemini Chat +11
AI & RAG

Generate AI viral videos with NanoBanana & VEO3, shared on socials via Blotato 2. Uses @blotato/n8n-nodes-blotato, googleSheets, lmChatOpenAi, toolThink. Event-driven trigger; 94 nodes.

@Blotato/N8N Nodes Blotato, Google Sheets, OpenAI Chat +9
AI & RAG

This project is a template for building a complete academic virtual assistant using n8n. It connects to Telegram, answers frequently asked questions by querying MongoDB, keeps the community informed a

Telegram, MongoDB, Telegram Trigger +6
AI & RAG

Telegram Trigger receives incoming messages (text, voice, photo, document). Switch routes by message type to appropriate processors: Text → forwarded as-is. Voice → downloaded and sent to Transcribe a

Memory Buffer Window, Telegram Trigger, Telegram +12