技术博客
易源合一接进客服机器人:一次接入拿到天气、快递、新闻三类答复

易源合一接进客服机器人:一次接入拿到天气、快递、新闻三类答复

作者: 万维易源
2026-09-15
易源合一客服机器人场景实战Flask意图分流
# 易源合一接进客服机器人:一次接入拿到天气、快递、新闻三类答复 > 接入点:3054-2 意图分析 + 3054-1 智能对话 | 请求方式:POST | 返回格式:JSON | 计费:各 5.5 厘/次,失败不扣费 | 最后实测核对:2026-09-15 ## 核心要点 - 客服机器人最常见的三类查询是「今天天气怎么样」「我的快递到哪了」「最近有什么新闻」,易源合一这三个意图实测都支持。 - 一次接入就拿到三类答复,代价是 5.5 厘/次,比自己写三套适配便宜在工时,不一定便宜在调用费。 - 快递意图返回的 `reply_msg.text` 和 `result[0].msg` 措辞不一致,两个都往上放会出现自相矛盾的两句话。 ## 这个场景的账怎么算 假设你的客服机器人每天有 1000 次这类查询。走易源合一,按 5.5 厘/次算,一天 5.5 元。 如果你自己接:天气接口一套、快递接口一套、新闻接口一套,每个接口都要写参数构造、字段映射、错误码转换、降级逻辑。三套代码的开发和后续维护成本,通常是按月计的。 便宜的是你的时间,不是调用费。这个取舍在 [易源合一、直连单接口、自建意图识别:三条路线怎么选](https://www.showapi.com/guides/united-api-vs-direct-integration-3054) 里有更细的算法。 ## 会话入口怎么写 客服机器人的消息一般从一个 webhook 进来。这里用 Flask 写一个最小可用的处理函数,把三类查询串起来。 ```python import json, logging, requests from flask import Flask, request, jsonify APP_KEY = "YOUR_APPKEY" API_2 = f"https://route.showapi.com/3054-2?appKey={APP_KEY}" API_1 = f"https://route.showapi.com/3054-1?appKey={APP_KEY}" SUPPORTED = {"weather", "query_express", "query_news"} FALLBACK = "这个问题我暂时答不上来,你可以试试问我天气、快递或者新闻。" app = Flask(__name__) log = logging.getLogger("kf") def post_json(url, text, timeout): r = requests.post(url, data={"text": text}, timeout=timeout) r.raise_for_status() return r.json() @app.post("/kf/webhook") def webhook(): user_text = (request.json or {}).get("text", "").strip() if not user_text: return jsonify({"reply": "你还没说话呢"}) # 1. 意图预判,20s 超时 d2 = post_json(API_2, user_text, timeout=20) b2 = d2.get("showapi_res_body", {}) if b2.get("ret_code") != 0: log.warning("intent_fail text=%s msg=%s", user_text, b2.get("ret_msg")) return jsonify({"reply": FALLBACK}) intent, conf = b2.get("intent"), b2.get("confidence") if intent not in SUPPORTED: log.info("intent_unsupported intent=%s text=%s", intent, user_text) return jsonify({"reply": "这个功能还没上线,我先记下来。"}) # 2. 真调业务,快递查询可能慢,超时给到 30s timeout = 30 if intent == "query_express" else 20 d1 = post_json(API_1, user_text, timeout=timeout) b1 = d1.get("showapi_res_body", {}) if b1.get("ret_code") != 0: log.warning("dialog_fail intent=%s msg=%s", intent, b1.get("ret_msg")) return jsonify({"reply": FALLBACK}) log.info("dialog_ok intent=%s conf=%s fee=%s", intent, conf, d1.get("showapi_fee_num")) return jsonify({ "reply": b1.get("reply_msg", {}).get("text", ""), "intent": intent, "confidence": conf, }) ``` `log.info` 里的 `fee` 不是装饰。实测每次成功调用都会返回 `showapi_fee_num`,把它记进日志,月底对账时你能直接知道每个意图花了多少钱。 ## 三类意图的返回怎么处理 三类意图的 `result` 结构完全不同,展示逻辑要分开写。下面是 2026-09-15 的真实返回片段。 **天气** — 答复文本里带了 Markdown 标题,`result[0].dayList` 是逐日数据: ``` reply_msg.text: "#### 昆明 26年09月15日的天气\n\n预计白天气温:24℃,多云,南风0-3级,夜间气温:17℃,多云,东风0-3级。\n\n" result[0].dayList[0]: daytime=20260915, day_weather=多云, day_air_temperature=24, night_air_temperature=17 ``` 温度字段是字符串 `"24"`,参与排序或计算前转成数字。`#### ` 是 Markdown 标记,你如果直接渲染纯文本,前端会看到一堆井号。 **快递** — 答复文本和业务字段的措辞会对不上: ``` reply_msg.text: "### 韵达速递,单号为7788990011223,暂未开始运送" result[0]: ret_code=2, msg="查不到物流信息", com=yunda, com_name="韵达速递", nu=7788990011223, tel="95546", update_time="2026-09-15 10:21:55", query_num=2, data=[] ``` 同一份响应里,一处说「暂未开始运送」,一处说「查不到物流信息」。这两句话给用户的感觉不一样,你只挑一句展示。我的做法是用 `reply_msg.text` 做主体文案,需要展示快递公司、客服电话时再从 `result[0]` 取 `com_name` 和 `tel`。 另外注意 `result[0].ret_code` 是 `2`,而外层业务 `ret_code` 是 `0`。业务层成功只代表流程走通了,不代表查到了物流。 **新闻** — `result[0]` 是分页对象,`contentlist` 一次给 20 条: ``` pagebean: allPages=1316, currentPage=1, maxResult=20, allNum=26305 contentlist[0]: title="广西筑牢母婴安全防线 妇女儿童健康水平稳步提升", source="中国新闻网", pubDate="2026-09-15 09:44:58", link="https://www.chinanews.com.cn/sh/2026/09-15/10696558.shtml" ``` 每条都带 `link`,做列表跳转很直接。`imageurls` 实测是空数组,不要指望靠它出缩略图。 ## 界面上的三个细节 **答复文本按 Markdown 渲染。** 天气给 `####`,快递给 `###`,笑话给正文。用 Markdown 渲染器,或者在后端把标记去掉再下发。 **低置信度不要静默兜底。** 实测「你好」这类短句在 3054-2 的置信度落在 50~65,意图还会跳变。这种输入与其猜,不如回一句「你是想问天气、快递还是新闻?」来得稳。 **别把三类答复的字段混着用。** 写一个 `render(intent, body)` 按意图分派,比写一个通用渲染函数少踩很多坑。 ## FAQ **Q1:客服机器人需要接几个接口?** 三类查询只接易源合一一个接口(apiCode=3054)。它在内部已经完成了「识别意图 → 调对应能力 → 整理答复」这一串动作,你不需要再单独接天气、快递、新闻接口。 **Q2:快递查询为什么可能慢?** 底层快递查询要串不同快递公司的数据源。实测 3054-1 的快递意图耗时 2.31 秒,比天气的 1.62 秒长。给快递分支单独放宽客户端超时。 **Q3:用户问的问题不在三类里怎么办?** 用 3054-2 先判意图,`intent` 不在你的支持集合里就走兜底话术。这样能区分「没听懂」和「没做这个功能」,用户体感完全不同。 **Q4:一天 1000 次查询大概多少钱?** 按接入点单价 5.5 厘/次计算,1000 次约 5.5 元。两段式调用会把请求数翻倍,成本也翻倍。专用资源包的规格与可调用次数以官方产品价格页为准。 **Q5:答复里的温度是实时的吗?** 不是。返回的是底层气象数据源的当前值,实测 2026-09-15 昆明白天 24℃。做展示时建议同时给出数据时间,避免用户按旧数据做判断。 ## 下一步阅读 - [易源合一 3054-2 与 3054-1 的搭配方式:先判意图,再决定要不要发起对话](https://www.showapi.com/guides/united-api-intent-precheck-3054) - [易源合一在对话式应用里的位置:意图层与执行层的切分方案](https://www.showapi.com/guides/united-api-dialog-architecture-3054) - [易源合一调用失败扣不扣费:ret_code 与 showapi_fee_num 实测对照表](https://www.showapi.com/guides/united-api-retcode-fee-3054) - **本系列共 12 篇**:查看[易源合一指南总目录](https://www.showapi.com/guides/united-api-guides-3054)