style: 统一处理历史状态展示口径
This commit is contained in:
@@ -99,3 +99,11 @@ class NotificationRecord(models.Model):
|
||||
|
||||
def __str__(self) -> str:
|
||||
return f"{self.notify_reason}:{self.batch_id}"
|
||||
|
||||
def get_message_status_display_text(self) -> str:
|
||||
"""返回通知状态的中文展示文案。"""
|
||||
return {
|
||||
self.STATUS_PENDING: "处理中",
|
||||
self.STATUS_SENT: "已发送",
|
||||
self.STATUS_FAILED: "失败",
|
||||
}.get(self.message_status, self.message_status)
|
||||
|
||||
@@ -7,6 +7,36 @@ from .models import AgentAuditLog, NotificationRecord
|
||||
|
||||
SUPPORTED_NOTIFY_REASONS = {"task_completed", "task_failed"}
|
||||
|
||||
RISK_STATUS_DISPLAY = {
|
||||
"high": "已阻断",
|
||||
"medium": "待复核",
|
||||
"low": "已完成",
|
||||
"failed": "失败",
|
||||
"processing": "处理中",
|
||||
"pending": "处理中",
|
||||
}
|
||||
|
||||
EXPORT_STATUS_DISPLAY = {
|
||||
"completed": "已完成",
|
||||
"draft_only": "待复核",
|
||||
"review_required": "待复核",
|
||||
"manual_review": "待复核",
|
||||
"blocked": "已阻断",
|
||||
"failed": "失败",
|
||||
"processing": "处理中",
|
||||
"pending": "处理中",
|
||||
}
|
||||
|
||||
CONVERSATION_STATUS_DISPLAY = {
|
||||
"success": "已完成",
|
||||
"completed": "已完成",
|
||||
"review_required": "待复核",
|
||||
"blocked": "已阻断",
|
||||
"failed": "失败",
|
||||
"processing": "处理中",
|
||||
"pending": "处理中",
|
||||
}
|
||||
|
||||
|
||||
def create_audit_log(
|
||||
scenario_id: str,
|
||||
@@ -138,11 +168,15 @@ def build_history_rows(logs) -> list[dict]:
|
||||
"conversation": conversation,
|
||||
"batch_scale": f"{batch.file_count} 份 / {batch.page_count} 页" if batch else "-",
|
||||
"batch_status": batch.get_import_status_display_text() if batch else "-",
|
||||
"conversation_status": conversation.task_status if conversation else "-",
|
||||
"risk_status": structured_output.get("highest_risk_level")
|
||||
or structured_output.get("risk_level")
|
||||
or "-",
|
||||
"notify_status": notification.message_status if notification else "-",
|
||||
"conversation_status": _get_conversation_status_display_text(
|
||||
conversation.task_status if conversation else "-"
|
||||
),
|
||||
"risk_status": _get_risk_status_display_text(
|
||||
structured_output.get("highest_risk_level")
|
||||
or structured_output.get("risk_level")
|
||||
or "-"
|
||||
),
|
||||
"notify_status": notification.get_message_status_display_text() if notification else "-",
|
||||
"notify_reason": notification.notify_reason if notification else "-",
|
||||
}
|
||||
)
|
||||
@@ -161,13 +195,13 @@ def build_history_metrics(history_rows: list[dict]) -> list[dict]:
|
||||
"""
|
||||
total_count = len(history_rows)
|
||||
success_count = sum(1 for row in history_rows if row["log"].status == "success")
|
||||
notify_sent_count = sum(1 for row in history_rows if row.get("notify_status") == "sent")
|
||||
blocked_count = sum(1 for row in history_rows if row.get("risk_status") == "high")
|
||||
notify_sent_count = sum(1 for row in history_rows if row.get("notify_status") == "已发送")
|
||||
blocked_count = sum(1 for row in history_rows if row.get("risk_status") == "已阻断")
|
||||
return [
|
||||
{"label": "处理任务数", "value": total_count, "note": "按当前筛选条件回看执行留痕。"},
|
||||
{"label": "成功执行", "value": success_count, "note": "执行完成并写入审计快照。"},
|
||||
{"label": "通知已发送", "value": notify_sent_count, "note": "已生成 sent 状态的通知留痕。"},
|
||||
{"label": "高风险阻断", "value": blocked_count, "note": "风险等级为 high 的处理记录。"},
|
||||
{"label": "通知已发送", "value": notify_sent_count, "note": "已生成已发送状态的通知留痕。"},
|
||||
{"label": "高风险阻断", "value": blocked_count, "note": "当前风险状态为已阻断的处理记录。"},
|
||||
]
|
||||
|
||||
|
||||
@@ -187,15 +221,33 @@ def build_detail_summary(log: AgentAuditLog, conversation, notifications) -> dic
|
||||
)
|
||||
latest_notification = notifications.first() if hasattr(notifications, "first") else None
|
||||
return {
|
||||
"export_status": structured_output.get("export_status") or (export_node or {}).get("status", "-"),
|
||||
"export_status": _get_export_status_display_text(
|
||||
structured_output.get("export_status") or (export_node or {}).get("status", "-")
|
||||
),
|
||||
"download_url": structured_output.get("download_url", ""),
|
||||
"output_file_name": output_file.get("file_name", ""),
|
||||
"output_file_relative_path": output_file.get("relative_path", ""),
|
||||
"export_mode": output_file.get("export_mode", ""),
|
||||
"template_name": structured_output.get("template_name", ""),
|
||||
"template_version": structured_output.get("template_version", ""),
|
||||
"draft_export_status": structured_output.get("draft_export_status", ""),
|
||||
"formal_export_status": structured_output.get("formal_export_status", ""),
|
||||
"draft_export_status": _get_export_status_display_text(
|
||||
structured_output.get("draft_export_status", "")
|
||||
),
|
||||
"formal_export_status": _get_export_status_display_text(
|
||||
structured_output.get("formal_export_status", "")
|
||||
),
|
||||
"blocked_items": structured_output.get("blocked_items") or [],
|
||||
"notification_receipt": latest_notification.receipt if latest_notification else {},
|
||||
}
|
||||
|
||||
|
||||
def _get_risk_status_display_text(status: str) -> str:
|
||||
return RISK_STATUS_DISPLAY.get(status, status or "-")
|
||||
|
||||
|
||||
def _get_export_status_display_text(status: str) -> str:
|
||||
return EXPORT_STATUS_DISPLAY.get(status, status or "-")
|
||||
|
||||
|
||||
def _get_conversation_status_display_text(status: str) -> str:
|
||||
return CONVERSATION_STATUS_DISPLAY.get(status, status or "-")
|
||||
|
||||
@@ -100,7 +100,7 @@
|
||||
<td>{{ item.notify_reason }}</td>
|
||||
<td>{{ item.owner_role }}</td>
|
||||
<td>{{ item.feishu_user_id }}</td>
|
||||
<td>{{ item.message_status }}</td>
|
||||
<td>{{ item.get_message_status_display_text }}</td>
|
||||
<td>{{ item.web_detail_url|default:"-" }}</td>
|
||||
</tr>
|
||||
{% empty %}
|
||||
|
||||
@@ -35,17 +35,17 @@
|
||||
<label for="id_risk_status">风险状态</label>
|
||||
<select id="id_risk_status" name="risk_status">
|
||||
<option value="">全部风险</option>
|
||||
<option value="high"{% if risk_status == "high" %} selected{% endif %}>high</option>
|
||||
<option value="medium"{% if risk_status == "medium" %} selected{% endif %}>medium</option>
|
||||
<option value="low"{% if risk_status == "low" %} selected{% endif %}>low</option>
|
||||
<option value="high"{% if risk_status == "high" %} selected{% endif %}>已阻断</option>
|
||||
<option value="medium"{% if risk_status == "medium" %} selected{% endif %}>待复核</option>
|
||||
<option value="low"{% if risk_status == "low" %} selected{% endif %}>已完成</option>
|
||||
</select>
|
||||
</div>
|
||||
<div>
|
||||
<label for="id_notify_status">通知状态</label>
|
||||
<select id="id_notify_status" name="notify_status">
|
||||
<option value="">全部状态</option>
|
||||
<option value="sent"{% if notify_status == "sent" %} selected{% endif %}>sent</option>
|
||||
<option value="failed"{% if notify_status == "failed" %} selected{% endif %}>failed</option>
|
||||
<option value="sent"{% if notify_status == "sent" %} selected{% endif %}>已发送</option>
|
||||
<option value="failed"{% if notify_status == "failed" %} selected{% endif %}>失败</option>
|
||||
</select>
|
||||
</div>
|
||||
<div class="button-row">
|
||||
@@ -117,7 +117,7 @@
|
||||
</span>
|
||||
</td>
|
||||
<td>
|
||||
<span class="pill {% if row.conversation_status == 'success' %}pill-success{% elif row.conversation_status == 'failed' %}pill-danger{% else %}pill-signal{% endif %}">
|
||||
<span class="pill {% if row.conversation_status == '已完成' %}pill-success{% elif row.conversation_status == '失败' or row.conversation_status == '已阻断' %}pill-danger{% else %}pill-signal{% endif %}">
|
||||
{{ row.conversation_status }}
|
||||
</span>
|
||||
</td>
|
||||
@@ -126,7 +126,7 @@
|
||||
<span class="pill {% if row.log.status == 'success' %}pill-success{% else %}pill-danger{% endif %}">{{ row.log.get_status_display_text }}</span>
|
||||
</td>
|
||||
<td>
|
||||
<span class="pill {% if row.risk_status == 'high' %}pill-danger{% elif row.risk_status == 'medium' %}pill-signal{% elif row.risk_status == 'low' %}pill-success{% endif %}">
|
||||
<span class="pill {% if row.risk_status == '已阻断' or row.risk_status == '失败' %}pill-danger{% elif row.risk_status == '待复核' or row.risk_status == '处理中' %}pill-signal{% elif row.risk_status == '已完成' %}pill-success{% endif %}">
|
||||
{{ row.risk_status }}
|
||||
</span>
|
||||
</td>
|
||||
@@ -134,7 +134,7 @@
|
||||
<span class="pill pill-accent">{{ row.notify_reason }}</span>
|
||||
</td>
|
||||
<td>
|
||||
<span class="pill {% if row.notify_status == 'sent' %}pill-success{% elif row.notify_status == 'failed' %}pill-danger{% else %}pill-signal{% endif %}">
|
||||
<span class="pill {% if row.notify_status == '已发送' %}pill-success{% elif row.notify_status == '失败' %}pill-danger{% else %}pill-signal{% endif %}">
|
||||
{{ row.notify_status }}
|
||||
</span>
|
||||
</td>
|
||||
|
||||
@@ -249,9 +249,9 @@ def test_audit_list_shows_risk_and_notification_status(client, db):
|
||||
content = response.content.decode("utf-8")
|
||||
assert response.status_code == 200
|
||||
assert "风险状态" in content
|
||||
assert "high" in content
|
||||
assert "已阻断" in content
|
||||
assert "通知状态" in content
|
||||
assert "sent" in content
|
||||
assert "已发送" in content
|
||||
assert "通知原因" in content
|
||||
assert "task_completed" in content
|
||||
|
||||
@@ -414,7 +414,7 @@ def test_audit_list_shows_batch_scale_and_conversation_status(client, db):
|
||||
assert "资料规模" in content
|
||||
assert "4 份 / 26 页" in content
|
||||
assert "会话状态" in content
|
||||
assert "failed" in content
|
||||
assert "失败" in content
|
||||
assert "待复核" in content
|
||||
|
||||
|
||||
@@ -476,6 +476,8 @@ def test_audit_list_shows_history_metrics_and_context_links(client, db):
|
||||
assert reverse("chat:detail", args=["conv-009"]) in content
|
||||
assert f"{reverse('documents:list')}?keyword=SUB-20260604-009" in content
|
||||
assert f"{reverse('audit:list')}?keyword=产品C" in content
|
||||
assert "已发送" in content
|
||||
assert "待复核" in content
|
||||
|
||||
|
||||
def test_audit_detail_page_shows_export_summary_and_notification_receipt(client, db):
|
||||
@@ -525,11 +527,12 @@ def test_audit_detail_page_shows_export_summary_and_notification_receipt(client,
|
||||
content = response.content.decode("utf-8")
|
||||
assert response.status_code == 200
|
||||
assert "导出状态摘要" in content
|
||||
assert "draft_only" in content
|
||||
assert "待复核" in content
|
||||
assert "/downloads/registration-report.docx" in content
|
||||
assert "风险项未清零" in content
|
||||
assert "通知回执" in content
|
||||
assert "msg-9" in content
|
||||
assert "已发送" in content
|
||||
|
||||
|
||||
def test_audit_detail_page_shows_export_file_name_and_mode(client, db):
|
||||
@@ -578,3 +581,16 @@ def test_audit_detail_page_shows_export_file_name_and_mode(client, db):
|
||||
assert "draft" in content
|
||||
assert "模板版本" in content
|
||||
assert "V1.0" in content
|
||||
assert "待复核" in content
|
||||
|
||||
|
||||
def test_audit_list_uses_chinese_filter_labels_for_risk_and_notification_status(client, db):
|
||||
response = client.get(reverse("audit:list"))
|
||||
|
||||
content = response.content.decode("utf-8")
|
||||
assert response.status_code == 200
|
||||
assert ">已阻断<" in content
|
||||
assert ">待复核<" in content
|
||||
assert ">已完成<" in content
|
||||
assert ">已发送<" in content
|
||||
assert ">失败<" in content
|
||||
|
||||
Reference in New Issue
Block a user