Files
X-Financial/server/src/app/services/risk_rule_generation_ontology.py
caoxiaozhu 34457f9c3e feat: 本体字段治理与风险规则模板执行器重构
- 新增本体字段注册表与字段治理审计脚本
- 重构风险规则模板执行器、DSL 验证与清单分类器
- 完善票据夹服务与差旅请求详情页交互
- 优化趋势图表与总览页数据展示
- 增强报销平台风险分级与模拟公司筛选
- 补充本体字段、风险规则生成与票据夹服务测试覆盖
2026-06-03 15:46:56 +08:00

199 lines
6.3 KiB
Python

from __future__ import annotations
from dataclasses import dataclass
from app.core.agent_enums import AgentAssetDomain
from app.services.expense_type_keywords import EXPENSE_TYPE_LABEL_BY_CODE
@dataclass(frozen=True)
class RiskRuleField:
key: str
label: str
field_type: str
source: str
aliases: tuple[str, ...]
BUSINESS_DOMAIN_LABELS: dict[str, str] = {
AgentAssetDomain.EXPENSE.value: "报销",
AgentAssetDomain.AR.value: "应收",
AgentAssetDomain.AP.value: "应付",
}
RISK_LEVEL_LABELS: dict[str, str] = {
"low": "低风险",
"medium": "中风险",
"high": "高风险",
"critical": "极高风险",
}
EXPENSE_RISK_CATEGORY_CODES: tuple[str, ...] = (
"all",
"travel",
"hotel",
"transport",
"meal",
"meeting",
"office",
"training",
"communication",
"welfare",
)
EXPENSE_RISK_CATEGORY_LABELS: dict[str, str] = {
"all": "全部",
**{
code: EXPENSE_TYPE_LABEL_BY_CODE[code]
for code in EXPENSE_RISK_CATEGORY_CODES
if code != "all"
},
}
EXPENSE_RISK_CATEGORY_ALIASES = {
"*": "all",
"overall": "all",
"general": "all",
"全部": "all",
"通用": "all",
"entertainment": "meal",
"business_meal": "meal",
"purchase": "office",
}
EXPENSE_BUSINESS_STAGE_LABELS: dict[str, str] = {
"expense_application": "费用申请",
"reimbursement": "费用报销",
}
FIELD_ONTOLOGY: tuple[RiskRuleField, ...] = (
RiskRuleField("claim.reason", "报销事由", "text", "claim", ("事由", "说明", "理由", "用途")),
RiskRuleField(
"claim.location",
"申报地点",
"text",
"claim",
("地点", "城市", "出差地", "申报地点", "申报目的地", "目的地"),
),
RiskRuleField(
"claim.trip_start_date",
"出差开始日期",
"date",
"claim",
("出差开始", "行程开始", "开始日期", "出差起始", "出发日期"),
),
RiskRuleField(
"claim.trip_end_date",
"出差结束日期",
"date",
"claim",
("出差结束", "行程结束", "结束日期", "返程日期", "返回日期"),
),
RiskRuleField("claim.amount", "申报金额", "number", "claim", ("金额", "费用", "超额", "额度")),
RiskRuleField("claim.attendee_count", "参与人数", "number", "claim", ("人数", "参与人员数", "招待人数")),
RiskRuleField("claim.per_capita_amount", "人均金额", "number", "claim", ("人均", "人均金额", "人均招待")),
RiskRuleField(
"budget.remaining_amount",
"预算可用余额",
"number",
"budget",
("预算余额", "可用预算", "可用余额", "剩余预算", "预算剩余"),
),
RiskRuleField(
"budget.limit_amount",
"预算额度",
"number",
"budget",
("预算额度", "预算上限", "预算阈值", "预算限额"),
),
RiskRuleField("claim.employee_name", "报销人", "text", "claim", ("报销人", "员工", "申请人")),
RiskRuleField("claim.department_name", "部门", "text", "claim", ("部门", "组织")),
RiskRuleField(
"employee.location",
"员工常驻地",
"text",
"employee",
("常驻地", "办公地", "员工所在地", "所在城市"),
),
RiskRuleField("item.item_type", "费用类型", "enum", "item", ("费用类型", "科目", "类型")),
RiskRuleField("item.item_reason", "明细事由", "text", "item", ("明细事由", "明细说明")),
RiskRuleField("item.item_location", "明细地点", "text", "item", ("明细地点", "发生地点")),
RiskRuleField("item.item_date", "明细发生日期", "date", "item", ("明细日期", "发生日期", "费用日期")),
RiskRuleField("item.invoice_id", "明细附件编号", "text", "item", ("附件编号", "票据编号", "发票附件")),
RiskRuleField(
"attachment.invoice_no", "发票号码", "text", "attachment", ("发票号", "发票号码", "票号")
),
RiskRuleField(
"attachment.buyer_name", "购买方名称", "text", "attachment", ("抬头", "购买方", "开票单位")
),
RiskRuleField(
"attachment.goods_name",
"商品服务名称",
"text",
"attachment",
("品名", "商品", "服务名称", "摘要"),
),
RiskRuleField(
"attachment.issue_date",
"开票日期",
"date",
"attachment",
("开票日期", "发票日期", "票据日期"),
),
RiskRuleField(
"attachment.stay_start_date",
"住宿开始日期",
"date",
"attachment",
("入住日期", "住宿开始", "入住时间", "住宿开始日期"),
),
RiskRuleField(
"attachment.stay_end_date",
"住宿结束日期",
"date",
"attachment",
("离店日期", "退房日期", "住宿结束", "住宿结束日期"),
),
RiskRuleField(
"attachment.hotel_city",
"住宿城市",
"text",
"attachment",
("住宿城市", "酒店城市", "酒店地点", "酒店发票城市", "酒店票城市", "住宿发票城市"),
),
RiskRuleField(
"attachment.route_cities",
"行程城市",
"list",
"attachment",
("行程", "路线", "途经城市", "出差城市", "交通票行程", "交通票城市"),
),
RiskRuleField(
"attachment.ocr_text",
"票据全文",
"text",
"attachment",
("票据内容", "OCR", "全文", "关键字", "关键词"),
),
RiskRuleField(
"receivable.aging_days", "应收账龄", "number", "receivable", ("账龄", "逾期", "应收逾期")
),
RiskRuleField(
"receivable.amount_outstanding",
"应收未收金额",
"number",
"receivable",
("未收金额", "欠款", "应收余额"),
),
RiskRuleField(
"payable.vendor_name", "供应商名称", "text", "payable", ("供应商", "付款方", "往来单位")
),
RiskRuleField(
"payable.amount_outstanding", "应付未付金额", "number", "payable", ("未付金额", "应付余额")
),
)
DOMAIN_FIELD_PREFIXES: dict[str, tuple[str, ...]] = {
AgentAssetDomain.EXPENSE.value: ("claim.", "item.", "attachment.", "employee.", "budget."),
AgentAssetDomain.AR.value: ("receivable.",),
AgentAssetDomain.AP.value: ("payable.",),
}