Day 18 · 综合实战 B:AI 客服 Agent(专栏收官)

「AI Python 系列」第 01 栏 · AI+办公自动化

全栏 18 篇 · 零成本跟完 · 完结篇

品牌:梅雅达编程笔记


摘要: 专栏收官之作。做一个能多轮对话的 AI 客服 Agent,整合意图分类、FAQ 检索、回复生成、人工转接四大能力。本篇使用 GLM-4.7-Flash,永久免费,8 次调用约 10,000 token,零成本跑完。

关键词:AI 客服、意图分类、FAQ 知识库、多轮对话、人工转接、Agent 实战


项目 版本 / 说明
操作系统 Windows 10/11、macOS、Linux 均可
Python 3.9 及以上
依赖库 json(标准库)、llm_client(Day 04 封装)
LLM 提供商 智谱 GLM-4.7-Flash(免费)
前置知识 需先完成 Day 01-16
预计耗时 阅读 15 分钟 + 动手验证 10 分钟

开篇 · 为什么最后一个项目选客服

写这个专栏的时候,我一直在想:最后一篇该做什么?

想了几天,最后选了 AI 客服。原因很简单------客服可能是 AI 在职场里最早大规模落地的场景之一。输入是文字,输出是文字,中间需要理解意图、检索知识、组织语言,全是 AI 的强项。而且它几乎用到了这个专栏前面教的所有东西:Prompt 工程、结构化输出、意图分类、多轮对话、记忆管理。

18 篇的收官之作,我觉得它最合适。


一、架构:四步流水线

客服 Agent 的工作流程分四步:

这四步里,第①步和第③步用到 AI,第②步和第④步是纯代码逻辑。跟 Day 17 的报告自动化一样------AI 做"理解"和"生成",代码做"确定性"的事。


二、核心代码

完整代码约 100 行,核心是 CustomerServiceAgent 类的四个方法。FAQ 知识库和演示场景做了精简,实际使用时按需扩展即可:

python 复制代码
"""
customer_service_agent.py - AI 客服 Agent
意图分类 → FAQ 检索 → 回复生成 → 人工转接
"""

import os
import sys
import json

sys.path.insert(0, os.path.dirname(os.path.dirname(os.path.abspath(__file__))))
from llm_client import LLMClient

# FAQ 知识库(实际使用可扩展到几十上百条,或换成向量数据库)
FAQ_KNOWLEDGE = {
    "价格": "编程教程基础版99元,进阶版199元,AI提示词手册59元。",
    "退款": "购买7天内支持无理由退款,在「我的订单」点击「申请退款」即可。",
    "安装": "教程为在线视频,购买后登录官网即可观看,无需安装。",
}


class CustomerServiceAgent:
    def __init__(self):
        self.client = LLMClient(provider="glm")
        self.history = []  # 对话记忆

    def search_faq(self, query):
        """关键词匹配 FAQ"""
        return [f"【{k}】{v}" for k, v in FAQ_KNOWLEDGE.items() if k in query]

    def classify_intent(self, message):
        """AI 分类意图,返回 JSON"""
        prompt = f"""判断意图,输出JSON:
{{"intent": "咨询/投诉/退款/技术/其他", "urgency": "低/中/高", "need_human": true/false}}
用户消息:{message}"""
        return json.loads(self.client.chat_json(prompt, temperature=0.1, max_tokens=200))

    def generate_response(self, message, intent):
        """结合 FAQ + 对话历史生成回复"""
        faq = "\n".join(self.search_faq(message)) or "无匹配FAQ"
        history = "\n".join(
            f"{'客户' if m['role']=='user' else '客服'}: {m['content']}"
            for m in self.history[-6:]
        )
        system_prompt = f"""你是梅雅达编程笔记客服。
知识库:{faq}
准则:友善简洁,能答则答,不能答引导拨400-888-9999,退款投诉先安抚,不编造信息。
意图分析:{intent}"""
        return self.client.chat(
            f"{'对话历史:\n'+history if history else ''}\n客户:{message}\n请回复:",
            system_prompt=system_prompt, temperature=0.4, max_tokens=300
        )

    def handle_message(self, message):
        """完整处理流程:分类 → 检索 → 生成 → 转人工判断"""
        print(f"\n  客户:{message}")
        intent = self.classify_intent(message)
        print(f"  意图:{intent['intent']} | 紧急度:{intent['urgency']} | 转人工:{intent['need_human']}")

        reply = self.generate_response(message, intent)
        if intent["need_human"]:
            reply += "\n\n如需进一步帮助,请联系人工客服:400-888-9999"
        print(f"  客服:{reply}")

        self.history += [
            {"role": "user", "content": message},
            {"role": "assistant", "content": reply},
        ]
        return reply


if __name__ == "__main__":
    agent = CustomerServiceAgent()
    agent.handle_message("你们的编程教程多少钱?")       # FAQ 咨询
    agent.handle_message("我买了三天还看不了,退款!")   # 投诉 → 转人工

运行方式

bash 复制代码
cd day18_code
pip install -r requirements.txt
python customer_service_agent.py

预期输出

复制代码
  客户:你们的编程教程多少钱?
  意图:咨询 | 紧急度:低 | 转人工:False
  客服:编程教程基础版99元,进阶版199元,AI提示词手册59元。
      您对哪个产品感兴趣?

  客户:我买了三天还看不了,退款!
  意图:投诉 | 紧急度:高 | 转人工:True
  客服:非常抱歉给您带来不好的体验!购买7天内支持无理由退款,
      请在「我的订单」点击「申请退款」。
      如需进一步帮助,请联系人工客服:400-888-9999

完整代码(含5条FAQ、3个演示场景、详细注释)可在 CSDN 下载区获取。


三、几个值得说的设计点

FAQ 检索为什么用关键词而不是语义

代码里的 search_faq() 是关键词匹配------用户消息里包含"价格"就匹配价格条目。你可能觉得这太粗糙了,应该用语义检索。

确实,语义检索效果更好。用户问"多少钱"、"怎么收费"、"价格是多少",关键词匹配只能靠运气撞上,语义检索都能找到"价格"条目。但这里我选了关键词匹配,原因是:

第一,简单。专栏到这里就结束了,我不想再引入一个 sentence-transformers 的依赖。第二,对于知识库只有 5-10 个条目的场景,关键词匹配其实够用了。真正需要语义检索是知识库有几十上百条的时候。

如果你想升级,把 search_faq() 换成向量检索就行,其他代码不用动。

对话历史只取最近 6 条

python 复制代码
recent = self.history[-6:]

这个设计跟 Day 16 的短时记忆截断是同一个道理。客服对话通常不会特别长,6 条(3 轮对话)基本能覆盖"追问"场景------比如场景 2 里用户说"那怎么安装",模型能从上一轮回溯到"那"指的是智能客服系统。

如果你的客服场景需要更长的上下文回溯,可以调大到 10 条。

投诉场景的处理

这是我觉得整个代码里最关键的设计:

python 复制代码
if intent.get("need_human"):
    response += "\n\n如需进一步帮助,请联系人工客服:400-888-9999"

AI 分类出 need_human=true 时,自动追加转人工提示。投诉和退款这种场景,让 AI 全权处理是有风险的------它可能说错话、可能安抚不到位。所以策略是:AI 负责第一轮安抚(它确实擅长组织语言),但一定要给人工兜底的机会。

我在 system prompt 里也加了相应的约束:"涉及退款、投诉等敏感问题,先安抚再处理"、"不要编造信息"。


四、真实场景怎么接

代码里的客服 Agent 是在终端里跑的 demo。要变成真实可用的客服系统,有几个方向:

接入 Web: 用 Flask 搭一个 HTTP 接口,前端页面把用户消息 POST 过来,Agent 处理后返回 JSON。十几行代码就能搞定。

接入企业微信/钉钉: 这两个平台都有 Webhook 机制,收到用户消息时回调你的接口,你调 Agent 处理后回复。

升级知识库: 把 FAQ 从 key-value 换成向量数据库(ChromaMilvus),实现语义检索。知识库从 5 条扩展到 500 条也没问题。

加情绪检测: 在意图分类的基础上加一个"情绪打分",如果用户连续两轮都是高负面情绪,不等 AI 判断 need_human,直接转人工。


五、专栏写完了,说几句

18 篇到这里全部结束了。

回头看这个专栏,核心思路其实就一条:AI 做理解和决策,Python 做执行和落地。AI 负责读懂数据、分析趋势、组织语言、判断意图------那些需要"理解"的事。Python 负责连接 API、操作文件、执行查询、生成报告------那些需要"确定性"的事。

整个专栏 18 篇,用的都是 GLM-4.7-Flash,永久免费。从零开始搭环境,到 Prompt 工程、Office 自动化、数据库查询、数据可视化、AI 爬虫,再到 Agent 架构、记忆系统、综合实战。18 篇跟完,总成本:0 元。

AI Agent 的世界才刚开始。Function Calling、RAG、向量数据库、多模态 Agent......每个方向都值得继续深挖。但有了这 18 篇的基础,你已经具备了用 Python + AI 解决实际问题的能力。

剩下的就是去用。去解决你工作中那些重复的、无聊的、浪费时间的事------让 AI 帮你做 80%,你做那 20% 有价值的判断。

感谢跟到最后的你。我们下个专栏见。


资源与工具


往期回顾

专栏:「AI Python 系列」第 01 栏 · AI+办公自动化

©️ 梅雅达编程笔记原创 · 首发 CSDN · 转载请注明出处

相关推荐
测试老哥1 小时前
Pytest自动化测试框架tep环境变量、fixtures、用例三者之间的关系
自动化测试·软件测试·python·测试工具·测试用例·pytest·职场发展
Buke..2 小时前
【APP 逆向】哔哩哔哩 sign 参数逆向(下):OLLVM 混淆还原 sign 算法
java·javascript·爬虫·python·算法
JacksonMx2 小时前
Java CompletableFuture 异步编程实战:从入门到架构师避坑指南
linux·数据库·python
W_326002 小时前
Python-OpenCV HSV颜色空间与inRange颜色分割:按颜色提取目标物体
图像处理·人工智能·python·opencv·机器学习
Buke..3 小时前
【APP 逆向】哔哩哔哩 sign 参数逆向(上):Frida 反调试绕过与 unidbg 调用
java·开发语言·爬虫·python·安卓
头发够用的程序员3 小时前
ImportError: libopenblas.so.0: cannot open shared object file 完整复盘与解决方案
python·ubuntu
梦痕长情3 小时前
记一次关于AI在数仓中的应用
开发语言·人工智能·python·ai
何以解忧,唯有..3 小时前
Python 线程编程:从入门到实战
开发语言·python