feat: extend MetadataFieldDefinition with field_roles and add SlotDefinition model [AC-MRS-01,02,03,07,08]
This commit is contained in:
parent
5ded0c5f75
commit
d534b4ef32
|
|
@ -110,6 +110,33 @@ class ChatMessageCreate(SQLModel):
|
||||||
content: str
|
content: str
|
||||||
|
|
||||||
|
|
||||||
|
class SharedSession(SQLModel, table=True):
|
||||||
|
"""
|
||||||
|
[AC-IDMP-SHARE] Shared session entity for dialogue sharing.
|
||||||
|
Allows sharing chat sessions via unique token with expiration and concurrent user limits.
|
||||||
|
"""
|
||||||
|
|
||||||
|
__tablename__ = "shared_sessions"
|
||||||
|
__table_args__ = (
|
||||||
|
Index("ix_shared_sessions_share_token", "share_token", unique=True),
|
||||||
|
Index("ix_shared_sessions_tenant_session", "tenant_id", "session_id"),
|
||||||
|
Index("ix_shared_sessions_expires_at", "expires_at"),
|
||||||
|
)
|
||||||
|
|
||||||
|
id: uuid.UUID = Field(default_factory=uuid.uuid4, primary_key=True)
|
||||||
|
share_token: str = Field(..., description="Unique share token (UUID)", index=True)
|
||||||
|
session_id: str = Field(..., description="Associated session ID", index=True)
|
||||||
|
tenant_id: str = Field(..., description="Tenant ID for multi-tenant isolation", index=True)
|
||||||
|
title: str | None = Field(default=None, description="Share title")
|
||||||
|
description: str | None = Field(default=None, description="Share description")
|
||||||
|
expires_at: datetime = Field(..., description="Expiration time")
|
||||||
|
is_active: bool = Field(default=True, description="Whether share is active")
|
||||||
|
max_concurrent_users: int = Field(default=10, description="Maximum concurrent users allowed")
|
||||||
|
current_users: int = Field(default=0, description="Current number of online users")
|
||||||
|
created_at: datetime = Field(default_factory=datetime.utcnow, description="Creation time")
|
||||||
|
updated_at: datetime = Field(default_factory=datetime.utcnow, description="Last update time")
|
||||||
|
|
||||||
|
|
||||||
class DocumentStatus(str, Enum):
|
class DocumentStatus(str, Enum):
|
||||||
PENDING = "pending"
|
PENDING = "pending"
|
||||||
PROCESSING = "processing"
|
PROCESSING = "processing"
|
||||||
|
|
@ -956,6 +983,17 @@ class MetadataFieldType(str, Enum):
|
||||||
ARRAY_ENUM = "array_enum"
|
ARRAY_ENUM = "array_enum"
|
||||||
|
|
||||||
|
|
||||||
|
class FieldRole(str, Enum):
|
||||||
|
"""
|
||||||
|
[AC-MRS-01] 字段角色枚举
|
||||||
|
用于标识元数据字段的职责分层
|
||||||
|
"""
|
||||||
|
RESOURCE_FILTER = "resource_filter"
|
||||||
|
SLOT = "slot"
|
||||||
|
PROMPT_VAR = "prompt_var"
|
||||||
|
ROUTING_SIGNAL = "routing_signal"
|
||||||
|
|
||||||
|
|
||||||
class MetadataFieldStatus(str, Enum):
|
class MetadataFieldStatus(str, Enum):
|
||||||
"""[AC-IDSMETA-13] 元数据字段状态"""
|
"""[AC-IDSMETA-13] 元数据字段状态"""
|
||||||
DRAFT = "draft"
|
DRAFT = "draft"
|
||||||
|
|
@ -992,6 +1030,7 @@ class MetadataField(SQLModel):
|
||||||
class MetadataFieldDefinition(SQLModel, table=True):
|
class MetadataFieldDefinition(SQLModel, table=True):
|
||||||
"""
|
"""
|
||||||
[AC-IDSMETA-13] 元数据字段定义表
|
[AC-IDSMETA-13] 元数据字段定义表
|
||||||
|
[AC-MRS-01,02,03] 支持字段角色分层配置
|
||||||
每个字段独立存储,支持字段级状态管理(draft/active/deprecated)
|
每个字段独立存储,支持字段级状态管理(draft/active/deprecated)
|
||||||
"""
|
"""
|
||||||
|
|
||||||
|
|
@ -1029,6 +1068,11 @@ class MetadataFieldDefinition(SQLModel, table=True):
|
||||||
)
|
)
|
||||||
is_filterable: bool = Field(default=True, description="是否可用于过滤")
|
is_filterable: bool = Field(default=True, description="是否可用于过滤")
|
||||||
is_rank_feature: bool = Field(default=False, description="是否用于排序特征")
|
is_rank_feature: bool = Field(default=False, description="是否用于排序特征")
|
||||||
|
field_roles: list[str] = Field(
|
||||||
|
default_factory=list,
|
||||||
|
sa_column=Column("field_roles", JSON, nullable=False, server_default="'[]'"),
|
||||||
|
description="[AC-MRS-01] 字段角色列表: resource_filter/slot/prompt_var/routing_signal"
|
||||||
|
)
|
||||||
status: str = Field(
|
status: str = Field(
|
||||||
default=MetadataFieldStatus.DRAFT.value,
|
default=MetadataFieldStatus.DRAFT.value,
|
||||||
description="字段状态: draft/active/deprecated"
|
description="字段状态: draft/active/deprecated"
|
||||||
|
|
@ -1039,7 +1083,7 @@ class MetadataFieldDefinition(SQLModel, table=True):
|
||||||
|
|
||||||
|
|
||||||
class MetadataFieldDefinitionCreate(SQLModel):
|
class MetadataFieldDefinitionCreate(SQLModel):
|
||||||
"""[AC-IDSMETA-13] 创建元数据字段定义"""
|
"""[AC-IDSMETA-13] [AC-MRS-01] 创建元数据字段定义"""
|
||||||
|
|
||||||
field_key: str = Field(..., min_length=1, max_length=64)
|
field_key: str = Field(..., min_length=1, max_length=64)
|
||||||
label: str = Field(..., min_length=1, max_length=64)
|
label: str = Field(..., min_length=1, max_length=64)
|
||||||
|
|
@ -1050,11 +1094,12 @@ class MetadataFieldDefinitionCreate(SQLModel):
|
||||||
scope: list[str] = Field(default_factory=lambda: [MetadataScope.KB_DOCUMENT.value])
|
scope: list[str] = Field(default_factory=lambda: [MetadataScope.KB_DOCUMENT.value])
|
||||||
is_filterable: bool = Field(default=True)
|
is_filterable: bool = Field(default=True)
|
||||||
is_rank_feature: bool = Field(default=False)
|
is_rank_feature: bool = Field(default=False)
|
||||||
|
field_roles: list[str] = Field(default_factory=list)
|
||||||
status: str = Field(default=MetadataFieldStatus.DRAFT.value)
|
status: str = Field(default=MetadataFieldStatus.DRAFT.value)
|
||||||
|
|
||||||
|
|
||||||
class MetadataFieldDefinitionUpdate(SQLModel):
|
class MetadataFieldDefinitionUpdate(SQLModel):
|
||||||
"""[AC-IDSMETA-14] 更新元数据字段定义"""
|
"""[AC-IDSMETA-14] [AC-MRS-01] 更新元数据字段定义"""
|
||||||
|
|
||||||
label: str | None = Field(default=None, min_length=1, max_length=64)
|
label: str | None = Field(default=None, min_length=1, max_length=64)
|
||||||
required: bool | None = None
|
required: bool | None = None
|
||||||
|
|
@ -1063,9 +1108,129 @@ class MetadataFieldDefinitionUpdate(SQLModel):
|
||||||
scope: list[str] | None = None
|
scope: list[str] | None = None
|
||||||
is_filterable: bool | None = None
|
is_filterable: bool | None = None
|
||||||
is_rank_feature: bool | None = None
|
is_rank_feature: bool | None = None
|
||||||
|
field_roles: list[str] | None = None
|
||||||
status: str | None = None
|
status: str | None = None
|
||||||
|
|
||||||
|
|
||||||
|
class ExtractStrategy(str, Enum):
|
||||||
|
"""
|
||||||
|
[AC-MRS-07] 槽位值提取策略
|
||||||
|
"""
|
||||||
|
RULE = "rule"
|
||||||
|
LLM = "llm"
|
||||||
|
USER_INPUT = "user_input"
|
||||||
|
|
||||||
|
|
||||||
|
class SlotValueSource(str, Enum):
|
||||||
|
"""
|
||||||
|
[AC-MRS-09] 槽位值来源
|
||||||
|
"""
|
||||||
|
USER_CONFIRMED = "user_confirmed"
|
||||||
|
RULE_EXTRACTED = "rule_extracted"
|
||||||
|
LLM_INFERRED = "llm_inferred"
|
||||||
|
DEFAULT = "default"
|
||||||
|
|
||||||
|
|
||||||
|
class SlotDefinition(SQLModel, table=True):
|
||||||
|
"""
|
||||||
|
[AC-MRS-07,08] 槽位定义表
|
||||||
|
独立的槽位定义模型,与元数据字段解耦但可复用
|
||||||
|
"""
|
||||||
|
|
||||||
|
__tablename__ = "slot_definitions"
|
||||||
|
__table_args__ = (
|
||||||
|
Index("ix_slot_definitions_tenant", "tenant_id"),
|
||||||
|
Index("ix_slot_definitions_tenant_key", "tenant_id", "slot_key", unique=True),
|
||||||
|
Index("ix_slot_definitions_linked_field", "linked_field_id"),
|
||||||
|
)
|
||||||
|
|
||||||
|
id: uuid.UUID = Field(default_factory=uuid.uuid4, primary_key=True)
|
||||||
|
tenant_id: str = Field(..., description="Tenant ID for multi-tenant isolation", index=True)
|
||||||
|
slot_key: str = Field(
|
||||||
|
...,
|
||||||
|
description="槽位键名,可与元数据字段 field_key 关联",
|
||||||
|
min_length=1,
|
||||||
|
max_length=100,
|
||||||
|
)
|
||||||
|
type: str = Field(
|
||||||
|
default=MetadataFieldType.STRING.value,
|
||||||
|
description="槽位类型: string/number/boolean/enum/array_enum"
|
||||||
|
)
|
||||||
|
required: bool = Field(default=False, description="是否必填槽位")
|
||||||
|
extract_strategy: str | None = Field(
|
||||||
|
default=None,
|
||||||
|
description="提取策略: rule/llm/user_input"
|
||||||
|
)
|
||||||
|
validation_rule: str | None = Field(
|
||||||
|
default=None,
|
||||||
|
description="校验规则(正则或 JSON Schema)"
|
||||||
|
)
|
||||||
|
ask_back_prompt: str | None = Field(
|
||||||
|
default=None,
|
||||||
|
description="追问提示语模板"
|
||||||
|
)
|
||||||
|
default_value: dict[str, Any] | None = Field(
|
||||||
|
default=None,
|
||||||
|
sa_column=Column("default_value", JSON, nullable=True),
|
||||||
|
description="默认值"
|
||||||
|
)
|
||||||
|
linked_field_id: uuid.UUID | None = Field(
|
||||||
|
default=None,
|
||||||
|
description="关联的元数据字段 ID",
|
||||||
|
foreign_key="metadata_field_definitions.id",
|
||||||
|
)
|
||||||
|
created_at: datetime = Field(default_factory=datetime.utcnow, description="创建时间")
|
||||||
|
updated_at: datetime = Field(default_factory=datetime.utcnow, description="更新时间")
|
||||||
|
|
||||||
|
|
||||||
|
class SlotDefinitionCreate(SQLModel):
|
||||||
|
"""[AC-MRS-07,08] 创建槽位定义"""
|
||||||
|
|
||||||
|
slot_key: str = Field(..., min_length=1, max_length=100)
|
||||||
|
type: str = Field(default=MetadataFieldType.STRING.value)
|
||||||
|
required: bool = Field(default=False)
|
||||||
|
extract_strategy: str | None = None
|
||||||
|
validation_rule: str | None = None
|
||||||
|
ask_back_prompt: str | None = None
|
||||||
|
default_value: dict[str, Any] | None = None
|
||||||
|
linked_field_id: str | None = None
|
||||||
|
|
||||||
|
|
||||||
|
class SlotDefinitionUpdate(SQLModel):
|
||||||
|
"""[AC-MRS-07] 更新槽位定义"""
|
||||||
|
|
||||||
|
type: str | None = None
|
||||||
|
required: bool | None = None
|
||||||
|
extract_strategy: str | None = None
|
||||||
|
validation_rule: str | None = None
|
||||||
|
ask_back_prompt: str | None = None
|
||||||
|
default_value: dict[str, Any] | None = None
|
||||||
|
linked_field_id: str | None = None
|
||||||
|
|
||||||
|
|
||||||
|
class SlotValue(SQLModel):
|
||||||
|
"""
|
||||||
|
[AC-MRS-09] 运行时槽位值
|
||||||
|
"""
|
||||||
|
|
||||||
|
key: str = Field(..., description="槽位键名")
|
||||||
|
value: Any = Field(..., description="槽位值")
|
||||||
|
source: str = Field(
|
||||||
|
default=SlotValueSource.DEFAULT.value,
|
||||||
|
description="来源: user_confirmed/rule_extracted/llm_inferred/default"
|
||||||
|
)
|
||||||
|
confidence: float = Field(
|
||||||
|
default=1.0,
|
||||||
|
ge=0.0,
|
||||||
|
le=1.0,
|
||||||
|
description="置信度 0.0~1.0"
|
||||||
|
)
|
||||||
|
updated_at: datetime = Field(
|
||||||
|
default_factory=datetime.utcnow,
|
||||||
|
description="最后更新时间"
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
class MetadataSchema(SQLModel, table=True):
|
class MetadataSchema(SQLModel, table=True):
|
||||||
"""
|
"""
|
||||||
元数据模式定义(保留兼容性)
|
元数据模式定义(保留兼容性)
|
||||||
|
|
@ -1213,3 +1378,137 @@ class DecompositionResult(SQLModel):
|
||||||
confidence: float | None = Field(default=None, description="拆解置信度")
|
confidence: float | None = Field(default=None, description="拆解置信度")
|
||||||
error: str | None = Field(default=None, description="错误信息")
|
error: str | None = Field(default=None, description="错误信息")
|
||||||
latency_ms: int | None = Field(default=None, description="处理耗时(毫秒)")
|
latency_ms: int | None = Field(default=None, description="处理耗时(毫秒)")
|
||||||
|
|
||||||
|
|
||||||
|
class HighRiskScenarioType(str, Enum):
|
||||||
|
"""[AC-IDMP-20] 高风险场景类型"""
|
||||||
|
REFUND = "refund"
|
||||||
|
COMPLAINT_ESCALATION = "complaint_escalation"
|
||||||
|
PRIVACY_SENSITIVE_PROMISE = "privacy_sensitive_promise"
|
||||||
|
TRANSFER = "transfer"
|
||||||
|
|
||||||
|
|
||||||
|
class HighRiskPolicy(SQLModel, table=True):
|
||||||
|
"""
|
||||||
|
[AC-IDMP-20] 高风险场景策略配置
|
||||||
|
定义高风险场景的最小集,支持动态配置
|
||||||
|
"""
|
||||||
|
|
||||||
|
__tablename__ = "high_risk_policies"
|
||||||
|
__table_args__ = (
|
||||||
|
Index("ix_high_risk_policies_tenant", "tenant_id"),
|
||||||
|
Index("ix_high_risk_policies_tenant_enabled", "tenant_id", "is_enabled"),
|
||||||
|
)
|
||||||
|
|
||||||
|
id: uuid.UUID = Field(default_factory=uuid.uuid4, primary_key=True)
|
||||||
|
tenant_id: str = Field(..., description="Tenant ID for multi-tenant isolation", index=True)
|
||||||
|
scenario: str = Field(..., description="场景类型: refund/complaint_escalation/privacy_sensitive_promise/transfer")
|
||||||
|
handler_mode: str = Field(
|
||||||
|
default="micro_flow",
|
||||||
|
description="处理模式: micro_flow/transfer"
|
||||||
|
)
|
||||||
|
flow_id: uuid.UUID | None = Field(
|
||||||
|
default=None,
|
||||||
|
description="微流程ID (handler_mode=micro_flow时使用)",
|
||||||
|
foreign_key="script_flows.id"
|
||||||
|
)
|
||||||
|
transfer_message: str | None = Field(
|
||||||
|
default=None,
|
||||||
|
description="转人工消息 (handler_mode=transfer时使用)"
|
||||||
|
)
|
||||||
|
keywords: list[str] | None = Field(
|
||||||
|
default=None,
|
||||||
|
sa_column=Column("keywords", JSON, nullable=True),
|
||||||
|
description="触发关键词列表"
|
||||||
|
)
|
||||||
|
patterns: list[str] | None = Field(
|
||||||
|
default=None,
|
||||||
|
sa_column=Column("patterns", JSON, nullable=True),
|
||||||
|
description="触发正则模式列表"
|
||||||
|
)
|
||||||
|
priority: int = Field(default=0, description="优先级 (值越高优先级越高)")
|
||||||
|
is_enabled: bool = Field(default=True, description="是否启用")
|
||||||
|
created_at: datetime = Field(default_factory=datetime.utcnow, description="创建时间")
|
||||||
|
updated_at: datetime = Field(default_factory=datetime.utcnow, description="更新时间")
|
||||||
|
|
||||||
|
|
||||||
|
class HighRiskPolicyCreate(SQLModel):
|
||||||
|
"""[AC-IDMP-20] 创建高风险策略"""
|
||||||
|
|
||||||
|
scenario: str
|
||||||
|
handler_mode: str = "micro_flow"
|
||||||
|
flow_id: str | None = None
|
||||||
|
transfer_message: str | None = None
|
||||||
|
keywords: list[str] | None = None
|
||||||
|
patterns: list[str] | None = None
|
||||||
|
priority: int = 0
|
||||||
|
|
||||||
|
|
||||||
|
class HighRiskPolicyUpdate(SQLModel):
|
||||||
|
"""[AC-IDMP-20] 更新高风险策略"""
|
||||||
|
|
||||||
|
handler_mode: str | None = None
|
||||||
|
flow_id: str | None = None
|
||||||
|
transfer_message: str | None = None
|
||||||
|
keywords: list[str] | None = None
|
||||||
|
patterns: list[str] | None = None
|
||||||
|
priority: int | None = None
|
||||||
|
is_enabled: bool | None = None
|
||||||
|
|
||||||
|
|
||||||
|
class SessionModeRecord(SQLModel, table=True):
|
||||||
|
"""
|
||||||
|
[AC-IDMP-09] 会话模式记录
|
||||||
|
记录会话的当前模式状态
|
||||||
|
"""
|
||||||
|
|
||||||
|
__tablename__ = "session_mode_records"
|
||||||
|
__table_args__ = (
|
||||||
|
Index("ix_session_mode_records_tenant_session", "tenant_id", "session_id", unique=True),
|
||||||
|
)
|
||||||
|
|
||||||
|
id: uuid.UUID = Field(default_factory=uuid.uuid4, primary_key=True)
|
||||||
|
tenant_id: str = Field(..., description="Tenant ID for multi-tenant isolation", index=True)
|
||||||
|
session_id: str = Field(..., description="会话ID", index=True)
|
||||||
|
mode: str = Field(
|
||||||
|
default="BOT_ACTIVE",
|
||||||
|
description="会话模式: BOT_ACTIVE/HUMAN_ACTIVE"
|
||||||
|
)
|
||||||
|
reason: str | None = Field(default=None, description="模式切换原因")
|
||||||
|
switched_at: datetime | None = Field(default=None, description="模式切换时间")
|
||||||
|
created_at: datetime = Field(default_factory=datetime.utcnow, description="创建时间")
|
||||||
|
updated_at: datetime = Field(default_factory=datetime.utcnow, description="更新时间")
|
||||||
|
|
||||||
|
|
||||||
|
class MidAuditLog(SQLModel, table=True):
|
||||||
|
"""
|
||||||
|
[AC-IDMP-07] 中台审计日志
|
||||||
|
记录 generation/request 维度的审计字段
|
||||||
|
"""
|
||||||
|
|
||||||
|
__tablename__ = "mid_audit_logs"
|
||||||
|
__table_args__ = (
|
||||||
|
Index("ix_mid_audit_logs_tenant_session", "tenant_id", "session_id"),
|
||||||
|
Index("ix_mid_audit_logs_tenant_request", "tenant_id", "request_id"),
|
||||||
|
Index("ix_mid_audit_logs_tenant_generation", "tenant_id", "generation_id"),
|
||||||
|
Index("ix_mid_audit_logs_created", "created_at"),
|
||||||
|
)
|
||||||
|
|
||||||
|
id: uuid.UUID = Field(default_factory=uuid.uuid4, primary_key=True)
|
||||||
|
tenant_id: str = Field(..., description="Tenant ID for multi-tenant isolation", index=True)
|
||||||
|
session_id: str = Field(..., description="会话ID", index=True)
|
||||||
|
request_id: str = Field(..., description="请求ID", index=True)
|
||||||
|
generation_id: str = Field(..., description="生成ID", index=True)
|
||||||
|
mode: str = Field(..., description="执行模式: agent/micro_flow/fixed/transfer")
|
||||||
|
intent: str | None = Field(default=None, description="意图")
|
||||||
|
tool_calls: list[dict[str, Any]] | None = Field(
|
||||||
|
default=None,
|
||||||
|
sa_column=Column("tool_calls", JSON, nullable=True),
|
||||||
|
description="工具调用记录"
|
||||||
|
)
|
||||||
|
guardrail_triggered: bool = Field(default=False, description="护栏是否触发")
|
||||||
|
fallback_reason_code: str | None = Field(default=None, description="降级原因码")
|
||||||
|
react_iterations: int | None = Field(default=None, description="ReAct循环次数")
|
||||||
|
high_risk_scenario: str | None = Field(default=None, description="触发的高风险场景")
|
||||||
|
latency_ms: int | None = Field(default=None, description="总耗时(ms)")
|
||||||
|
created_at: datetime = Field(default_factory=datetime.utcnow, description="创建时间", index=True)
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue