feat:新增投顾agent和nl2sqlagent

This commit is contained in:
2026-09-13 16:19:24 +08:00
parent c80c6acac0
commit 163192bf55
122 changed files with 7488 additions and 362 deletions
+22 -2
View File
@@ -2,8 +2,14 @@
from __future__ import annotations
from datetime import datetime
from typing import Any
from typing import Any, Literal
from common_const import (
TALK_SCENE_CUSTOMER_COMPLAINT,
TALK_SCENE_MARKET_FLUCTUATION,
TALK_SCENE_PORTFOLIO_DIVERGENCE,
TALK_SCENE_RISK_BLOCK_ORDER,
)
from pydantic import BaseModel, Field
@@ -31,7 +37,12 @@ class TalkScriptReq(BaseModel):
"""生成沟通话术草稿(同步,超时由工作台降级为「稍后重试」)。"""
customer_id: int = Field(gt=0)
scene_type: str = Field(min_length=1, max_length=64)
scene_type: Literal[
TALK_SCENE_RISK_BLOCK_ORDER,
TALK_SCENE_MARKET_FLUCTUATION,
TALK_SCENE_PORTFOLIO_DIVERGENCE,
TALK_SCENE_CUSTOMER_COMPLAINT,
]
class RelationReq(BaseModel):
@@ -51,6 +62,15 @@ class VisitCreateReq(BaseModel):
audio_url: str | None = Field(default=None, max_length=512)
class VisitUpdateReq(BaseModel):
"""回访记录可编辑字段;不提供字段时拒绝空更新。"""
visit_type: str | None = Field(default=None, min_length=1, max_length=32)
visit_time: datetime | None = None
summary: str | None = None
audio_url: str | None = Field(default=None, max_length=512)
class TodoHandleReq(BaseModel):
"""待办处理入参(process=开始处理 / done=完成)。"""
+60
View File
@@ -0,0 +1,60 @@
"""投顾 Agent HTTP 请求 DTO。"""
from __future__ import annotations
from typing import Any, Literal
from pydantic import BaseModel, Field
from common.common_const import (
AGENT_INTENT_DIALOGUE_SCRIPT,
AGENT_INTENT_FUND_ANALYSIS,
AGENT_INTENT_REBALANCE,
AGENT_INTENT_RECOMMEND,
TALK_SCENE_CUSTOMER_COMPLAINT,
TALK_SCENE_MARKET_FLUCTUATION,
TALK_SCENE_PORTFOLIO_DIVERGENCE,
TALK_SCENE_RISK_BLOCK_ORDER,
)
class AdvisorDraftSaveReq(BaseModel):
title: str | None = Field(default=None, max_length=128)
content: str | None = None
structured_data: dict[str, Any] | None = None
class AdvisorDraftOperateReq(BaseModel):
operation: Literal["discard"]
class AdvisorRebalanceRunReq(BaseModel):
customer_id: int = Field(gt=0)
class AdvisorChatReq(BaseModel):
customer_id: int = Field(gt=0)
intent: Literal[
AGENT_INTENT_RECOMMEND,
AGENT_INTENT_REBALANCE,
AGENT_INTENT_FUND_ANALYSIS,
AGENT_INTENT_DIALOGUE_SCRIPT,
] | None = None
query: str | None = Field(default=None, max_length=4000)
class AdvisorFundAnalysisReq(BaseModel):
customer_id: int | None = Field(default=None, gt=0)
fund_codes: list[str] = Field(min_length=1)
fund: dict[str, Any] | None = None
performance: list[dict[str, Any]] | None = None
class AdvisorTalkScriptReq(BaseModel):
customer_id: int = Field(gt=0)
scene_type: Literal[
TALK_SCENE_RISK_BLOCK_ORDER,
TALK_SCENE_MARKET_FLUCTUATION,
TALK_SCENE_PORTFOLIO_DIVERGENCE,
TALK_SCENE_CUSTOMER_COMPLAINT,
]
customer_name: str = Field(default="客户", max_length=32)
+40
View File
@@ -0,0 +1,40 @@
"""NL2SQL HTTP 请求模型。"""
from __future__ import annotations
from typing import Literal
from pydantic import BaseModel, Field
class DataQueryReq(BaseModel):
"""自然语言查询请求。"""
question: str = Field(min_length=1, max_length=2000)
session_id: str | None = Field(default=None, max_length=64)
caller_agent: str | None = Field(default=None, max_length=64)
data_scope: dict | None = None
max_rows: int | None = Field(default=None, gt=0, le=10000)
include_sql: bool = False
page: int = Field(default=1, ge=1, le=100000)
page_size: int = Field(default=100, ge=1, le=10000)
sort_by: str | None = Field(default=None, max_length=128)
sort_order: Literal["asc", "desc"] = "asc"
output_format: Literal["json", "csv"] = "json"
class DataExplainReq(BaseModel):
"""安全 EXPLAIN 请求。"""
sql: str = Field(min_length=1, max_length=20000)
class DataKillReq(BaseModel):
"""管理员中止运行中查询请求。"""
query_id: str = Field(min_length=1, max_length=64)
class DataCacheInvalidateReq(BaseModel):
"""管理员按业务表失效查询缓存。"""
table_names: list[str] = Field(min_length=1, max_length=50)
+76
View File
@@ -0,0 +1,76 @@
"""NL2SQL 管理接口请求模型。"""
from __future__ import annotations
from typing import Literal
from pydantic import BaseModel, Field
class RoleCreateReq(BaseModel):
role_code: str = Field(min_length=1, max_length=64)
role_name: str = Field(min_length=1, max_length=128)
employee_role: str = Field(min_length=1, max_length=32)
can_query: bool = False
max_rows: int = Field(default=1000, gt=0, le=100000)
daily_quota: int = Field(default=0, ge=0, le=1000000)
class RoleUpdateReq(BaseModel):
role_name: str | None = Field(default=None, min_length=1, max_length=128)
can_query: bool | None = None
max_rows: int | None = Field(default=None, gt=0, le=100000)
daily_quota: int | None = Field(default=None, ge=0, le=1000000)
status: Literal["active", "inactive"] | None = None
class TablePermissionCreateReq(BaseModel):
table_name: str = Field(min_length=1, max_length=128)
row_scope_type: Literal["none", "customer_ids", "product_ids"] = "none"
row_scope_column: str | None = Field(default=None, max_length=128)
class TablePermissionUpdateReq(BaseModel):
row_scope_type: Literal["none", "customer_ids", "product_ids"] | None = None
row_scope_column: str | None = Field(default=None, max_length=128)
status: Literal["active", "inactive"] | None = None
class ColumnPermissionCreateReq(BaseModel):
table_name: str = Field(min_length=1, max_length=128)
column_name: str = Field(min_length=1, max_length=128)
access_mode: Literal["allow", "deny", "mask"] = "allow"
mask_type: Literal["partial", "hash"] | None = None
class ColumnPermissionUpdateReq(BaseModel):
access_mode: Literal["allow", "deny", "mask"] | None = None
mask_type: Literal["partial", "hash"] | None = None
status: Literal["active", "inactive"] | None = None
class SensitiveFieldCreateReq(BaseModel):
table_name: str = Field(min_length=1, max_length=128)
column_name: str = Field(min_length=1, max_length=128)
mask_type: Literal["partial", "hash"] = "partial"
description: str | None = Field(default=None, max_length=255)
class SensitiveFieldUpdateReq(BaseModel):
mask_type: Literal["partial", "hash"] | None = None
description: str | None = Field(default=None, max_length=255)
status: Literal["active", "inactive"] | None = None
class MaintenanceJobReq(BaseModel):
task: Literal["metadata_sync", "vector_cleanup", "consistency_check", "history_cleanup"]
before_days: int = Field(default=180, ge=1, le=3650)
class RuntimeConfigUpdateReq(BaseModel):
"""管理员动态调整 NL2SQL 非敏感运行参数。"""
cache_ttl: int | None = Field(default=None, ge=30, le=86400)
retrieval_top_k: int | None = Field(default=None, ge=1, le=50)
retrieval_threshold: float | None = Field(default=None, ge=0.0, le=1.0)
max_rows: int | None = Field(default=None, ge=1, le=100000)
max_join_depth: int | None = Field(default=None, ge=0, le=10)