第三章 需求分析与系统设计
好,咱们进入正题。上一章聊了项目管理的整体框架,这一章我带你落地到具体设计上。说白了,就是搞清楚「我们要做什么」和「系统长什么样」。
我个人习惯,在写一行代码之前,先花时间把需求理清楚。你想想看,如果需求都没搞明白,后面返工的成本可就大了。我在项目中遇到过好几次,因为需求遗漏导致架构推倒重来,那叫一个痛。
3.1 功能需求清单
一个嵌入式项目管理系统,核心功能就四个模块:任务管理、版本管理、文档管理、缺陷追踪。嗯,咱们一个一个来看。
3.1.1 任务管理
任务管理是系统的基石。说白了,就是把项目拆成一个个可执行的小单元。
- 任务创建:支持填写任务名称、描述、优先级(P0-P3)、截止日期、负责人
- 任务状态流转:待办 → 进行中 → 评审中 → 已完成 → 已关闭
- 任务依赖:可以设置前置任务,比如「硬件设计」完成后才能开始「驱动开发」
- 任务看板:支持拖拽式看板视图,方便快速调整状态
- 工时记录:每个任务可以记录实际投入工时,方便后续评估
我的经验:任务粒度要适中。太细了管理成本高,太粗了没法跟踪。我一般建议一个任务的工作量控制在2-5天。曾经有个项目,我把任务拆到半天一个,结果光维护任务状态就花了一半时间,得不偿失。
3.1.2 版本管理
嵌入式项目最怕版本混乱。你想想看,固件版本、硬件版本、文档版本,哪个对不上都得出问题。
- 版本号规范:采用语义化版本号,比如 v1.2.3(主版本.次版本.修订号)
- 版本基线:每个发布版本对应一个固定的代码、文档、固件集合
- 版本对比:支持两个版本之间的变更差异查看
- 版本回滚:出问题时能快速回退到上一个稳定版本
- 发布审批:版本发布前需要经过测试确认和项目经理审批
避坑指南:我曾经在一个项目中,团队直接用日期当版本号,结果同一天发布了三个版本,彻底乱套了。后来我强制要求使用语义化版本号,配合Git标签管理,才把这个问题解决。
3.1.3 文档管理
文档是项目的记忆。没有文档,人走了知识就没了。
- 文档分类:需求文档、设计文档、测试文档、用户手册、会议纪要
- 文档模板:每种文档类型提供标准模板,保证格式统一
- 版本控制:文档修改有历史记录,可以查看谁在什么时候改了哪里
- 在线预览:支持Markdown、PDF、Word等格式在线查看
- 权限管理:不同角色有不同的读写权限,比如测试人员不能修改设计文档
3.1.4 缺陷追踪
缺陷追踪说白了就是Bug管理。但别小看它,好的缺陷管理能帮你发现流程中的薄弱环节。
- 缺陷报告:填写缺陷标题、描述、复现步骤、环境信息、严重程度(致命/严重/一般/轻微)
- 缺陷状态:新建 → 已确认 → 修复中 → 已修复 → 验证通过 → 关闭
- 缺陷关联:可以关联到具体任务、版本、测试用例
- 缺陷统计:按模块、按负责人、按严重程度统计缺陷分布
- 缺陷看板:类似任务看板,方便跟踪缺陷处理进度
核心观点:缺陷不是用来追责的,是用来改进流程的。如果一个模块反复出现同类缺陷,说明测试用例需要补充,或者设计上需要重构。
3.2 数据库ER图设计
需求清楚了,接下来就是设计数据库。我习惯用ER图来梳理实体之间的关系。嗯,这里我画一个简化的ER图,用文字描述给你看。
主要实体:
- 用户(User):用户ID、用户名、邮箱、角色、创建时间
- 项目(Project):项目ID、项目名称、描述、开始日期、结束日期、状态
- 任务(Task):任务ID、标题、描述、优先级、状态、负责人ID、项目ID、截止日期、工时
- 版本(Version):版本ID、版本号、项目ID、基线信息、发布时间、审批人ID
- 文档(Document):文档ID、标题、类型、内容、项目ID、创建人ID、版本号
- 缺陷(Bug):缺陷ID、标题、描述、严重程度、状态、项目ID、发现人ID、修复人ID、关联版本ID
实体关系:
| 实体A | 关系 | 实体B | 说明 |
|---|---|---|---|
| 项目 | 1:N | 任务 | 一个项目有多个任务 |
| 项目 | 1:N | 版本 | 一个项目有多个版本 |
| 项目 | 1:N | 文档 | 一个项目有多个文档 |
| 项目 | 1:N | 缺陷 | 一个项目有多个缺陷 |
| 用户 | 1:N | 任务 | 一个用户负责多个任务 |
| 用户 | 1:N | 缺陷 | 一个用户发现/修复多个缺陷 |
| 版本 | 1:N | 缺陷 | 一个版本关联多个缺陷 |
设计心得:ER图不用画得太复杂,够用就行。我见过有人把ER图画得像蜘蛛网,结果开发的时候根本用不上。记住,数据库设计是服务于业务的,不是用来炫技的。
3.3 API接口设计
数据库设计好了,接下来就是API接口。我习惯用RESTful风格,简单明了。
接口设计原则:
- 使用名词复数形式,比如
/api/tasks而不是/api/getTask - 使用HTTP方法表示操作:GET查询、POST创建、PUT更新、DELETE删除
- 返回统一的JSON格式,包含状态码、消息和数据
- 分页查询统一使用
page和size参数
核心接口列表:
| 方法 | 路径 | 说明 |
|---|---|---|
| GET | /api/projects | 获取项目列表 |
| POST | /api/projects | 创建项目 |
| GET | /api/projects/{id} | 获取项目详情 |
| PUT | /api/projects/{id} | 更新项目信息 |
| DELETE | /api/projects/{id} | 删除项目 |
| GET | /api/tasks | 获取任务列表(支持按项目、状态筛选) |
| POST | /api/tasks | 创建任务 |
| PUT | /api/tasks/{id}/status | 更新任务状态 |
| GET | /api/versions | 获取版本列表 |
| POST | /api/versions | 创建版本基线 |
| GET | /api/bugs | 获取缺陷列表 |
| POST | /api/bugs | 报告缺陷 |
| PUT | /api/bugs/{id}/status | 更新缺陷状态 |
接口返回格式示例:
{
"code": 200,
"message": "success",
"data": {
"id": 123,
"title": "修复UART驱动中断丢失问题",
"status": "进行中",
"priority": "P0",
"assignee": "张三",
"createdAt": "2024-01-15 10:30:00"
}
}
注意:接口设计时一定要考虑异常情况。比如任务状态流转不合法时,要返回明确的错误信息。我曾经遇到一个项目,前端传了错误的状态值,后端直接抛500,排查了半天才发现是状态机校验没做好。
好了,这一章的内容就到这儿。需求清单、ER图、API接口,这三样东西搞清楚了,系统设计阶段就算完成了。下一章咱们开始动手搭建开发环境,到时候我会分享一些我常用的工具链配置技巧。