INTERNAL REVIEW · UC-SHANGHE-001

最终二维码入口:保留https://szs.yyangpt.cn/haerbin/shanghe/,商户段可变化;也兼容https://域名/shanghe/。以shanghe段区分业务,其后完整密文由设备追加。查看当前入口配置

二维码前缀已通用化:按https://域名/商户标识/提取设备追加的完整密文,前后端均不再限定szs或haerbin。查看格式与验证说明

开发库数据闭环实测通过:已核对用户执行的SQL,当前两端代码连接开发库完成关联、追加、人员同步及真实HTTP失败重试,测试数据已逐表清理。查看实测报告

当前采用最简数据库配置版:设备RC4密钥直接存入qr_secret;已取消AES主密钥及额外环境开关。查看当前执行说明。下方AES方案为历史评审内容,已不适用。

最新进展:上传数据业务修复通过。已修复下游失败重试并验证两边人员数据和积分;用户明确将扫码报告展示延后。设备新密钥与部署环境仍需真机联调。查看本轮修复和测试证据

实施更新:已在三个仓库当前分支完成软件实现与本地验证,新增 SQL 为 v2.35.15.sql,Apifox 已登记。查看部署配置、实际测试与待真机验证项

上禾体检一体机
匿名检测二维码认领整体方案

第一条检测模块上传后即可扫码认领;后续人体成分和左右臂血压自动补入同一人员、同一检测会话。客户端不解密、不指定人员,全部可信判断留在后台。

版本 v0.2-review 日期 2026-09-07 涉及 ai_api / ai_app / store / Apifox DoR: BLOCKED · 待评审

01 · 核心决策

最新实施调整:按用户最小改动要求,后台沿用现有日志规则,取消下文原方案的后台二维码脱敏,公共日志配置和中间件已恢复。二维码请求参数可能被记录,真实设备密钥不记录。

两种入口都支持:输入手机号匹配成功即自动关联;直接检测后扫码则关联登录本人。手机号未匹配到也能扫码关联,无需重新检测。手机号已关联的报告,本人再扫码打开同一报告,其他人不能覆盖归属。

认领对象认领本次检测的人员归属:只测一种也能认领;当时有几种就先保存几种,后续同次检测自动追加。
认领时机任意一个模块形成 raw 后立即可认领,不等待四项完成。
身份边界最终人员只取后台登录态;客户端不能提交目标人员 ID。
解密边界小程序只传完整 q;密钥、解密、匹配都在服务端。
后续上传认领后相同会话的新模块沿用人员并增量结构化。
重复扫码同用户幂等成功;其他用户禁止覆盖。
真实 RC4 密钥不进入 Git、SQL、Apifox、客户端、日志或本评审文档。设备表保存的是 AES-GCM 密文,不复用不可逆的 app_secret_hash

02 · 已验证事实

事实真实证据设计影响
四个模块分四次上传真实设备回调及线上只读日志不能依赖全量完成标志
四次上传共用同一 recordNo、匿名 userID、deviceNo、measureTimeraw 快照与数据库回读可归并成一个 session
右臂报文重复左臂数据右臂真实报文按 metric + segment 幂等 upsert
每次扫码 q 完全相同微信小程序启动参数一个二维码对应整次会话
只有 scancode_time 随扫码变化10:21、10:22、10:25 启动参数只能辅助审计,不能作为可信凭证
未匹配数据当前 raw-only现有代码与 session/raw/record 回读认领时必须回放 raw

03 · 目标流程

1
任意模块上传
建立/更新检测 session,保存 raw,并建立 PENDING 认领索引。
2
微信打开小程序
pages/index/index 取得完整 options.q;未登录先登录。
3
后台认领
小程序提交完整 URL;后台取设备密钥、RC4 解密、验证设备/租户/时间并唯一匹配 session。
4
绑定与回放
行锁事务中绑定当前登录人员,回放当前全部 raw,生成已有模块指标。
5
后续自动追加
相同 recordNo 的人体成分和血压继续沿用已认领人员,无需再次扫码。
6
幂等查看
同一人员重复扫码打开同一报告;其他人员扫描明确冲突。

04 · 业务规则

ID规则
BR-001vendor + deviceNo + recordNo 对应一个 session 和至多一个有效认领。
BR-002一个或部分模块均可认领,未测模块不导致整份报告失败。
BR-003匿名 userID 只关联厂家会话,不能当手机号或系统人员 ID。
BR-004人员归属只取服务端鉴权得到的当前登录用户。
BR-005零条或多条候选均拒绝自动绑定,禁止猜“最近一条”。
BR-006认领后续传必须同时匹配 claim 外部标识,才沿用 ai_user_id。
BR-007同用户重复扫码幂等;不同用户禁止覆盖。
BR-008人员资料以系统档案为准,设备姓名/性别/年龄只保留 raw。
BR-009指标按 session_id + metric_code + segment_key 幂等写入。
BR-010手机号模式和现有设备鉴权行为保持兼容。

05 · 二维码协议与密钥管理

timeMillis_rawData_deviceID_Sex_Age_UserID
  • 小程序只做一次 URL 解码并提交完整 URL。
  • 后台校验固定前缀 https://szs.yyangpt.cn/haerbin/
  • 密文可包含 /+=,不能按最后一个斜杠截取。
  • Base64 严格解码;RC4 使用与设备一致的 UTF-8 密钥。
  • RC4 不带认证,必须与真实回调会话、设备、匿名标识、时间和认领状态交叉验证。

设备密钥

每台设备生成独立 32 位 [A-Za-z0-9_] 密钥,通过 U 盘根目录的 svh/upanconfig.sh 写入 qrCodeSecretKey=<密钥>

服务端保存

字段用途
qr_secret_ciphertextAES-256-GCM 加密后的 RC4 设备密钥包
qr_secret_key_version主密钥版本,用于轮换

AES 主密钥只保存在服务器环境变量或 KMS。正式 SQL 只建字段,不包含任何真实密钥。

06 · 数据设计

新增 ydy_measurement_claim,将匿名定位、认领状态和审计从 raw JSON 中独立出来。

对象职责
ydy_health_device设备、租户、Token 鉴权、二维码密钥密文与版本
ydy_measurement_session一次检测会话及最终 ai_user_id/is_valid
ydy_measurement_session_raw各模块原始快照和认领回放来源
ydy_measurement_claimdeviceNo、匿名 userID、recordNo、状态、认领人、有效期和密文指纹
ydy_health_record认领后结构化指标
ydy_staff / 现有体重路径只复用现有已确认的身高体重同步逻辑

唯一键建议 vendor + session_id;定位索引建议 external_user_id + device_no + measure_time。正式 SQL 版本由发布负责人确认。

07 · API 契约

既有上传接口

POST /api/shanghe.callback/result

外部协议不变。匿名首条建立 PENDING claim;已认领会话后续上传按 claim 外部标识沿用身份。

新增小程序认领接口

POST /api/shanghe.claim/bind
Access-Token: <当前登录令牌>

{
  "qrUrl": "https://szs.yyangpt.cn/haerbin/<完整密文>",
  "scancodeTime": 1788747677
}

qrUrl 必填;scancodeTime 可选。请求禁止出现 targetUserId、aiUserId 或手机号。

结果处理
CLAIMED / ALREADY_CLAIMED返回同一 session 和已测模块
RESULT_NOT_READY客户端在有限窗口重试
QR_INVALID / QR_EXPIRED停止重试,提示重新检测或扫码
DEVICE_UNAVAILABLE拒绝并记录安全审计
CLAIM_AMBIGUOUS拒绝猜测,进入排查
CLAIMED_BY_OTHER / CLAIM_CONFLICT禁止覆盖

接口登记位置:AI运动营养师 / 上禾体检一体机

08 · 系统改造

ai_api独立二维码 cipher/payload 服务、认领 service/controller、raw 回放复用、后续回调继承 claim 身份、脱敏日志和限流。
ai_app复用首页已有 q 解析和登录恢复模式,增加上禾类型识别、短期暂存、加载/等待/成功/冲突状态及报告跳转。
store SQL新增设备密钥密文字段和 claim 表;只做增量结构,不写真实密钥,不猜版本号。
Apifox登记字段、鉴权、成功/异常响应和主/分支/并发测试,保留原上传接口兼容性。

发布顺序

  1. 数据库结构。
  2. 服务端主密钥配置、设备密钥密文和后端代码。
  3. Apifox 联调与自动化。
  4. 小程序发布。
  5. 最后通过 U 盘配置设备密钥,执行真机验收。

09 · 异常、事务与回滚

  • 结果未落库:返回可重试,不创建空认领。
  • 密文、设备、时间或租户不合法:拒绝且业务数据不变。
  • 并发认领:claim/session 行锁,仅一个用户成功。
  • 认领事务失败:回滚 claim、session 和 health_record;raw 始终保留。
  • 跨库身高体重附属同步在核心事务提交后执行,失败记录 WARN,不撤销健康报告。
  • 功能回滚通过开关停用认领;上传继续 raw-only,不删除已产生的 claim 和已认领报告。
禁止按最近时间自动挑一条匿名记录;只要不是唯一候选,就必须拒绝绑定。

10 · 验收与测试

场景通过标准证据
单模块认领首条 raw 后可认领并生成对应指标API + DB
部分后续追加认领后人体成分/血压自动归入同一人员日志 + DB + 真机
未登录扫码登录后自动恢复,无需再次扫码E2E 录像
重复扫码同用户幂等;无重复指标、同步和积分副作用自动化 + DB
并发抢占仅一人成功,另一人明确冲突并发集成测试
右臂重复左臂左臂不重复,右臂按 right_arm 保存唯一性查询
非法/过期/跨租户拒绝且所有业务表不变安全测试
手机号模式既有自动匹配和结构化不回归回归测试
两入口兼容手机号成功后本人扫码幂等、他人扫码拒绝;手机号未匹配后可扫码关联真机 + 集成测试
真机协议闭环解密 deviceID/UserID 与回调字段关系明确厂家样例 + 真机对照

建议性能目标:正常认领 p95 ≤ 800ms、错误率 < 0.1%;最终阈值需技术负责人结合现网容量确认。

11 · P0 待确认项

ID问题建议
Q-001二维码 deviceID/UserID 与回调字段的确切关系配置真实密钥后做一条真机对照
Q-002UserID 是否二次 Base64;rawData 是否含下划线厂家样例与实测共同确认
Q-003二维码有效期建议 30 分钟,由产品确认
Q-004认领成功后的精确跳转页建议对应日期的体重档案/检测报告
上述四项关闭前 DoR 保持 BLOCKED,不进入正式实现。

12 · 请审核这些决策

  • 第一条模块上传后即可认领。
  • 同一二维码只认领一个 session,后续模块自动追加。
  • 同用户重复扫码幂等,不同用户禁止覆盖。
  • 设备级密钥加密存储,真实值不进入 Git。
  • 新增独立的 ydy_measurement_claim,不扫描 raw JSON 猜测。
  • 确认二维码有效期、未就绪等待时间和认领后跳转页。
  • 确认手机号模式和既有指标映射完全兼容。

完整 AI 可执行方案、字段明细、AC 编号和测试矩阵:shanghe-qrcode-claim-solution.md

内部评审材料 · 真实密钥与个人数据已排除 · 2026-09-07