电商客户反馈处理场景 实现
本篇博客主要是将LangChain的基础应用到业务场景中去。,接口部分不再展示。相应的代码会放到github,项目位置:/AICustomerService ,感兴趣的可以去看一下,这个场景后面还会更新代码,最基础的逻辑已完成。前端页面的话,后续会截图展示在博客中。
需求场景:现在有一个电商平台客户反馈处理的场景。
1. 文档概述
| 项目 | 内容 |
|---|---|
| 场景名称 | 智能电商客户反馈处理系统 (Intelligent Feedback Processing System, IFPS) |
| 版本号 | V1.0 |
| 目标用户 | 客服团队、运营团队、产品经理、技术运维 |
| 核心价值 | 提升客诉响应速度,实现分级处理,降低人工成本,挖掘用户痛点数据。 |
2.背景及痛点
目前电商平台日均产生海量用户反馈(评论、工单、IM聊天记录),主要解决以下痛点:
-
响应滞后:人工筛选紧急客诉耗时久,导致高优先级问题处理不及时(如物流丢件、资金安全)处理不及时,引发舆情风险
-
分类不准,依赖人工打标,标准不一、难以准确统计各类问题占比,无法知道业务改进
-
回复效率低:客服人员需要重复撰写相似回复,占用大量时间
-
情感盲区,难以实时量化用户情绪变化,无法在用户流失前进行干预
3. 功能需求详解
-
智能问题分类
目标是精准识别用户情绪倾向及强度,将非结构化文本映射到标准化的业务标签体系,便于路由和统计
- 一级分类:自动归类至核心业务域,包括
物流配送、商品质量、售后服务、支付结算、账号安全、平台活动、其他。 - 二级细分:在一级分类下自动提取具体问题点。
- 例:物流 ->
发货延迟、包裹破损、快递员态度差。 - 例:商品 ->
假货嫌疑、描述不符、缺少配件。
- 例:物流 ->
- 关键词提取:自动提取反馈中的核心实体(如订单号、商品SKU、快递单号、具体日期)
- 情感分析
目标:精准识别用户情绪倾向及强度,为后续优先级判定提供基础数据。
- 功能描述:
- 极性判断:自动将反馈标记为
正面 (Positive)、中性 (Neutral)、负面 (Negative)。
- 极性判断:自动将反馈标记为
-
紧急程度动态评估
目标:基于规则引擎与AI模型,计算工单优先级,实现“急事急办”。
Python代码实现
import json
import os
import re
import time
from langchain_core.output_parsers import JsonOutputParser
from langchain_core.runnables import RunnableParallel, RunnableLambda, RunnablePassthrough
from langchain_openai import ChatOpenAI
# 创建模型client
model = ChatOpenAI(
model="qwen3-max",
temperature=0,
base_url= "https://dashscope.aliyuncs.com/compatible-mode/v1",
api_key= os.getenv("DASHSCOPE_API_KEY")
)
# 带重试的调用模型函数
def call_qwen_with_retry(prompt,max_retry=3,retry_delay=2):
"""调用模型,并重试"""
for i in range(max_retry):
try:
return model.invoke(prompt).content
except Exception as e:
time.sleep(retry_delay)
print(f"第{i+1}次重试,错误信息:{e}")
raise Exception("调用模型失败")
# 业务逻辑处理
# 获取订单信息
def get_order_info(feedback:str) -> dict:
"""获取订单信息"""
prompt = f"""
你是一名电商订单处理专家,请从用户反馈中提取订单ID:
{feedback}
订单ID通常是以订单ORD开头的10位数字组合,例如:ORD2023010101,如果找不到,请返回"订单ID未找到"
请严格按照JSON格式返回结果:
{{"order_id": "提取结果"}}
"""
try:
match = re.search(r"ORD\d{10}", feedback)
return {"order_id": match.group(0) if match else "订单ID未找到"}
except Exception as e:
print(f"获取订单信息失败:{e}")
result = call_qwen_with_retry(prompt)
return json.loads(result.strip())
# 情感分析
def analyze_sentiment(feedback:str) ->dict:
"""分析用户反馈"""
prompt = f"""
请分析以下用户反馈的情感倾向
{feedback}
要求:
1. 判断用户反馈的情感倾向,并返回结果为"POSITIVE(积极)/NEUTRAL(中性)/NEGATIVE(消极)",
2. 评价信誉度(0-1)
3. 提取3个关键词
返回的结果为JSON格式:
{{
"sentiment": "POSITIVE(积极)/NEUTRAL(中性)/NEGATIVE(消极)",
"credit": "信誉度",
"keywords": [关键词 1, 关键词 2, 关键词 3]
}}
"""
try:
result = call_qwen_with_retry(prompt)
paser = JsonOutputParser()
result = paser.parse(result)
return result
except Exception as e:
print(f"情感分析失败:{e}")
return {
"sentiment": "NEGATIVE",
"credit": 0.7,
"keywords": []
}
# 问题分类
def classify_problem(feedback:str) -> dict :
prompt = f"""
你是一名电商客服专家,请从用户反馈中提取问题类型:{feedback}
分类的选项:
- 物流问题:配送延迟、物流损坏等
- 产品质量:商品瑕疵、功能故障等
- 客户服务:客服态度、响应速度等
- 支付问题:扣款异常、退款延迟等
- 退货退款:退货流程、退款金额等
- 其他:无法归类的反馈
要求:
1.选择一个最合适的问题类型,并返回结果为"物流问题"、"产品质量"、"客户服务"、"支付问题"、"退货退款"、"其他"
2.按照相关度进行排序
返回的结果为JSON格式:
{{
"problem_type": [分类 1、分类 2、分类 3]
}}
"""
try:
result = call_qwen_with_retry(prompt)
output_paseter = JsonOutputParser()
result = output_paseter.parse(result)
return result
except Exception as e:
print(f"问题分类失败:{e}")
return {
"problem_type": ["其他"]
}
# 处理订单紧急程度
def handle_order_urgency(feedback:str) -> dict:
prompt = f"""
你作为一名电商客服主管,请从用户反馈的紧急程度:{feedback}
评估标准:
- High: 包含"紧急“、”立刻“、”马上“ 或者威胁投诉
- Medium: 表达强烈不满但无立即行动要求
- Low: 一般反馈或者建议
要求:
1.选择一个最合适的订单紧急程度,并返回结果为"紧急(High)"、"一般(Medium)"、"不紧急(Low)"
2.按照相关度进行排序
返回的结果为JSON格式:
{{
"urgency_level": "紧急程度",
"reason": "原因",
"sla": "服务时间 (小时)"
}}
"""
try:
result = call_qwen_with_retry(prompt)
output_passer = JsonOutputParser()
result = output_passer.parse(result)
result["sla"] = int(result["sla"])
return result
except Exception as e:
print(f"订单紧急程度评估失败:{e}")
return {
"urgency_level": "Medium",
"reason": "无法评估",
"sla":24
}
# 生成最终的答案
def generate_response(data:dict) -> dict:
print(data)
prompt_template = """
你作为一名电商客服专家,请根据下列分析结果生成客户回复:
### 客户反馈原文
{feedback}
### 分析结果
- 订单ID:{order_id}
- 情感倾向:{sentiment}
- 信誉度:{credit}
- 问题类型:{problem_type}
- 紧急程度:{urgency_level},需要在{sla}小时内处理
{key_phrases_section}
### 回复要求
1. 请使用中文回复
2. 根据情感倾向调整语气
- 积极反馈:表达感谢,适当赞美
- 消极反馈:诚恳道歉,明确解决方案
3. 包含订单ID、问题类型
4. 明确说明处理时间和后续步骤
5. 长度在100-150字,避免重复,使用自然口语
6. 结尾处询问是否还有其他问题
请直接输出答案,不需要额外说明
"""
# 构建关键词短语
key_phrases= data.get('keywords',[])
if key_phrases:
### 关键短语
key_phrases_section = "- 关键要点:"+ ",".join(key_phrases[:3])
else:
key_phrases_section = ""
prompt = prompt_template.format(
feedback=data["origin_feedback"],
order_id=data["order_id"],
sentiment=data["sentiment"],
credit=data.get('credit',0.8),
problem_type=data["problem_type"],
urgency_level=data["urgency_level"],
sla=data["sla"],
key_phrases_section=key_phrases_section
)
try:
result = call_qwen_with_retry(prompt)
# 添加紧急表示
if data["urgency_level"] == "High":
result = f"[紧急] {result}"
return {
"final_response": result,
"assigned_team":data["problem_type"][0] if data["problem_type"] else "其他",
"result":data
}
except Exception as e:
print(f"回复生成失败:{e}")
return {
"final_response": "感谢您的反馈,我们团队会尽快处理问题",
"assigned_team": "其他",
}
# lcel处理链
# 1.基本信息的提取
extract_parallel_chain = RunnableParallel(
order_id = RunnableLambda(get_order_info),
origin_feedback = lambda x: x
)
# 2. 并行任务分析
analyze_chain = RunnableParallel(
sentiment = RunnableLambda(analyze_sentiment),
urgency_level = RunnableLambda(handle_order_urgency),
problem_type = RunnableLambda(classify_problem)
)
print("analyze_chain:",analyze_chain)
# 3. 组合完整流程
process_chain = (
extract_parallel_chain
|
RunnablePassthrough.assign(
analysis=lambda x: analyze_chain.invoke(x["origin_feedback"])
)
|{
"order_id": lambda x: x["order_id"]["order_id"],
"origin_feedback": lambda x: x["origin_feedback"],
"sentiment": lambda x: x["analysis"]["sentiment"].get("sentiment","NEGATIVE"),
"problem_type": lambda x: x["analysis"]["problem_type"].get("problem_type",["其他"]),
"keywords": lambda x: (x["analysis"]["sentiment"].get("keywords",[])),
"credit" : lambda x: x["analysis"]["sentiment"]["credit"],
"urgency_level": lambda x:x["analysis"]["urgency_level"]["urgency_level"],
"sla": lambda x: x["analysis"]["urgency_level"]["sla"],
"reason": lambda x: x["analysis"]["urgency_level"].get("reason","无法评估"),
}
| RunnableLambda(generate_response)
)
本文来自博客园,作者:前端加油站,转载请注明原文链接:https://www.cnblogs.com/bllx/p/19726470

浙公网安备 33010602011771号