Files
hms/docs/discussions/2026-05-14-taro-performance-audit.md
iven 8f353946e1 fix(mp): T40 UI 审计修复 — 28 项设计系统合规 + 安全加固 + 讨论记录
T40 UI 审计修复(60 页面全覆盖):
- 新增 $acc-d/$wrn-d 渐变中间色变量,修复首页轮播渐变硬编码
- 替换 8 处裸 white 为 $white 设计变量(5 个 SCSS 文件)
- 修复 7 处触摸目标 40/44px → 48px(健康/消息/咨询/预约/首页)
- 3 页面新增 Loading 状态(体征录入/个人中心/就诊人添加)
- statusTag 移除硬编码布局值,改用 SCSS mixin 控制
- 医生端 14 页面架构 Hook 层补充(useThrottledDidShow 替换 useEffect)
- 移除 action-inbox 未使用 import

安全 P0 修复:
- JWT 中间件加固:token 类型校验 + 过期预检 + 类型别名简化
- 速率限制增强:滑动窗口 + 暴力破解防护
- analytics handler 错误处理完善

文档:
- T40 审计报告(24 PASS / 36 PASS_WITH_ISSUES / 0 NEEDS_WORK)
- 5 份 DevTools/性能审计讨论记录
- wiki 症状导航 + 小程序章节更新
2026-05-14 23:12:54 +08:00

80 lines
4.5 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# Taro 小程序穷尽性能审计报告
> 日期: 2026-05-14 | 范围: apps/miniprogram/ (124 TS/TSX 文件, 66 页面)
## 审计维度
4 个并行审计 agent 覆盖同步阻塞操作、依赖体积、API 调用+内存管理、渲染性能+导航。
## 已修复的问题
### CRITICAL (6 项 — 全部已修复)
| # | 问题 | 文件 | 修复 |
|---|------|------|------|
| C1 | DataBuffer `while(true)` Sync Storage 无上限 | `ble/DataBuffer.ts` | 添加 `MAX_BUCKETS=20` 循环保护 |
| C2 | DataBuffer.push 每次同步序列化大桶 | `ble/DataBuffer.ts` | 同上,限制桶数 |
| C3 | `Math.max(...arr)` 展开大数组栈溢出风险 | `TrendChart/index.tsx`, `health/index.tsx` | 改用 `reduce` |
| C4 | `responseCache` Map 无大小上限 | `services/request.ts` | 添加 `MAX_CACHE_SIZE=100` + LRU 淘汰 |
| C5 | BLE 事件监听器累积(多次 connect 不移除旧监听) | `ble/BLEManager.ts` | 保存 handler 引用connect 前先 off |
| C6 | `navigateToLogin` 用 navigateTo 可能栈溢出 | `utils/navigate.ts` | 改为 `reLaunch` |
### HIGH (7 项 — 全部已修复)
| # | 问题 | 文件 | 修复 |
|---|------|------|------|
| H1 | EcCanvas 死代码 + echarts 58MB 死依赖 | `components/EcCanvas/`, `package.json` | 删除文件 + 移除依赖 |
| H2 | 访客首页每次 useDidShow 重新下载所有 banner 图片 | `pages/index/index.tsx` | 移除 downloadFile直接用 URL + lazyLoad |
| H3 | analytics 每次 track 两次 Sync Storage | `services/analytics.ts` | 内存队列 + 异步 `setStorage` |
| H4 | `request.ts` getCacheKey 每次请求同步读 patientId | `services/request.ts` | 内存缓存 `cachedPatientId` |
| H5 | 切换就诊人不清理请求缓存和 healthStore | `stores/auth.ts` | `setCurrentPatient` 中调用 `clearRequestCache` |
| H6 | logout 不清理 healthStore/pointsStore | `stores/auth.ts` | logout 中调用 `healthStore.clearCache()` |
| H7 | zod (5.5MB) + react-dom (4.4MB) 死依赖 | `package.json` | 移除两个未使用的依赖 |
| H8 | 25 个页面 useDidShow 无条件全量刷新 | 多个页面 | 4 tabBar 页改 `useThrottledDidShow` + 子包页面同步更新 |
| H9 | 12 处 `useAuthStore()` 无参数导致全 store 订阅 | 15 个文件 | 全部改为精确选择器模式38 个订阅优化) |
### MEDIUM (已修复)
| # | 问题 | 文件 | 修复 |
|---|------|------|------|
| M1 | settings 清缓存 17 次同步 Storage 操作 | `pkg-profile/settings/index.tsx` | 改为异步 `getStorage`/`clearStorage`/`setStorage` |
| M2 | 6 个页面 JSX 渲染路径中调用 getStorageSync | 6 个 pkg-profile 页面 | 提取 `hasPatient` state渲染时引用 state 而非 sync 调用 |
| M5 | health/index.tsx indicatorCapsules/healthItems 每次 render 重建 | `pages/index/index.tsx` | `useMemo` 包裹,依赖 `todaySummary` 子字段 |
| M6 | BLEManager 模块级单例导出 vs 页面独立创建双实例 | `services/ble/BLEManager.ts` | 移除 `export default new BLEManager()` |
| M7 | device-sync useDidShow cleanup 不生效 | `pages/device-sync/index.tsx` | 清理逻辑移至 `useEffect` return |
| M3 | AI 报告 sanitizeHtml 正则替换链 | `pages/ai-report/detail/index.tsx` | 合并 6 步 regex 为 2 步,合并 h1/h2/h3 为单步 |
| M4 | doctor 子包 barrel re-export 全量引入 | 17 个 doctor 页面 | `import * as doctorApi` → 直接子模块具名导入 |
| M8 | 聊天消息全量渲染无上限 | 2 个 consultation detail 页面 | 添加 `MAX_RENDER_MESSAGES=200` 渲染上限 + 截断提示 |
## 待后续修复的问题
### HIGH (记录但未在本次修复)
| # | 问题 | 文件 | 建议修复 |
|---|------|------|----------|
| H10 | 积分商城加载 100 商品只为查 1 个详情 | `pkg-mall/exchange` | 后端新增单品查询 API |
| H11 | auth restore 启动路径 6 次同步 Storage 读取 | `stores/auth.ts` | 改异步 + 合并读取 |
## 包体积审计
| 指标 | 值 |
|------|-----|
| 编译产物总大小 | 1.4 MB |
| 主包 (taro + app + vendors + common) | ~380 KB |
| 最大子包 (doctor, 18 页面) | 268 KB |
| 移除的死依赖 | echarts (58MB) + zod (5.5MB) + react-dom (4.4MB) |
## 正面发现
- Taro 4.x 编译产物干净,无 crypto-js 残留
- 所有列表页使用页面级 `useReachBottom` 而非 ScrollView性能最佳实践
- TabBar 图标均为 334 bytes 极简图标
- app.tsx 的 analytics 定时器和事件监听 cleanup 正确
- 无内联 base64 图片、无 require 图片资源
- 文章列表 Image 已正确设置 `lazyLoad`
## 编译验证
- `taro build --type weapp` 编译成功 (10.46s)
- 所有修复已确认包含在编译产物中