feat: chat integration, tenant admin spec, backend chat service, miniprogram updates, DEMO moved to tmp, XCX-TEST removed, migrations & docs

This commit is contained in:
Neo
2026-03-20 09:02:10 +08:00
parent 3d2e5f8165
commit beb88d5bea
388 changed files with 6436 additions and 25458 deletions

View File

@@ -1,24 +1,33 @@
# BD_Manualbiz Schema AI 表(对话记录 + 消息 + 缓存)
> 目标库:`test_zqyy_app`(通过 `APP_DB_DSN` 连接)
> 迁移脚本:`db/zqyy_app/migrations/2026-03-08__create_ai_tables.sql`
> 关联 SPEC`05-miniapp-ai-integration`P5 AI 集成层
> 迁移脚本:
> - `db/zqyy_app/migrations/2026-03-08__create_ai_tables.sql`(初始建表
> - `db/zqyy_app/migrations/2026-03-20__rns14_chat_module_extend.sql`RNS1.4 CHAT 扩展)
> 关联 SPEC`05-miniapp-ai-integration`P5 AI 集成层)、`rns1-chat-integration`RNS1.4 CHAT 对齐与联调收尾)
---
## 1. 变更说明
### 新增表3 张)
### 新增表3 张P5 初始建表
| # | 表名 | 用途 | 字段数 |
|---|------|------|--------|
| 1 | `biz.ai_conversations` | AI 对话记录:每次 AI 调用(用户主动或系统自动)创建一条 | 8 |
| 2 | `biz.ai_messages` | AI 消息记录:对话中的每条消息(输入/输出/系统) | 6 |
| # | 表名 | 用途 | 字段数(初始→当前) |
|---|------|------|---------------------|
| 1 | `biz.ai_conversations` | AI 对话记录:每次 AI 调用(用户主动或系统自动)创建一条 | 8 → 13 |
| 2 | `biz.ai_messages` | AI 消息记录:对话中的每条消息(输入/输出/系统) | 6 → 7 |
| 3 | `biz.ai_cache` | AI 应用缓存:各应用的结构化输出结果 | 9 |
### RNS1.4 CHAT 模块扩展字段2026-03-20
| # | 表名 | 新增字段 | 用途 |
|---|------|---------|------|
| 1 | `biz.ai_conversations` | `context_type`, `context_id`, `title`, `last_message`, `last_message_at` | 多入口对话复用 + 历史列表展示与排序 |
| 2 | `biz.ai_messages` | `reference_card` | 引用卡片 JSON客户概览等结构化上下文数据 |
### 表字段明细
#### biz.ai_conversations8 字段)
#### biz.ai_conversations13 字段)
| 字段 | 类型 | 约束 | 说明 |
|------|------|------|------|
@@ -30,8 +39,13 @@
| `source_page` | VARCHAR(100) | 可空 | 来源页面标识 |
| `source_context` | JSONB | 可空 | 页面上下文 JSON |
| `created_at` | TIMESTAMPTZ | NOT NULL DEFAULT NOW() | 创建时间 |
| `context_type` | VARCHAR(20) | 可空 | **RNS1.4 新增** — 对话关联上下文类型task任务/ customer客户/ coach助教/ general通用 |
| `context_id` | VARCHAR(50) | 可空 | **RNS1.4 新增** — 关联上下文 IDtask 入口为 taskIdcustomer 入口为 customerIdcoach 入口为 coachIdgeneral 为 NULL |
| `title` | VARCHAR(200) | 可空 | **RNS1.4 新增** — 对话标题:自定义 > 上下文名称 > 首条消息前20字 |
| `last_message` | TEXT | 可空 | **RNS1.4 新增** — 最后一条消息内容摘要截断至100字 |
| `last_message_at` | TIMESTAMPTZ | 可空 | **RNS1.4 新增** — 最后消息时间,用于历史列表排序和对话复用时限判断 |
#### biz.ai_messages6 字段)
#### biz.ai_messages7 字段)
| 字段 | 类型 | 约束 | 说明 |
|------|------|------|------|
@@ -41,6 +55,7 @@
| `content` | TEXT | NOT NULL | 消息内容 |
| `tokens_used` | INTEGER | 可空 | 本条消息消耗的 token 数 |
| `created_at` | TIMESTAMPTZ | NOT NULL DEFAULT NOW() | 创建时间 |
| `reference_card` | JSONB | 可空 | **RNS1.4 新增** — 引用卡片 JSON`{type, title, summary, data}`,用于展示客户概览等结构化上下文数据 |
#### biz.ai_cache9 字段)
@@ -80,6 +95,8 @@
| `ai_cache` | `chk_ai_cache_type` | CHECK | 7 个枚举值 |
| `ai_cache` | `idx_ai_cache_lookup` | INDEX | `(cache_type, site_id, target_id, created_at DESC)` — 查询最新缓存 |
| `ai_cache` | `idx_ai_cache_cleanup` | INDEX | `(cache_type, site_id, target_id, created_at)` — 清理超限记录ASC 排序便于删除最旧) |
| `ai_conversations` | `idx_ai_conv_context` | INDEX条件 | **RNS1.4 新增**`(user_id, site_id, context_type, context_id, last_message_at DESC NULLS LAST) WHERE context_type IS NOT NULL` — 上下文对话查找(多入口复用) |
| `ai_conversations` | `idx_ai_conv_last_msg` | INDEX | **RNS1.4 新增**`(user_id, site_id, last_message_at DESC NULLS LAST)` — 历史列表排序优化CHAT-1 倒序) |
---
@@ -89,15 +106,44 @@
|------|------|
| ETL 任务 | 无影响。AI 表属于 `biz` Schema不参与 ETL 流程 |
| 后端 API | 直接依赖。P5 AI 模块(`apps/backend/app/ai/`将基于这三张表实现对话持久化、缓存读写、SSE 流式对话等功能 |
| 后端 APIRNS1.4 | **直接依赖**。CHAT 模块(`apps/backend/app/routers/xcx_chat.py``apps/backend/app/services/chat_service.py`)依赖 `ai_conversations` 的 5 个新字段(`context_type`/`context_id`/`title`/`last_message`/`last_message_at`)实现多入口对话复用、历史列表展示与排序;依赖 `ai_messages.reference_card` 存储引用卡片 JSON |
| 小程序 | 间接依赖。小程序通过后端 AI API 间接使用对话和缓存数据 |
| 小程序RNS1.4 | **间接依赖**`pages/chat/chat.ts``pages/chat-history/chat-history.ts` 通过 CHAT-1/2/3/4 端点间接依赖新字段(`title`→对话标题、`lastMessage`→摘要、`timestamp`→排序、`referenceCard`→引用卡片渲染) |
| 管理后台 | 暂无影响。后续可能增加 AI 调用统计和缓存管理界面 |
| `member_retention_clue` | 间接关联。App8维客线索整理的结果同时写入 `ai_cache``member_retention_clue` 表 |
| 现有 `biz` Schema | 兼容。新增 3 张表不修改已有对象coach_tasks、notes、trigger_jobs 等) |
| 现有 `biz` Schema | 兼容。P5 新增 3 张表RNS1.4 仅在已有表上 ADD COLUMN / CREATE INDEX不修改已有字段或约束 |
---
## 3. 回滚策略
### 3a. 回滚 RNS1.4 CHAT 扩展2026-03-20 迁移)
按逆序 DROP 新增索引和字段:
```sql
-- 删除 RNS1.4 新增索引
DROP INDEX IF EXISTS biz.idx_ai_conv_context;
DROP INDEX IF EXISTS biz.idx_ai_conv_last_msg;
-- 回退 ai_messages 新增字段
ALTER TABLE biz.ai_messages DROP COLUMN IF EXISTS reference_card;
-- 回退 ai_conversations 新增字段(逆序)
ALTER TABLE biz.ai_conversations DROP COLUMN IF EXISTS last_message_at;
ALTER TABLE biz.ai_conversations DROP COLUMN IF EXISTS last_message;
ALTER TABLE biz.ai_conversations DROP COLUMN IF EXISTS title;
ALTER TABLE biz.ai_conversations DROP COLUMN IF EXISTS context_id;
ALTER TABLE biz.ai_conversations DROP COLUMN IF EXISTS context_type;
```
注意:
- 回滚后 CHAT 模块xcx_chat 路由、chat_service将无法正常工作
- 如果新字段中已有数据,需先备份再执行回滚
- 回滚不影响 P5 初始建表的 8 个原始字段
### 3b. 回滚 P5 初始建表2026-03-08 迁移)
按逆序 DROPCASCADE 处理外键依赖):
```sql
@@ -123,6 +169,8 @@ DROP TABLE IF EXISTS biz.ai_conversations CASCADE;
## 4. 验证 SQL
### 4a. P5 初始建表验证
```sql
-- 1. 验证 3 张 AI 表全部存在
SELECT table_name
@@ -137,7 +185,7 @@ SELECT column_name, data_type, is_nullable
FROM information_schema.columns
WHERE table_schema = 'biz' AND table_name = 'ai_conversations'
ORDER BY ordinal_position;
-- 预期:返回 8 行,包含 id/user_id/nickname/app_id/site_id/source_page/source_context/created_at
-- 预期:返回 13 行P5 原始 8 字段 + RNS1.4 新增 5 字段)
-- 3. 验证 ai_messages 的外键和 CHECK 约束
SELECT conname, contype, pg_get_constraintdef(oid) AS constraint_def
@@ -152,7 +200,7 @@ FROM pg_constraint
WHERE conrelid = 'biz.ai_cache'::regclass AND contype = 'c';
-- 预期:返回 1 行 chk_ai_cache_type包含 7 个枚举值
-- 5. 验证索引全部存在5 个)
-- 5. 验证 P5 初始索引全部存在5 个)
SELECT indexname
FROM pg_indexes
WHERE schemaname = 'biz'
@@ -164,3 +212,35 @@ WHERE schemaname = 'biz'
ORDER BY indexname;
-- 预期:返回 5 行
```
### 4b. RNS1.4 CHAT 扩展验证
```sql
-- 6. 验证 ai_conversations 新增 5 个字段存在
SELECT column_name, data_type, character_maximum_length
FROM information_schema.columns
WHERE table_schema = 'biz' AND table_name = 'ai_conversations'
AND column_name IN ('context_type', 'context_id', 'title', 'last_message', 'last_message_at');
-- 预期:返回 5 行
-- context_type | character varying | 20
-- context_id | character varying | 50
-- title | character varying | 200
-- last_message | text | NULL
-- last_message_at | timestamp with time zone | NULL
-- 7. 验证 ai_messages 新增 reference_card 字段存在
SELECT column_name, data_type
FROM information_schema.columns
WHERE table_schema = 'biz' AND table_name = 'ai_messages'
AND column_name = 'reference_card';
-- 预期:返回 1 行data_type = 'jsonb'
-- 8. 验证 RNS1.4 新增 2 个索引存在
SELECT indexname, indexdef
FROM pg_indexes
WHERE schemaname = 'biz' AND tablename = 'ai_conversations'
AND indexname IN ('idx_ai_conv_context', 'idx_ai_conv_last_msg');
-- 预期:返回 2 行
-- idx_ai_conv_context — 含 WHERE context_type IS NOT NULL 条件
-- idx_ai_conv_last_msg — (user_id, site_id, last_message_at DESC NULLS LAST)
```