Files
group_fqcd_jr/docs/evidence/20260909-before-constraint-fix.sql
T
lzf_0626 6516ccb385 feat: 第二版——接口契约对齐 docs/05,修复静默故障与数据库基线
相对第一版 46fc976 的完整变更。组员迁移对照表见 docs/20。

一、对外契约对齐 docs/05(破坏性,共 4 处,组员需按 docs/20 调整)
1) 配置发布端点改为文档规定的复数资源名:submit→validations、
   approve→reviews(需 body decision)、activate→activations、
   rollback→rollbacks;第一版这 4 个动词式路径 docs/05 从未定义过。
2) 错误码由 8 个笼统码改为 15 个具体语义码(FORBIDDEN→AGENT_PERMISSION_DENIED、
   UNAUTHORIZED→AUTHENTICATION_REQUIRED、CONFLICT→RESOURCE_VERSION_CONFLICT、
   RESOURCE_NOT_FOUND→RUN_NOT_FOUND/SESSION_NOT_FOUND 等),
   输入类错误状态码 400→422。
3) POST /api/v1/agent-runs 与 GET /api/v1/agent-runs/{run_id} 统一为
   {data, meta} 信封(data 内字段名与语义未变)。
4) 错误响应体统一为 {error:{code,message,retryable,field_errors}, meta:{trace_id}},
   不再返回 FastAPI 默认的 {"detail": ...}。

二、数据库基线与约束
新增 39 张表的基线迁移(链根)与联合唯一键纠偏(4 张表、删 8 增 4,幂等收敛);
撤下 config_release 的双人复核 CHECK(应用层已允许自审,审核节点保留,
自审如实写入 reviewer_id);记忆 active key 生成列与唯一键;
activate 开始记录 supersedes_release_id 使版本链可追溯。
docs/00 基线未修改,未重命名或删除任何表与字段。

三、修复会静默出错或无报错的缺陷
- 跑完集成测试后平台会静默失去生效配置:清理只删自己创建的版本,却没有恢复被它
  顶成 superseded 的原生效版本,且审计一并删除因而完全无痕,表现为所有工具被拒
  但没有任何报错。已修清理逻辑并加恢复。
- Worker 单轮异常导致进程退出;记忆抽取调用方的“事务已开始”异常;
  召回缓存丢失 degraded 标记;连接时区未生效导致 created_at/updated_at 差 8 小时;
  .env 与 os.getenv 密钥来源分裂导致“没有可用的已批准模型端点”。
- 记忆信号识别漏判与跨键误命中;SSE 未带 Accept 的协商行为。

四、功能补齐
记忆链路 P1/P2/P3(抽取、受控词表、召回与缓存、生命周期级联及投影事件)、
fin_* 场内交易只读 ORM 层、agent_intent_config 状态流转并在运行期真正生效、
限流(Redis 固定窗口、故障一律放行)、游标校验、trace_id 中间件、
示例业务 Agent fund_query_demo 与一键端到端验证脚本,以及审计/指纹/迁移状态工具。

五、文档与验证
新增 docs/19(业务 Agent 接入实操)、docs/20(第一版迁移指南)与 docs/evidence 证据;
docs/01/02/06/08/09/17 同步实现现状。

验证结果:ruff 通过、mypy 103 文件无错、unit+contract 447 passed、
integration 29 passed、acceptance_check --production 7 PASS、
demo_agent_e2e 9/9 PASS(含失败关闭反证)。
2026-09-10 15:55:54 +08:00

1161 lines
52 KiB
SQL

-- jr schema snapshot: SHOW CREATE TABLE for every table
-- purpose: evidence for the 20260909 baseline constraint correction
SET FOREIGN_KEY_CHECKS=0;
CREATE TABLE `agent_faq_synonym` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`knowledge_id` bigint unsigned NOT NULL,
`phrase` varchar(500) NOT NULL,
`normalized_phrase` varchar(500) NOT NULL,
`phrase_hash` char(64) NOT NULL,
`language_code` varchar(16) NOT NULL DEFAULT 'zh-CN',
`source_type` varchar(24) NOT NULL DEFAULT 'manual',
`hit_count` bigint unsigned NOT NULL DEFAULT '0',
`status` varchar(16) NOT NULL DEFAULT 'pending',
`created_by` bigint unsigned NOT NULL,
`reviewer_id` bigint unsigned DEFAULT NULL,
`reviewed_at` datetime(6) DEFAULT NULL,
`created_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6),
`updated_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6) ON UPDATE CURRENT_TIMESTAMP(6),
PRIMARY KEY (`id`),
UNIQUE KEY `uk_faq_synonym` (`knowledge_id`,`phrase_hash`),
KEY `idx_faq_synonym_status` (`status`),
KEY `idx_faq_synonym_normalized` (`normalized_phrase`(191)),
KEY `fk_synonym_created_by` (`created_by`),
KEY `fk_synonym_reviewer` (`reviewer_id`),
CONSTRAINT `fk_synonym_created_by` FOREIGN KEY (`created_by`) REFERENCES `sys_user` (`id`),
CONSTRAINT `fk_synonym_knowledge` FOREIGN KEY (`knowledge_id`) REFERENCES `fin_knowledge_meta` (`id`),
CONSTRAINT `fk_synonym_reviewer` FOREIGN KEY (`reviewer_id`) REFERENCES `sys_user` (`id`),
CONSTRAINT `chk_synonym_source` CHECK ((`source_type` in (_utf8mb4'manual',_utf8mb4'conversation',_utf8mb4'ticket',_utf8mb4'import'))),
CONSTRAINT `chk_synonym_status` CHECK ((`status` in (_utf8mb4'pending',_utf8mb4'approved',_utf8mb4'disabled',_utf8mb4'archived')))
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci COMMENT='FAQ同义问法';
CREATE TABLE `agent_intent_config` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`agent_type` varchar(32) NOT NULL,
`intent_code` varchar(64) NOT NULL,
`intent_name` varchar(128) NOT NULL,
`description` varchar(500) DEFAULT NULL,
`examples` json NOT NULL,
`classifier_instruction` text,
`confidence_threshold` decimal(5,4) NOT NULL DEFAULT '0.6000',
`max_clarification_rounds` tinyint unsigned NOT NULL DEFAULT '2',
`transfer_on_failure` tinyint(1) NOT NULL DEFAULT '1',
`collection_routes` json DEFAULT NULL,
`allowed_tools` json DEFAULT NULL,
`priority` int NOT NULL DEFAULT '100',
`version` int unsigned NOT NULL DEFAULT '1',
`status` varchar(16) NOT NULL DEFAULT 'draft',
`active_key` varchar(128) GENERATED ALWAYS AS (if((`status` = _utf8mb4'active'),concat(`agent_type`,_utf8mb4':',`intent_code`),NULL)) STORED,
`effective_at` datetime(6) DEFAULT NULL,
`expire_at` datetime(6) DEFAULT NULL,
`created_by` bigint unsigned NOT NULL,
`reviewer_id` bigint unsigned DEFAULT NULL,
`reviewed_at` datetime(6) DEFAULT NULL,
`created_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6),
`updated_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6) ON UPDATE CURRENT_TIMESTAMP(6),
PRIMARY KEY (`id`),
UNIQUE KEY `uk_intent_config_version` (`agent_type`,`intent_code`,`version`),
UNIQUE KEY `uk_intent_config_active_one` (`active_key`),
KEY `idx_intent_config_active` (`agent_type`,`status`,`priority`),
KEY `fk_intent_created_by` (`created_by`),
KEY `fk_intent_reviewer` (`reviewer_id`),
CONSTRAINT `fk_intent_created_by` FOREIGN KEY (`created_by`) REFERENCES `sys_user` (`id`),
CONSTRAINT `fk_intent_reviewer` FOREIGN KEY (`reviewer_id`) REFERENCES `sys_user` (`id`),
CONSTRAINT `chk_intent_confidence` CHECK ((`confidence_threshold` between 0 and 1)),
CONSTRAINT `chk_intent_status` CHECK ((`status` in (_utf8mb4'draft',_utf8mb4'approved',_utf8mb4'active',_utf8mb4'archived'))),
CONSTRAINT `chk_intent_window` CHECK (((`expire_at` is null) or (`effective_at` is null) or (`expire_at` > `effective_at`)))
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci COMMENT='Agent意图路由配置';
CREATE TABLE `agent_negative_word` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`rule_code` varchar(64) NOT NULL,
`word_pattern` varchar(256) NOT NULL,
`match_type` varchar(16) NOT NULL DEFAULT 'contains',
`category` varchar(32) NOT NULL,
`severity` varchar(16) NOT NULL DEFAULT 'block',
`applicable_agents` json DEFAULT NULL,
`safe_reply_template_code` varchar(64) DEFAULT NULL,
`status` varchar(16) NOT NULL DEFAULT 'draft',
`version` int unsigned NOT NULL DEFAULT '1',
`created_by` bigint unsigned NOT NULL,
`reviewer_id` bigint unsigned DEFAULT NULL,
`reviewed_at` datetime(6) DEFAULT NULL,
`created_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6),
`updated_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6) ON UPDATE CURRENT_TIMESTAMP(6),
PRIMARY KEY (`id`),
UNIQUE KEY `uk_negative_rule_code` (`rule_code`),
KEY `idx_negative_status_category` (`status`,`category`),
KEY `idx_negative_reviewer` (`reviewer_id`),
KEY `fk_negative_created_by` (`created_by`),
CONSTRAINT `fk_negative_created_by` FOREIGN KEY (`created_by`) REFERENCES `sys_user` (`id`),
CONSTRAINT `fk_negative_reviewer` FOREIGN KEY (`reviewer_id`) REFERENCES `sys_user` (`id`),
CONSTRAINT `chk_negative_match_type` CHECK ((`match_type` in (_utf8mb4'exact',_utf8mb4'contains',_utf8mb4'regex'))),
CONSTRAINT `chk_negative_severity` CHECK ((`severity` in (_utf8mb4'warn',_utf8mb4'regenerate',_utf8mb4'block'))),
CONSTRAINT `chk_negative_status` CHECK ((`status` in (_utf8mb4'draft',_utf8mb4'active',_utf8mb4'disabled',_utf8mb4'archived')))
) ENGINE=InnoDB AUTO_INCREMENT=12 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci COMMENT='Agent禁止表达配置';
CREATE TABLE `agent_reply_template` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`template_code` varchar(64) NOT NULL,
`scene` varchar(32) NOT NULL,
`title` varchar(128) NOT NULL,
`content_text` mediumtext NOT NULL,
`variables` json DEFAULT NULL,
`locale` varchar(16) NOT NULL DEFAULT 'zh-CN',
`version` int unsigned NOT NULL DEFAULT '1',
`status` varchar(16) NOT NULL DEFAULT 'draft',
`active_key` varchar(128) GENERATED ALWAYS AS (if((`status` = _utf8mb4'active'),concat(`template_code`,_utf8mb4':',`locale`),NULL)) STORED,
`effective_at` datetime(6) DEFAULT NULL,
`expire_at` datetime(6) DEFAULT NULL,
`created_by` bigint unsigned NOT NULL,
`reviewer_id` bigint unsigned DEFAULT NULL,
`reviewed_at` datetime(6) DEFAULT NULL,
`created_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6),
`updated_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6) ON UPDATE CURRENT_TIMESTAMP(6),
PRIMARY KEY (`id`),
UNIQUE KEY `uk_reply_template_version` (`template_code`,`version`),
UNIQUE KEY `uk_reply_template_active_one` (`active_key`),
KEY `idx_reply_template_active` (`scene`,`status`,`effective_at`,`expire_at`),
KEY `fk_template_created_by` (`created_by`),
KEY `fk_template_reviewer` (`reviewer_id`),
CONSTRAINT `fk_template_created_by` FOREIGN KEY (`created_by`) REFERENCES `sys_user` (`id`),
CONSTRAINT `fk_template_reviewer` FOREIGN KEY (`reviewer_id`) REFERENCES `sys_user` (`id`),
CONSTRAINT `chk_template_scene` CHECK ((`scene` in (_utf8mb4'disclaimer',_utf8mb4'low_confidence',_utf8mb4'compliance_block',_utf8mb4'transfer',_utf8mb4'model_failure',_utf8mb4'system_busy',_utf8mb4'clarification'))),
CONSTRAINT `chk_template_status` CHECK ((`status` in (_utf8mb4'draft',_utf8mb4'approved',_utf8mb4'active',_utf8mb4'archived'))),
CONSTRAINT `chk_template_window` CHECK (((`expire_at` is null) or (`effective_at` is null) or (`expire_at` > `effective_at`)))
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci COMMENT='Agent回复模板';
CREATE TABLE `agent_run` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`run_id` char(36) NOT NULL,
`idempotency_id` bigint unsigned NOT NULL,
`session_id` varchar(64) NOT NULL,
`user_id` bigint unsigned NOT NULL,
`agent_type` varchar(32) NOT NULL,
`trace_id` varchar(64) NOT NULL,
`request_message_id` bigint unsigned NOT NULL,
`result_message_id` bigint unsigned DEFAULT NULL,
`status` varchar(24) NOT NULL DEFAULT 'queued',
`attempt_count` int unsigned NOT NULL DEFAULT '0',
`worker_id` varchar(128) DEFAULT NULL,
`locked_until` datetime(6) DEFAULT NULL,
`result_version` int unsigned DEFAULT NULL,
`error_code` varchar(64) DEFAULT NULL,
`cancel_requested_at` datetime(6) DEFAULT NULL,
`started_at` datetime(6) DEFAULT NULL,
`completed_at` datetime(6) DEFAULT NULL,
`created_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6),
`updated_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6) ON UPDATE CURRENT_TIMESTAMP(6),
PRIMARY KEY (`id`),
UNIQUE KEY `uk_agent_run_id` (`run_id`),
UNIQUE KEY `uk_agent_run_idempotency` (`idempotency_id`),
UNIQUE KEY `uk_agent_run_trace` (`trace_id`),
KEY `idx_agent_run_worker_lease` (`status`,`locked_until`),
CONSTRAINT `chk_agent_run_status` CHECK ((`status` in (_utf8mb4'queued',_utf8mb4'running',_utf8mb4'succeeded',_utf8mb4'failed',_utf8mb4'cancel_requested',_utf8mb4'cancelled')))
) ENGINE=InnoDB AUTO_INCREMENT=488 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `alembic_version` (
`version_num` varchar(32) NOT NULL,
PRIMARY KEY (`version_num`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `api_request_receipt` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`user_id` bigint unsigned NOT NULL,
`scope_hash` char(64) NOT NULL,
`idempotency_key` varchar(128) NOT NULL,
`request_hash` char(64) NOT NULL,
`response_json` json DEFAULT NULL,
`created_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6),
PRIMARY KEY (`id`),
UNIQUE KEY `uk_api_receipt` (`user_id`,`scope_hash`,`idempotency_key`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `biz_work_order` (
`id` bigint unsigned NOT NULL,
`work_order_no` varchar(64) NOT NULL,
`customer_id` bigint unsigned NOT NULL,
`order_type` varchar(16) DEFAULT NULL,
`product_id` bigint unsigned DEFAULT NULL,
`amount` decimal(18,2) DEFAULT NULL,
`channel` varchar(32) DEFAULT NULL,
`advisor_id` bigint unsigned DEFAULT NULL,
`risk_rule_hits` json DEFAULT NULL,
`risk_disclosure_ack_at` datetime DEFAULT NULL,
`second_confirmation_at` datetime DEFAULT NULL,
`recording_reference` varchar(64) DEFAULT NULL,
`ops_handler_id` bigint unsigned DEFAULT NULL,
`ops_handled_at` datetime DEFAULT NULL,
`compliance_handler_id` bigint unsigned DEFAULT NULL,
`compliance_handled_at` datetime DEFAULT NULL,
`reject_reason` text,
`alert_id` bigint unsigned DEFAULT NULL,
`work_order_type` varchar(32) DEFAULT NULL,
`submitter_id` bigint unsigned DEFAULT NULL,
`handler_id` bigint unsigned DEFAULT NULL,
`priority` varchar(8) DEFAULT NULL,
`status` varchar(24) NOT NULL DEFAULT '待风控扫描',
`request_detail` json DEFAULT NULL,
`handle_result` json DEFAULT NULL,
`submitted_at` datetime DEFAULT NULL,
`accepted_at` datetime DEFAULT NULL,
`completed_at` datetime DEFAULT NULL,
`created_at` datetime NOT NULL,
`updated_at` datetime NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `uk_biz_work_order_work_order_no` (`work_order_no`),
KEY `idx_biz_work_order_customer_id` (`customer_id`),
KEY `idx_biz_work_order_product_id` (`product_id`),
KEY `idx_biz_work_order_advisor_id` (`advisor_id`),
KEY `idx_biz_work_order_alert_id` (`alert_id`),
KEY `idx_biz_work_order_work_order_type` (`work_order_type`),
KEY `idx_biz_work_order_submitter_id` (`submitter_id`),
KEY `idx_biz_work_order_handler_id` (`handler_id`),
KEY `idx_biz_work_order_priority` (`priority`),
KEY `idx_biz_work_order_status` (`status`),
KEY `idx_biz_work_order_submitted_at` (`submitted_at`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `client_facing_content` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`customer_id` bigint unsigned NOT NULL,
`content_type` varchar(32) NOT NULL,
`draft_content` json NOT NULL,
`generated_by_portal` varchar(32) NOT NULL,
`review_status` varchar(16) NOT NULL,
`reviewer_user_id` bigint unsigned DEFAULT NULL,
`reviewed_at` datetime DEFAULT NULL,
`published_at` datetime DEFAULT NULL,
`created_at` datetime NOT NULL,
`updated_at` datetime NOT NULL,
PRIMARY KEY (`id`),
KEY `idx_content_customer_status` (`customer_id`,`review_status`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `config_release` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`release_no` varchar(64) NOT NULL,
`title` varchar(128) NOT NULL,
`change_summary` varchar(1000) NOT NULL,
`status` varchar(20) NOT NULL DEFAULT 'draft',
`created_by` bigint unsigned NOT NULL,
`reviewer_id` bigint unsigned DEFAULT NULL,
`reviewed_at` datetime(6) DEFAULT NULL,
`activated_at` datetime(6) DEFAULT NULL,
`supersedes_release_id` bigint unsigned DEFAULT NULL,
`rollback_of_release_id` bigint unsigned DEFAULT NULL,
`active_slot` tinyint GENERATED ALWAYS AS (if((`status` = _utf8mb4'active'),1,NULL)) STORED,
`created_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6),
`updated_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6) ON UPDATE CURRENT_TIMESTAMP(6),
PRIMARY KEY (`id`),
UNIQUE KEY `uk_config_release_no` (`release_no`),
UNIQUE KEY `uk_config_release_active_one` (`active_slot`),
CONSTRAINT `chk_config_release_separation` CHECK (((`reviewer_id` is null) or (`reviewer_id` <> `created_by`))),
CONSTRAINT `chk_config_release_status` CHECK ((`status` in (_utf8mb4'draft',_utf8mb4'validating',_utf8mb4'pending_review',_utf8mb4'approved',_utf8mb4'active',_utf8mb4'superseded',_utf8mb4'rejected',_utf8mb4'rolled_back')))
) ENGINE=InnoDB AUTO_INCREMENT=54 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `conversation_feedback` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`feedback_no` varchar(32) NOT NULL,
`session_id` varchar(64) NOT NULL,
`message_id` bigint unsigned NOT NULL,
`customer_id` bigint unsigned DEFAULT NULL,
`rating` tinyint NOT NULL,
`feedback_type` varchar(32) DEFAULT NULL,
`feedback_content` varchar(1000) DEFAULT NULL,
`status` varchar(16) NOT NULL DEFAULT 'open',
`handler_id` bigint unsigned DEFAULT NULL,
`handled_at` datetime(6) DEFAULT NULL,
`handling_note` varchar(1000) DEFAULT NULL,
`created_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6),
`updated_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6) ON UPDATE CURRENT_TIMESTAMP(6),
PRIMARY KEY (`id`),
UNIQUE KEY `uk_feedback_no` (`feedback_no`),
UNIQUE KEY `uk_feedback_message_customer` (`message_id`,`customer_id`),
KEY `idx_feedback_session` (`session_id`,`created_at`),
KEY `idx_feedback_status_type` (`status`,`feedback_type`),
KEY `fk_feedback_customer` (`customer_id`),
KEY `fk_feedback_handler` (`handler_id`),
CONSTRAINT `fk_feedback_customer` FOREIGN KEY (`customer_id`) REFERENCES `sys_user` (`id`),
CONSTRAINT `fk_feedback_handler` FOREIGN KEY (`handler_id`) REFERENCES `sys_user` (`id`),
CONSTRAINT `fk_feedback_message` FOREIGN KEY (`message_id`) REFERENCES `conversation_message` (`id`),
CONSTRAINT `chk_feedback_rating` CHECK ((`rating` in (-(1),1))),
CONSTRAINT `chk_feedback_status` CHECK ((`status` in (_utf8mb4'open',_utf8mb4'reviewed',_utf8mb4'resolved',_utf8mb4'ignored')))
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci COMMENT='对话回复反馈';
CREATE TABLE `conversation_message` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`session_id` varchar(64) NOT NULL,
`message_no` int DEFAULT NULL,
`customer_id` bigint unsigned DEFAULT NULL,
`portal` varchar(32) NOT NULL,
`role` varchar(16) NOT NULL,
`content` mediumtext NOT NULL,
`tool_calls` json DEFAULT NULL,
`trace_id` varchar(64) DEFAULT NULL,
`intent` varchar(32) DEFAULT NULL,
`confidence` decimal(5,4) DEFAULT NULL,
`source_references` json DEFAULT NULL,
`created_at` datetime NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `uk_message_session_no` (`session_id`,`message_no`),
KEY `idx_message_customer_created` (`customer_id`,`created_at`)
) ENGINE=InnoDB AUTO_INCREMENT=941 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `domain_event_outbox` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`event_id` char(36) NOT NULL,
`event_type` varchar(64) NOT NULL,
`aggregate_type` varchar(32) NOT NULL,
`aggregate_id` varchar(64) NOT NULL,
`trace_id` varchar(64) NOT NULL,
`payload` json NOT NULL,
`status` varchar(16) NOT NULL DEFAULT 'pending',
`retry_count` int unsigned NOT NULL DEFAULT '0',
`next_retry_at` datetime(6) DEFAULT NULL,
`last_error` varchar(500) DEFAULT NULL,
`occurred_at` datetime(6) NOT NULL,
`published_at` datetime(6) DEFAULT NULL,
`created_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6),
`updated_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6) ON UPDATE CURRENT_TIMESTAMP(6),
PRIMARY KEY (`id`),
UNIQUE KEY `uk_domain_event_id` (`event_id`),
KEY `idx_domain_outbox_pending` (`status`,`next_retry_at`,`id`),
CONSTRAINT `chk_domain_outbox_status` CHECK ((`status` in (_utf8mb4'pending',_utf8mb4'published',_utf8mb4'failed',_utf8mb4'dead')))
) ENGINE=InnoDB AUTO_INCREMENT=675 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `episodes` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`episode_uuid` char(36) DEFAULT NULL,
`customer_id` bigint unsigned NOT NULL,
`session_id` varchar(64) NOT NULL,
`start_message_no` int DEFAULT NULL,
`end_message_no` int DEFAULT NULL,
`portals_involved` json NOT NULL,
`summary` text NOT NULL,
`extraction_status` varchar(16) NOT NULL DEFAULT '待提取',
`content_hash` char(64) DEFAULT NULL,
`retry_count` int NOT NULL DEFAULT '0',
`started_at` datetime DEFAULT NULL,
`ended_at` datetime DEFAULT NULL,
`handoff_to_employee_id` bigint unsigned DEFAULT NULL,
`start_at` datetime DEFAULT NULL,
`end_at` datetime DEFAULT NULL,
`promoted_to_ltm` tinyint(1) NOT NULL DEFAULT '0',
`created_at` datetime NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `episode_uuid` (`episode_uuid`),
UNIQUE KEY `content_hash` (`content_hash`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `fin_capital_flow` (
`id` bigint unsigned NOT NULL,
`flow_no` varchar(64) NOT NULL,
`customer_id` bigint unsigned NOT NULL,
`account_id` bigint unsigned DEFAULT NULL,
`transaction_id` bigint unsigned DEFAULT NULL,
`flow_type` varchar(16) NOT NULL,
`amount` decimal(18,2) NOT NULL,
`balance_after` decimal(18,2) DEFAULT NULL,
`status` varchar(16) NOT NULL,
`settled_at` datetime DEFAULT NULL,
`occurred_at` datetime DEFAULT NULL,
`payer_name` varchar(64) DEFAULT NULL,
`source_type` varchar(16) NOT NULL,
`related_work_order_id` bigint unsigned DEFAULT NULL,
`match_status` varchar(16) NOT NULL DEFAULT '不适用',
`created_at` datetime NOT NULL,
`updated_at` datetime NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `uk_fin_capital_flow_flow_no` (`flow_no`),
KEY `idx_fin_capital_flow_customer_id` (`customer_id`),
KEY `idx_fin_capital_flow_account_id` (`account_id`),
KEY `idx_fin_capital_flow_transaction_id` (`transaction_id`),
KEY `idx_fin_capital_flow_status` (`status`),
KEY `idx_fin_capital_flow_settled_at` (`settled_at`),
KEY `idx_fin_capital_flow_occurred_at` (`occurred_at`),
KEY `idx_fin_capital_flow_related_work_order_id` (`related_work_order_id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `fin_cash_ledger` (
`id` bigint unsigned NOT NULL,
`ledger_no` varchar(64) NOT NULL,
`account_id` bigint unsigned NOT NULL,
`transaction_id` bigint unsigned DEFAULT NULL,
`entry_type` varchar(24) NOT NULL,
`amount` decimal(18,2) NOT NULL,
`balance_after` decimal(18,2) NOT NULL,
`available_cash_after` decimal(18,2) NOT NULL,
`frozen_cash_after` decimal(18,2) NOT NULL,
`idempotency_key` varchar(128) NOT NULL,
`occurred_at` datetime NOT NULL,
`created_at` datetime NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `uk_fin_cash_ledger_ledger_no` (`ledger_no`),
UNIQUE KEY `uk_fin_cash_ledger_idempotency_key` (`idempotency_key`),
KEY `idx_fin_cash_ledger_account_id` (`account_id`),
KEY `idx_fin_cash_ledger_transaction_id` (`transaction_id`),
KEY `idx_fin_cash_ledger_occurred_at` (`occurred_at`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `fin_customer_profile` (
`customer_id` bigint unsigned NOT NULL,
`trade_account` varchar(32) NOT NULL,
`real_name` varchar(64) NOT NULL,
`birth_date` date DEFAULT NULL,
`occupation` varchar(64) DEFAULT NULL,
`mobile_masked` varchar(32) DEFAULT NULL,
`investor_type` varchar(8) NOT NULL,
`investment_horizon` varchar(32) DEFAULT NULL,
`preferred_asset_class` json DEFAULT NULL,
`trading_frequency` varchar(32) DEFAULT NULL,
`last_active_at` datetime DEFAULT NULL,
`total_asset` decimal(18,2) NOT NULL,
`behavior_score` int NOT NULL,
`risk_tags` json DEFAULT NULL,
`opened_at` datetime DEFAULT NULL,
`updated_at` datetime NOT NULL,
PRIMARY KEY (`customer_id`),
UNIQUE KEY `uk_fin_customer_profile_trade_account` (`trade_account`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `fin_fee_rule` (
`id` bigint unsigned NOT NULL,
`rule_code` varchar(64) NOT NULL,
`product_id` bigint unsigned DEFAULT NULL,
`exchange_code` varchar(16) DEFAULT NULL,
`order_side` varchar(8) NOT NULL,
`customer_tier` varchar(16) DEFAULT NULL,
`min_trade_amount` decimal(18,2) DEFAULT NULL,
`max_trade_amount` decimal(18,2) DEFAULT NULL,
`fee_rate` decimal(10,6) NOT NULL,
`minimum_fee` decimal(18,2) NOT NULL DEFAULT '0.00',
`fixed_fee` decimal(18,2) NOT NULL DEFAULT '0.00',
`priority` int NOT NULL DEFAULT '0',
`effective_from` datetime NOT NULL,
`effective_until` datetime DEFAULT NULL,
`status` varchar(16) NOT NULL,
`created_at` datetime NOT NULL,
`updated_at` datetime NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `uk_fin_fee_rule_rule_code` (`rule_code`),
KEY `idx_fin_fee_rule_product_id` (`product_id`),
KEY `idx_fin_fee_rule_exchange_code` (`exchange_code`),
KEY `idx_fin_fee_rule_customer_tier` (`customer_tier`),
KEY `idx_fin_fee_rule_status` (`status`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `fin_holding` (
`id` bigint unsigned NOT NULL,
`customer_id` bigint unsigned NOT NULL,
`trade_account` varchar(32) NOT NULL,
`product_id` bigint unsigned NOT NULL,
`total_quantity` decimal(18,4) NOT NULL,
`shares` decimal(18,4) NOT NULL,
`available_quantity` decimal(18,4) NOT NULL,
`frozen_quantity` decimal(18,4) NOT NULL DEFAULT '0.0000',
`average_cost` decimal(18,6) NOT NULL,
`cost_amount` decimal(18,2) NOT NULL,
`market_value` decimal(18,2) DEFAULT NULL,
`current_value` decimal(18,2) NOT NULL,
`profit_loss` decimal(18,2) DEFAULT NULL,
`profit_loss_ratio` decimal(10,4) DEFAULT NULL,
`status` varchar(16) NOT NULL,
`first_acquired_at` datetime DEFAULT NULL,
`version` bigint unsigned NOT NULL DEFAULT '0',
`updated_at` datetime NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `uk_fin_holding_customer_id` (`customer_id`),
UNIQUE KEY `uk_fin_holding_product_id` (`product_id`),
KEY `idx_fin_holding_trade_account` (`trade_account`),
KEY `idx_fin_holding_status` (`status`),
KEY `idx_fin_holding_first_acquired_at` (`first_acquired_at`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `fin_knowledge_meta` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`knowledge_type` varchar(32) NOT NULL,
`title` varchar(256) NOT NULL,
`source_file` varchar(256) DEFAULT NULL,
`minio_path` varchar(512) DEFAULT NULL,
`milvus_collection` varchar(64) NOT NULL,
`version` varchar(16) DEFAULT NULL,
`effective_date` date DEFAULT NULL,
`expire_date` date DEFAULT NULL,
`content_text` mediumtext NOT NULL,
`tags` json DEFAULT NULL,
`reviewer_id` bigint unsigned DEFAULT NULL,
`review_status` varchar(16) NOT NULL DEFAULT 'pending',
`status` varchar(16) NOT NULL,
`created_at` datetime NOT NULL,
`updated_at` datetime NOT NULL,
PRIMARY KEY (`id`),
KEY `idx_knowledge_status` (`status`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `fin_market_price` (
`id` bigint unsigned NOT NULL,
`product_id` bigint unsigned NOT NULL,
`trade_date` date NOT NULL,
`open_price` decimal(18,6) NOT NULL,
`high_price` decimal(18,6) NOT NULL,
`low_price` decimal(18,6) NOT NULL,
`close_price` decimal(18,6) NOT NULL,
`volume` decimal(24,4) DEFAULT NULL,
`turnover_amount` decimal(24,2) DEFAULT NULL,
`total_fund_shares` decimal(24,4) NOT NULL,
`source` varchar(32) NOT NULL,
`source_updated_at` datetime NOT NULL,
`created_at` datetime NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `uk_fin_market_price_product_id` (`product_id`),
UNIQUE KEY `uk_fin_market_price_trade_date` (`trade_date`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `fin_nav_history` (
`id` bigint unsigned NOT NULL,
`product_id` bigint unsigned NOT NULL,
`nav_date` date NOT NULL,
`nav` decimal(12,6) NOT NULL,
`created_at` datetime NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `uk_fin_nav_history_product_id` (`product_id`),
UNIQUE KEY `uk_fin_nav_history_nav_date` (`nav_date`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `fin_product` (
`id` bigint unsigned NOT NULL,
`product_code` varchar(32) NOT NULL,
`product_name` varchar(128) NOT NULL,
`exchange_code` varchar(16) NOT NULL,
`product_category` varchar(32) NOT NULL,
`risk_level` varchar(8) NOT NULL,
`fund_manager` varchar(64) DEFAULT NULL,
`currency` varchar(8) NOT NULL DEFAULT 'CNY',
`lot_size` decimal(18,4) NOT NULL,
`price_tick` decimal(18,6) NOT NULL,
`current_nav` decimal(18,6) DEFAULT NULL,
`current_nav_at` datetime DEFAULT NULL,
`min_amount` decimal(18,2) NOT NULL DEFAULT '0.00',
`open_start_at` datetime DEFAULT NULL,
`open_end_at` datetime DEFAULT NULL,
`open_period_start` date DEFAULT NULL,
`open_period_end` date DEFAULT NULL,
`transaction_fee_rate` decimal(10,6) DEFAULT NULL,
`single_investor_max_holding_ratio` decimal(7,4) NOT NULL DEFAULT '100.0000',
`management_fee_rate` decimal(7,4) DEFAULT NULL,
`custodian_fee_rate` decimal(7,4) DEFAULT NULL,
`risk_disclosure_required` tinyint(1) NOT NULL DEFAULT '0',
`second_confirmation_required` tinyint(1) NOT NULL DEFAULT '0',
`recording_required` tinyint(1) NOT NULL DEFAULT '0',
`status` varchar(16) NOT NULL,
`created_at` datetime NOT NULL,
`updated_at` datetime NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `uk_fin_product_product_code` (`product_code`),
KEY `idx_fin_product_exchange_code` (`exchange_code`),
KEY `idx_fin_product_product_category` (`product_category`),
KEY `idx_fin_product_risk_level` (`risk_level`),
KEY `idx_fin_product_status` (`status`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `fin_risk_alert` (
`id` bigint unsigned NOT NULL,
`alert_no` varchar(64) NOT NULL,
`customer_id` bigint unsigned NOT NULL,
`related_transaction_id` bigint unsigned DEFAULT NULL,
`related_order_id` bigint unsigned DEFAULT NULL,
`related_work_order_id` bigint unsigned DEFAULT NULL,
`primary_risk_work_order_id` bigint unsigned DEFAULT NULL,
`alert_type` varchar(64) NOT NULL,
`alert_level` varchar(8) NOT NULL,
`trigger_rule_codes` json NOT NULL,
`evidence_summary` text NOT NULL,
`evidence_snapshot` json NOT NULL,
`priority_score` int NOT NULL,
`event_status` varchar(16) NOT NULL,
`status` varchar(16) NOT NULL,
`ack_status` varchar(16) NOT NULL,
`ack_at` datetime DEFAULT NULL,
`handler_id` bigint unsigned DEFAULT NULL,
`due_at` datetime DEFAULT NULL,
`is_escalated` tinyint(1) NOT NULL DEFAULT '0',
`escalated_at` datetime DEFAULT NULL,
`escalation_reason` text,
`handle_result` text,
`closed_at` datetime DEFAULT NULL,
`close_reason` text,
`ai_analysis` json DEFAULT NULL,
`manual_remark` text,
`created_at` datetime NOT NULL,
`updated_at` datetime NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `uk_fin_risk_alert_alert_no` (`alert_no`),
KEY `idx_fin_risk_alert_customer_id` (`customer_id`),
KEY `idx_fin_risk_alert_related_transaction_id` (`related_transaction_id`),
KEY `idx_fin_risk_alert_related_order_id` (`related_order_id`),
KEY `idx_fin_risk_alert_related_work_order_id` (`related_work_order_id`),
KEY `idx_fin_risk_alert_primary_risk_work_order_id` (`primary_risk_work_order_id`),
KEY `idx_fin_risk_alert_alert_type` (`alert_type`),
KEY `idx_fin_risk_alert_alert_level` (`alert_level`),
KEY `idx_fin_risk_alert_priority_score` (`priority_score`),
KEY `idx_fin_risk_alert_status` (`status`),
KEY `idx_fin_risk_alert_handler_id` (`handler_id`),
KEY `idx_fin_risk_alert_due_at` (`due_at`),
KEY `idx_fin_risk_alert_created_at` (`created_at`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `fin_risk_assessment` (
`id` bigint unsigned NOT NULL,
`customer_id` bigint unsigned NOT NULL,
`questionnaire_version` varchar(32) NOT NULL,
`answers` json NOT NULL,
`total_score` int NOT NULL,
`investor_type` varchar(8) NOT NULL,
`assessed_at` datetime NOT NULL,
`valid_until` datetime NOT NULL,
`created_at` datetime NOT NULL,
PRIMARY KEY (`id`),
KEY `idx_fin_risk_assessment_customer_id` (`customer_id`),
KEY `idx_fin_risk_assessment_questionnaire_version` (`questionnaire_version`),
KEY `idx_fin_risk_assessment_valid_until` (`valid_until`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `fin_risk_notification` (
`id` bigint unsigned NOT NULL,
`notification_no` varchar(64) NOT NULL,
`alert_id` bigint unsigned NOT NULL,
`channel` varchar(16) NOT NULL,
`receiver_user_id` bigint unsigned DEFAULT NULL,
`receiver_email` varchar(128) DEFAULT NULL,
`title` varchar(128) NOT NULL,
`content` text NOT NULL,
`send_status` varchar(16) NOT NULL,
`sent_at` datetime DEFAULT NULL,
`read_at` datetime DEFAULT NULL,
`acknowledged_at` datetime DEFAULT NULL,
`fail_reason` text,
`created_at` datetime NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `uk_fin_risk_notification_notification_no` (`notification_no`),
KEY `idx_fin_risk_notification_alert_id` (`alert_id`),
KEY `idx_fin_risk_notification_channel` (`channel`),
KEY `idx_fin_risk_notification_receiver_user_id` (`receiver_user_id`),
KEY `idx_fin_risk_notification_send_status` (`send_status`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `fin_sim_account` (
`id` bigint unsigned NOT NULL,
`account_no` varchar(32) NOT NULL,
`customer_id` bigint unsigned NOT NULL,
`currency` varchar(8) NOT NULL DEFAULT 'CNY',
`cash_balance` decimal(18,2) NOT NULL,
`available_cash` decimal(18,2) NOT NULL,
`frozen_cash` decimal(18,2) NOT NULL DEFAULT '0.00',
`initial_balance` decimal(18,2) NOT NULL,
`status` varchar(16) NOT NULL,
`version` bigint unsigned NOT NULL DEFAULT '0',
`created_at` datetime NOT NULL,
`updated_at` datetime NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `uk_fin_sim_account_account_no` (`account_no`),
UNIQUE KEY `uk_fin_sim_account_customer_id` (`customer_id`),
KEY `idx_fin_sim_account_status` (`status`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `fin_sim_order` (
`id` bigint unsigned NOT NULL,
`order_no` varchar(64) NOT NULL,
`customer_id` bigint unsigned NOT NULL,
`account_id` bigint unsigned NOT NULL,
`product_id` bigint unsigned NOT NULL,
`order_side` varchar(8) NOT NULL,
`price_type` varchar(8) NOT NULL,
`quantity` decimal(18,4) NOT NULL,
`limit_price` decimal(18,6) DEFAULT NULL,
`quote_price` decimal(18,6) NOT NULL,
`quote_at` datetime NOT NULL,
`quote_source` varchar(32) NOT NULL,
`channel` varchar(32) DEFAULT NULL,
`advisor_id` bigint unsigned DEFAULT NULL,
`filled_quantity` decimal(18,4) NOT NULL DEFAULT '0.0000',
`average_executed_price` decimal(18,6) DEFAULT NULL,
`status` varchar(24) NOT NULL,
`risk_rule_hits` json DEFAULT NULL,
`risk_disclosure_ack_at` datetime DEFAULT NULL,
`second_confirmation_at` datetime DEFAULT NULL,
`recording_reference` varchar(64) DEFAULT NULL,
`ops_handler_id` bigint unsigned DEFAULT NULL,
`ops_handled_at` datetime DEFAULT NULL,
`compliance_handler_id` bigint unsigned DEFAULT NULL,
`compliance_handled_at` datetime DEFAULT NULL,
`reject_reason` text,
`submitted_at` datetime NOT NULL,
`cancelled_at` datetime DEFAULT NULL,
`created_at` datetime NOT NULL,
`updated_at` datetime NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `uk_fin_sim_order_order_no` (`order_no`),
KEY `idx_fin_sim_order_customer_id` (`customer_id`),
KEY `idx_fin_sim_order_account_id` (`account_id`),
KEY `idx_fin_sim_order_product_id` (`product_id`),
KEY `idx_fin_sim_order_advisor_id` (`advisor_id`),
KEY `idx_fin_sim_order_status` (`status`),
KEY `idx_fin_sim_order_submitted_at` (`submitted_at`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `fin_transaction` (
`id` bigint unsigned NOT NULL,
`transaction_no` varchar(64) NOT NULL,
`order_id` bigint unsigned NOT NULL,
`work_order_id` bigint unsigned DEFAULT NULL,
`customer_id` bigint unsigned NOT NULL,
`account_id` bigint unsigned NOT NULL,
`product_id` bigint unsigned NOT NULL,
`order_side` varchar(8) NOT NULL,
`transaction_type` varchar(16) NOT NULL,
`executed_price` decimal(18,6) NOT NULL,
`nav` decimal(12,6) NOT NULL,
`executed_quantity` decimal(18,4) NOT NULL,
`shares` decimal(18,4) NOT NULL,
`gross_amount` decimal(18,2) NOT NULL,
`amount` decimal(18,2) NOT NULL,
`fee_rule_id` bigint unsigned DEFAULT NULL,
`fee_rate_snapshot` decimal(10,6) NOT NULL,
`fee_amount` decimal(18,2) NOT NULL,
`fee` decimal(18,2) DEFAULT NULL,
`net_amount` decimal(18,2) NOT NULL,
`quote_at` datetime NOT NULL,
`quote_source` varchar(32) NOT NULL,
`executed_at` datetime NOT NULL,
`confirmed_at` datetime NOT NULL,
`confirmed_by` int DEFAULT NULL,
`auto_confirmed` tinyint(1) NOT NULL DEFAULT '0',
`created_at` datetime NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `uk_fin_transaction_transaction_no` (`transaction_no`),
UNIQUE KEY `uk_fin_transaction_work_order_id` (`work_order_id`),
KEY `idx_fin_transaction_order_id` (`order_id`),
KEY `idx_fin_transaction_customer_id` (`customer_id`),
KEY `idx_fin_transaction_account_id` (`account_id`),
KEY `idx_fin_transaction_product_id` (`product_id`),
KEY `idx_fin_transaction_transaction_type` (`transaction_type`),
KEY `idx_fin_transaction_fee_rule_id` (`fee_rule_id`),
KEY `idx_fin_transaction_executed_at` (`executed_at`),
KEY `idx_fin_transaction_confirmed_at` (`confirmed_at`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `interaction_audit` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`actor_type` varchar(16) NOT NULL,
`actor_id` bigint unsigned DEFAULT NULL,
`target_customer_id` bigint unsigned DEFAULT NULL,
`session_id` varchar(64) DEFAULT NULL,
`portal` varchar(32) DEFAULT NULL,
`action_type` varchar(64) NOT NULL,
`detail` json NOT NULL,
`created_at` datetime NOT NULL,
PRIMARY KEY (`id`),
KEY `idx_audit_actor` (`actor_type`,`actor_id`,`created_at`),
KEY `idx_audit_customer` (`target_customer_id`,`created_at`)
) ENGINE=InnoDB AUTO_INCREMENT=282 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `memory_conflict` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`left_memory_id` bigint unsigned NOT NULL,
`right_memory_id` bigint unsigned NOT NULL,
`conflict_type` varchar(24) NOT NULL,
`severity` varchar(8) NOT NULL,
`status` varchar(16) NOT NULL,
`resolution` text,
`winner_memory_id` bigint unsigned DEFAULT NULL,
`resolved_by` bigint unsigned DEFAULT NULL,
`resolved_at` datetime DEFAULT NULL,
`created_at` datetime NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `memory_evidence` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`memory_id` bigint unsigned NOT NULL,
`evidence_type` varchar(24) NOT NULL,
`source_table` varchar(64) DEFAULT NULL,
`source_record_id` varchar(64) DEFAULT NULL,
`source_episode_id` bigint unsigned DEFAULT NULL,
`evidence_excerpt` text,
`evidence_snapshot` json DEFAULT NULL,
`weight` decimal(5,4) NOT NULL,
`idempotency_key` varchar(128) NOT NULL,
`occurred_at` datetime NOT NULL,
`created_at` datetime NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `idempotency_key` (`idempotency_key`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `memory_sync_outbox` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`event_uuid` char(36) NOT NULL,
`aggregate_type` varchar(24) NOT NULL,
`aggregate_uuid` char(36) NOT NULL,
`aggregate_version` bigint unsigned NOT NULL,
`target_store` varchar(16) NOT NULL,
`operation` varchar(16) NOT NULL,
`payload` json NOT NULL,
`status` varchar(16) NOT NULL,
`retry_count` int NOT NULL DEFAULT '0',
`next_retry_at` datetime DEFAULT NULL,
`last_error` text,
`created_at` datetime NOT NULL,
`processed_at` datetime DEFAULT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `uk_memory_sync_event` (`event_uuid`,`target_store`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `memory_unit` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`memory_uuid` char(36) NOT NULL,
`customer_id` bigint unsigned NOT NULL,
`memory_key` varchar(128) NOT NULL,
`content` text NOT NULL,
`structured_value` json DEFAULT NULL,
`memory_type` varchar(24) NOT NULL,
`source_type` varchar(24) NOT NULL,
`source_confidence` decimal(5,4) NOT NULL,
`confidence` decimal(5,4) NOT NULL,
`evidence_count` int NOT NULL DEFAULT '0',
`conflict_count` int NOT NULL DEFAULT '0',
`recall_count` int NOT NULL DEFAULT '0',
`status` varchar(16) NOT NULL,
`valid_from` datetime NOT NULL,
`valid_until` datetime DEFAULT NULL,
`last_evidenced_at` datetime DEFAULT NULL,
`last_recall_at` datetime DEFAULT NULL,
`promoted_at` datetime DEFAULT NULL,
`version` bigint unsigned NOT NULL DEFAULT '1',
`created_at` datetime NOT NULL,
`updated_at` datetime NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `memory_uuid` (`memory_uuid`),
KEY `idx_memory_unit_customer` (`customer_id`,`status`,`confidence`)
) ENGINE=InnoDB AUTO_INCREMENT=11 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `model_endpoint_config` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`endpoint_code` varchar(64) NOT NULL,
`provider` varchar(32) NOT NULL,
`model_name` varchar(128) NOT NULL,
`base_url` varchar(500) NOT NULL,
`secret_ref` varchar(256) NOT NULL,
`capabilities` json NOT NULL,
`allowed_data_levels` json NOT NULL,
`context_window` int unsigned NOT NULL,
`timeout_ms` int unsigned NOT NULL DEFAULT '15000',
`status` varchar(16) NOT NULL DEFAULT 'disabled',
`created_by` bigint unsigned NOT NULL,
`reviewer_id` bigint unsigned DEFAULT NULL,
`reviewed_at` datetime(6) DEFAULT NULL,
`created_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6),
`updated_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6) ON UPDATE CURRENT_TIMESTAMP(6),
PRIMARY KEY (`id`),
UNIQUE KEY `uk_model_endpoint_code` (`endpoint_code`),
CONSTRAINT `chk_model_endpoint_status` CHECK ((`status` in (_utf8mb4'draft',_utf8mb4'approved',_utf8mb4'active',_utf8mb4'disabled',_utf8mb4'archived')))
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `model_routing_fallback` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`routing_rule_id` bigint unsigned NOT NULL,
`endpoint_id` bigint unsigned NOT NULL,
`fallback_order` tinyint unsigned NOT NULL,
`retryable_error_codes` json DEFAULT NULL,
`created_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6),
PRIMARY KEY (`id`),
UNIQUE KEY `uk_model_fallback_order` (`routing_rule_id`,`fallback_order`),
UNIQUE KEY `uk_model_fallback_endpoint` (`routing_rule_id`,`endpoint_id`),
CONSTRAINT `chk_model_fallback_order` CHECK ((`fallback_order` between 1 and 2))
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `model_routing_rule` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`release_id` bigint unsigned NOT NULL,
`rule_code` varchar(64) NOT NULL,
`agent_type` varchar(32) NOT NULL,
`task_type` varchar(48) NOT NULL,
`model_policy` varchar(32) NOT NULL,
`primary_endpoint_id` bigint unsigned NOT NULL,
`fallback_endpoint_ids` json DEFAULT NULL,
`condition_json` json DEFAULT NULL,
`max_attempts` tinyint unsigned NOT NULL DEFAULT '2',
`latency_budget_ms` int unsigned NOT NULL DEFAULT '15000',
`priority` int NOT NULL DEFAULT '100',
`created_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6),
PRIMARY KEY (`id`),
UNIQUE KEY `uk_model_route_release` (`release_id`,`rule_code`),
CONSTRAINT `chk_model_route_attempts` CHECK ((`max_attempts` between 1 and 3))
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `outbox_delivery` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`event_id` char(36) NOT NULL,
`consumer_name` varchar(64) NOT NULL,
`delivered_at` datetime(6) NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `uk_outbox_delivery_event_consumer` (`event_id`,`consumer_name`)
) ENGINE=InnoDB AUTO_INCREMENT=64 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `platform_config_item` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`release_id` bigint unsigned NOT NULL,
`namespace` varchar(64) NOT NULL,
`config_key` varchar(128) NOT NULL,
`value_json` json NOT NULL,
`schema_version` varchar(32) NOT NULL,
`checksum` char(64) NOT NULL,
`created_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6),
PRIMARY KEY (`id`),
UNIQUE KEY `uk_config_item_release` (`release_id`,`namespace`,`config_key`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `profile_snapshots` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`profile_uuid` char(36) DEFAULT NULL,
`customer_id` bigint unsigned NOT NULL,
`version` bigint unsigned NOT NULL,
`snapshot` json NOT NULL,
`generation_basis` json DEFAULT NULL,
`snapshot_hash` char(64) DEFAULT NULL,
`is_current` tinyint(1) NOT NULL DEFAULT '0',
`current_customer_id` bigint unsigned DEFAULT NULL,
`generated_at` datetime DEFAULT NULL,
`created_at` datetime NOT NULL,
`updated_at` datetime NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `uk_profile_snapshot_version` (`customer_id`,`version`),
UNIQUE KEY `profile_uuid` (`profile_uuid`),
UNIQUE KEY `uk_profile_snapshot_current` (`current_customer_id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `prompt_template_version` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`release_id` bigint unsigned NOT NULL,
`prompt_code` varchar(64) NOT NULL,
`task_type` varchar(48) NOT NULL,
`agent_type` varchar(32) DEFAULT NULL,
`version` int unsigned NOT NULL,
`system_prompt` mediumtext NOT NULL,
`user_prompt_template` mediumtext NOT NULL,
`input_schema` json DEFAULT NULL,
`output_schema` json DEFAULT NULL,
`checksum` char(64) NOT NULL,
`created_by` bigint unsigned NOT NULL,
`created_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6),
PRIMARY KEY (`id`),
UNIQUE KEY `uk_prompt_version` (`prompt_code`,`version`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `request_idempotency` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`user_id` bigint unsigned NOT NULL,
`session_id` varchar(64) NOT NULL,
`agent_type` varchar(32) NOT NULL,
`idempotency_key` varchar(64) NOT NULL,
`request_hash` char(64) NOT NULL,
`trace_id` varchar(64) NOT NULL,
`status` varchar(16) NOT NULL DEFAULT 'processing',
`result_message_id` bigint unsigned DEFAULT NULL,
`error_code` varchar(64) DEFAULT NULL,
`locked_until` datetime(6) DEFAULT NULL,
`expire_at` datetime(6) NOT NULL,
`created_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6),
`updated_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6) ON UPDATE CURRENT_TIMESTAMP(6),
PRIMARY KEY (`id`),
UNIQUE KEY `uk_idempotency_scope` (`user_id`,`agent_type`,`idempotency_key`),
KEY `idx_idempotency_expire` (`expire_at`),
KEY `idx_idempotency_trace` (`trace_id`),
CONSTRAINT `chk_idempotency_status` CHECK ((`status` in (_utf8mb4'processing',_utf8mb4'completed',_utf8mb4'failed')))
) ENGINE=InnoDB AUTO_INCREMENT=816 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `svc_conversation_session` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`session_id` varchar(64) NOT NULL,
`user_id` bigint unsigned NOT NULL,
`portal` varchar(32) NOT NULL,
`agent_type` varchar(32) DEFAULT NULL,
`status` varchar(16) NOT NULL DEFAULT 'active',
`clarification_round` tinyint unsigned NOT NULL DEFAULT '0',
`message_count` int unsigned NOT NULL DEFAULT '0',
`last_intent` varchar(32) DEFAULT NULL,
`config_version` varchar(64) DEFAULT NULL,
`started_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6),
`last_active_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6),
`ended_at` datetime(6) DEFAULT NULL,
`created_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6),
`updated_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6) ON UPDATE CURRENT_TIMESTAMP(6),
PRIMARY KEY (`id`),
UNIQUE KEY `uk_session_id` (`session_id`),
KEY `idx_session_user_active` (`user_id`,`last_active_at`),
KEY `idx_session_status_active` (`status`,`last_active_at`),
CONSTRAINT `fk_session_user` FOREIGN KEY (`user_id`) REFERENCES `sys_user` (`id`),
CONSTRAINT `chk_session_clarification` CHECK ((`clarification_round` <= 10)),
CONSTRAINT `chk_session_status` CHECK ((`status` in (_utf8mb4'active',_utf8mb4'ended',_utf8mb4'transferred',_utf8mb4'expired')))
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci COMMENT='Agent会话状态与澄清轮次';
CREATE TABLE `svc_handover_ticket` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`ticket_no` varchar(32) NOT NULL,
`session_id` varchar(64) NOT NULL,
`customer_id` bigint unsigned DEFAULT NULL,
`source_agent` varchar(32) NOT NULL DEFAULT 'customer_service',
`source_message_id` bigint unsigned DEFAULT NULL,
`intent` varchar(32) DEFAULT NULL,
`confidence` decimal(5,4) DEFAULT NULL,
`priority` varchar(8) NOT NULL DEFAULT 'P1',
`reason_code` varchar(64) NOT NULL,
`reason_detail` varchar(500) DEFAULT NULL,
`conversation_summary` mediumtext,
`source_references` json DEFAULT NULL,
`status` varchar(16) NOT NULL DEFAULT 'pending',
`assigned_to` bigint unsigned DEFAULT NULL,
`assigned_at` datetime(6) DEFAULT NULL,
`accepted_at` datetime(6) DEFAULT NULL,
`resolved_at` datetime(6) DEFAULT NULL,
`closed_at` datetime(6) DEFAULT NULL,
`resolution` text,
`created_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6),
`updated_at` datetime(6) NOT NULL DEFAULT CURRENT_TIMESTAMP(6) ON UPDATE CURRENT_TIMESTAMP(6),
PRIMARY KEY (`id`),
UNIQUE KEY `uk_handoff_ticket_no` (`ticket_no`),
KEY `idx_handoff_session` (`session_id`,`created_at`),
KEY `idx_handoff_customer` (`customer_id`,`created_at`),
KEY `idx_handoff_queue` (`status`,`priority`,`created_at`),
KEY `idx_handoff_assignee` (`assigned_to`,`status`),
KEY `fk_handoff_source_message` (`source_message_id`),
CONSTRAINT `fk_handoff_assignee` FOREIGN KEY (`assigned_to`) REFERENCES `sys_user` (`id`),
CONSTRAINT `fk_handoff_customer` FOREIGN KEY (`customer_id`) REFERENCES `sys_user` (`id`),
CONSTRAINT `fk_handoff_source_message` FOREIGN KEY (`source_message_id`) REFERENCES `conversation_message` (`id`),
CONSTRAINT `chk_handoff_confidence` CHECK (((`confidence` is null) or (`confidence` between 0 and 1))),
CONSTRAINT `chk_handoff_priority` CHECK ((`priority` in (_utf8mb4'P0',_utf8mb4'P1',_utf8mb4'P2'))),
CONSTRAINT `chk_handoff_status` CHECK ((`status` in (_utf8mb4'pending',_utf8mb4'assigned',_utf8mb4'processing',_utf8mb4'resolved',_utf8mb4'closed',_utf8mb4'cancelled')))
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci COMMENT='客服转人工工单';
CREATE TABLE `sys_customer_assignment` (
`id` bigint unsigned NOT NULL,
`customer_id` bigint unsigned NOT NULL,
`employee_id` bigint unsigned NOT NULL,
`employee_role` varchar(32) NOT NULL,
`assigned_at` datetime NOT NULL,
`unassigned_at` datetime DEFAULT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `uk_sys_customer_assignment_customer_id` (`customer_id`),
UNIQUE KEY `uk_sys_customer_assignment_employee_role` (`employee_role`),
KEY `idx_sys_customer_assignment_customer_id` (`customer_id`),
KEY `idx_sys_customer_assignment_employee_id` (`employee_id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `sys_login_record` (
`id` bigint unsigned NOT NULL,
`user_id` bigint unsigned NOT NULL,
`login_at` datetime NOT NULL,
`login_result` varchar(16) NOT NULL,
`ip_region` varchar(64) DEFAULT NULL,
`device_id` varchar(128) DEFAULT NULL,
`is_common_device` tinyint(1) NOT NULL DEFAULT '1',
`failure_reason` varchar(128) DEFAULT NULL,
`created_at` datetime NOT NULL,
PRIMARY KEY (`id`),
KEY `idx_sys_login_record_user_id` (`user_id`),
KEY `idx_sys_login_record_login_at` (`login_at`),
KEY `idx_sys_login_record_login_result` (`login_result`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `sys_permission` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`permission_code` varchar(64) NOT NULL,
`resource` varchar(64) NOT NULL,
`action` varchar(32) NOT NULL,
`data_scope` varchar(32) NOT NULL,
`field_policy` json DEFAULT NULL,
`created_at` datetime NOT NULL,
`updated_at` datetime NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `permission_code` (`permission_code`),
KEY `idx_sys_permission_resource_action` (`resource`,`action`)
) ENGINE=InnoDB AUTO_INCREMENT=1927130244427137 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `sys_role` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`role_code` varchar(32) NOT NULL,
`role_name` varchar(64) NOT NULL,
`status` varchar(16) NOT NULL,
`created_at` datetime NOT NULL,
`updated_at` datetime NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `role_code` (`role_code`)
) ENGINE=InnoDB AUTO_INCREMENT=1927130244427136 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `sys_role_permission` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`role_id` bigint unsigned NOT NULL,
`permission_id` bigint unsigned NOT NULL,
`created_at` datetime NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `uk_sys_role_permission` (`role_id`,`permission_id`)
) ENGINE=InnoDB AUTO_INCREMENT=15 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `sys_user` (
`id` bigint unsigned NOT NULL,
`user_no` varchar(32) NOT NULL,
`username` varchar(64) NOT NULL,
`email` varchar(128) DEFAULT NULL,
`password_hash` varchar(255) NOT NULL,
`user_type` varchar(16) NOT NULL,
`employee_role` varchar(32) DEFAULT NULL,
`customer_tier` varchar(16) DEFAULT NULL,
`investor_type` varchar(8) DEFAULT NULL,
`investor_type_assessed_at` datetime DEFAULT NULL,
`is_professional_investor` tinyint(1) NOT NULL DEFAULT '0',
`professional_investor_status` varchar(16) NOT NULL,
`professional_investor_certified_at` datetime DEFAULT NULL,
`fund_account_status` varchar(16) NOT NULL,
`fund_account_opened_at` datetime DEFAULT NULL,
`status` varchar(16) NOT NULL,
`created_at` datetime NOT NULL,
`updated_at` datetime NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `uk_sys_user_user_no` (`user_no`),
UNIQUE KEY `uk_sys_user_username` (`username`),
UNIQUE KEY `uk_sys_user_email` (`email`),
KEY `idx_sys_user_user_type` (`user_type`),
KEY `idx_sys_user_employee_role` (`employee_role`),
KEY `idx_sys_user_status` (`status`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `sys_user_role` (
`id` bigint unsigned NOT NULL AUTO_INCREMENT,
`user_id` bigint unsigned NOT NULL,
`role_id` bigint unsigned NOT NULL,
`assigned_at` datetime NOT NULL,
`expires_at` datetime DEFAULT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `uk_sys_user_role` (`user_id`,`role_id`)
) ENGINE=InnoDB AUTO_INCREMENT=15 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `user_facts` (
`id` bigint unsigned NOT NULL,
`customer_id` bigint unsigned NOT NULL,
`fact_key` varchar(128) NOT NULL,
`fact_value` json NOT NULL,
`source_portal` varchar(16) NOT NULL,
`source_episode_id` bigint unsigned DEFAULT NULL,
`confidence` float NOT NULL DEFAULT '1',
`is_critical` tinyint(1) NOT NULL DEFAULT '0',
`created_at` datetime NOT NULL,
PRIMARY KEY (`id`),
KEY `idx_user_facts_customer_id` (`customer_id`),
KEY `idx_user_facts_fact_key` (`fact_key`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
SET FOREIGN_KEY_CHECKS=1;