188 lines
6.5 KiB
Python
188 lines
6.5 KiB
Python
|
|
# -*- coding: utf-8 -*-
|
|||
|
|
"""
|
|||
|
|
复聊配置 API(需要登录):
|
|||
|
|
- GET /api/followup-configs -> 查询复聊配置列表
|
|||
|
|
- POST /api/followup-configs -> 创建复聊配置
|
|||
|
|
- GET /api/followup-configs/{id} -> 查询单个配置
|
|||
|
|
- PUT /api/followup-configs/{id} -> 更新配置
|
|||
|
|
- DELETE /api/followup-configs/{id} -> 删除配置
|
|||
|
|
|
|||
|
|
- GET /api/followup-scripts -> 查询话术列表
|
|||
|
|
- POST /api/followup-scripts -> 创建话术
|
|||
|
|
- GET /api/followup-scripts/{id} -> 查询单个话术
|
|||
|
|
- PUT /api/followup-scripts/{id} -> 更新话术
|
|||
|
|
- DELETE /api/followup-scripts/{id} -> 删除话术
|
|||
|
|
|
|||
|
|
- GET /api/followup-records -> 查询复聊记录
|
|||
|
|
- POST /api/followup-records/send -> 手动发送复聊消息
|
|||
|
|
"""
|
|||
|
|
from rest_framework import status
|
|||
|
|
from rest_framework.decorators import api_view
|
|||
|
|
|
|||
|
|
from server.core.response import api_success, api_error
|
|||
|
|
from server.models import FollowUpConfig, FollowUpScript, FollowUpRecord, ContactRecord
|
|||
|
|
from server.serializers import (
|
|||
|
|
FollowUpConfigSerializer,
|
|||
|
|
FollowUpScriptSerializer,
|
|||
|
|
FollowUpRecordSerializer
|
|||
|
|
)
|
|||
|
|
|
|||
|
|
|
|||
|
|
# ────────────────────────── 复聊配置 ──────────────────────────
|
|||
|
|
|
|||
|
|
@api_view(["GET", "POST"])
|
|||
|
|
def followup_config_list(request):
|
|||
|
|
"""复聊配置列表。"""
|
|||
|
|
if request.method == "GET":
|
|||
|
|
position = request.query_params.get("position")
|
|||
|
|
is_active = request.query_params.get("is_active")
|
|||
|
|
|
|||
|
|
qs = FollowUpConfig.objects.all()
|
|||
|
|
if position:
|
|||
|
|
qs = qs.filter(position__icontains=position)
|
|||
|
|
if is_active is not None:
|
|||
|
|
qs = qs.filter(is_active=is_active.lower() in ("true", "1"))
|
|||
|
|
|
|||
|
|
configs = qs.order_by("-created_at")
|
|||
|
|
return api_success(FollowUpConfigSerializer(configs, many=True).data)
|
|||
|
|
|
|||
|
|
# POST
|
|||
|
|
ser = FollowUpConfigSerializer(data=request.data)
|
|||
|
|
ser.is_valid(raise_exception=True)
|
|||
|
|
ser.save()
|
|||
|
|
return api_success(ser.data, http_status=status.HTTP_201_CREATED)
|
|||
|
|
|
|||
|
|
|
|||
|
|
@api_view(["GET", "PUT", "DELETE"])
|
|||
|
|
def followup_config_detail(request, pk):
|
|||
|
|
"""复聊配置详情。"""
|
|||
|
|
try:
|
|||
|
|
obj = FollowUpConfig.objects.get(pk=pk)
|
|||
|
|
except FollowUpConfig.DoesNotExist:
|
|||
|
|
return api_error(status.HTTP_404_NOT_FOUND, "复聊配置不存在")
|
|||
|
|
|
|||
|
|
if request.method == "GET":
|
|||
|
|
return api_success(FollowUpConfigSerializer(obj).data)
|
|||
|
|
|
|||
|
|
if request.method == "PUT":
|
|||
|
|
ser = FollowUpConfigSerializer(obj, data=request.data, partial=True)
|
|||
|
|
ser.is_valid(raise_exception=True)
|
|||
|
|
ser.save()
|
|||
|
|
return api_success(ser.data)
|
|||
|
|
|
|||
|
|
# DELETE
|
|||
|
|
obj.delete()
|
|||
|
|
return api_success(msg="复聊配置已删除")
|
|||
|
|
|
|||
|
|
|
|||
|
|
# ────────────────────────── 复聊话术 ──────────────────────────
|
|||
|
|
|
|||
|
|
@api_view(["GET", "POST"])
|
|||
|
|
def followup_script_list(request):
|
|||
|
|
"""复聊话术列表。"""
|
|||
|
|
if request.method == "GET":
|
|||
|
|
config_id = request.query_params.get("config_id")
|
|||
|
|
day_number = request.query_params.get("day_number")
|
|||
|
|
|
|||
|
|
qs = FollowUpScript.objects.all()
|
|||
|
|
if config_id:
|
|||
|
|
qs = qs.filter(config_id=config_id)
|
|||
|
|
if day_number is not None:
|
|||
|
|
qs = qs.filter(day_number=day_number)
|
|||
|
|
|
|||
|
|
scripts = qs.order_by("config_id", "day_number", "order")
|
|||
|
|
return api_success(FollowUpScriptSerializer(scripts, many=True).data)
|
|||
|
|
|
|||
|
|
# POST
|
|||
|
|
ser = FollowUpScriptSerializer(data=request.data)
|
|||
|
|
ser.is_valid(raise_exception=True)
|
|||
|
|
ser.save()
|
|||
|
|
return api_success(ser.data, http_status=status.HTTP_201_CREATED)
|
|||
|
|
|
|||
|
|
|
|||
|
|
@api_view(["GET", "PUT", "DELETE"])
|
|||
|
|
def followup_script_detail(request, pk):
|
|||
|
|
"""复聊话术详情。"""
|
|||
|
|
try:
|
|||
|
|
obj = FollowUpScript.objects.get(pk=pk)
|
|||
|
|
except FollowUpScript.DoesNotExist:
|
|||
|
|
return api_error(status.HTTP_404_NOT_FOUND, "复聊话术不存在")
|
|||
|
|
|
|||
|
|
if request.method == "GET":
|
|||
|
|
return api_success(FollowUpScriptSerializer(obj).data)
|
|||
|
|
|
|||
|
|
if request.method == "PUT":
|
|||
|
|
ser = FollowUpScriptSerializer(obj, data=request.data, partial=True)
|
|||
|
|
ser.is_valid(raise_exception=True)
|
|||
|
|
ser.save()
|
|||
|
|
return api_success(ser.data)
|
|||
|
|
|
|||
|
|
# DELETE
|
|||
|
|
obj.delete()
|
|||
|
|
return api_success(msg="复聊话术已删除")
|
|||
|
|
|
|||
|
|
|
|||
|
|
# ────────────────────────── 复聊记录 ──────────────────────────
|
|||
|
|
|
|||
|
|
@api_view(["GET"])
|
|||
|
|
def followup_record_list(request):
|
|||
|
|
"""复聊记录列表。"""
|
|||
|
|
contact_id = request.query_params.get("contact_id")
|
|||
|
|
config_id = request.query_params.get("config_id")
|
|||
|
|
got_reply = request.query_params.get("got_reply")
|
|||
|
|
page = int(request.query_params.get("page", 1))
|
|||
|
|
page_size = int(request.query_params.get("page_size", 20))
|
|||
|
|
|
|||
|
|
qs = FollowUpRecord.objects.all()
|
|||
|
|
if contact_id:
|
|||
|
|
qs = qs.filter(contact_id=contact_id)
|
|||
|
|
if config_id:
|
|||
|
|
qs = qs.filter(config_id=config_id)
|
|||
|
|
if got_reply is not None:
|
|||
|
|
qs = qs.filter(got_reply=got_reply.lower() in ("true", "1"))
|
|||
|
|
|
|||
|
|
total = qs.count()
|
|||
|
|
start = (page - 1) * page_size
|
|||
|
|
end = start + page_size
|
|||
|
|
records = qs[start:end]
|
|||
|
|
|
|||
|
|
return api_success({
|
|||
|
|
"total": total,
|
|||
|
|
"page": page,
|
|||
|
|
"page_size": page_size,
|
|||
|
|
"results": FollowUpRecordSerializer(records, many=True).data,
|
|||
|
|
})
|
|||
|
|
|
|||
|
|
|
|||
|
|
@api_view(["POST"])
|
|||
|
|
def followup_send_manual(request):
|
|||
|
|
"""手动发送复聊消息。"""
|
|||
|
|
contact_id = request.data.get("contact_id")
|
|||
|
|
content = request.data.get("content", "").strip()
|
|||
|
|
|
|||
|
|
if not contact_id:
|
|||
|
|
return api_error(status.HTTP_400_BAD_REQUEST, "请提供 contact_id")
|
|||
|
|
if not content:
|
|||
|
|
return api_error(status.HTTP_400_BAD_REQUEST, "请提供发送内容")
|
|||
|
|
|
|||
|
|
try:
|
|||
|
|
contact = ContactRecord.objects.get(pk=contact_id)
|
|||
|
|
except ContactRecord.DoesNotExist:
|
|||
|
|
return api_error(status.HTTP_404_NOT_FOUND, "联系人不存在")
|
|||
|
|
|
|||
|
|
# TODO: 这里需要调用浏览器自动化发送消息
|
|||
|
|
# 暂时只记录到数据库
|
|||
|
|
|
|||
|
|
record = FollowUpRecord.objects.create(
|
|||
|
|
contact_id=contact_id,
|
|||
|
|
config_id=0, # 手动发送
|
|||
|
|
script_id=0, # 手动发送
|
|||
|
|
day_number=0,
|
|||
|
|
content=content,
|
|||
|
|
)
|
|||
|
|
|
|||
|
|
return api_success({
|
|||
|
|
"record": FollowUpRecordSerializer(record).data,
|
|||
|
|
"message": "复聊消息已发送"
|
|||
|
|
})
|