docs(tplus): 新增 2008 R2 验收手册与数据导入设计稿

This commit is contained in:
liuwenxin 2026-10-28 11:52:39 +08:00
parent 87a0884953
commit 8242aae454
3 changed files with 147 additions and 3 deletions

View File

@ -0,0 +1,63 @@
# SQL Server 2008 R2 测试环境与验收手册
> 目标:在真实 Windows + SQL Server 2008 R2(10.50.x)环境中恢复客户原始备份,完成同版本兼容验收,关闭「2008 R2 状态 PENDING」。本手册在取得合法安装介质后即可照做;介质到位前的准备工作只做第 2、3 节中不依赖介质的部分。
## 1. 背景与当前状态(2026-10-28)
- 客户源备份 `ceshi20261026.bak` 版本为 10.50.1600;生产库具体版本待客户提供(确认单 B3)。
- 本地 Docker 已用 SQL Server 2022 副本完成恢复 PoC:完整 CHECKDB 通过、只读账号可用、六类查询两轮核验 933,203 行无失败。该副本只用于结构核验与开发,**不能替代同版本验收**。
- Hyper-V 虚拟机外壳已建于 `D:\work\app\tplus-vm`,处于关机、断网状态;Windows 与 SQL Server 2008 R2 安装介质尚未到位(确认单 B5)。
## 2. 环境约定
| 项目 | 约定 |
| --- | --- |
| 虚拟机目录 | `D:\work\app\tplus-vm` |
| SQL Server 数据与日志 | `D:\work\app\tplus-sqlserver`(绑定目录,不入项目仓库) |
| 备份文件 | `D:\work\app\tplus-backup`(先校验 SHA-256 再使用) |
| 虚拟机网络 | 安装与验收期间保持仅主机或内网隔离,不接入公网 |
| 凭据 | 只读账号凭据走双方认可的私密渠道交接;不写入本文档、代码或 Git |
| 项目依赖脚本 | `scripts/tplus/`(工作区准备、备份检查、恢复、只读账号、结构盘点) |
## 3. 装机步骤(依赖介质,介质到位后执行)
1. 运行 `scripts/tplus/prepare_sql2008r2_vm.ps1` 核对虚拟机外壳与磁盘位置;确认网卡保持断开。
2. 挂载 Windows 安装介质,安装操作系统;完成后安装集成服务与全部安全更新,重新启用受限网络。
3. 挂载 SQL Server 2008 R2 安装介质,安装数据库引擎实例;版本不低于 10.50.1600(RTM 即可还原源备份),实例排序规则与源备份一致(默认 Chinese_PRC_CI_AS)。
4. 安装 SQL Server 2008 R2 的 SP3 与后续补丁(可选);补丁不影响 10.50 主版本兼容性。
5. 在虚拟机内安装 `ODBC Driver 17 for SQL Server`(pyodbc 依赖;Driver 17 支持连接 2008 R2)。
## 4. 备份恢复步骤
1. `scripts/tplus/inspect_sqlserver_backup.ps1`:对 `ceshi20261026.bak` 执行 VERIFYONLY 与 FILELISTONLY,确认备份完整并列出数据/日志文件逻辑名。
2. `scripts/tplus/restore_sqlserver_backup.ps1`:执行 RESTORE DATABASE,文件落位 `D:\work\app\tplus-sqlserver`;恢复模式按脚本默认。
3. 恢复完成后执行 `DBCC CHECKDB` 全库检查,结果留档。
4. `scripts/tplus/create_tplus_readonly_login.ps1`:创建专用只读登录与数据库用户,仅授予 `db_datareader`;凭据按第 2 节约定交接。
5. `scripts/tplus/inventory_tplus_database.ps1`:盘点核心表结构与行数,与 Docker 副本的结构核验结果比对。
## 5. 同版本验收清单(逐项通过后关闭 PENDING)
| # | 验收项 | 通过标准 |
| --- | --- | --- |
| 1 | 版本确认 | `SELECT @@VERSION` 返回 10.50.x,与源备份主版本一致 |
| 2 | 驱动连接 | 后端配置指向该实例,pyodbc + ODBC Driver 17 连接成功 |
| 3 | 只读权限 | 用只读账号执行六类查询成功;执行任何写操作被拒绝 |
| 4 | 六类查询 | 人员、客户、产品、订单、发货、收付款九个白名单 SQL 全部返回,行数与 Docker 副本一致 |
| 5 | 中文数据 | 姓名、客户名、产品名中文读写无乱码 |
| 6 | 日期字段 | 凭证日期、审核日期、到账日期等候选字段格式与空值表现正常 |
| 7 | 金额精度 | 金额字段以 Decimal 读取,小数位与源数据一致 |
| 8 | 断连超时 | 人为断网/停实例,同步错误进入 `tplus_sync_errors`,不静默丢数据 |
| 9 | 重复同步 | 同一备份重复 staging,相同行哈希全部去重跳过,行数不变 |
| 10 | 关联核验 | `relationship_audit` 数量统计与 Docker 副本结果一致 |
## 6. 产出与归档
- 验收通过后产出报告(含上表逐项结果与 `@@VERSION` 输出),归档至 `.ai/archive/ai-aux/`;项目文档更新结论为「2008 R2 验收通过」。
- 同步更新 `.ai/AI_CONTEXT.md` 与 `.ai/PROJECT_PROGRESS.md`。
- 验收中发现的字段差异回到 `docs/待确认事项清单_2026-10-28_v2.xlsx` 对应编号,不直接改代码。
## 7. 明确边界
- 本环境仅验收 T+ 源库只读访问;工资系统生产部署(确认单 B4)另行确认。
- 客户生产 T+ 原库不升级、不改动;2022 副本不回迁。
- 时间增量(确认单 #13)不在本手册范围内,待 rowversion 验证方案另行评审。

View File

@ -0,0 +1,81 @@
# T+ 数据导入设计:staging → 工资业务表(2026-10-28)
> 状态:设计稿,未实现。客户确认单(`docs/待确认事项清单_2026-10-28_v2.xlsx`)13 项业务口径闭环前,不启动本文档对应代码开发。文中「预留参数」按编号挂到系统设置模块,客户答复后先更新清单、再回填参数、最后实现导入。
## 1. 目标与边界
- 将 `tplus_sync_records`(staging)中 PENDING 的原始行,按映射规则写入六类工资业务表:人员 `personnel`、客户 `customers`、产品 `products`、业务 `businesses`(含 `business_items`)、发货 `shipments`(含明细)、回款 `receipts`。
- 同步链路已具备:批次/错误/水位/锁/重试由现有 `tplus_sync_batches`、`tplus_sync_errors`、`tplus_sync_watermarks` 与 `tplus-worker` 承担;本设计只增加「应用器」环节,不改动现有读取链路。
- 不在范围内:工资核算、月结、审批(沿用既有模块);时间增量(确认单 #13 闭环前水位保持禁用)。
## 2. 总体流程
```text
staging PENDING
→ 应用器按实体分批读取(entity_type + row_hash)
→ 字段映射 + 口径参数校验(含预留参数缺省值)
→ 幂等检查(锚点已存在则置 SKIPPED)
→ 写业务表(应用层关联,不建物理外键)
→ 成功置 APPLIED;失败置 ERROR 并写 tplus_sync_errors
```
- 每个实体一个应用器,导入顺序固定:人员 → 产品 → 客户 → 业务(含明细)→ 发货(含明细)→ 回款。上层实体失败时跳过下层并保留 PENDING,供重试。
- 新增「导入运行记录」需求:每个批次的每个实体记录读取数、写入数、跳过数、失败数(实现时以新表或复用批次审计字段承载,评审时定稿)。
## 3. 幂等与锚点
- staging 层唯一键 `uk_tplus_sync_records_entity_source_hash`(entity_type + source_id + row_hash)保证重复快照不重复入库。
- 业务表锚点:订单/发货/回款以 `source_no`(T+ 单据号)幂等;主数据以 `source_id` 幂等。锚点字段在实现时补唯一约束(如 `uk_receipts_source_no`)。
- 每笔回款只能核算一次:已存在核算记录的回款,重复导入直接跳过,不做金额合并。
## 4. 金额与精度
- 金额字段一律 `Decimal`;比例、日斜率一律 `Fraction`;全程禁用 float。
- 业务员计提沿用既定公式:`10‰ − 回款天数 × 4/360‰`,1–360 天线性递减,360 天 6‰,361 天及以上固定 4‰。
- 毛利润不含运费(9.8 方案蓝色字体原算法作废);混合产品按明细行分别计算;负绩效照算不归零。
- 多单分批回款的分摊与尾差处理属预留参数(#5),未定前不实现分摊逻辑。
## 5. 人工字段保护(T+ 不覆盖)
| 字段 | 保护方式 |
| --- | --- |
| 人员岗位角色ID | T+ 同步不覆盖,只填新人员缺省角色 |
| 回款批次号 / 发货单号 | `HK…` / `SH…` 系统生成,同步行只记录 source_no 追溯 |
| 业务归属变更 | 只影响变更后的核算,不回溯历史 |
| 客户负责人、客户分类 | 由人工维护,同步不覆盖 |
| 产品计提分类、指导价 | 由人工维护(#11) |
| 回款/发货批次人工指定 | 系统提供人工指定入口,导入只建待指定数据 |
## 6. 事务与错误边界
- 应用器按「批次 × 实体 × 每 N 行」开事务;单行失败不回滚整批,错误行写 `tplus_sync_errors`(含 error_code 与说明)。
- 批次状态机沿用现有 QUEUED/RUNNING/SUCCEEDED/PARTIAL/FAILED;出现 ERROR 行时批次终态为 PARTIAL。
- 应用器与 worker 共用 MySQL 连接级锁,避免与读取任务并发写同一批次。
- 重算必须授权并留痕:已核算数据不允许静默覆盖,重算入口生成带请求人、时间、原因的审计记录(复用操作日志)。
## 7. 预留参数清单(等待客户答复)
| 编号 | 预留参数 | 等待内容 |
| --- | --- | --- |
| #1 | 成本取值 | 订单 LatestCost 与销货 costPrice/costAmount 的取舍(含税 L1 一并确认) |
| #2 | 发货日期口径 | 凭证/发送/交货/审核日的取舍与缺失处理 |
| #3 | 到账日期口径 | 主表时间与明细 arrivalDate 的认定,预收与分次到账 |
| #4 | 无订单回款 | 补录、人工指定或不纳入 |
| #5 | 多单分摊规则 | 分摊方式与尾差对账 |
| #6 | 可计提收款范围 | 期初/预收/退款/费用单的排除与承接 |
| #7 | 有效性与核销条件 | 生效即可计提还是须核销 |
| #8 | 负向事件 | 退货/红冲的冲减月份与重复冲减防护 |
| #9 | 人员口径 | 工号确认、取数范围、经理归属(L6 经理个人户只调参数) |
| #10 | 客户口径 | 往来单位筛选、改名合并 |
| #11 | 产品口径 | 单位换算、价格类型、计提分类维护方 |
| #12 | 收款方式 | 结算方式枚举与以物抵顶差异 |
| #13 | 初始化与增量 | 起始日期、历史已结算款识别、rowversion 验证 |
| L2–L5 | 二次分配三项 | 追认后回填分摊参数 |
| L7 | 三级角色职权 | 页面验收时核对 |
| B1–B4 | 环境接入 | 主机地址、只读账号、版本号、部署条件(写到部署配置,不进代码) |
## 8. 实现触发条件
1. 确认单 13 项 + 材料 5 项 + L1–L7 全部闭环(检查点 A)。
2. 本设计按答复修订并评审定稿。
3. 先实现主数据导入并通过可回滚验收(检查点 B),再进入交易数据与负向事件。

View File

@ -3,11 +3,11 @@
依照 `tasks/plan.md`(2026-10-28)。上一轮清单已归档至 `tasks/archive/2026-10-27-tplus-sync-todo.md`。
## P0 工程收口
- [ ] 拆分提交本轮 T+ 同步管理成果(迁移、后端、前端、文档);提交前 Ruff、单元测试、前端类型检查与构建通过。
- [x] 拆分提交本轮 T+ 同步管理成果(迁移、后端、前端、文档);提交前 Ruff、单元测试、前端类型检查与构建通过。
依赖:无。
## 轨道 A:同版本验收环境
- [ ] A1 细化 2008 R2 测试环境与验收手册(无介质可先做)。
- [x] A1 细化 2008 R2 测试环境与验收手册(无介质可先做)。
- [ ] A2 取得合法介质并完成虚拟机安装。
- [ ] A3 恢复原始备份并执行完整验收,产出报告。
依赖:A2 等介质到位;A3 依赖 A2。
@ -19,7 +19,7 @@
依赖:无;B1 立即可发。
## 轨道 C:T+ 数据导入开发
- [ ] C1 起草 staging → 业务表写入设计,标注等待确认的差异点。
- [x] C1 起草 staging → 业务表写入设计,标注等待确认的差异点。
- [ ] C2 主数据导入实现与测试。
- [ ] C3 订单/发货/回款导入实现与测试。
- [ ] C4 负向事件处理实现与测试。