# 前端代码静态分析报告 > 分析范围: apps/web/src/ (316 TS/TSX) + apps/miniprogram/src/ (167 TS/TSX) > 分析工具: Grep/Read/Bash ## 1. TypeScript 类型安全 — MEDIUM ### Web 前端 生产代码仅 1 处 `any`: | 文件 | 行号 | 问题 | |------|------|------| | `hooks/usePaginatedData.ts` | 39 | `fetchFn: (...args: any[]) =>` — 建议用泛型 `A extends unknown[]` | 测试文件中 17 处 `as any`(mock 场景),影响低。 ### 小程序 — 10 处 `as any` | 文件 | 行号 | 问题 | 严重性 | |------|------|------|--------| | `app.tsx` | 24, 29 | `(globalThis as any).__hms` | LOW — 调试辅助 | | `pages/login/index.tsx` | 9 | `(__wxConfig as any).envVersion` | MEDIUM | | `services/request.ts` | 250 | `method: method as any` | MEDIUM | | `pages/pkg-health/device-sync/index.tsx` | 69 | `(bleManager as any).dataBuffer` | HIGH | | `pages/appointment/create/index.tsx` | 132 | `(Taro.requestSubscribeMessage as any)` | MEDIUM | **修复建议:** 创建 `types/global.d.ts` 和 `types/taro.d.ts` 补全缺失类型。 ## 2. 错误处理 — HIGH ### Web 前端静默吞错 (10+ 处) | 文件 | 行号 | 模式 | |------|------|------| | `pages/Home.tsx` | 224, 232, 238 | 个人统计加载失败被吞 | | `pages/Roles.tsx` | 46 | 权限列表加载失败被吞 | | `pages/health/ArticleManageList.tsx` | 119 | 文章列表加载失败被吞 | | `pages/health/DialysisManageList.tsx` | 49 | 透析列表加载失败被吞 | | `pages/health/components/DoctorSelect.tsx` | 28 | 医生列表加载失败被吞 | | `pages/health/components/workbench/OperatorWorkbench.tsx` | 35 | 工作台数据加载失败被吞 | 另有 10 处 `catch { }`(ChatPage 4 处 / useAlertSSE 2 处 / MainLayout 1 处 / usePaginatedData 1 处 / NotificationPanel 1 处 / App.tsx 1 处)。 **修复:** `.catch(() => {})` → `.catch((err) => console.warn('[context] 操作失败:', err))`,或设置错误状态。 ### 小程序 仅 1 处静默 catch(`followups/detail/index.tsx:58`),有注释解释,属合理模式。 ## 3. 安全问题 — HIGH (1 处) ### dangerouslySetInnerHTML 无消毒 `pages/health/articleEditor/ArticlePhonePreview.tsx:243`: ```tsx
``` - `content` 来自 wangEditor 富文本输出 - 后台管理预览组件,内容由管理员创建(非 UGC) - **仍建议引入 DOMPurify 做客户端消毒** - 预计工时: 30min ### 硬编码 URL — LOW | 文件 | 内容 | 评估 | |------|------|------| | `AiConfigPage.tsx:340,402` | `http://localhost:11434` | Ollama 默认 URL,仅作 placeholder | | `miniprogram/services/request.ts:4` | `localhost:3000` fallback | 开发环境 fallback,生产需运行时校验 | **无硬编码密钥或密码。** ✅ ## 4. 可访问性 — LOW - 未发现缺少 `alt` 的 `` — Web 前端全用 Ant Design 组件 - 3 处 `onClick` 在非 button 元素上使用(MainLayout 侧边栏 logo/折叠按钮 + ActionThreadDrawer 事件链接) - **修复:** 添加 `role="button"` + `tabIndex={0}` + `onKeyDown` ## 5. 大文件 — MEDIUM ### Web 前端 (500+ 行) | 文件 | 行数 | 建议 | |------|------|------| | `AdminDashboard.tsx` | 734 | 拆分统计卡片、图表、表格 | | `ArticleManageList.tsx` | 654 | 拆分筛选栏、表格、详情抽屉 | | `FollowUpTaskList.tsx` | 543 | 拆分筛选、列表、详情 | | `ConsultationDetail.tsx` | 542 | 拆分消息区、信息栏 | | `BannerManage.tsx` | 526 | 拆分表格和表单 | | `AppointmentList.tsx` | 520 | 拆分筛选和表格 | | `AiKnowledgePage.tsx` | 508 | 拆分列表和编辑 | 所有文件在 800 行限制内(CLAUDE.md 规范),但建议拆分提升可维护性。 ### 小程序 (300+ 行) | 文件 | 行数 | |------|------| | `daily-monitoring/index.tsx` | 449 | | `health/index.tsx` | 376 | | `index/index.tsx` | 371 | 小程序文件总体控制得更好。 ## 6. 国际化 — MEDIUM (不阻塞) - **Web 前端:** 97 个文件 / 375 处硬编码中文文本 - **高频文件:** DashboardWidgets (47) / DoctorWorkbench (19) / OperatorWorkbench (18) - **影响:** 当前定位国内单语平台,短期不影响 - **建议:** 新代码使用 i18n key,旧代码逐步迁移 ## 7. 内联样式 — LOW - **1,548 处** `style={{}}` 分布在 129 个文件 - **高频:** DoctorWorkbench (68) / AdminDashboard (54) / OperatorWorkbench (49) / DashboardWidgets (47) - 部分动态计算(width/height)不可避免,静态样式应迁移到 CSS ## 8. 值得肯定的方面 1. **TypeScript 类型安全整体优秀** — 生产代码仅 1 处 `any` 2. **小程序已完全消除 Web API 依赖** — 无 `localStorage`/`btoa`/`atob` 3. **无硬编码密钥或密码** — 敏感值全走环境变量 4. **eslint-disable 使用规范** — 每处有注释解释 5. **所有文件在 800 行限制内** 6. **小程序 console 日志格式统一** — `[模块名] 描述: error` ## 9. 问题汇总 | 严重性 | 问题 | 文件数 | 修复工作量 | |--------|------|--------|-----------| | HIGH | 静默吞错 `.catch(() => {})` | 10+ | 小 — 改为 warn 日志 | | HIGH | dangerouslySetInnerHTML 无消毒 | 1 | 小 — 引入 DOMPurify | | MEDIUM | 小程序 `as any` 类型断言 | 10 | 中 — 补全类型声明 | | MEDIUM | 硬编码中文 (i18n) | 97 | 大 — 渐进迁移 | | MEDIUM | 500+ 行大文件 | 7 | 中 — 拆分子组件 | | LOW | 内联样式过多 | 129 | 大 — 渐进迁移 | | LOW | localhost fallback URL | 2 | 小 — 运行时校验 | | LOW | 非交互元素 onClick 缺 a11y | 3 | 小 |