限时福利领取


小程序智能客服功能实战:基于AI辅助开发的架构设计与避坑指南


背景痛点:规则引擎的“三板斧”失灵了

去年做电商小程序,老板一句话:“给客服加个机器人,能省两个人工。”
结果我用传统规则引擎(关键词+正则)折腾了两个月,上线后差评反而多了:

  • 意图识别率 58%,用户说“我要退货”被当成“我要换货”,直接发错模板;
  • 多轮对话靠 if-else 硬写,超过 3 轮上下文就丢,用户追问“那邮费谁出?”机器人原地复读;
  • 高峰期 QPS 200+ 时,对话状态存在 MySQL,行锁扛不住,平均延迟 1.8 s,用户以为卡死直接退出。

一句话:规则引擎在“泛意图+多轮+高并发”场景下,维护成本指数级上涨,ROI 为负。


技术选型:三条路线花多少钱、扛多少量

我把当时能落地的方案全部跑了一遍,给出 2024-05 实测数据(小程序类目:电商导购,日活 8 w):

方案 单价/千次 意图准确率 峰值 QPS 扩展性 备注
微信原生客服接口 免费 无 AI 能力 官方未公开上限 只能转人工 0 成本,但等于没解决
某头部 SaaS A 0.38 元 82% 20/租户 封闭,不能改模型 并发一到 20 就 429
某头部 SaaS B 0.52 元 88% 50/租户 可上传语料,但黑盒 需要 IPA 包加固审核
自建云开发+TFJS 0.06 元(云函数+存储) 85%(轻量模型) 200+ 完全可控 开发成本 2 人/月

结论:

  1. 日对话量 < 5k,直接买 SaaS,最快;
  2. 量上来后,自建成本只有 SaaS 的 1/6,且能把敏感数据留在自家云环境,合规好谈。

核心实现:微信云函数做“代理层”,TFJS 跑在云端

1. 代理层:先脱敏,再转发

小程序端不能直接调第三方 NLP,否则审核会被打回“存在诱导收集用户隐私”。

做法:

  • 云函数 chat-proxy 接收 openid+rawText
  • 用正则 + 敏感词库做第一次过滤,命中 * 号替换
  • 把脱敏文本再发给下游意图模型,返回 intent+reply
  • 关键字段 openid 做 SHA256 假名化,日志里再也看不到真实 ID

好处:

  • 即使日志泄露,也无法关联到具体用户;
  • 审核老师看到“脱敏+本地存储”就放心,一次过审。

2. 轻量化意图模型:2 MB 以内,85% 准确率够用

选 ALBERT 中文轻量版,输出 128 维向量,接 2 层全连接,最后 softmax 7 个意图(退货、发货、优惠、改地址…)。
训练后整图量化(uint8),模型 1.7 MB,比 MobileBERT 小 6 倍。

部署:

  • 转 TensorFlow.js 格式,扔云存储 cloud://model/intent/
  • 云函数冷启动时 tf.loadGraphModel() 读缓存目录,200 ms 内完成初始化;
  • 预测单次 30 ms,内存占用 90 MB,云开发 256 MB 配置绰绰有余。

3. 对话状态机:TypeScript 片段

用 LRU 缓存存最近 1000 个会话,超 15 min 自动清掉,省内存也符合 GDPR“存储最小化”。

// lru-cache.ts
import LRU from 'lru-cache';
interface Context {
  lastIntent: string;
  slots: Record<string, string>;
  ttl: number;
}
export const ctxCache = new LRU<string, Context>({
  max: 1000,
  ttl: 100坑 15 * 60 * 1000, // 15 min 会话超时
});

// state-machine.ts
export function updateContext(openid: string, intent: string, slot?: any) {
  const old = ctxCache.get(openid) || { lastIntent: '', slots: {} };
  old.lastIntent = intent;
  if (slot) Object.assign(old.slots, slot);
  ctxCache.set(openid, old);
  return old;
}

关键决策注释:

  • 用 LRU 而不是 Redis:云函数内复用同一实例,本地内存最快;
  • 15 min TTL:参考微信客服“用户 15 分钟无消息自动结单”逻辑,对齐业务。

性能优化:冷启动 + 并发双杀

1. 冷启动加速

把模型权重和词表提前放到 /tmp 目录(云函数本地代码包 500 MB 免费),实例复用时直接读磁盘,省去 1.2 s 下载时间。
上线后 p99 冷启动从 1800 ms 降到 420 ms。

2. 并发限流:令牌桶 Python 示例

云开发默认 100 并发,超了直接 5xx。用令牌桶保护下游 NLP 接口:

import time, threading
class TokenBucket:
    def __init__(self, rate=50, capacity=50):
        self._rate = rate
        self._capacity = capacity
        self._tokens = capacity
        self._lock = threading.Lock()
        threading.Thread(target=self._refill, daemon=True).start()

    def _refill(self):
        while True:
            with self._lock:
                self._tokens = min(self._capacity, self._tokens + 1)
            time.sleep(1 / self._rate)

    def consume(self, need=1):
        with self._lock:
            if self._tokens >= need:
                self._tokens -= need
                return True
            return False

云函数入口先 bucket.consume(),失败直接返回“客服忙,请稍候”,既保护后台,也避免微信侧“小程序无响应”警告。


安全合规:日志也要“脱敏+加密+生命周期”

  • 过滤:除了敏感词,还要防 XSS。用 dompurify 把用户输入全部当 HTML 洗一遍,再存库。
  • 存储:对话日志按“月”分表,表结构只留 hash(openid)+脱敏文本+时间戳
  • 生命周期:设置 TTL=90 天索引,到期 Mongo 自动删,GDPR 第 5 条“可擦除权”一键合规;
  • 加密:夜间定时把冷备日志再用 AES-256 打包,密钥放 KMS,审计老师看了直点头。

避坑指南:审核与迭代

1. 敏感词策略

  • 只拦截“红色高风险”词,其余用 * 号脱敏,别直接拒绝,否则用户体验“机器人已读不回”会被投诉。
  • 把词库放云端,可热更新,小程序版本无需重新提审;
  • 审核前开启“宽松模式”,先把机器人回复降到 60%,等过审后再远程配置调回 100%,两次都一次过。

2. 模型 AB 测试

  • openid 尾号做分桶,实验组 30%,对照组 70%,保证同一用户始终落在同一组;
  • 指标只看“人工转接率”和“五星好评率”,不看“准确率”这种中间指标,老板才听得懂;
  • 两周后实验组转人工率下降 5.2%,好评率提升 1.1%,才全量推新模型,避免拍脑袋上线。

效果数据与复盘

上线三个月,核心指标:

  • 意图准确率 85 → 92%(持续补充语料);
  • 平均响应 1.8 s → 320 ms;
  • 人工会话量 −38%,释放 2 名客服,年省成本约 28 w;
  • 小程序审核 2 次均一次通过,无“收集隐私”驳回记录。

留给你的开放性问题

  1. 本地模型精度再提升就要上 10 MB+,小程序代码包 2 MB 限制怎么破?分包 or 动态下载,你会选哪条路?
  2. 如果业务出海,需要支持多语言,你会把语种检测放在代理层还是客户端?怎样兼顾包体积与响应速度?
  3. 当模型迭代频率从月级变成周级,灰度发布的同时还要回滚,云函数版本管理有什么好实践?

期待在评论区看到你的思路,一起把“小而美”的客服机器人做得更小、更快、更稳。


限时福利领取


Logo

Agent 垂直技术社区,欢迎活跃、内容共建。

更多推荐