13 KiB
13 KiB
开发指南
**本文引用的文件** - [fms-vue/package.json](file://fms-vue/package.json) - [fms-vue/.oxfmtrc.json](file://fms-vue/.oxfmtrc.json) - [fms-vue/.oxlintrc.json](file://fms-vue/.oxlintrc.json) - [fms-vue/vitest.config.js](file://fms-vue/vitest.config.js) - [fms-vue/tests/README.md](file://fms-vue/tests/README.md) - [fms-vue/tests/setup.js](file://fms-vue/tests/setup.js) - [fms-vue/src/main.js](file://fms-vue/src/main.js) - [fms-vue/src/services/http.js](file://fms-vue/src/services/http.js) - [fms-vue/src/stores/auth.js](file://fms-vue/src/stores/auth.js) - [fms-vue/src/components/ui/button/Button.vue](file://fms-vue/src/components/ui/button/Button.vue) - [fms-api/pom.xml](file://fms-api/pom.xml) - [fms-api/src/main/java/cn/g3soft/fmsapi/FmsApiApplication.java](file://fms-api/src/main/java/cn/g3soft/fmsapi/FmsApiApplication.java)目录
简介
本指南面向FMS项目的开发者,聚焦以下目标:
- 明确前端(Vue/JS)与后端(Java/Spring Boot)的开发规范与编码标准
- 解释目录结构与模块划分原则,帮助新成员快速上手
- 提供Vue组件开发模式、Props设计、事件处理的最佳实践
- 统一测试策略与用例编写规范(单元、集成、E2E)
- 给出调试技巧与常见问题排查方法(浏览器工具、日志、性能分析)
项目结构
仓库采用前后端分离的多模块组织:
- fms-vue:基于Vite + Vue 3的前端工程,包含UI组件库、页面、路由、状态管理、服务层与测试
- fms-api:基于Spring Boot的后端API工程,包含控制器、服务、数据库配置、迁移脚本等
- fms-vue-old1 / fms-vue-old2:历史版本或实验分支,当前以fms-vue为主
- .playwright-cli / .fps-probe:辅助调试与测量脚本
- 参考组件库:外部参考实现,不直接参与构建
graph TB
subgraph "前端 fms-vue"
A["src/main.js"] --> B["src/router/index.js"]
A --> C["src/stores/*.js"]
A --> D["src/services/http.js"]
D --> E["后端 fms-api"]
F["src/components/ui/*"] --> G["页面 views/*"]
end
subgraph "后端 fms-api"
H["FmsApiApplication.java"] --> I["controller/service/database"]
end
图表来源
- fms-vue/src/main.js:1-22
- fms-vue/src/services/http.js:1-15
- fms-api/src/main/java/cn/g3soft/fmsapi/FmsApiApplication.java:1-22
章节来源
核心组件
- 应用入口与启动流程:初始化Pinia、插件、路由、主题同步,并在路由就绪后挂载应用,处理引导屏与错误兜底
- HTTP客户端:封装Axios,统一注入Authorization头、统一响应格式、鉴权失败跳转登录、网络异常提示
- 认证状态:集中管理登录凭证与用户信息,支持持久化到sessionStorage/localStorage
- UI组件:统一的按钮等基础组件,遵循Props校验、可访问性属性、加载态与禁用态组合
章节来源
- fms-vue/src/main.js:14-22
- fms-vue/src/services/http.js:40-47
- fms-vue/src/stores/auth.js:14-25
- fms-vue/src/components/ui/button/Button.vue:11-41
架构总览
前端通过HTTP客户端调用后端API;鉴权失败时由拦截器清理会话并跳转登录页;状态通过Pinia管理并持久化。
sequenceDiagram
participant U as "用户"
participant V as "Vue应用"
participant H as "http.js"
participant S as "后端API"
participant P as "Pinia(auth)"
U->>V : 触发操作
V->>H : 发起请求
H->>P : 读取token
H->>S : 携带Authorization头
alt 成功
S-->>H : {code : 0, data}
H-->>V : 返回数据
else 鉴权失败(401/40101)
S-->>H : {code : 401/40101}
H->>P : clearSession()
H-->>U : 跳转/login?reason=...
else 网络/服务器错误
S-->>H : 无status或5xx
H-->>U : 弹出Message提示
end
图表来源
详细组件分析
前端应用启动流程
- 创建Pinia并启用持久化插件
- 注册路由与主题同步
- 等待路由就绪后挂载应用,处理引导屏淡出与错误兜底
flowchart TD
Start(["应用启动"]) --> Init["创建Pinia并安装插件"]
Init --> Router["注册路由"]
Router --> Theme["初始化主题同步"]
Theme --> Ready{"路由是否就绪?"}
Ready -- 否 --> Wait["等待路由就绪"]
Wait --> Ready
Ready -- 是 --> Mount["挂载应用 #app"]
Mount --> Boot["显示/隐藏引导屏"]
Boot --> End(["完成"])
图表来源
章节来源
HTTP客户端与鉴权流程
- 请求拦截器:从auth store读取token并注入Authorization头
- 响应拦截器:统一包装success/code/message/data;鉴权失败清理会话并跳转;网络/服务端错误统一提示
- 便捷方法:post(path, data, config)
flowchart TD
Req["发起请求"] --> Interp["请求拦截器注入Token"]
Interp --> Send["发送HTTP请求"]
Send --> Resp{"响应码"}
Resp -- code==0 --> Ok["返回data"]
Resp -- 401/40101 --> AuthErr["clearSession并跳转登录"]
Resp -- 其他业务错误 --> BizErr["抛出带code/data的错误"]
Resp -- 网络/5xx --> NetErr["Message.error并标记toasted"]
图表来源
章节来源
认证状态管理(Pinia)
- 维护loginInfo(token/user)与userInfo(orgId/account)
- setSession兼容不同字段名;clearSession仅清空会话,不清“记住的账号”
- 持久化:loginInfo存sessionStorage,userInfo存localStorage
classDiagram
class AuthStore {
+loginInfo
+userInfo
+isAuthenticated
+setSession(session, organizationId)
+clearSession()
+saveLastLogin(orgId, account)
}
图表来源
章节来源
UI组件开发模式(以Button为例)
- Props设计:type/disabled/loading/block/htmlType,均提供默认值与校验
- 计算属性:isDisabled合并disabled与loading;classes根据props动态生成
- 模板:使用原生button语义,暴露aria-busy,支持插槽内容
- 样式:按BEM风格命名类,便于主题扩展
classDiagram
class Button {
+props : type, disabled, loading, block, htmlType
+computed : isDisabled, classes
+template : button(slot)
}
图表来源
章节来源
后端应用启动
- Spring Boot主类初始化雪花ID生成器选项并启动应用
章节来源
依赖分析
- 前端依赖:Vue 3、Vue Router、Pinia、Axios、DayJS、Lucide图标、stk-table-vue、Vitest、Oxlint/Oxfmt等
- 后端依赖:Spring Boot Web/JDBC、Druid、JWT、Jackson、IP定位、UA解析、SQL Server驱动等
graph LR
FE["fms-vue/package.json"] --> Vue["Vue 3"]
FE --> Pinia["Pinia"]
FE --> Axios["Axios"]
FE --> Vitest["Vitest"]
FE --> OX["Oxlint/Oxfmt"]
BE["fms-api/pom.xml"] --> SB["Spring Boot"]
BE --> JDBC["JDBC/Druid"]
BE --> JWT["JWT"]
BE --> DB["SQL Server"]
图表来源
章节来源
性能考虑
- 首屏优化:路由就绪后再挂载应用,避免菜单“跳出”;引导屏使用合成属性过渡,减少重排
- 按需特性:表格区域选择等能力按需注册,减少无关逻辑
- 网络层:超时与统一错误提示,避免重复弹窗(toasted标记)
- 状态持久化:仅持久化必要字段,降低存储体积
章节来源
故障排查指南
- 启动失败:检查main.js中的bootstrap异常捕获与引导屏错误展示
- 鉴权问题:确认http拦截器是否正确注入Authorization;401/40101会清理会话并跳转
- 网络异常:检查超时配置与Message提示;区分业务错误与服务端不可达
- 测试环境问题:setup.js已补齐ResizeObserver/IntersectionObserver/matchMedia等全局对象;确保在jsdom环境运行
- 覆盖率门槛:使用test:coverage命令检查阈值(lines/functions/branches/statements ≥ 60%)
章节来源
- fms-vue/src/main.js:24-39
- fms-vue/src/services/http.js:19-38
- fms-vue/tests/setup.js:11-57
- fms-vue/vitest.config.js:17-31
结论
本指南总结了FMS项目的目录结构、核心流程、组件开发模式与测试策略。建议新成员:
- 先阅读tests/README.md了解测试命令与规范
- 在新增功能时遵循现有组件Props设计与事件约定
- 通过http.js统一进行网络交互,避免绕过拦截器
- 使用vitest与覆盖率门禁保障质量
附录
开发规范与编码标准
- 代码风格
- 使用Oxlint进行静态检查,规则见配置文件
- 使用Oxfmt进行格式化,单引号、尾随逗号、行宽等见配置文件
- 命名约定
- 组件目录按功能拆分(如ui/button),文件名与组件名一致
- Store按领域划分(auth/app/preferences等)
- 服务层集中在services,HTTP封装在http.js
- 注释规范
- Props使用JSDoc标注类型与说明
- 关键函数与拦截器添加行为说明
章节来源
- fms-vue/.oxlintrc.json:1-21
- fms-vue/.oxfmtrc.json:1-8
- fms-vue/src/components/ui/button/Button.vue:6-19
组件开发最佳实践
- Props设计:最小可用集合,提供默认值与校验;对敏感/可选参数使用validator
- 事件处理:优先使用v-model双向绑定;复杂交互通过emit传递结构化数据
- 可访问性:为交互元素设置aria-*属性(如aria-busy)
- 样式:使用BEM命名,避免全局污染;通过CSS变量支持主题
章节来源
测试策略与用例规范
- 命令速查:全部测试、单文件测试、覆盖率、监听模式
- 目录与命名:按源码结构对应spec文件;每个被测对象一个spec
- 模板与装配:页面测试用mountPage;store测试用createTestPinia;纯函数直接断言
- 覆盖率:≥60%;仅在coverage模式下检查阈值
- 常见坑:pinia必须用createTestPinia;persist格式注意;跨用例清理存储;异步用flushPromises+nextTick
章节来源
- fms-vue/tests/README.md:10-57
- fms-vue/tests/README.md:59-189
- fms-vue/tests/README.md:191-256
- fms-vue/vitest.config.js:12-31
调试技巧与常见问题
- 浏览器调试:利用Network面板查看请求头Authorization;Console中查看Message提示
- 日志分析:关注http拦截器的错误分支与跳转逻辑
- 性能分析:使用Performance面板观察首屏渲染与引导屏过渡;关注表格虚拟滚动与懒加载
- 常见问题:
- 401反复跳转:检查是否在/login路径重复跳转
- 网络错误误登出:确认仅鉴权错误清会话
- 组件尺寸相关断言失败:jsdom下尺寸多为0,应改为状态/事件断言
章节来源