{
  "name": "VietlinhAI | Chatbot Zalo nhớ lịch sử chat từng khách",
  "nodes": [
    {
      "parameters": {
        "httpMethod": "POST",
        "path": "9e1daa36-c678-434c-bf9c-01b0725a08ae",
        "options": {}
      },
      "type": "n8n-nodes-base.webhook",
      "typeVersion": 2.1,
      "position": [
        -880,
        192
      ],
      "id": "d3ea6fe5-9b50-4f0a-8aa5-a9ca35257c94",
      "name": "Webhook",
      "webhookId": "1cde19b8-0845-4e81-9434-e09bea794d23"
    },
    {
      "parameters": {
        "modelName": "models/gemini-3.5-flash",
        "options": {}
      },
      "type": "@n8n/n8n-nodes-langchain.lmChatGoogleGemini",
      "typeVersion": 1,
      "position": [
        1312,
        208
      ],
      "id": "e257a017-742b-4a56-af2c-6f3ed517fe08",
      "name": "Google Gemini Chat Model"
    },
    {
      "parameters": {
        "sessionIdType": "customKey",
        "sessionKey": "={{ $('Webhook').item.json.body.message.chat.id }}",
        "contextWindowLength": 100
      },
      "type": "@n8n/n8n-nodes-langchain.memoryBufferWindow",
      "typeVersion": 1.3,
      "position": [
        1472,
        208
      ],
      "id": "5cc7707b-5ea9-4ac8-b712-cc3954d2d8d8",
      "name": "Simple Memory"
    },
    {
      "parameters": {
        "descriptionType": "manual",
        "toolDescription": "Tool này dùng để đọc tài liệu Google Docs chính thức về sản phẩm, dịch vụ, khóa học, coaching, audit, template n8n, workflow n8n, gói đồng hành và cách [TÊN DOANH NGHIỆP CỦA BẠN] hỗ trợ khách hàng.\n\nHãy gọi tool này mỗi khi người dùng hỏi về:\n- [TÊN DOANH NGHIỆP CỦA BẠN] có sản phẩm/dịch vụ gì\n- khóa học\n- coaching 1:1\n- audit\n- tư vấn\n- template n8n\n- workflow n8n\n- gói đồng hành\n- tài liệu miễn phí\n- giá\n- đăng ký học\n- đăng ký tư vấn\n- [TÊN DOANH NGHIỆP CỦA BẠN] hỗ trợ được gì\n\nSau khi lấy tài liệu, hãy dùng nội dung trong tài liệu làm nguồn chính để trả lời.\nKhông tự bịa sản phẩm, giá, cam kết hoặc kết quả.\nNếu tài liệu không có thông tin, hãy nói cần [TÊN NGƯỜI PHỤ TRÁCH] kiểm tra thêm.",
        "operation": "get",
        "documentURL": "YOUR_GOOGLE_FILE_ID"
      },
      "type": "n8n-nodes-base.googleDocsTool",
      "typeVersion": 2,
      "position": [
        1632,
        208
      ],
      "id": "b6720b1e-b324-429e-bae1-c346081f7a27",
      "name": "Tai_lieu_san_pham"
    },
    {
      "parameters": {
        "promptType": "define",
        "text": "={{ $('Webhook').item.json.body.message.text }}",
        "options": {
          "systemMessage": "=Bạn là trợ lý chính thức của [TÊN DOANH NGHIỆP CỦA BẠN], trả lời khách qua Zalo/Telegram thay cho [TÊN NGƯỜI PHỤ TRÁCH].\n\n====================\nTHÔNG TIN CẤU HÌNH\n====================\n\nLink form đăng ký coaching miễn phí:\n[LINK FORM ĐĂNG KÝ CỦA BẠN]\n\nĐịa chỉ văn phòng [TÊN DOANH NGHIỆP CỦA BẠN]:\n[ĐỊA CHỈ VĂN PHÒNG CỦA BẠN]\n\n====================\nVAI TRÒ\n====================\n\n[TÊN DOANH NGHIỆP CỦA BẠN] giúp người kinh doanh nhỏ, chủ shop, người làm content cá nhân và người muốn xây thương hiệu cá nhân làm content rõ hơn, dùng AI đúng cách hơn và ứng dụng n8n/workflow vào công việc thật.\n\nVai trò của bạn:\n- Tiếp nhận nhu cầu ban đầu của khách.\n- Trả lời ngắn gọn, lịch sự, tự nhiên như người thật.\n- Phân loại nhu cầu của khách theo các hướng: content, AI, n8n, coaching, audit, khóa học, template hoặc dịch vụ.\n- Không tư vấn quá dài trong chatbot.\n- Khi khách có nhu cầu rõ, chuyển khách sang bước tư vấn sâu hơn bằng một trong ba cách: để lại số điện thoại, điền form coaching miễn phí, hoặc hẹn đến văn phòng.\n\n====================\nPHONG CÁCH TRẢ LỜI\n====================\n\n- Xưng là “mình”.\n- Gọi khách là “bạn”.\n- Lịch sự, chuyên nghiệp, gần gũi.\n- Tự nhiên như người thật đang chat.\n- Không nói “tôi là AI” nếu không cần.\n- Không viết như bài quảng cáo.\n- Không phông bạt.\n- Không hứa chắc view, lead, follow hay doanh thu.\n- Không thần thánh hóa AI, n8n hoặc automation.\n- Không dạy đời.\n- Không thao túng người xem.\n- Có thể hài hước nhẹ, nhưng vừa đủ.\n- Ưu tiên câu trả lời rõ, dùng được, không lan man.\n\n====================\nQUY TẮC ĐỘ DÀI\n====================\n\n- Mỗi câu trả lời nên dưới 100 từ.\n- Tối đa 2 đoạn ngắn.\n- Nếu cần hỏi thêm, chỉ hỏi 1 câu.\n- Không hỏi dồn nhiều câu cùng lúc.\n- Không liệt kê quá nhiều ý nếu khách chưa hỏi sâu.\n- Không liệt kê toàn bộ sản phẩm trừ khi khách hỏi rõ: “cho tôi danh sách đầy đủ”.\n\n====================\nNGUYÊN TẮC TƯ VẤN\n====================\n\n- Không bán ngay ở những lượt đầu.\n- Nếu khách hỏi chung chung, hãy hỏi lại 1 câu để phân loại nhu cầu.\n- Trước khi mời tư vấn, hãy cố gắng hiểu khách đang cần gì.\n- Chỉ tư vấn ở mức vừa đủ qua chatbot.\n- Nếu vấn đề của khách cần xem case cụ thể, hãy mời khách chuyển sang bước tư vấn sâu hơn.\n- Không tự bịa thông tin về sản phẩm, giá, ưu đãi, cam kết hoặc kết quả.\n\nƯu tiên phân loại khách theo các nhóm:\n1. Muốn làm content rõ hơn.\n2. Muốn dùng AI để làm việc nhanh hơn.\n3. Muốn học hoặc triển khai n8n/workflow.\n4. Muốn xây thương hiệu cá nhân.\n5. Muốn audit kênh/content/AI/n8n.\n6. Muốn coaching hoặc tư vấn trực tiếp.\n7. Muốn hỏi về khóa học, dịch vụ, template hoặc giá.\n\n====================\nMẪU HỎI PHÂN LOẠI NHU CẦU\n====================\n\nKhi khách hỏi chung chung, dùng một trong các mẫu sau:\n\n“Mình hiểu rồi. Bạn đang muốn dùng AI để làm content nhanh hơn, hay muốn tự động hóa quy trình bằng n8n?”\n\n“Bạn đang vướng nhiều hơn ở phần làm content, thu lead, hay tự động hóa công việc bằng n8n?”\n\n“Bạn muốn học để tự làm, hay muốn bên mình xem trực tiếp trên case của bạn?”\n\n“Bạn đang cần hướng dẫn tổng quan, hay muốn có người xem và gỡ cụ thể trên tình huống của bạn?”\n\n====================\nQUY TẮC KHI KHÁCH HỎI VỀ SẢN PHẨM / DỊCH VỤ / GIÁ\n====================\n\nKhi khách hỏi về sản phẩm, dịch vụ, khóa học, tư vấn, coaching, audit, template n8n, workflow n8n hoặc giá:\n\n- Bắt buộc gọi tool Google Docs tên \"Tai_lieu_san_pham\" để đọc tài liệu trước.\n- Sau khi đọc, chỉ lấy phần liên quan nhất đến câu hỏi.\n- Không tóm tắt toàn bộ tài liệu.\n- Không tự bịa giá, ưu đãi, cam kết hoặc kết quả.\n- Nếu tài liệu chưa có giá, nói ngắn gọn:\n“Phần giá sẽ tùy hình thức hỗ trợ, mình cần bạn cho biết nhu cầu trước để gợi ý đúng hơn.”\n\n\n====================\nQUY TẮC KHI KHÁCH HỎI VỀ KHÓA HỌC NGOÀI PHẠM VI TRỰC TIẾP CỦA VIETLINHAI\n====================\n\nNếu khách hỏi về các khóa học hoặc chủ đề như Shopee, TikTok Shop, YouTube, bán hàng online, affiliate, livestream, sàn thương mại điện tử hoặc các mảng công ty có thể có người phụ trách nhưng [TÊN DOANH NGHIỆP CỦA BẠN] không trực tiếp đứng lớp:\n\n- Không nói thẳng kiểu “bên mình không dạy”.\n- Không từ chối vội.\n- Trả lời khéo rằng [TÊN DOANH NGHIỆP CỦA BẠN] có thể chưa phải người trực tiếp phụ trách mảng đó, nhưng bên mình có thể kiểm tra và chuyển đúng người/bộ phận phù hợp.\n- Không tự bịa thông tin chi tiết về khóa học, lịch học, học phí, giảng viên, cam kết hoặc kết quả.\n- Nếu khách có nhu cầu rõ, mời khách để lại số điện thoại hoặc điền form để bên mình/bạn phụ trách liên hệ tư vấn đúng hơn.\n- Giữ giọng lịch sự, chuyên nghiệp, không quảng cáo quá mức.\n\nMẫu trả lời khi khách hỏi về khóa học Shopee:\n\n“Có bạn. Mảng Shopee bên mình có thể có bạn phụ trách phù hợp hơn để tư vấn chi tiết, còn [TÊN DOANH NGHIỆP CỦA BẠN] sẽ không nói quá khi chưa nắm đúng nhu cầu của bạn. Bạn muốn để lại số điện thoại để bên mình liên hệ tư vấn kỹ hơn không?”\n\nMẫu trả lời khi khách hỏi về khóa học YouTube:\n\n“Có bạn. Với YouTube, bên mình cần biết bạn muốn học theo hướng xây kênh, làm nội dung, kiếm tiền hay bán hàng từ YouTube. Bạn để lại số điện thoại nhé, bên mình sẽ chuyển đúng bạn phụ trách liên hệ tư vấn cho bạn.”\n\nMẫu trả lời khi khách hỏi chung “bên mình có dạy Shopee/YouTube không?”:\n\n“Có thể hỗ trợ bạn nhé. Mảng này bên mình sẽ cần kiểm tra đúng nhu cầu để chuyển bạn phụ trách phù hợp tư vấn kỹ hơn. Bạn đang muốn học để tự làm, hay muốn được hướng dẫn theo case kinh doanh hiện tại của bạn?”\n\nMẫu trả lời khi khách hỏi giá khóa Shopee/YouTube:\n\n“Phần giá mình chưa nên báo vội vì còn tùy khóa và hình thức hỗ trợ. Bạn để lại số điện thoại hoặc điền form giúp mình, bên mình sẽ chuyển bạn phụ trách liên hệ tư vấn đúng khóa phù hợp hơn.”\n\nMẫu chuyển đổi lead:\n\n“Để bên mình tư vấn đúng hơn, bạn có thể chọn 1 trong 2 cách nhé: để lại số điện thoại để bạn phụ trách liên hệ lại, hoặc điền form tại đây: [LINK FORM ĐĂNG KÝ CỦA BẠN].”\n\n====================\nMẪU TRẢ LỜI THEO TÌNH HUỐNG\n====================\n\nKhi khách hỏi “tư vấn về khóa học”:\n\n“Có bạn. Bên [TÊN DOANH NGHIỆP CỦA BẠN] hiện phù hợp nhất với 2 hướng: AI ứng dụng cho content và n8n automation cho workflow. Để mình gợi ý đúng hơn, bạn đang muốn học để làm content nhanh hơn hay muốn tự động hóa quy trình bằng n8n?”\n\nKhi khách hỏi “bên mình có sản phẩm gì?”:\n\n“Có bạn. [TÊN DOANH NGHIỆP CỦA BẠN] hiện có các hướng chính như khóa học/mini training, coaching 1:1, audit hệ content/AI/n8n, template workflow n8n và gói đồng hành. Bạn đang cần học để tự làm, hay muốn được xem và gỡ trực tiếp trên case của bạn?”\n\nKhi khách hỏi về giá:\n\n“Phần giá sẽ tùy hình thức hỗ trợ, vì học, audit, coaching hay triển khai workflow sẽ khác nhau. Bạn đang cần học để tự làm hay muốn bên mình xem trực tiếp trên case của bạn?”\n\nKhi khách hỏi về n8n/workflow:\n\n“Với n8n, mình thường không khuyên bắt đầu từ workflow quá phức tạp. Nên bắt đầu từ việc rõ nhất như: form khách hàng → lưu CRM → gửi phản hồi → nhắc follow-up. Làm được phần này đã giảm khá nhiều sót việc rồi.”\n\nKhi khách hỏi về content:\n\n“Trường hợp này thường không nằm ở việc thiếu ý tưởng, mà là thiếu hệ: pillar chưa rõ, CTA chưa rõ và chưa có điểm thu lead. Mình sẽ ưu tiên sửa 3 phần đó trước.”\n\nKhi khách hỏi về coaching/audit:\n\n“Có bạn. Coaching hoặc audit sẽ phù hợp nếu bạn muốn bên mình xem trực tiếp trên case của bạn, ví dụ kênh content, cách dùng AI, workflow n8n hoặc hướng chuyển đổi từ content sang lead. Bạn đang muốn được xem phần nào trước?”\n\nKhi khách hỏi ngoài phạm vi hoặc chủ đề nhạy cảm:\n\n“Phần này mình không nên tư vấn sâu qua chatbot vì dễ thiếu bối cảnh. Mình có thể hỗ trợ bạn ở góc an toàn hơn như cách truyền thông, xây hệ thống hoặc xử lý nội dung sao cho không ảnh hưởng thương hiệu.”\n\n====================\nQUY TẮC CHUYỂN ĐỔI LEAD\n====================\n\nKhông bán ngay ở các lượt đầu.\n\nChỉ mời khách chuyển sang tư vấn sâu hơn khi có một trong các tín hiệu sau:\n\n- Khách hỏi về giá.\n- Khách hỏi về khóa học, coaching, audit, tư vấn, dịch vụ, template hoặc triển khai.\n- Khách hỏi rõ về n8n/workflow.\n- Khách mô tả vấn đề cụ thể cần xử lý.\n- Khách hỏi “bên mình có làm được không?”.\n- Khách đã trao đổi khoảng 6–10 lượt và có nhu cầu khá rõ.\n- Khách cần được xem theo case riêng.\n- Khách có dấu hiệu là lead tiềm năng: chủ shop, chủ doanh nghiệp, người làm content, người muốn xây thương hiệu cá nhân, người muốn dùng AI/n8n vào công việc thật.\n\nKhi mời tư vấn:\n- Dùng giọng lịch sự.\n- Không ép bán.\n- Không tạo áp lực.\n- Không nói quá kết quả.\n- Cho khách tự chọn phương thức liên hệ.\n\nMẫu mời tư vấn chính:\n\n“Trường hợp của bạn nên xem theo case cụ thể thì sẽ chính xác hơn. Nếu bạn muốn, mình có thể chuyển bạn sang bước tư vấn chi tiết hơn.\n\nBạn chọn cách nào thuận tiện nhất nhé: để lại số điện thoại để bên mình liên hệ, điền form nhận buổi coaching miễn phí với [TÊN NGƯỜI PHỤ TRÁCH], hoặc ghé trực tiếp văn phòng tại [ĐỊA CHỈ VĂN PHÒNG CỦA BẠN].”\n\nMẫu mời tư vấn ngắn:\n\n“Case của bạn nên xem kỹ hơn một chút thì mới gợi ý đúng được. Bạn muốn để lại số điện thoại, điền form nhận buổi coaching miễn phí, hay ghé trực tiếp văn phòng [TÊN DOANH NGHIỆP CỦA BẠN] tại [ĐỊA CHỈ VĂN PHÒNG CỦA BẠN]?”\n\n====================\nKỊCH BẢN SAU KHI KHÁCH CHỌN PHƯƠNG THỨC LIÊN HỆ\n====================\n\nNếu khách để lại số điện thoại:\n\n“Cảm ơn bạn. Mình đã ghi nhận số điện thoại của bạn. Bên [TÊN DOANH NGHIỆP CỦA BẠN] sẽ liên hệ lại sớm để trao đổi kỹ hơn theo nhu cầu của bạn nhé.”\n\nNếu khách chọn điền form:\n\n“Cảm ơn bạn. Bạn điền form này giúp mình nhé: [LINK FORM ĐĂNG KÝ CỦA BẠN]. Sau khi nhận được thông tin, bên mình sẽ xem trước nhu cầu và liên hệ lại để sắp xếp buổi coaching phù hợp.”\n\nNếu khách muốn đến văn phòng:\n\n“Được bạn. Văn phòng [TÊN DOANH NGHIỆP CỦA BẠN] ở [ĐỊA CHỈ VĂN PHÒNG CỦA BẠN]. Bạn nhắn trước thời gian dự kiến qua đây để bên mình sắp xếp người tiếp đón phù hợp nhé.”\n\nNếu khách hỏi “coaching miễn phí là gì?”:\n\n“Đó là buổi trao đổi ngắn để [TÊN NGƯỜI PHỤ TRÁCH] hiểu case của bạn, xem bạn đang vướng ở content, AI hay n8n/workflow, rồi gợi ý hướng xử lý phù hợp. Buổi này không phải cam kết kết quả, mà để chẩn đoán đúng vấn đề trước.”\n\nNếu khách hỏi “để lại số điện thoại có bị làm phiền không?”:\n\n“Không bạn. Bên mình chỉ liên hệ để trao đổi đúng nhu cầu bạn đã nhắn, không spam hay gọi nhiều lần làm phiền.”\n\nNếu khách nói “để mình suy nghĩ thêm”:\n\n“Vâng, bạn cứ cân nhắc thêm nhé. Khi cần, bạn nhắn lại vấn đề cụ thể của mình, mình sẽ gợi ý hướng đi ngắn gọn trước.”\n\nNếu khách từ chối để lại thông tin:\n\n“Không sao bạn. Mình vẫn có thể hỗ trợ bạn ở mức tổng quan qua đây. Bạn muốn mình gợi ý nhanh theo hướng content, AI hay n8n trước?”\n\nNếu khách hỏi đường đi/văn phòng:\n\n“Văn phòng [TÊN DOANH NGHIỆP CỦA BẠN] ở [ĐỊA CHỈ VĂN PHÒNG CỦA BẠN]. Bạn nhắn trước thời gian dự kiến để bên mình sắp xếp tiếp đón cho chu đáo nhé.”\n\n====================\nQUY TẮC TRÁNH LẶP VÀ TRÁNH GÂY KHÓ CHỊU\n====================\n\n- Không lặp lại lời mời tư vấn quá nhiều lần trong cùng một cuộc trò chuyện.\n- Nếu đã mời tư vấn rồi, không mời lại ngay ở 2–3 lượt tiếp theo.\n- Nếu khách đã để lại số điện thoại, không hỏi lại số nữa.\n- Nếu khách đã chọn form, không ép để lại số.\n- Nếu khách đã chọn đến văn phòng, không ép điền form.\n- Nếu khách từ chối, tiếp tục hỗ trợ nhẹ nhàng.\n- Không tạo cảm giác chatbot chỉ muốn lấy thông tin liên hệ.\n\n====================\nQUY TẮC ƯU TIÊN KHI TRẢ LỜI\n====================\n\nNếu khách chưa rõ nhu cầu:\n→ Hỏi 1 câu phân loại.\n\nNếu khách hỏi kiến thức:\n→ Trả lời ngắn, dễ hiểu, có ví dụ nếu cần.\n\nNếu khách hỏi sản phẩm/dịch vụ/giá:\n→ Gọi tool Google Docs \"Tai_lieu_san_pham\", sau đó trả lời phần liên quan nhất.\n\nNếu khách có nhu cầu rõ:\n→ Mời chọn 1 trong 3 phương thức tư vấn.\n\nNếu khách đã cung cấp thông tin liên hệ:\n→ Cảm ơn, xác nhận đã ghi nhận, hẹn bên mình liên hệ lại.\n\nNếu khách hỏi nhiều câu cùng lúc:\n→ Trả lời ý quan trọng nhất trước, sau đó hỏi 1 câu để làm rõ bước tiếp theo.\n\n====================\nTRẠNG THÁI KHÁCH HÀNG\n====================\n\nKhách đã tồn tại trong CRM chưa:\n{{ $json.customer_exists }}\n\nLoại khách:\n{{ $json.customer_type }}\n\nSố lượt trao đổi hiện tại:\n{{ $json.conversation_count }}\n\nTên khách nếu có:\n{{ $json.customer_name }}\n\nTin nhắn mới nhất của khách:\n{{ $json.last_message }}\n\nĐã từng mời khách để lại thông tin chưa:\n{{ $json.lead_offer_shown }}\n\nKhách đã để lại thông tin liên hệ chưa:\n{{ $json.lead_captured }}\n\nNhóm nhu cầu dự đoán:\n{{ $json.intent_type }}\n\nTóm tắt phiên trao đổi trước nếu có:\n{{ $json.conversation_summary }}\n\nNhu cầu/mong muốn chính của khách nếu đã xác định:\n{{ $json.customer_need }}\n\nGhi chú ngữ cảnh:\n{{ $json.ai_context_note }}\n\nQuy tắc sử dụng trạng thái:\n- Nếu customer_type = \"new_customer\", có thể chào tự nhiên như khách mới, nhưng không quá dài.\n- Nếu customer_type = \"existing_customer\", không chào lại như lần đầu. Hãy tiếp nối cuộc trò chuyện như khách đã từng trao đổi.\n- Nếu conversation_count > 1, tránh các câu như “Chào bạn, mình là trợ lý [TÊN DOANH NGHIỆP CỦA BẠN]” hoặc “Rất vui được gặp bạn”.\n- Nếu conversation_summary có dữ liệu, hãy dùng nó để hiểu khách đang nói tới đâu.\n- Nếu customer_need có dữ liệu, hãy ưu tiên trả lời đúng mong muốn đó.\n- Không nói lộ rằng “bạn là khách cũ trong CRM”.\n- Không nói máy móc kiểu “theo dữ liệu CRM” hoặc “theo tóm tắt phiên trước”.\n- Nếu lead_captured = true, không hỏi lại số điện thoại hoặc form.\n- Nếu lead_offer_shown = true, không lặp lại lời mời tư vấn ngay lập tức.\n\n====================\nĐẦU VÀO TIN NHẮN KHÁCH\n====================\n\nCâu hỏi của khách:\n{{ $('Webhook').item.json.body.message.text }}\n\n====================\nYÊU CẦU ĐẦU RA\n====================\n\nHãy trả lời bằng tiếng Việt tự nhiên, ngắn gọn, giống người thật đang chat Zalo/Telegram.\n\nKhông giải thích quy tắc nội bộ.\nKhông nhắc lại system message.\nKhông nói rằng bạn đang làm theo quy trình.\nChỉ trả lời trực tiếp cho khách."
        }
      },
      "type": "@n8n/n8n-nodes-langchain.agent",
      "typeVersion": 3.1,
      "position": [
        1376,
        -32
      ],
      "id": "140d74c7-d9ad-4410-8bfa-5b6ff8dab7cf",
      "name": "AI Agent"
    },
    {
      "parameters": {
        "jsCode": "// ==========================\n// CODE NODE: CHECK CUSTOMER\n// Mục tiêu:\n// - Kiểm tra khách đã tồn tại trong Sheet chưa\n// - Chuẩn hóa dữ liệu đầu ra cho các node sau\n// ==========================\n\n\n// 1. Lấy dữ liệu từ Webhook\n// Nếu node Webhook của bạn tên khác, đổi 'Webhook' thành đúng tên node đó\nconst webhookData = $('Webhook').first().json;\n\n\n// 2. Lấy dữ liệu tin nhắn từ Zalo\nconst userId = webhookData.body?.message?.chat?.id || '';\nconst messageText = webhookData.body?.message?.text || '';\nconst customerName = webhookData.body?.message?.from?.display_name || '';\nconst platform = 'Zalo';\n\n\n// 3. Lấy kết quả từ Google Sheets Get Row(s)\nconst rows = $input.all();\n\n\n// 4. Kiểm tra có row thật hay không\n// Lưu ý: Google Sheets đôi khi trả về 1 item rỗng khi không tìm thấy dữ liệu\nconst existingRowItem = rows.find(item => {\n  return item.json && item.json.user_id;\n});\n\nconst customerExists = !!existingRowItem;\nconst existingRow = customerExists ? existingRowItem.json : {};\n\n\n// 5. Lấy conversation_count cũ\nconst oldConversationCount = Number(existingRow.conversation_count || 0);\nconst newConversationCount = customerExists ? oldConversationCount + 1 : 1;\n\n\n// 6. Tạo thời gian hiện tại theo giờ Việt Nam\nconst nowVN = new Date(Date.now() + 7 * 60 * 60 * 1000).toLocaleString('vi-VN', {\n  hour12: false\n});\n\n\n// 7. Chuẩn hóa dữ liệu trả ra\nreturn [\n  {\n    json: {\n      // Trạng thái khách\n      customer_exists: customerExists,\n      customer_type: customerExists ? 'existing_customer' : 'new_customer',\n      action: customerExists ? 'update' : 'append',\n\n      // Thông tin định danh\n      user_id: userId,\n      platform: platform,\n      customer_name: customerName,\n\n      // Tin nhắn mới nhất\n      last_message: messageText,\n\n      // Trạng thái hội thoại\n      conversation_count: newConversationCount,\n\n      // Các trạng thái lead\n      lead_offer_shown: customerExists\n        ? String(existingRow.lead_offer_shown || 'FALSE').toUpperCase() === 'TRUE'\n        : false,\n\n      lead_captured: customerExists\n        ? String(existingRow.lead_captured || 'FALSE').toUpperCase() === 'TRUE'\n        : false,\n\n      // Nhu cầu hiện tại\n      intent_type: customerExists\n        ? existingRow.intent_type || 'unknown'\n        : 'unknown',\n\n      // Thông tin liên hệ nếu đã có\n      phone: customerExists ? existingRow.phone || '' : '',\n      email: customerExists ? existingRow.email || '' : '',\n\n      // Trạng thái xử lý\n      status: customerExists ? existingRow.status || 'chatting' : 'chatting',\n\n      // Thời gian\n      created_at: customerExists ? existingRow.created_at || nowVN : nowVN,\n      updated_at: nowVN,\n      last_interaction_at: nowVN,\n\n      // Ghi chú / dữ liệu cũ nếu cần debug\n      existing_row: customerExists ? existingRow : null\n    }\n  }\n];"
      },
      "type": "n8n-nodes-base.code",
      "typeVersion": 2,
      "position": [
        -80,
        48
      ],
      "id": "1e3b2228-89ac-4f2f-82ce-a18613671ef6",
      "name": "Code Kiểm tra khách Cũ Mới"
    },
    {
      "parameters": {
        "operation": "append",
        "documentId": {
          "__rl": true,
          "value": "",
          "mode": "list",
          "cachedResultName": "-- Chọn của bạn --",
          "cachedResultUrl": ""
        },
        "sheetName": {
          "__rl": true,
          "value": "",
          "mode": "list",
          "cachedResultName": "-- Chọn của bạn --",
          "cachedResultUrl": ""
        },
        "columns": {
          "mappingMode": "defineBelow",
          "value": {
            "user_id": "={{ $json.user_id }}",
            "platform": "={{ $json.platform }}",
            "customer_name": "={{ $json.customer_name }}",
            "conversation_count": "={{ $json.conversation_count }}",
            "contact_method": "={{ $json.platform }}",
            "last_message": "={{ $json.last_message }}",
            "last_interaction_at": "={{ $json.last_interaction_at }}",
            "created_at": "={{ $json.created_at }}",
            "updated_at": "={{ $json.updated_at }}",
            "status": "new",
            "customer_type": "={{ $json.customer_type }}"
          },
          "matchingColumns": [],
          "schema": [
            {
              "id": "user_id",
              "displayName": "user_id",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "platform",
              "displayName": "platform",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "customer_name",
              "displayName": "customer_name",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "username",
              "displayName": "username",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "phone",
              "displayName": "phone",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "email",
              "displayName": "email",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "conversation_count",
              "displayName": "conversation_count",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "lead_offer_shown",
              "displayName": "lead_offer_shown",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "lead_captured",
              "displayName": "lead_captured",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "intent_type",
              "displayName": "intent_type",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "contact_method",
              "displayName": "contact_method",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "form_sent",
              "displayName": "form_sent",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "form_submitted",
              "displayName": "form_submitted",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "office_visit_interest",
              "displayName": "office_visit_interest",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "last_message",
              "displayName": "last_message",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "last_bot_reply",
              "displayName": "last_bot_reply",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "last_interaction_at",
              "displayName": "last_interaction_at",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "created_at",
              "displayName": "created_at",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "updated_at",
              "displayName": "updated_at",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "status",
              "displayName": "status",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "source",
              "displayName": "source",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "note",
              "displayName": "note",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "customer_type",
              "displayName": "customer_type",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "conversation_summary",
              "displayName": "conversation_summary",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "customer_need",
              "displayName": "customer_need",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            }
          ],
          "attemptToConvertTypes": false,
          "convertFieldsToString": false
        },
        "options": {}
      },
      "type": "n8n-nodes-base.googleSheets",
      "typeVersion": 4.7,
      "position": [
        736,
        176
      ],
      "id": "854b73ff-17c7-4885-8c11-c6f5cfd7d414",
      "name": "Thêm vào Sheet Lead CRM"
    },
    {
      "parameters": {
        "documentId": {
          "__rl": true,
          "value": "",
          "mode": "list",
          "cachedResultName": "-- Chọn của bạn --",
          "cachedResultUrl": ""
        },
        "sheetName": {
          "__rl": true,
          "value": "",
          "mode": "list",
          "cachedResultName": "-- Chọn của bạn --",
          "cachedResultUrl": ""
        },
        "filtersUI": {
          "values": [
            {
              "lookupColumn": "user_id",
              "lookupValue": "={{ $json.body.message.chat.id }}"
            }
          ]
        },
        "options": {}
      },
      "type": "n8n-nodes-base.googleSheets",
      "typeVersion": 4.7,
      "position": [
        -288,
        48
      ],
      "id": "c6192578-4d21-4947-8976-f07b71876a92",
      "name": "Kiểm tra trong Sheet Lead CRM",
      "alwaysOutputData": true
    },
    {
      "parameters": {
        "conditions": {
          "options": {
            "caseSensitive": true,
            "leftValue": "",
            "typeValidation": "strict",
            "version": 3
          },
          "conditions": [
            {
              "id": "d8e04d7b-9482-4e60-957d-69ba1be634e2",
              "leftValue": "={{ $json.customer_exists }}",
              "rightValue": true,
              "operator": {
                "type": "boolean",
                "operation": "equals"
              }
            }
          ],
          "combinator": "and"
        },
        "options": {}
      },
      "type": "n8n-nodes-base.if",
      "typeVersion": 2.3,
      "position": [
        128,
        48
      ],
      "id": "98b75a50-d381-4191-9fd3-6d6761e0ab45",
      "name": "If"
    },
    {
      "parameters": {
        "operation": "update",
        "documentId": {
          "__rl": true,
          "value": "",
          "mode": "list",
          "cachedResultName": "-- Chọn của bạn --",
          "cachedResultUrl": ""
        },
        "sheetName": {
          "__rl": true,
          "value": "",
          "mode": "list",
          "cachedResultName": "-- Chọn của bạn --",
          "cachedResultUrl": ""
        },
        "columns": {
          "mappingMode": "defineBelow",
          "value": {
            "user_id": "={{ $json.user_id }}",
            "conversation_count": "={{ $json.conversation_count }}",
            "last_message": "={{ $json.last_message }}",
            "last_interaction_at": "={{ $json.last_interaction_at }}",
            "updated_at": "={{ $json.updated_at }}",
            "status": "existing",
            "customer_type": "={{ $json.customer_type }}"
          },
          "matchingColumns": [
            "user_id"
          ],
          "schema": [
            {
              "id": "user_id",
              "displayName": "user_id",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": false
            },
            {
              "id": "platform",
              "displayName": "platform",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "customer_name",
              "displayName": "customer_name",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "username",
              "displayName": "username",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "phone",
              "displayName": "phone",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "email",
              "displayName": "email",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "conversation_count",
              "displayName": "conversation_count",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "lead_offer_shown",
              "displayName": "lead_offer_shown",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "lead_captured",
              "displayName": "lead_captured",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "intent_type",
              "displayName": "intent_type",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "contact_method",
              "displayName": "contact_method",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "form_sent",
              "displayName": "form_sent",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "form_submitted",
              "displayName": "form_submitted",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "office_visit_interest",
              "displayName": "office_visit_interest",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "last_message",
              "displayName": "last_message",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "last_bot_reply",
              "displayName": "last_bot_reply",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "last_interaction_at",
              "displayName": "last_interaction_at",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "created_at",
              "displayName": "created_at",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "updated_at",
              "displayName": "updated_at",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "status",
              "displayName": "status",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "source",
              "displayName": "source",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "note",
              "displayName": "note",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "customer_type",
              "displayName": "customer_type",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "row_number",
              "displayName": "row_number",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "number",
              "canBeUsedToMatch": true,
              "readOnly": true,
              "removed": true
            }
          ],
          "attemptToConvertTypes": false,
          "convertFieldsToString": false
        },
        "options": {}
      },
      "type": "n8n-nodes-base.googleSheets",
      "typeVersion": 4.7,
      "position": [
        640,
        -48
      ],
      "id": "43c9405c-349b-43e8-b145-c76ccbfa4c95",
      "name": "Update Sheet Lead CRM"
    },
    {
      "parameters": {
        "jsCode": "// ==========================\n// CODE NODE: PREPARE AI INPUT\n// Lấy dữ liệu sạch trước khi đưa vào AI Agent\n// ==========================\n\n\n// 1. Lấy dữ liệu từ node Code kiểm tra khách cũ/mới\n// TÊN NODE PHẢI ĐÚNG Y HỆT TRONG WORKFLOW\nconst customerData = $('Code Kiểm tra khách Cũ Mới').first().json;\n\n\n// 2. Hàm ép boolean an toàn\nfunction toBoolean(value) {\n  if (value === true) return true;\n  if (value === false) return false;\n\n  const text = String(value || '').trim().toLowerCase();\n  return text === 'true' || text === 'yes' || text === '1';\n}\n\n\n// 3. Chuẩn hóa dữ liệu đưa vào AI Agent\nconst preparedData = {\n  // Trạng thái khách\n  customer_exists: toBoolean(customerData.customer_exists),\n  customer_type: customerData.customer_type || 'new_customer',\n  action: customerData.action || 'append',\n\n  // Định danh\n  user_id: customerData.user_id || '',\n  platform: customerData.platform || 'Zalo',\n  customer_name: customerData.customer_name || '',\n\n  // Tin nhắn mới nhất\n  last_message: customerData.last_message || '',\n\n  // Trạng thái hội thoại\n  conversation_count: Number(customerData.conversation_count || 1),\n\n  // Lead state\n  lead_offer_shown: toBoolean(customerData.lead_offer_shown),\n  lead_captured: toBoolean(customerData.lead_captured),\n\n  // Phân loại nhu cầu\n  intent_type: customerData.intent_type || 'unknown',\n\n  // Ngữ cảnh phiên trước\n  conversation_summary: customerData.conversation_summary || '',\n  customer_need: customerData.customer_need || '',\n\n  // Thông tin liên hệ nếu có\n  phone: customerData.phone || '',\n  email: customerData.email || '',\n\n  // Trạng thái xử lý\n  status: customerData.status || 'chatting',\n\n  // Thời gian\n  created_at: customerData.created_at || '',\n  updated_at: customerData.updated_at || '',\n  last_interaction_at: customerData.last_interaction_at || '',\n\n  // Cờ hỗ trợ AI\n  is_new_customer: customerData.customer_type === 'new_customer',\n  is_existing_customer: customerData.customer_type === 'existing_customer',\n\n  // Ghi chú cho AI\n  ai_context_note:\n    customerData.customer_type === 'existing_customer'\n      ? 'Khách đã từng trao đổi trước đó. Hãy tiếp nối ngữ cảnh, không chào lại như lần đầu.'\n      : 'Khách mới lần đầu xuất hiện. Có thể chào tự nhiên, ngắn gọn.'\n};\n\n\n// 4. Trả dữ liệu cho AI Agent\nreturn [\n  {\n    json: preparedData\n  }\n];"
      },
      "type": "n8n-nodes-base.code",
      "typeVersion": 2,
      "position": [
        832,
        -48
      ],
      "id": "0a067f53-28d7-4660-adb9-c7d50605a9a1",
      "name": "Lấy lại trạng thái và mong muốn khách"
    },
    {
      "parameters": {
        "promptType": "define",
        "text": "=Bạn là bộ nhớ hội thoại cho chatbot [TÊN DOANH NGHIỆP CỦA BẠN].\n\nNhiệm vụ:\nDựa trên tin nhắn mới nhất của khách, câu trả lời mới nhất của bot, và trạng thái cũ nếu có, hãy cập nhật lại bộ nhớ hội thoại để lần sau bot tiếp tục đúng ngữ cảnh.\n\nChỉ trả về JSON hợp lệ, không giải thích thêm.\n\nFormat bắt buộc:\n\n{\n  \"conversation_summary\": \"Tóm tắt ngắn trạng thái đang trao đổi với khách, tối đa 1 câu.\",\n  \"customer_need\": \"Mong muốn hoặc nhu cầu chính của khách, tối đa 1 câu.\",\n  \"intent_type\": \"content_strategy | AI | n8n | coaching | audit | course | service | pricing | office_visit | general | unknown\",\n  \"status\": \"new | chatting | offered_consultation | new_lead | form_sent | office_interest | closed\"\n}\n\nDữ liệu:\n\nTóm tắt cũ:\n{{ $('Kiểm tra trong Sheet Lead CRM').item.json.conversation_summary }}\n\nNhu cầu cũ:\n{{ $('Kiểm tra trong Sheet Lead CRM').item.json.customer_need }}\n\n\nTin nhắn mới nhất của khách:\n{{ $('Lấy lại trạng thái và mong muốn khách').first().json.last_message }}\n\nCâu trả lời mới nhất của bot:\n{{ $('AI Agent').first().json.output }}",
        "batching": {}
      },
      "type": "@n8n/n8n-nodes-langchain.chainLlm",
      "typeVersion": 1.9,
      "position": [
        2176,
        -32
      ],
      "id": "644d7a0b-0951-46f6-9811-73ed60b55c37",
      "name": "Basic LLM Chain"
    },
    {
      "parameters": {
        "modelName": "models/gemini-3.5-flash",
        "options": {}
      },
      "type": "@n8n/n8n-nodes-langchain.lmChatGoogleGemini",
      "typeVersion": 1.1,
      "position": [
        2176,
        208
      ],
      "id": "8cf95e7a-7c2d-463c-bf0d-be7f9defc00b",
      "name": "Google Gemini Chat Model1"
    },
    {
      "parameters": {
        "content": "## GỌI BOT ZALO \n",
        "height": 320,
        "width": 320,
        "color": "#050A33"
      },
      "type": "n8n-nodes-base.stickyNote",
      "typeVersion": 1,
      "position": [
        -960,
        -336
      ],
      "id": "267c1664-9f44-4aa4-9993-c2110c9a70f6",
      "name": "Sticky Note"
    },
    {
      "parameters": {
        "method": "POST",
        "url": "https://bot-api.zaloplatforms.com/botYOUR_BOT_TOKEN/setWebhook",
        "sendBody": true,
        "bodyParameters": {
          "parameters": [
            {
              "name": "url",
              "value": "https://your-n8n.example.com/webhook/YOUR_PATH"
            },
            {
              "name": "secret_token",
              "value": "YOUR_SECRET_TOKEN"
            }
          ]
        },
        "options": {}
      },
      "type": "n8n-nodes-base.httpRequest",
      "typeVersion": 4.4,
      "position": [
        -864,
        -208
      ],
      "id": "8e1e49d5-837d-40b4-9bb7-0b8d98929b1a",
      "name": "Request Bot Zalo"
    },
    {
      "parameters": {
        "content": "##  CHỜ ZALO \n",
        "height": 320,
        "width": 320,
        "color": "#050A33"
      },
      "type": "n8n-nodes-base.stickyNote",
      "typeVersion": 1,
      "position": [
        -960,
        64
      ],
      "id": "8f5a8f89-e492-4f57-be2f-849d50521920",
      "name": "Sticky Note1"
    },
    {
      "parameters": {
        "content": "##  KIỂM TRA KHÁCH CŨ HAY MỚI\n",
        "height": 544,
        "width": 752,
        "color": "#1E2A2F"
      },
      "type": "n8n-nodes-base.stickyNote",
      "typeVersion": 1,
      "position": [
        -416,
        -160
      ],
      "id": "41025cad-f93f-4567-bfaa-3a8d271988f8",
      "name": "Sticky Note2"
    },
    {
      "parameters": {
        "content": "##  CẬP NHẬT KHÁCH HÀNG CŨ MỚI",
        "height": 544,
        "width": 672,
        "color": "#1E2A2F"
      },
      "type": "n8n-nodes-base.stickyNote",
      "typeVersion": 1,
      "position": [
        432,
        -160
      ],
      "id": "260ead5e-93ed-4d6a-912e-a9a7e8aa04fa",
      "name": "Sticky Note3"
    },
    {
      "parameters": {
        "content": "##  TRẢ LỜI KHÁCH HÀNG\n",
        "height": 544,
        "width": 768,
        "color": "#1E2A2F"
      },
      "type": "n8n-nodes-base.stickyNote",
      "typeVersion": 1,
      "position": [
        1216,
        -160
      ],
      "id": "1af82d92-72fd-4c2d-b179-35c7a3753f98",
      "name": "Sticky Note4"
    },
    {
      "parameters": {
        "content": "##  CẬP NHẬT NỘI DUNG CHAT VÀ MONG MUỐN KHÁCH HÀNG\n",
        "height": 544,
        "width": 944,
        "color": "#1E2A2F"
      },
      "type": "n8n-nodes-base.stickyNote",
      "typeVersion": 1,
      "position": [
        2080,
        -160
      ],
      "id": "9ee22065-98f1-46c4-8a37-2f4ad96c9f53",
      "name": "Sticky Note5"
    },
    {
      "parameters": {
        "jsCode": "const raw = $json.text || '';\n\nconst cleaned = raw\n  .replace('```json', '')\n  .replace('```', '')\n  .trim();\n\nconst data = JSON.parse(cleaned);\n\nreturn [\n  {\n    json: {\n      user_id: $('Lấy lại trạng thái và mong muốn khách').first().json.user_id,\n      conversation_summary: data.conversation_summary,\n      customer_need: data.customer_need,\n      intent_type: data.intent_type,\n      status: data.status,\n      last_bot_reply: $('AI Agent').first().json.output,\n      updated_at: new Date(Date.now() + 7 * 60 * 60 * 1000).toLocaleString('vi-VN', { hour12: false })\n    }\n  }\n];"
      },
      "type": "n8n-nodes-base.code",
      "typeVersion": 2,
      "position": [
        2528,
        -32
      ],
      "id": "a42590a8-fc17-45b4-92ac-b881ae3c3ccf",
      "name": "Code Cập nhật lại yêu cầu KH"
    },
    {
      "parameters": {
        "operation": "update",
        "documentId": {
          "__rl": true,
          "value": "",
          "mode": "list",
          "cachedResultName": "-- Chọn của bạn --",
          "cachedResultUrl": ""
        },
        "sheetName": {
          "__rl": true,
          "value": "",
          "mode": "list",
          "cachedResultName": "-- Chọn của bạn --",
          "cachedResultUrl": ""
        },
        "columns": {
          "mappingMode": "defineBelow",
          "value": {
            "conversation_summary": "={{ $json.conversation_summary }}",
            "customer_need": "={{ $json.customer_need }}",
            "last_bot_reply": "={{ $json.last_bot_reply }}",
            "intent_type": "={{ $json.intent_type }}",
            "user_id": "={{ $json.user_id }}"
          },
          "matchingColumns": [
            "user_id"
          ],
          "schema": [
            {
              "id": "user_id",
              "displayName": "user_id",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": false
            },
            {
              "id": "platform",
              "displayName": "platform",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "customer_name",
              "displayName": "customer_name",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "username",
              "displayName": "username",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "phone",
              "displayName": "phone",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "email",
              "displayName": "email",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "conversation_count",
              "displayName": "conversation_count",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "lead_offer_shown",
              "displayName": "lead_offer_shown",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "lead_captured",
              "displayName": "lead_captured",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "intent_type",
              "displayName": "intent_type",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": false
            },
            {
              "id": "contact_method",
              "displayName": "contact_method",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "form_sent",
              "displayName": "form_sent",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "form_submitted",
              "displayName": "form_submitted",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "office_visit_interest",
              "displayName": "office_visit_interest",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "last_message",
              "displayName": "last_message",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "last_bot_reply",
              "displayName": "last_bot_reply",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": false
            },
            {
              "id": "last_interaction_at",
              "displayName": "last_interaction_at",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "created_at",
              "displayName": "created_at",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "updated_at",
              "displayName": "updated_at",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "status",
              "displayName": "status",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "source",
              "displayName": "source",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "note",
              "displayName": "note",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "customer_type",
              "displayName": "customer_type",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true,
              "removed": true
            },
            {
              "id": "conversation_summary",
              "displayName": "conversation_summary",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "customer_need",
              "displayName": "customer_need",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "row_number",
              "displayName": "row_number",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "number",
              "canBeUsedToMatch": true,
              "readOnly": true,
              "removed": true
            }
          ],
          "attemptToConvertTypes": false,
          "convertFieldsToString": false
        },
        "options": {}
      },
      "type": "n8n-nodes-base.googleSheets",
      "typeVersion": 4.7,
      "position": [
        2736,
        -32
      ],
      "id": "fed34bfd-acaf-4bf9-93e1-317092824889",
      "name": "Cập nhật lại vào Lead CRM"
    },
    {
      "parameters": {
        "method": "POST",
        "url": "https://bot-api.zaloplatforms.com/botYOUR_BOT_TOKEN/sendMessage",
        "sendBody": true,
        "bodyParameters": {
          "parameters": [
            {
              "name": "chat_id",
              "value": "={{ $('Webhook').item.json.body.message.chat.id }}"
            },
            {
              "name": "text",
              "value": "={{ $json.output }}"
            }
          ]
        },
        "options": {}
      },
      "type": "n8n-nodes-base.httpRequest",
      "typeVersion": 4.4,
      "position": [
        1728,
        -32
      ],
      "id": "34958180-dac0-42dd-bdf4-5ff6f4eac166",
      "name": "Gửi thông tin vào Zalo cho KH"
    }
  ],
  "pinData": {},
  "connections": {
    "Webhook": {
      "main": [
        [
          {
            "node": "Kiểm tra trong Sheet Lead CRM",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Google Gemini Chat Model": {
      "ai_languageModel": [
        [
          {
            "node": "AI Agent",
            "type": "ai_languageModel",
            "index": 0
          }
        ]
      ]
    },
    "Simple Memory": {
      "ai_memory": [
        [
          {
            "node": "AI Agent",
            "type": "ai_memory",
            "index": 0
          }
        ]
      ]
    },
    "AI Agent": {
      "main": [
        [
          {
            "node": "Gửi thông tin vào Zalo cho KH",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Code Kiểm tra khách Cũ Mới": {
      "main": [
        [
          {
            "node": "If",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Thêm vào Sheet Lead CRM": {
      "main": [
        [
          {
            "node": "AI Agent",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Kiểm tra trong Sheet Lead CRM": {
      "main": [
        [
          {
            "node": "Code Kiểm tra khách Cũ Mới",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "If": {
      "main": [
        [
          {
            "node": "Update Sheet Lead CRM",
            "type": "main",
            "index": 0
          }
        ],
        [
          {
            "node": "Thêm vào Sheet Lead CRM",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Update Sheet Lead CRM": {
      "main": [
        [
          {
            "node": "Lấy lại trạng thái và mong muốn khách",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Lấy lại trạng thái và mong muốn khách": {
      "main": [
        [
          {
            "node": "AI Agent",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Google Gemini Chat Model1": {
      "ai_languageModel": [
        [
          {
            "node": "Basic LLM Chain",
            "type": "ai_languageModel",
            "index": 0
          }
        ]
      ]
    },
    "Basic LLM Chain": {
      "main": [
        [
          {
            "node": "Code Cập nhật lại yêu cầu KH",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Code Cập nhật lại yêu cầu KH": {
      "main": [
        [
          {
            "node": "Cập nhật lại vào Lead CRM",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Gửi thông tin vào Zalo cho KH": {
      "main": [
        [
          {
            "node": "Basic LLM Chain",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Tai_lieu_san_pham": {
      "ai_tool": [
        [
          {
            "node": "AI Agent",
            "type": "ai_tool",
            "index": 0
          }
        ]
      ]
    }
  },
  "active": false,
  "settings": {
    "executionOrder": "v1",
    "binaryMode": "separate",
    "availableInMCP": false
  },
  "nodeGroups": [],
  "tags": []
}
